ASP.NET StateBag和自定义控件

drs*_*222 5 c# asp.net viewstate custom-server-controls

让我假装由于某种原因我想创建一个派生自Control而不是WebControl的自定义控件.让我们假设我需要处理属性(即实现IAttributeAccessor),并且我想通过像WebControl一样使用AttributeCollection来实现.

WebControl实现Attributes属性,如下所示:


public AttributeCollection Attributes
{
    get
    {
        if (this.attrColl == null)
        {
            if (this.attrState == null)
            {
                this.attrState = new StateBag(true);
                if (base.IsTrackingViewState])
                {
                    this.attrState.TrackViewState();
                }
            }
            this.attrColl = new AttributeCollection(this.attrState);
        }
        return this.attrColl;
    }
}

请注意以下事项:

  1. 如果没有给StateBag,就不能创建AttributeCollection.
  2. 我们必须创建一个新的StateBag.重用控件StateBag是不明智的,因为属性可能将名称作为控件存储的值.
  3. 我们不能在StateBag上调用TrackViewState,因为这是一个内部方法.
  4. StateBag是一个密封的类.

因此,据我所知,如果我想使用AttributeCollection,我必须使用一个新的StateBag,它永远不会(不采用像反射这样的技巧)实际正确地管理状态.

我错过了什么吗?

wom*_*omp 3

要在自定义 StateBag 上调用 TrackViewState,您必须将其强制转换为其接口。

StateBag mybag = new StateBag();
(mybag as IStateManager).TrackViewState();
Run Code Online (Sandbox Code Playgroud)

我猜测这个设计决策是为了向消费者隐藏 ViewState 的实现。IStateManager 的文档页面上有一些有关实现自定义状态跟踪的信息。