0

我有一个复合数据绑定控件,它承载一个 IBindableTemplate 并根据某些条件将标记动态加载到控件中。现在,当这些子控件被加载到复合控件中并且回发在那里时,我失去了子控件的视图状态。有没有办法,我可以在回发中保存子控件的视图状态?

我也参考。使用http://scottonwriting.net/sowblog/posts/2129.aspx对 Scott 的解释;但没有用。

4

2 回答 2

0

没有足够的信息。什么时候创建控件?什么时候将它们添加到 Controls 集合中?什么是条件,它在回发时会改变吗?

鉴于控件是在正确的时间添加的,视图状态会在页面周期结束时自动保存(无论是否回发)。

如果您稍后添加控件,在某些情况下在所有初始化完成之后,那么为时已晚。

更新

如果没有代码,很难猜测故障发生在哪里。让我们检查一个带有自定义模板的Repeater,它可以根据某些条件加载控件。此示例正在运行,但如果在 Page_Load 上完成模板分配,它将失败。这和你的情况相似吗?

形式:

<div>
    <asp:Repeater ID="repeater" runat="server" />
    <asp:Button ID="submitButton" runat="server" Text="Submit" onclick="submitButton_Click" />
    <asp:Button ID="postButton" runat="server" Text="PostBack" />
</div>

代码:

public partial class _Default : System.Web.UI.Page
{
    protected override void OnInit(EventArgs e)
    {
        base.OnInit(e);
        repeater.ItemTemplate = new MyTemplate();
    }

    protected void Page_Load(object sender, EventArgs e)
    {
        //however, if I was to move repeater.ItemTemplate = new MyTemplate() here
        //it would not reload the view state
        if (!IsPostBack)
        {
            repeater.DataSource = new int[] { 1, 2, 3, 4, 5 };
            repeater.DataBind();
        }
    }

    protected void submitButton_Click(object sender, EventArgs e)
    {
        submitButton.Text = "Do it again";
    }
}

public class MyTemplate : IBindableTemplate, INamingContainer
{
    #region IBindableTemplate Members
    public System.Collections.Specialized.IOrderedDictionary ExtractValues(Control container)
    {
        OrderedDictionary dictionary = new OrderedDictionary();
        return dictionary;
    }
    #endregion

    #region ITemplate Members
    public void InstantiateIn(Control container)
    {
        Label label = new Label();
        label.Text = "Label";
        container.Controls.Add(label);

        TextBox textbox = new TextBox();
        container.Controls.Add(textbox);
    }
    #endregion
}
于 2009-03-19T15:31:38.497 回答
0

您的理论代码几乎接近我的情况,只有一个主要区别是我没有从 IBindable 扩展我的模板类,而是我在标记本身中为模板提供控件,这是要求。

斯科特也明确表示,如果我们像您所做的那样将控件添加到模板中

         #region ITemplate Members
         public void InstantiateIn(Control container)
         {
             Label label = new Label();
             label.Text = "Label";
             container.Controls.Add(label);

             TextBox textbox = new TextBox();
             container.Controls.Add(textbox);
         }
         #endregion

然后视图状态将在每次回发时自动持久化。我所需要的只是让我的模板在标记中被实例化,并且在回发时仍然保持视图状态,并允许我获取控制状态,即使我曾经使用一些不同的数据重新启动模板。

于 2009-03-23T08:22:54.987 回答