【问题标题】:Get text from dynamically created textbox in asp.net从asp.net中动态创建的文本框中获取文本
【发布时间】:2012-08-13 02:33:14
【问题描述】:

我整个早上都在努力解决这个问题,所以希望我能得到一些帮助。本质上,我在从我在 .net 4 中动态创建的一些文本框控件获取值时遇到问题。

这是所需的应用程序流程。

1)。用户从作为信件模板的下拉菜单中选择一个 html 文档。此 html 文档包含格式为 $VARIABLENAME$ 的标签,这些标签将替换为正确的值。

2)。程序通过模板运行并提取所有格式为 $STRING$ 的字符串并将它们存储在一个列表中。

3)。对于此列表中的每个条目,程序会根据原始 $VARIABLENAME$ 字段生成一个 asp:label 和一个带有唯一 ID 的 asp:textbox。

4)。用户输入替换值,然后点击提交。

5)。程序用替换值替换所有 $STRING$ 并输出结果。

在我需要从文本框中获取值之前,一切都运行良好。我很确定这是页面生命周期的问题,但是因为直到用户从下拉列表中选择所需的模板才生成文本框,所以我不确定如何使它们通过回发持久化,以便我可以引用它们。

这一切都错了吗?在 submitbutton 事件发生回发后,如何访问从下拉事件创建的文本字段?

编辑: 这是大部分相关代码。

protected void createTextBoxes(List<string> results)
    {
        if (results != null)
        {
            foreach (string result in results)
            {
                string formattedResult = result.Substring(1, result.Length - 2);
                formattedResult = formattedResult.ToLower();
                formattedResult = char.ToUpper(formattedResult[0]) + formattedResult.Substring(1);


                var label = new Label();
                label.ID = formattedResult;
                label.Text = formattedResult + ": ";
                templateFormPlaceholder.Controls.Add(label);

                var textBox = new TextBox();
                textBox.ID = result;
                templateFormPlaceholder.Controls.Add(textBox);
                templateFormPlaceholder.Controls.Add(new LiteralControl("<br />"));

                previewBtn.Visible = true;
            }
        }
    }

protected void templateDD_SelectedIndexChanged(object sender, EventArgs e)
    {
        var templatePath = "";
        if (templateDD.SelectedIndex == 0)
        {
            previewBtn.Visible = false;
        }

        if (templateDD.SelectedIndex == 1)
        {
            templatePath = employeePath;
        }
        else if (templateDD.SelectedIndex == 2)
        {
            templatePath = managerPath;
        }
        List<string> regMatches = FindMatches(templatePath);
        Session["regMatches"] = regMatches;
        createTextBoxes(regMatches);
    }

protected void Page_Init(object sender, EventArgs e)
    {
        if (Session["regMatches"] != null)
        {
            createTextBoxes((List<string>)Session["regMatches"]);
        }
    }

稍后,我尝试将这些文本框中的值添加到字典中。参数是字典的名称。关键字段是 $STRING$,结果是用户在文本框中输入的内容。

   protected void previewBtn_Click(object sender, EventArgs e)
    {
        List<string> matchResults = (List<string>)Session["regMatches"];
        Dictionary<string, string> parameters = new Dictionary<string, string>();
        foreach (string result in matchResults)
        {
            TextBox tb = (TextBox)templateFormPlaceholder.FindControl(result);
            parameters.Add(result, tb.Text);
        }

        var template = ReplaceKeys(parameters);
        outputLBL.Text = template;

这是 .aspx 代码。

<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="offerLetter.aspx.cs"     Inherits="templateRegexTesting.offerLetter" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
    <title></title>
</head>
<body>
<form id="form1" runat="server">
<div>
    <p>
        Which template would you like to use?
    </p>
    <asp:DropDownList ID="templateDD" runat="server" OnSelectedIndexChanged="templateDD_SelectedIndexChanged"
        AutoPostBack="true">
        <asp:ListItem></asp:ListItem>
        <asp:ListItem Value="1">Employee</asp:ListItem>
        <asp:ListItem Value="2">Manager</asp:ListItem>
    </asp:DropDownList>
    <br />
    <asp:PlaceHolder ID="templateFormPlaceholder" runat="server" />
    <div>
        <asp:Button ID="previewBtn" runat="server" Text="Preview" Visible="false" OnClick="previewBtn_Click" />
    </div>
    <div>
        <asp:Label ID="outputLBL" runat="server"></asp:Label>
    </div>
    <br />
</div>
</form>
</body>
</html>

编辑:当我发现它时,我把它放在评论中,但我认为我应该将它移到问题中以便它更明显:

我想我应该更新一下。我觉得自己像个白痴,但我确实设法让它发挥作用。基本上,我为控件分配了一个等于替换令牌的 ID(例如 ID="$FIRSTNAME$")。我什至没有意识到 $ 会引起任何问题。当我刚刚更改为 ID="Firstname" 格式时,它可以完美运行。感谢大家的帮助!

【问题讨论】:

  • ..尤其是在您创建控件的地方。
  • 认为我应该更新这个。我觉得自己像个白痴,但我确实设法让它发挥作用。基本上,我为控件分配了一个等于替换令牌的 ID(例如 ID="$FIRSTNAME$")。我什至没有意识到 $ 会引起任何问题。当我刚刚更改为 ID="Firstname" 格式时,它可以完美运行。感谢大家的帮助!

标签: c# asp.net .net dynamic controls


【解决方案1】:

你说得对,这一切都与页面生命周期有关。动态创建的控件必须在Page_Init 阶段重新创建,以便在视图状态绑定阶段之前存在。这意味着必须以某种方式(可能使用Session)存储您在先前处理中创建的textboxes 数量以重新创建它们。提醒使用相同的 ID 并将它们添加到您的控制树(中继器或您正在使用的其他东西)。


更新

让我给你一个建议: 1.声明一个List&lt;TextBox&gt;类型的类属性(我们称之为CreatedTextBoxes)

  1. 声明一个接收创建文本框所需内容的方法。此方法不得读取超出其范围的任何内容。它只会接收一些参数,创建文本框并将它们添加到另一个控件(例如Repeater)。将创建的每个文本框添加到CreatedTextBoxes

  2. 在下拉更改事件中,读取选项,保存到Session并调用此方法

  3. 在Page_Init,验证Session 的对象。如果它为 null 或为空,则不执行任何操作。如果它有一个值,调用相同的方法,传递相同的参数

  4. 当您需要从动态创建的文本框中检索它时,请使用 CreatedTextBoxes 而不是 FindControls()

【讨论】:

  • 所以在 Page_Init 阶段,我是否必须再次运行基于下拉选择创建文本框的方法?将它放在 Page_Init 方法中不会导致页面在首次访问页面时尝试创建文本框(在进行下拉选择之前)?
  • 是的,是的,这就是为什么你必须弄清楚一些“流量控制”。我会用建议更新问题
  • 不幸的是,我仍然无法找到文本框控件来获取文本。我再次编辑了最初的帖子,以包含所有似乎相关的代码。
  • @mElling 如果您调试previewBtn_Click,您可以检索到TextBox 还是为空?
  • 此外,多次从下拉列表中选择会导致此操作中断,因为下拉列表和 page_init 方法都将尝试创建具有相同 ID 的控件。
【解决方案2】:

您将TextBox 控件添加到templateFormPlaceholder.Controls,但使用form1.FindControl 来查找它们。 FindControl 方法仅当控件直接包含在指定容器中时才会找到控件 - 来自http://msdn.microsoft.com/en-us/library/486wc64h.aspx。请尝试致电 templateFormPlaceholder.FindControl。

【讨论】:

  • 不错,但不幸的是,将其更改为 form1 只是在黑暗中尝试的最后一搏。甚至将其改回 TextBox tb = (TextBox)templateFormPlaceholder.FindControl(result);参数。添加(结果,tb.Text);导致空引用异常。我将更新我的原始帖子以反映这一点。
【解决方案3】:

创建动态文本框并将其添加到 asp 面板,以便您可以轻松访问它。

这是 ASP.NET 设计元素。

<div class="form-group">
<asp:Panel ID="panel" runat="server" CssClass="form-group">

</asp:Panel>
</div>

生成动态文本框的 C# 代码

 protected void create_dynamic_text(object sender, EventArgs e)
{
    int num = 5; // you can give the number here
    for (int i = 0; i < num;i++ )
    {
        TextBox tb = new TextBox();
        tb.ID = "txt_box_name" + i.ToString();
        tb.CssClass = "add classes if you need";
        tb.Width = 400; //Manage width and height 
        panel.Controls.Add(tb); //panel is my ASP.Panel object. Look above for the design code of ASP panel
    }
}

获取值的 C# 代码

 protected void reade_values(object sender, EventArgs e)
{
   int num=5; // your count goes here
    TextBox tb = new TextBox();
        for (int i = 0; i < num; i++)
        {
           tb=(TextBox)panel.FindControl("txt_box_name"+i.ToString());
           string value = tb.Text; //You have the data now
        }
    }
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-01-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多