asp.net - 无法加载 View 状态 - ASP.NET 中的动态控件

标签 asp.net dynamic controls viewstate

我读过很多关于 viewstate 的文章,但我无法理解它。

基本上我想要两个带有添加和删除按钮以及继续按钮的列表框。

当按下“继续”按钮时,前一项将被隐藏,并为第一个列表框中的每个项目显示一个文本框,并有 2 个下拉框来描述它+为第二个列表框中的每个项目提供一个文本框(也适用于用户添加描述)。

然后我想要一个 Finalize 按钮将所有这些信息保存到数据库中。

到目前为止,我有以下代码:

   <script runat="server">   

    void Page_Load(Object sender, EventArgs e)
    {
        CreateDynamicControls();
        Page.MaintainScrollPositionOnPostBack = true;
        Build2.Visible = false;
        Build3.Visible = false;
        Build4.Visible = false;
        Finish.Visible = false;
    }

    void AddC_Click(Object sender, EventArgs e)
    {
                criteria.Items.Add(addnewc.Text.ToString());
                addnewc.Text = null;
    }

    void RemoveCriterion_Click(Object sender, EventArgs e)
    {
        for (int i = 0; i < criteria.Items.Count; i++)
        {
            if (criteria.Items[i].Selected)
            {
                criteria.Items.Remove(criteria.Items[i]);
                i--;
            }
        }
    }

    void AddAlternative_Click(Object sender, EventArgs e)
    {
                alternatives.Items.Add(addnewa.Text.ToString());
                addnewa.Text = null;
    }

    void RemoveAlternative_Click(Object sender, EventArgs e)
    {
        for (int i = 0; i < alternatives.Items.Count; i++)
        {
            if (alternatives.Items[i].Selected)
            {
                alternatives.Items.Remove(alternatives.Items[i]);
                i--;
            }
        }
    }

    void Continue_Click(Object sender, EventArgs e)
    {
            Build1.Visible = false;
            Build2.Visible = true; 
            Build3.Visible = true;

            CreateDynamicControls();

            Finish.Visible = true;
    }

    void CreateDynamicControls()
    {
        Build2.Controls.Clear();
        Build3.Controls.Clear();

        Build2.Controls.Add(new LiteralControl("<h3>Please define each criterion.</h3><p>By describing it and indicating if it is 1/2 and a/b.</p>"));

        for (int i = 0; i < criteria.Items.Count; i++)
        {
            Build2.Controls.Add(new LiteralControl("<strong>" + criteria.Items[i].Text + "</strong>&nbsp;&nbsp;Description:<br />"));
            TextBox criteriondesc = new TextBox();
            Build2.Controls.Add(criteriondesc);
            criteriondesc.ID = "c" + i.ToString();
            criteriondesc.Rows = 3;
            criteriondesc.Width = 850;
            criteriondesc.TextMode = TextBoxMode.MultiLine;
            Build2.Controls.Add(new LiteralControl("<br />"));

            Build2.Controls.Add(new LiteralControl("Desc1: "));
            DropDownList aim = new DropDownList();
            aim.ID = i.ToString();
            aim.Width = 250;
            aim.Items.Add(new ListItem("1"));
            aim.Items.Add(new ListItem("2"));
            Build2.Controls.Add(aim);

            Build2.Controls.Add(new LiteralControl("&nbsp;&nbsp;&nbsp;&nbsp;Desc2: "));
            DropDownList source = new DropDownList();
            source.ID = i.ToString();
            source.Width = 250;
            source.Items.Add(new ListItem("a"));
            source.Items.Add(new ListItem("b"));
            Build2.Controls.Add(source);

            Build2.Controls.Add(new LiteralControl("<br /><br />"));

        }

        Build3.Controls.Add(new LiteralControl("<h3>Please define each alternative.</h3><p>Please describe each alternaitve in detail.</p>"));

        for (int i = 0; i < alternatives.Items.Count; i++)
        {
            Build3.Controls.Add(new LiteralControl("<strong>" + alternatives.Items[i].Text + "</strong>&nbsp;&nbsp;Description:<br />"));
            TextBox altdesc = new TextBox();
            altdesc.ID = "a" + i.ToString();
            altdesc.Rows = 3;
            altdesc.Width = 850;
            altdesc.TextMode = TextBoxMode.MultiLine;
            Build3.Controls.Add(altdesc);
            Build3.Controls.Add(new LiteralControl("<br />"));
        }

        Build3.Controls.Add(new LiteralControl("<br /><h3>Review dates.</h3><p>Please select a date for a meeting.</p>"));
        OboutInc.Calendar2.Calendar selectdates = new OboutInc.Calendar2.Calendar();
        Build3.Controls.Add(selectdates);
    }

    void Finish_Click(Object sender, EventArgs e)
    {

            Build4.Visible = true;

            foreach (var control in Build2.Controls)
            {
                if (control.GetType() == typeof(TextBox))
                {
                    Build4.Controls.Add(new LiteralControl(((TextBox)control).Text + "<br>"));
                }
            }

            foreach (var control in Build3.Controls)
            {
                if (control.GetType() == typeof(TextBox))
                {
                    Build4.Controls.Add(new LiteralControl(((TextBox)control).Text + "<br>"));
                }
            }

    }
</script>

<asp:Content runat="server" ID="MainContent" ContentPlaceHolderID="MainContent">
    <asp:Panel ID="Build1" runat="server">
    <h3>What is your aim?</h3>
    <p>
        <asp:TextBox ID="goal" runat="server" Width="850px"></asp:TextBox>
    </p>

        <h3>What are the criteria of your decision?</h3>
    <p>
        <asp:ListBox ID="criteria" runat="server" Rows="8" Width="850px"></asp:ListBox><br />
        <asp:Button ID="RemoveCriterion" runat="server" Text="Remove" OnClick="RemoveCriterion_Click" />&nbsp;&nbsp;&nbsp;&nbsp;
        <asp:TextBox ID="addnewc" runat="server" Width="650px"></asp:TextBox>
        <asp:Button ID="AddC" runat="server" Text="Add" OnClick="AddC_Click" />
    </p>

        </p>
        <h3>What are the alternatives of your decision?</h3>

    <p>
        <asp:ListBox ID="alternatives" runat="server" Rows="8" Width="850px"></asp:ListBox><br />
        <asp:Button ID="RemoveAlternative" runat="server" Text="Remove" OnClick="RemoveAlternative_Click" />&nbsp;&nbsp;&nbsp;&nbsp;
        <asp:TextBox ID="addnewa" runat="server" Width="650px"></asp:TextBox>
        <asp:Button ID="AddAlternative" runat="server" Text="Add" OnClick="AddAlternative_Click" />
    </p>
    <p align="right"><asp:Button ID="continue" runat="server" Text="Continue" OnClick="Continue_Click" /></p>


    </asp:Panel>

        <asp:Panel ID="Build2" runat="server">
        </asp:Panel>
            <asp:Panel ID="Build3" runat="server">
        </asp:Panel>
                <asp:Panel ID="Build4" runat="server">
        </asp:Panel>

    <p align="right"><asp:Button ID="Finish" runat="server" Text="Finish" OnClick="Finish_Click" /></p>


</asp:Content>

如您所见,目前我只是尝试从动态创建的文本框字段中输出用户的文本。

但是,我收到错误

Failed to load viewstate. The control tree into which viewstate is being loaded must match the control tree that was used to save viewstate during the previous request. For example, when adding controls dynamically, the controls added during a post-back must match the type and position of the controls added during the initial request.

位于:第 169 行:Build3.Controls.Add(altdesc);

有人知道如何解决 View 状态的这个问题吗?

我对 ASP.NET 非常陌生,我的背景主要是 WinForms。

感谢您的帮助和建议!!

最佳答案

您创建控件太晚了。您应该在页面的 Init 事件期间创建它们,而不是页面加载期间。我建议您阅读一下有关 page life cycle 的内容

关于asp.net - 无法加载 View 状态 - ASP.NET 中的动态控件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15640840/

相关文章:

c# - Request.Url.Host 和 ApplicationPath 一次调用

asp.net - 免费的录制/回放网络测试工具

c# - 如何在 Entity Framework Core 中正确编写种子方法?

c++ - C++中的动态嵌套?

mysql - 如何将表数据作为预定义字符串中的变量返回 - SQL

.net - 我需要 WPF 4 的 Accordion 控件

asp.net - 将 CSS 模板应用于包含内容/控件的 ASP 页面

dynamic - View 中的 Couchbase 通配符/变量键

C# Windows 窗体 : Looping through Dynamically created TextBoxes and checking to see if Text has changed

.net - 如何将 dll 永久添加到 .net 工具箱中?