Persisting ListItemCollection values across postback, using ViewSt

Discussion in 'ASP .Net Web Controls' started by Christophe Peillet, Jan 23, 2006.

  1. I have a series of composite controls to replace most common form controls
    (adding Ajax support and a built in validator), and have all of the simple
    controls working (textbox, checkbox, button, etc.), but have an issue with
    Viewstate and Postback when it comes to ListItem based controls
    (CheckboxList, DropDownList and RadioButtonList).

    I need to set the Item properties value in Viewstate, but they do not seem
    to persist on postback when I do this (all of the other properties do except
    this one, so it isn't, I don't think, a problem like unique ID, etc.).

    When I set the collection directly to the underlying child control, it works
    propertly and persists across viewstates (see first example below), but,
    because of other restrictions in my control, I am unable to do this, and NEED
    to keep this information in Viewstate, and reassign the appropriate value to
    m_chk after a postback.

    This is what I have at the moment, which maintains data across postback, but
    doesn't work in my case since I need to keep it in Viewstate and manually
    reassign it to m_chk.

    /// <summary>
    /// Gets the CheckBoxList items.
    /// </summary>
    /// <value>The CheckBoxList items.</value>
    [Bindable(true)]
    [DefaultValue((string)null)]
    [PersistenceMode(PersistenceMode.InnerProperty)]
    [Editor("System.Web.UI.Design.WebControls.ListItemsCollectionEditor,System.Design,
    Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a",
    typeof(UITypeEditor))]
    [MergableProperty(false)]
    [Category("CheckBox")]
    public ListItemCollection Items
    {
    get
    {
    EnsureChildControls();
    return m_chk.Items;
    }
    }

    When I try this, it adds everything to ViewState, but the contents are
    always lost on postback.

    /// <summary>
    /// Gets the CheckBoxList items.
    /// </summary>
    /// <value>The CheckBoxList items.</value>
    [Bindable(true)]
    [DefaultValue((string)null)]
    [PersistenceMode(PersistenceMode.InnerProperty)]
    [Editor("System.Web.UI.Design.WebControls.ListItemsCollectionEditor,System.Design,
    Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a",
    typeof(UITypeEditor))]
    [MergableProperty(false)]
    [Category("CheckBox")]
    public ListItemCollection Items
    {
    get
    {
    ListItemCollection l = (ListItemCollection)Viewstate["CheckboxListItems"];
    return l;
    }
    }

    How can I persist this information across postbacks, but assigning it to
    viewstate.

    Thanks for any help on this. (Someone should real write a good book on
    custom component development for ASP using real world development examples
    (inheritance, etc.) ... there are surprisingly few helpful resources out
    there.)
    Christophe Peillet, Jan 23, 2006
    #1
    1. Advertising

  2. Hi Christophe,

    See you again. How are you doing on your original problems, have you got
    them resolved?
    As for this problem that use ListItemCollection as custom property and
    persist them into ViewState, I think we have to take care of the following
    things:

    1. ListItemCollection class is not marked as Serializable, so they can not
    be directly stored in ViewState collection(can not be persisted in any
    other persistent storage suc has file or database.......). The .net 2.0
    ListItemCollection class implement the IStateManager interface, we can call
    this method to let it help us do generate the data which can be
    persisted....

    2. For the ListItemCollection, we can just override our custom control's
    LoadViewState and SaveViewState methods and manually store their state
    value into ViewState collection...... (this is also what asp.net's
    buildin ListControl do in their implementation)

    In addition, we have to call the TraceViewState method(in IStateManager
    interface) when we created the ListItemCollection property's field
    instance.... This make sure that our change on the ListItemCollection
    instance will be persisted....

    here is a test control which demonstrate the above things:

    =====================================
    namespace WebControlLib
    {
    [DefaultProperty("Text")]
    [ToolboxData("<{0}:LinkListControl
    runat=server></{0}:LinkListControl>")]
    [Designer(typeof(LinkListControlDesigner),typeof(IDesigner))]
    public class LinkListControl : WebControl, INamingContainer
    {

    private ListItemCollection _items;

    [Bindable(true)]
    [Category("Appearance")]
    [DefaultValue("")]
    [Localizable(true)]
    public string Text
    {
    get
    {
    String s = (String)ViewState["Text"];
    return ((s == null) ? String.Empty : s);
    }

    set
    {
    ViewState["Text"] = value;
    }
    }


    [Bindable(true)]
    [DefaultValue((string)null)]
    [PersistenceMode(PersistenceMode.InnerProperty)]

    [Editor("System.Web.UI.Design.WebControls.ListItemsCollectionEditor,System.D
    esign, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a",
    typeof(UITypeEditor))]
    [MergableProperty(false)]
    [Category("Data")]
    public ListItemCollection Items
    {
    get
    {
    if (_items == null)
    {
    _items = new ListItemCollection();


    ((IStateManager)_items).TrackViewState();

    }

    return _items;
    }
    }


    protected override void CreateChildControls()
    {
    Controls.Clear();

    LiteralControl lc = new LiteralControl("<table ><tr><td>");
    lc.ID = "lc1";
    Controls.Add(lc);

    if (_items == null || Items.Count == 0)
    {
    Label lbl = new Label();
    lbl.ID = "lblEmpty";
    lbl.Text = "No Link in Collection.";

    Controls.Add(lbl);
    }
    else
    {
    foreach (ListItem item in _items)
    {
    HyperLink link = new HyperLink();
    link.ID = "link" + _items.IndexOf(item);
    link.Text = item.Text;
    link.NavigateUrl = item.Value;

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

    lc = new LiteralControl("</td></tr></table>");
    lc.ID = "lc2";
    Controls.Add(lc);

    }


    protected override void LoadViewState(object savedState)
    {
    Pair pair = (Pair)savedState;


    ((IStateManager)_items).LoadViewState(pair.Second);

    base.LoadViewState(pair.First);
    }

    protected override object SaveViewState()
    {
    Pair pair = new Pair();
    pair.First = base.SaveViewState();
    pair.Second = ((IStateManager)_items).SaveViewState();


    return pair;
    }


    }

    public class LinkListControlDesigner : ControlDesigner
    {
    public override string GetDesignTimeHtml()
    {
    StringBuilder sb = new StringBuilder();

    LinkListControl llc = Component as LinkListControl;

    if (llc.Items == null || llc.Items.Count == 0)
    {
    sb.Append("<font size='20' color='red'>Empty Link
    Collection.</font>");
    }
    else
    {
    sb.Append("<font size='20' color='red'>");


    foreach (ListItem item in llc.Items)
    {
    sb.Append("Text: ");
    sb.Append(item.Text);
    sb.Append(" ");
    sb.Append("Value: ");
    sb.Append(item.Value);
    sb.Append("<br/>");
    }

    sb.Append("</font>");
    }

    return sb.ToString();
    }
    }
    }
    ===================================

    Hope helps. Thanks,

    Steven Cheng
    Microsoft Online Support

    Get Secure! www.microsoft.com/security
    (This posting is provided "AS IS", with no warranties, and confers no
    rights.)






    --------------------
    | Thread-Topic: Persisting ListItemCollection values across postback, using
    ViewSt
    | thread-index: AcYgOxl94SUrizHMTcKNRWRECeel7w==
    | X-WBNR-Posting-Host: 193.172.19.20
    | From: =?Utf-8?B?Q2hyaXN0b3BoZSBQZWlsbGV0?=
    <>
    | Subject: Persisting ListItemCollection values across postback, using
    ViewSt
    | Date: Mon, 23 Jan 2006 08:36:02 -0800
    | Lines: 72
    | Message-ID: <>
    | MIME-Version: 1.0
    | Content-Type: text/plain;
    | charset="Utf-8"
    | Content-Transfer-Encoding: 7bit
    | X-Newsreader: Microsoft CDO for Windows 2000
    | Content-Class: urn:content-classes:message
    | Importance: normal
    | Priority: normal
    | X-MimeOLE: Produced By Microsoft MimeOLE V6.00.3790.0
    | Newsgroups: microsoft.public.dotnet.framework.aspnet.webcontrols
    | NNTP-Posting-Host: TK2MSFTNGXA03.phx.gbl 10.40.2.250
    | Path: TK2MSFTNGXA02.phx.gbl!TK2MSFTNGXA03.phx.gbl
    | Xref: TK2MSFTNGXA02.phx.gbl
    microsoft.public.dotnet.framework.aspnet.webcontrols:32749
    | X-Tomcat-NG: microsoft.public.dotnet.framework.aspnet.webcontrols
    |
    | I have a series of composite controls to replace most common form
    controls
    | (adding Ajax support and a built in validator), and have all of the
    simple
    | controls working (textbox, checkbox, button, etc.), but have an issue
    with
    | Viewstate and Postback when it comes to ListItem based controls
    | (CheckboxList, DropDownList and RadioButtonList).
    |
    | I need to set the Item properties value in Viewstate, but they do not
    seem
    | to persist on postback when I do this (all of the other properties do
    except
    | this one, so it isn't, I don't think, a problem like unique ID, etc.).
    |
    | When I set the collection directly to the underlying child control, it
    works
    | propertly and persists across viewstates (see first example below), but,
    | because of other restrictions in my control, I am unable to do this, and
    NEED
    | to keep this information in Viewstate, and reassign the appropriate value
    to
    | m_chk after a postback.
    |
    | This is what I have at the moment, which maintains data across postback,
    but
    | doesn't work in my case since I need to keep it in Viewstate and manually
    | reassign it to m_chk.
    |
    | /// <summary>
    | /// Gets the CheckBoxList items.
    | /// </summary>
    | /// <value>The CheckBoxList items.</value>
    | [Bindable(true)]
    | [DefaultValue((string)null)]
    | [PersistenceMode(PersistenceMode.InnerProperty)]
    |
    [Editor("System.Web.UI.Design.WebControls.ListItemsCollectionEditor,System.D
    esign,
    | Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a",
    | typeof(UITypeEditor))]
    | [MergableProperty(false)]
    | [Category("CheckBox")]
    | public ListItemCollection Items
    | {
    | get
    | {
    | EnsureChildControls();
    | return m_chk.Items;
    | }
    | }
    |
    | When I try this, it adds everything to ViewState, but the contents are
    | always lost on postback.
    |
    | /// <summary>
    | /// Gets the CheckBoxList items.
    | /// </summary>
    | /// <value>The CheckBoxList items.</value>
    | [Bindable(true)]
    | [DefaultValue((string)null)]
    | [PersistenceMode(PersistenceMode.InnerProperty)]
    |
    [Editor("System.Web.UI.Design.WebControls.ListItemsCollectionEditor,System.D
    esign,
    | Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a",
    | typeof(UITypeEditor))]
    | [MergableProperty(false)]
    | [Category("CheckBox")]
    | public ListItemCollection Items
    | {
    | get
    | {
    | ListItemCollection l =
    (ListItemCollection)Viewstate["CheckboxListItems"];
    | return l;
    | }
    | }
    |
    | How can I persist this information across postbacks, but assigning it to
    | viewstate.
    |
    | Thanks for any help on this. (Someone should real write a good book on
    | custom component development for ASP using real world development
    examples
    | (inheritance, etc.) ... there are surprisingly few helpful resources out
    | there.)
    |
    Steven Cheng[MSFT], Jan 24, 2006
    #2
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Shawn McNiven

    Persisting Information across forms

    Shawn McNiven, Apr 7, 2004, in forum: ASP .Net
    Replies:
    1
    Views:
    389
    Richard Saunders
    Apr 7, 2004
  2. John Hoge

    Persisting form data across page load

    John Hoge, Nov 28, 2004, in forum: ASP .Net
    Replies:
    2
    Views:
    394
    =?Utf-8?B?S3Jpc2g=?=
    Nov 29, 2004
  3. Stu
    Replies:
    3
    Views:
    4,957
  4. Server Control
    Replies:
    4
    Views:
    760
  5. =?Utf-8?B?V2lsbGlhbSBTdWxsaXZhbg==?=

    Large (over 1 meg) website takes long time to post back W/O Viewst

    =?Utf-8?B?V2lsbGlhbSBTdWxsaXZhbg==?=, Oct 23, 2006, in forum: ASP .Net
    Replies:
    1
    Views:
    427
    bruce barker \(sqlwork.com\)
    Oct 23, 2006
Loading...

Share This Page