动态创建的表单值在回发后仍然存在

时间:2019-05-31 17:20:31

标签: .net dynamic user-controls postback

我有一个用户控件,其中包含动态生成的Web控件(TextBox,DropDownList等...)

在某些按钮单击事件上加载了用户控件。

在用户控件上,偶尔有一些回发事件需要处理(Button.OnClick等)。

为了适应在点击事件中加载用户控件这一事实,在用户控件父级的Page_Load()期间,我重新执行了加载用户控件的代码。

IE-本质上,我有以下内容:

public partial class parentPage : System.Web.UI.Page
{
    protected void Page_Load(object sender, EventArgs e)
    {
        If(Page.IsPostBack)
        {
            // Conditions are usually here to make sure this only happens when I want it to
            userControl.LoadUserControl();
        }
    } 

    protected void Button_Click(object sender, EventArgs e)
    {
        userControl.LoadUserControl();
    }
}

public partial class userControl : System.Web.UI.UserControl
{
    public void LoadUserControl()
    {
        // Generate dynamic controls and bind events
    }

    protected void Button_Click(object sender, EventArgs e)
    {
        // Do stuff
    }
}

我面临的问题是,在处理完用户控件的Button_Click()事件之后,下次我单击父控件上的按钮时,用户控件的动态生成字段将以某种方式自动填充之前的内容用户控件的按钮被单击了-尽管在父级按钮单击期间调用LoadUserControl()函数时我明确地设置了值。

更奇怪的是,填充的字段不一定一致。在某些情况下,文本框具有正确的文本,但DropDownLists具有旧的选定项。在其他情况下,可以正确选择DropDownLists,但TextBoxes保留旧文本。

有人对您有任何建议或见解吗?我尝试了100万种不同的想法,但似乎没有任何效果。

**编辑**

也许有些见识-如果我将usercontrol设置为ViewStateMode = Disabled,似乎可以解决问题。我不愿意这样做,因为我真的不确定它是否会影响其他功能。我已经发现了与更改有关的一些故障,即使解决了这些问题,我仍然有一种感觉,最终我会发现更多。因此,希望任何解决方案都不需要进行如此大的改变。也许可以解决这个问题的事实可能有助于找到更优雅的解决方案?

**编辑2 **

使用dotPeek在System.Web.UI.ControlCollection.Add()的框架中进行调试显示,将控件添加到集合中后,将调用System.Web.UI.Control.AddedControl()。在 的末尾,将调用System.Web.UI.Control.LoadViewStateRecursive()。麻烦就在其中出现。尽管这是一个动态生成的控件,但它似乎仍然可以保存在ViewState中。继续挖掘...

1 个答案:

答案 0 :(得分:0)

好的!在通过.NET Framework的深入,黑暗的内部进行了两天的调试之后,我终于找到了解决方案。

我仍然不确定为什么会出现此问题,但是解决方案是为要手动加载的控件禁用ViewState,但只能在初始加载时使用。

由于控件的加载是在Postback上进行的,因此我无法使用简单的if(!Page.IsPostBack)选项,因此我使用已经编写的函数返回了Postback控件执行回发的控件的ID。如果ID与我最初用于加载控件的按钮相匹配,那么在创建不同的输入时,我会将其ViewStateMode设置为Disabled,并且为了获得加分,还将EnableViewState设置为false。

关键是,当这些控件随后进行其 own 回发(即,IE,DropDownList.SelectedIndexChanged,Button.Click等)时,将启用它们的ViewStateMode-这样就可以了正确!