2010-05-19 48 views
5

好的:我在包含一個佔位符的aspx頁面上有一個UpdatePanel。UpdatePanel中的JavaScript代碼

這裏面佔位符,我追加選擇取決於某些外部條件的usercontrols的(這是一個配置頁)之一。

在每個這些用戶控件的存在bindUcEvents()的javascript結合的各種jQuery和JavaScript事件到該用戶控件內的按鈕和驗證功能。

我遇到的問題是usercontrol的javascript未被識別。通常,updatepanel中的javascript在updatepanel回發時執行,但是這些代碼都不能被頁面找到(我試過通過螢幕控制檯手動運行這個函數,但它告訴我它找不到函數)。

有沒有人有任何建議?

Cheers,Ed。

編輯:

減少(但功能)例如:

標記:

<script src="/js/jquery-1.3.2.min.js"></script> 
    <form id="form1" runat="server"> 
    <div> 

    <asp:ScriptManager ID="Script" runat="server" /> 

    <asp:Button ID="Postback" runat="server" Text="Populate" OnClick="PopulatePlaceholder" /> 

    <asp:UpdatePanel ID="UpdateMe" runat="server"> 
    <Triggers> 
     <asp:AsyncPostBackTrigger ControlID="Postback" EventName="Click" /> 
    </Triggers> 
     <ContentTemplate> 
      <asp:Literal ID="Code" runat="server" /> 
      <asp:PlaceHolder ID="PlaceMe" runat="server" /> 
     </ContentTemplate> 
    </asp:UpdatePanel> 
    </div> 
</form> 

C#:

protected void PopulatePlaceholder(object sender, EventArgs e) 
{ 
    Button button = new Button(); 
    button.ID = "Push"; 
    button.Text = "push"; 
    button.OnClientClick = "javascript:return false;"; 
    Code.Text = "<script type=\"text/javascript\"> function bindEvents() { $('#" + button.ClientID + "').click(function() { alert('hello'); }); } bindEvents(); </script>"; 
    PlaceMe.Controls.Add(button); 
} 

你會看到按鈕不會poput警報消息,即使代碼存在於頁面上。

EDIT2:

好,這只是爲了清楚,生產代碼爲顯著比結合到一個文字只是一個單一的功能更復雜的,並且包含大量的

<%= Control.ClientID %> 

比特代碼非常難以分解成非特定的函數,因爲它們都只在一個地方使用(我們正在談論非常具體的驗證以及奇怪的彈出式觸發器+某些邏輯),因此它們毫無意義。

+1

你可以發佈一些源代碼或生成的代碼嗎?沒有它,這很難診斷。 – scunliffe 2010-05-19 10:03:05

+0

當然,我只是傾向於避免這樣做,因爲它有很多,我會盡量減少一點 – 2010-05-19 10:38:05

+0

你說過你有很多代碼,所以它不在代碼隱藏中。那麼它在哪裏?在aspx中?在外部的js文件?從數據庫/ xml文件加載並通過後面的代碼讀取? ascx文件中的 – Stobor 2010-05-31 02:53:58

回答

8

擺脫該文字控制並使用ScriptManager註冊您的腳本。你在做什麼出於同樣的原因

window.document.getElementById('someId').innerHtml = "<script type=\"text/javascript\">alert('hey');</script>"; 

不工作不工作。試試這個:

protected void PopulatePlaceholder(object sender, EventArgs e) 
{ 
    Button button = new Button(); 
    button.ID = "Push"; 

    button.Text = "push"; 
    button.OnClientClick = "return false;"; 


    string script = "function bindEvents() { $('#" + button.ClientID + "').click(function() { alert('hello'); }); } bindEvents();"; 

    ScriptManager.RegisterClientScriptBlock(this.Page, typeof(SomeClass), Guid.NewGuid().ToString(), script, true); 


    PlaceMe.Controls.Add(button); 
} 

RegisterClientScriptBlock的參數可能需要更改,但您明白了。

+3

可維護性下降到零,但如果我這樣做:我們談論的200行JS做了很多東西,其中大部分使用控制clientID來做。那種代碼在後臺時很難維護...... – 2010-05-25 08:31:01

+1

然後你需要重構你的腳本。這是做這件事的正確方法。抱歉。 – 2010-05-26 13:15:48

+1

即,您將不得不重寫您的腳本,以便它們可以放置在js文件中。然後你將不得不調用ScriptManager。根據需要配置RegisterClientScriptBlock和ScriptManager.RegisterStartupScript。沒有任何方法可以讓你在沒有調用ScriptManager的情況下工作。 無論如何,ascx/aspx中的腳本並不是很好的練習,並且不利於性能。 – 2010-05-26 19:28:14

2

使用ScriptManager(阿賈克斯擴展)添加到您的網頁,並添加經理裏面你scriptreferences。 管理器會在ajax-based-pageload上加載每個腳本標記(而不僅僅是初始加載) - 在updatepanel內部移動所有需要的javascript代碼,並且你已經完成了很多工作。

<asp:ScriptManager ID="ScriptManager1" runat="server"> 
     <Scripts> 
      <asp:ScriptReference Path="../lib/jquery-1.2.6.pack.js" /> 

沒有讀好的問題(沒有樣本)。看到我的新回覆。

+1

你需要一個腳本管理器來使用updatepanels,而且這個代碼在usercontrol內部(嵌入在頁面中)都是內部的,因爲它使用了特定於控件的ID,所以這不是真正的幫助。 – 2010-05-19 11:57:30

5

重新運行一些JS後的更新面板已經解僱我一直用這個

Sys.WebForms.PageRequestManager.getInstance().add_endRequest(
    function(sender, args) { 
     //update whatever here 
    }); 

此外,如果你有更新面板中的元素的任何引用您可以在該函數內刷新這些變量以及,否則你會有舊的裁判不會工作。

+0

是的,不幸的是只有當代碼出現在原始頁面上時才起作用。當我使用動態控件並通過UpdatePanel加載它時(即通過JavaScript),新的JavaScript函數不被識別爲函數! – 2010-05-19 16:46:14

+0

嗯...我知道evals並不是最好的事情,但是如何將此調用放在上面列出的UpdatePanel回調中呢? ... //更新這裏的任何內容 eval(document.getElementById('Code')。innerHtml); ... – Justin 2010-05-19 20:37:52

+0

可能會工作,但這幾乎是我想訴諸的最後一件事! – 2010-05-20 11:31:36

-1

不知何故,它似​​乎是你的代碼。文本在翻譯的某個地方迷失了 - 不知道細節,也許是按照設計;反正接下來做的工作:

protected void PopulatePlaceholder(object sender, EventArgs e) 
    { 
     Button button = new Button(); 
     button.ID = "Push"; 
     button.Text = "push"; 
     button.OnClientClick = "javascript:return false;"; 
//  Code.Text = 
     PlaceMe.Controls.Add(button); 
     PlaceMe.Controls.Add(new LiteralControl("<script type=\"text/javascript\"> function bindEvents() { $('#" + button.ClientID + "').click(function() { alert('hello'); }); } bindEvents(); </script>")); 
    } 

既然你已經從代碼隱藏建設的JavaScript代碼,你還不如添加控件動態了。

+0

這個小例子只是我的過程的指示,真正的代碼是大約200行的javascript,它會做一些非常複雜的事情。我需要保持它,所以沒有真正的選項將javascript保留在代碼中! – 2010-05-20 11:30:46

+0

在您的示例中,您已經從代碼隱藏構建Code.Text;你現在說你不想從代碼隱藏執行JavaScript? 我認爲你會將呼叫替換爲一個新功能的呼叫,傳遞ID作爲參數或類似的東西,無論如何 - 只是試圖幫助 – riffnl 2010-05-20 11:42:52

+0

我明白,但我確實說過,它還有更多在我原來的職位。 – 2010-05-24 14:19:34

0

也許您正在尋找這樣的:http://api.jquery.com/live/

近.bind()兼容的(在上面的鏈接中列出例外) - 但也結合添加/更改的元素以後。

或者也許也給.delegate()一個嘗試 - 不能直接替換.bind()調用,但在大多數情況下,更快。