【问题标题】:Insert TextBoxes into a Repeater dynamically and retrieve their value将文本框动态插入到中继器中并检索它们的值
【发布时间】:2012-10-17 13:58:00
【问题描述】:

我有一个从 SQL 绑定的中继器,其中包含可编辑和只读元素的混合。当您单击一行上的“编辑”按钮时,可编辑部分应转换为文本框,当您单击“更新”时,它应保存您的更改。

这是编辑和更新按钮的 OnClick 代码的(非常)简化版本:

switch(commandName)
{
    case "Edit":
        Label1.Visible = false; //hide read-only version
        PlaceHolder1.Visible = true; //show editing version

        //Dict1 is Dictionary<string, string> in this example.
        foreach (var key in Dict1)
        {
            //insert a TextBox dynamically into the PlaceHolder
            PlaceHolder1.Controls.Add(new TextBox 
            { 
                ID = "txt" + key, 
                Text = Dict1[key] 
            });
        }
        break;

    case "Update":
        //retrieve user input from dynamically-added TextBoxes
        foreach (var TextBox1 in PlaceHolder1.Controls.Where(c => c.ID.StartsWith("txt")))
        {
            doStuff(TextBox1);
        }

        Label1.Visible = true; //show read-only version
        PlaceHolder1.Visible = false; //hide editing version
        break;
}

问题是当页面回发时我的动态添加的文本框不存在。我在调试器中检查了PlaceHolder1.Controls,其中没有文本框。 PlaceHolder1 本身在中继器内,但我不会在 PostBack 上重新绑定中继器。

我考虑过使用原始 HTML 来代替 TextBox 控件并将值从 Request.Form 中提取出来,但这对我来说感觉很生硬。如何使动态添加的文本框在回发中持久化?


编辑:

这里有一些复杂性,如果没有大量示例代码很难说明。以下是大的:

  • 中继器中的每个单元格都可以混合使用只读和可编辑文本(即动态插入的标签和文本框)
  • 我不知道每个单元格中有多少可编辑区域。原始文本可能看起来像 blah blah @A1@ blah blah @A2@ blah...,我必须插入替换文本来代替 @A1@、@A2@ 等。在编辑模式下,只有替换文本是可编辑的。

【问题讨论】:

  • 顺便说一下,这是非常简化的示例代码。我实际上并没有给我的控件命名,比如Label1

标签: c# asp.net viewstate repeater dynamic-controls


【解决方案1】:

当您动态添加控件时,它们不会在回发中保留。您必须在回发后再次将它们添加到页面中。我通常在 Page_Load 中执行此操作。然后,一旦添加它们,它们的回发状态将在 ASP.NET 页面生命周期的后期正确恢复。

所以,

  • 每次加载页面时都必须添加动态控件,
  • 但一旦添加它们,ASP.NET 就会正确恢复它们的状态。

希望这会有所帮助!

【讨论】:

  • 这可能很复杂,因为在绑定中继器之前我不知道有多少控件。如果我重新绑定中继器,我不会丢失输入的值吗?
  • 正如您所建议的,我通过在 Page_Load 期间添加文本框而不是编辑按钮的 OnClick 事件来解决问题。感谢您的帮助!
【解决方案2】:

一个可能的答案是在 ITEM TEMPLATE 中预定义 TEXTBOX,然后在点击事件中为给定行设置其可见性。

第二种可能性是重构转发器以改用 GRIDVIEW 控件。它支持开箱即用的可编辑模板。

无论如何,发生的事情是,由于这些控件是动态添加的,因此它们不会在下一次回发时重新创建。在回发时,如果要访问它们,则需要重新创建控件。 但是,不要忘记该值存储在表单集合中:

myval =  request.form["txt" + key];

【讨论】:

  • Request.Form 的想法很好。不知何故,我只想将它用于纯 HTML 输入。但是我不需要知道每个 TextBox 的 ClientID 吗?在这种情况下,我必须在某处捕获 ItemIndex。
  • 是的(除非您在占位符中使用标准 html 控件到文字中)。但是您始终可以使用 LINQ 根据已知字符串查询集合(类似于您使用 'txt' 的方式,只需将其称为 'myRptrtxt' 作为前缀或其他东西
  • 酷,感谢您的帮助。这一次在 Page_Load 期间构建 TextBoxes 似乎已经成功了,但这对未来有好处。 +1。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-08-03
  • 1970-01-01
  • 1970-01-01
  • 2016-04-16
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多