【问题标题】:Handling events from dynamic controls NOT added on Page_Load?处理来自未在 Page_Load 上添加的动态控件的事件?
【发布时间】:2012-05-04 01:55:38
【问题描述】:

我在这里和网络上阅读了几篇文章,这些文章告诉我,我不能简单地将新控件动态添加到页面,将其连接到处理程序,并期望它能够工作。

每次给出的解决方法是每次Init上的页面都需要添加动态控件。

我的问题是,我的控件没有在初始化时添加到页面中,它们是在另一个回发之后添加的。

工作流程是这样的:

  1. 页面加载
  2. 用户填写文本框,点击按钮
  3. 页面回帖,根据输入在button_click事件中创建动态链接控件
  4. 用户单击其中一个链接控件以继续下一步。

所以如果这是我需要支持的行为,有什么办法可以做到这一点吗?它必须发生在第 2 步的 button_click 中,因为动态控件是基于用户在第 2 步中输入的。

我有没有把自己画到一个角落里?我还能如何处理这样的工作流程?

【问题讨论】:

  • 如果您的工作流程涉及“步骤”,请查看 ASP.Net 向导控件。
  • 这是一个很好的建议,我最初是这么想的,但想尽快完成,然后回去看看使用向导。这可能只是解决问题,谢谢,会报告

标签: asp.net postback page-lifecycle dynamic-controls


【解决方案1】:

动态创建链接按钮后,在页面的视图状态中设置一个标志。在回发时,如果标志设置为视图状态,则重新创建链接按钮。这是一个演示:

标记:

<asp:Button runat="server" ID="button1" OnClick="button_Click" Text="Create button A" CommandArgument="A" />
<asp:Button runat="server" ID="button2" OnClick="button_Click" Text="Create button B" CommandArgument="B" />
<asp:PlaceHolder runat="server" ID="placeHolder"></asp:PlaceHolder>

代码隐藏:

public partial class Default : System.Web.UI.Page
{
    private bool LinkButtonCreated
    {
        get { return ((bool?)this.ViewState["LinkButtonCreated"]).GetValueOrDefault(); }
        set { this.ViewState["LinkButtonCreated"] = value; }
    }

    private string LinkButtonCommandArgument
    {
        get { return (string)this.ViewState["LinkButtonCommandArgument"]; }
        set { this.ViewState["LinkButtonCommandArgument"] = value; }
    }

    protected override void LoadViewState(object savedState)
    {
        base.LoadViewState(savedState);
        if (this.LinkButtonCreated)
            this.CreateLinkButton(this.LinkButtonCommandArgument);
    }

    protected void button_Click(object sender, EventArgs e)
    {
        if (!this.LinkButtonCreated)
        {
            string commandArgument = ((Button)sender).CommandArgument;
            this.LinkButtonCreated = true;
            this.LinkButtonCommandArgument = commandArgument;
            this.CreateLinkButton(commandArgument);
        }
    }

    private void CreateLinkButton(string commandArgument)
    {
        LinkButton linkButton =
            new LinkButton
            {
                ID = "linkButton",
                Text = "Click me",
                CommandArgument = commandArgument,
            };
        linkButton.Click += this.linkButton_Click;
        this.placeHolder.Controls.Add(linkButton);
    }

    private void linkButton_Click(object sender, EventArgs e)
    {
        LinkButton linkButton = (LinkButton)sender;
        linkButton.Text = "I was clicked! Argument: " + linkButton.CommandArgument;
    }
}

【讨论】:

  • 谢谢您,这看起来很有希望,但是当单击按钮时如何根据输入重新创建链接按钮?我需要将值传递给命令参数的链接按钮,当我重新创建按钮时如何处理?
  • 使用视图状态保存重新创建链接按钮所需的任何其他内容,例如命令参数。有关示例,请参阅我的更新答案。
  • 我尝试根据您的示例进行设置,但 LoadViewState 没有触发。我应该提一下,这是在用户控件中而不是页面中(不确定这是否重要)。但我在 LoadViewState 中放了一个断点,它永远不会触发......即使在回发时
  • 我将代码移到了用户控件,它仍然有效; LoadViewState 在每次回发时被调用(它不会在初始请求中被调用)。确保页面或用户控件上没有任何 EnableViewState="False" 属性。此外,您的用户控件或任何其他控件(链接按钮除外)是否是动态创建的?
  • 实际上,LoadViewState 应该只在链接按钮创建后的每个回发中被调用。
猜你喜欢
  • 2019-09-16
  • 2010-11-08
  • 1970-01-01
  • 2011-04-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多