dynamic创build控件在回发后丢失数据

实际上,我在Pageload上创build1个TextBox并将该TextBox添加到Panel 。 现在,我有一个LinkButtonAdd Another

我在该TextBoxinput文本,如果需要,我需要创build新TextBox ,通过单击Add Another LinkButton

实际上,我能够获得计数并重新创buildTextBoxes 。 但是,问题是,我以前生成的Textboxesinput的文本是丢失。

任何人都可以,build议我一个这样的解决scheme?

 protected void Page_Load(object sender, EventArgs e) { try { if (!IsPostBack) { for (int i = 0; i < 5; i++) { TableRow row = new TableRow(); for (int j = 0; j < 5; j++) { TableCell cell = new TableCell(); TextBox tb = new TextBox(); tb.ID = "TextBoxRow_" + i + "Col_" + j; cell.Controls.Add(tb); row.Cells.Add(cell); } Table1.Rows.Add(row); } } } catch (Exception ex) { throw; } } 

这是一个示例代码,同样的代码是写在Button_Click

  protected void ASPxButton1_Click(object sender, EventArgs e) { int k = Table1.Controls.Count; } 

我得到了Button_Click上的Count=0

使用dynamic控件时,您必须记住它们只会在下一次回发之前存在.ASP.NET将不会重新创builddynamic添加的控件。 如果您需要多次重新创build控件,则应该在PageLoad事件处理程序中执行控件创build(因为您当前仅使用Condition:!IsPostabck仅创buildTextBox)。 这还有一个额外的好处,就是允许你在dynamic控制中使用视图状态。 即使视图状态通常在Page.Load事件之前恢复,如果您在PageLoad事件的处理程序中创build一个控件,ASP.NET将应用PageLoad事件处理程序结束后的任何视图状态信息。

所以,删除条件:!IsPostback,这样每次页面加载时,TextBox控件也被创build。 PageLoad处理程序完成后,您还将看到“文本状态”框保存。 [显然你没有禁用ViewState! ]

例:

 protected void Page_Load(object sender, EventArgs e) { TextBox txtBox = new TextBox(); // Assign some text and an ID so you can retrieve it later. txtBox.ID = "newButton"; PlaceHolder1.Controls.Add(txtBox); } 

现在运行后,在文本框中input任何东西,看看当你点击任何导致回发的button时会发生什么。 文本框仍然保持其状态!

您只需要在页面加载事件之前或之内重新实例化/重新初始化dynamic控件,并且每次在回发过程中添加此控件到页面/窗体/占位符。 然后,发布的数据将通过父控件调用LoadPostData方法自动分配给控件。

检查文章以及如何编写dynamic控制代码 – 如何在asp.net中回发期间维护dynamic控制事件,数据

在这里输入图像描述

dynamic生成的控件不保持状态。 你必须自己维护它。 您可以使用一些隐藏字段来保持控件的状态,这将在服务器端用于提取状态。 Asp.net使用隐藏域来维护请求之间的状态,可以在源码中看到__VIEWSTATE

在ASP.NET页面中,视图状态代表页面在服务器上次处理时的状态。 它被用来构build一个调用上下文,并为相同页面的两个连续请求保留值。 默认情况下,状态在客户端使用添加到页面的隐藏字段持久化,并在处理页面请求之前在服务器上恢复。 视图状态与页面本身来回传递,但不表示或包含与客户端页面显示相关的任何信息。

只要删除这一行

  if (!IsPostBack) 

在与Dynamic Controls合作之后,这是我的最终答案

的.aspx

 <form id="form1" runat="server"> <asp:ScriptManager ID="ScriptManager1" runat="server"> </asp:ScriptManager> <div style="text-align: center"> <div style="background-color: Aqua; width: 250px;"> <br /> <asp:UpdatePanel ID="UpdatePanel1" runat="server"> <ContentTemplate> <asp:PlaceHolder runat="server" ID="myPlaceHolder"></asp:PlaceHolder> </ContentTemplate> <Triggers> <asp:AsyncPostBackTrigger ControlID="btnAddTextBox" EventName="Click" /> </Triggers> </asp:UpdatePanel> <br /> </div> <br /> <asp:Button ID="btnAddTextBox" runat="server" Text="Add TextBox" OnClick="btnAddTextBox_Click" /> <br /><br /> <asp:UpdatePanel ID="UpdatePanel2" runat="server"> <ContentTemplate> <asp:Button runat="server" ID="MyButton" Text="Get Values." OnClick="MyButton_Click" /> <br /><br /> <asp:Label runat="server" ID="MyLabel"></asp:Label> </ContentTemplate> </asp:UpdatePanel> </div> </form> 

.aspx.cs

 static int myCount = 0; private TextBox[] dynamicTextBoxes; protected void Page_PreInit(object sender, EventArgs e) { Control myControl = GetPostBackControl(this.Page); if ((myControl != null)) { if ((myControl.ClientID.ToString() == "btnAddTextBox")) { myCount = myCount + 1; } } } protected override void OnInit(EventArgs e) { base.OnInit(e); dynamicTextBoxes = new TextBox[myCount]; int i; for (i = 0; i < myCount; i += 1) { TextBox textBox = new TextBox(); textBox.ID = "myTextBox" + i.ToString(); myPlaceHolder.Controls.Add(textBox); dynamicTextBoxes[i] = textBox; LiteralControl literalBreak = new LiteralControl("<br />"); myPlaceHolder.Controls.Add(literalBreak); } } protected void btnAddTextBox_Click(object sender, EventArgs e) { // Handled in preInit due to event sequencing. } protected void MyButton_Click(object sender, EventArgs e) { MyLabel.Text = ""; foreach (TextBox tb in dynamicTextBoxes) { MyLabel.Text += tb.Text + " :: "; } } public static Control GetPostBackControl(Page thePage) { Control myControl = null; string ctrlName = thePage.Request.Params.Get("__EVENTTARGET"); if (((ctrlName != null) & (ctrlName != string.Empty))) { myControl = thePage.FindControl(ctrlName); } else { foreach (string Item in thePage.Request.Form) { Control c = thePage.FindControl(Item); if (((c) is System.Web.UI.WebControls.Button)) { myControl = c; } } } return myControl; } 

其实,我用Javascript来完成我的任务。 它是这样的:

 <form id="form1" runat="server" enctype="multipart/form-data" method="post"> <span style="font-family: Arial">Click to add files</span>&nbsp;&nbsp; <input id="Button1" type="button" value="add" onclick="AddFileUpload()" /> <br /> <br /> <div id="FileUploadContainer"> <!--FileUpload Controls will be added here --> </div> <asp:HiddenField ID="HdFirst1" runat="server" Value="" /> <br /> <asp:Button ID="btnUpload" runat="server" Text="Upload" OnClick="btnUpload_Click" /> </form> 

脚本:

  <script type="text/javascript"> var counter = 0; function AddFileUpload() { var div = document.createElement('DIV'); div.innerHTML = '<input id="file' + counter + '"name = "file' + counter + '"type="text"/><input id="file' + counter + '" name = "file' + counter + '" type="file" /><input id="Button' + counter + '" type="button" value="Remove" onclick = "RemoveFileUpload(this)" />'; document.getElementById("FileUploadContainer").appendChild(div); counter++; } function RemoveFileUpload(div) { document.getElementById("FileUploadContainer").removeChild(div.parentNode); } function mydetails(div) { var info; for (var i = 0; i < counter; i++) { var dd = document.getElementById('file' + i).value; info = info + "~" + dd; } document.getElementById('<%= HdFirst1.ClientID %>').value = info; } </script> 

并在Upload_Clickbutton中:

 for (int i = 0; i < Request.Files.Count; i++) { string strname = HdFirst1.Value; string[] txtval = strname.Split('~'); HttpPostedFile PostedFile = Request.Files[i]; if (PostedFile.ContentLength > 0) { string FileName = System.IO.Path.GetFileName(PostedFile.FileName); // string textname= //PostedFile.SaveAs(Server.MapPath("Files\\") + FileName); } } 

当你使用dynamic控件时,他们将无法在回发期间保持其状态,并且数据丢失。因为他们没有任何视图状态来维护他们的数据。

您只需要将创build的控件数据dynamic地保存到ViewState中,并在回发完成后将数据加载到页面中。

 public Dictionary<Guid, string> UcList { get { return ViewState["MyUcIds"] != null ? (Dictionary<Guid, string>)ViewState["MyUcIds"] : new Dictionary<Guid, string>(); } set { ViewState["MyUcIds"] = value; } } public void InitializeUC() { int index = 1; foreach (var item in UcList) { var myUc = (UserControls_uc_MyUserControl)LoadControl("~/UserControls/uc_MyUserControl.ascx"); myUc.ID = item.Value; pnlMyUC.Controls.AddAt(index, myUc); index++; } } protected void Page_Load(object sender, EventArgs e) { if (!IsPostBack) LoadControl(); else InitializeUC(); } 

在这里,您可以find关于dynamic控件的回发和回发的最佳理解。 在每次回发或事件点击时保留dynamic控制值 。

在这里输入图像描述