2012-10-11 72 views
2

我有一個ASP.Net頁面,其中包含實現IPostBackEventHandler接口的多個控件。代碼的簡化版本在下面給出:ASP.NET頁面與多個自定義控件實現IPostBackEventHandler

public partial class WebForm1 : System.Web.UI.Page 
{ 
    protected void Page_Load(object sender, EventArgs e) 
    { 
     //Custom Control 
     MyTextBox mytxt = new MyTextBox(); 
     mytxt.ID = "mytxt"; 
     mytxt.TextChange += mytxt_TextChange; 
     this.Form.Controls.Add(mytxt); 

     //Custom Control 
     MyButton mybtn = new MyButton(); 
     mybtn.ID = "mybtn"; 
     mybtn.Click += mybtn_Click; 
     this.Form.Controls.Add(mybtn); 
    } 

    void mybtn_Click(object sender, EventArgs e) 
    { 
     Response.Write("mybtn_Click"); 
    } 

    void mytxt_TextChange(object sender, EventArgs e) 
    { 
     Response.Write("mytxt_TextChange"); 
    } 
} 

[System.Security.Permissions.PermissionSet(System.Security.Permissions.SecurityAction.Demand, Name = "FullTrust")] 
public class MyTextBox : Control, IPostBackEventHandler 
{ 
    public event EventHandler TextChange; 

    protected virtual void OnTextChange(EventArgs e) 
    { 
     if (TextChange != null) 
     { 
      TextChange(this, e); 
     } 
    } 

    public void RaisePostBackEvent(string eventArgument) 
    { 
     OnTextChange(new EventArgs()); 
    } 

    protected override void Render(HtmlTextWriter output) 
    { 
     output.Write("<input type='text' id='" + ID + "' name='" + ID + "' onchange='__doPostBack(&#39;" + ID + "&#39;,&#39;&#39;)' />"); 
    } 
} 

[System.Security.Permissions.PermissionSet(System.Security.Permissions.SecurityAction.Demand, Name = "FullTrust")] 
public class MyButton : Control, IPostBackEventHandler 
{ 
    public event EventHandler Click; 

    protected virtual void OnClick(EventArgs e) 
    { 
     if (Click != null) 
     { 
      Click(this, e); 
     } 
    } 

    public void RaisePostBackEvent(string eventArgument) 
    { 
     OnClick(new EventArgs()); 
    } 

    protected override void Render(HtmlTextWriter output) 
    { 
     output.Write("<input type='button' id='" + ID + "' name='" + ID + "' value='Click Me' onclick='__doPostBack(&#39;" + ID + "&#39;,&#39;&#39;)' />"); 
    } 
} 

有2個定製控件 - MyTextBox & myButton的實施IPostBackEventHandler接口。 MyTextBox有TextChange事件,MyButton有Click事件。

如果我只在頁面上保留一個控件(MyTextBox或MyButton) - 事件觸發屬性。但是,即使在單擊MyButton之後,頁面上的兩個控件都會觸發MyTextBox TextChange事件。當MyTextBox在頁面上時,MyButton Click事件不會被觸發。

我在這裏發佈之前已經嘗試過多件事情。先謝謝您的幫助。

回答

0

問題的原因是您需要使用控件的UniqueID調用__doPostBack方法。這是至關重要的。此外,基本上服務器控件將ClientID作爲元素的ID和UniqueID作爲元素名稱呈現。所以,如果你更新你的渲染方法,下面這樣就可以了:

文本框:

output.Write("<input type='text' id='" + this.ClientID + "' name='" + this.UniqueID + "' onchange='__doPostBack(&#39;" + this.UniqueID + "&#39;,&#39;&#39;)' />"); 

按鈕:

output.Write("<input type='button' id='" + this.ClientID + "' name='" + this.UniqueID + "' value='Click Me' onclick='__doPostBack(&#39;" + this.UniqueID + "&#39;,&#39;&#39;)' />"); 

編輯

使用的UniqueID似乎真的沒」幫助解決你的問題。我不知道問題的原因,但我嘗試使用基本WebControl類覆蓋自定義文本框,這有助於解決問題。所以,你可以嘗試去執行這個實現。

[System.Security.Permissions.PermissionSet(System.Security.Permissions.SecurityAction.Demand, Name = "FullTrust")] 
public class MyTextBox : WebControl, IPostBackEventHandler 
{ 
    public event EventHandler TextChange; 

    protected virtual void OnTextChange(EventArgs e) 
    { 
     if (TextChange != null) 
     { 
      TextChange(this, e); 
     } 

    } 

    public void RaisePostBackEvent(string eventArgument) 
    { 
     OnTextChange(new EventArgs()); 
    } 

    protected override HtmlTextWriterTag TagKey 
    { 
     get 
     { 
      return HtmlTextWriterTag.Input; 
     } 
    } 

    protected override void AddAttributesToRender(HtmlTextWriter writer) 
    { 
     base.AddAttributesToRender(writer); 
     writer.AddAttribute(HtmlTextWriterAttribute.Onchange, Page.ClientScript.GetPostBackEventReference(this, string.Empty)); 
     writer.AddAttribute("onkeypress", "if (WebForm_TextBoxKeyHandler(event) == false) return false;"); 
     writer.AddAttribute(HtmlTextWriterAttribute.Type, "text"); 
    } 
} 
+0

Maxim,感謝您的回覆。我已經嘗試過更新的代碼,但我仍然面臨同樣的問題。如果我只在頁面上保留一個控件(MyTextBox或MyButton) - 事件觸發屬性。但是,即使在單擊MyButton之後,頁面上的兩個控件都會觸發MyTextBox TextChange事件。當MyTextBox在頁面上時,MyButton Click事件不會被觸發。 –

+0

@Yuvi,我更新了我的答案。我真的沒有找到根本原因(什麼是錯誤的),但我試圖使用WebControl作爲基類實現相同的功能,這有助於解決問題。可能這個解決方案對你很有意思。 –

+0

感謝主動,非常感謝。我試圖從WebControl繼承,它確實有效。但我試圖通過從Control類繼承來實現相同的功能。控件類是您可以從中開始構建控件的最重要的部分。看起來UniqueID和ClientID在Control類級別沒有太大意義,它們在WebControl級別上有意義。 –

相關問題