alkampfer on December 4th, 2007

It is a while that I do not write in my English blog, today I want to continue a issue discussed in an old post. Consider this code

<body>
    <form id=”form1″ runat=”server” oninit=”Page_Init”>
        <div>
            <asp:DropDownList ID=”ddlist1″ EnableViewState=”false” AutoPostBack=”true” AppendDataBoundItems=”true”
                runat=”server” OnSelectedIndexChanged=”SelectedIndexChanged”>
                <asp:ListItem>Select a team</asp:ListItem>
            </asp:DropDownList>
            
            <asp:DropDownList ID=”ddlist2″ EnableViewState=”false” AutoPostBack=”true” AppendDataBoundItems=”true”
                runat=”server” OnSelectedIndexChanged=”SelectedIndexChanged”>
                <asp:ListItem>Select a team</asp:ListItem>
            </asp:DropDownList>
        </div>
    </form>
</
body>
</
html>

<
script runat=”server”>

    protected void Page_Init(object sender, EventArgs e) {
         ddlist1.DataSource = new string[] { “Ferrari”, “McLaren”, “Renault” };
         ddlist2.DataSource = new string[] { “Ferrari”, “McLaren”, “Renault” };
       DataBind();
    }
    protected void SelectedIndexChanged(object sender, EventArgs e) {
        DropDownList ddl = (DropDownList) sender;
        Response.Write(String.Format(“SelectedIndexChanged {0} value = {1}<BR/>”,
                                     ddl.ID, ddl.SelectedValue));
    } 
</script>
This code contains two simple DropDownList, both with ViewState disabled, the datasource is rebound at each PageInit and in SelectedIndexChanged we simple write a string in response output. You can be surprised that if you change the first dropdown all was good, but when you change the second one you find that the output contains string like this

SelectedIndexChanged ddlist1 value = McLaren
SelectedIndexChanged ddlist2 value = Ferrari

This means that the SelectedIndexChanged of the first DropDownList fired even if we do not change it. This is due to the ViewState, the DropDownList control store in viewstate his current selected value, so at LoadPostData() he can find if the selected item is really changed, but if you have no viewstate the control assumes that previous selectedvalue is 0, so it fire the event at each postback. To solve this problem change the code in this way

<script runat=”server”>

    protected void Page_Init(object sender, EventArgs e) {
         ddlist1.DataSource = new string[] { “Ferrari”, “McLaren”, “Renault” };
         ddlist2.DataSource = new string[] { “Ferrari”, “McLaren”, “Renault” };
       DataBind();
    }
    protected void SelectedIndexChanged(object sender, EventArgs e) {
        DropDownList ddl = (DropDownList) sender;
        if ((String) ViewState[ddl.ID] != ddl.SelectedValue) {
                Response.Write(String.Format(“SelectedIndexChanged {0} value = {1}<BR/>”,
                                     ddl.ID, ddl.SelectedValue));
        }
    }

    protected void Page_PreRender(object sender, EventArgs e) {
        ViewState["ddlist1"] = ddlist1.SelectedValue;
        ViewState["ddlist2"] = ddlist2.SelectedValue;
    }
    
</script>
Now we store in viewstate the selection of each dropdown list, so we can use in SelectedIndexChanged to verify that the selection is really changed.

Alk.

 

kick it on DotNetKicks.com

One Response to “DropDownList And ViewState = false”

  1. Great idea! I was struggling with this issue, and am surprised I didn’t think of this myself :)