Checkbox state persisting thru postback when it shouldn't

As covered at question

I have the following code that generates a table and a grid of checkboxes at runtime. The code correctly initializes checkbox on the 1st pass but persits changes after postback. Since it's generating everything at runtime and i haven't yet implemented 'save to db' code the post back should re-initialize everything back to original state. Here's th code....note that I've explicitly turned off viewstate for both the table and the checkboxes. The function's called at each Page_Load.

    Function CreateCheckBoxGrid()
        Dim GetTimePeriods = "select distinct datename(m,dateDue) + '-' + datename(day,dateDue) + '-' + datename(year,dateDue) , dateDue from RequiredModules order by dateDue"
        Dim myConnection As New SqlConnection(connStr)

        Dim myCommand As SqlCommand = New SqlCommand(GetTimePeriods, myConnection)

        Dim reader As SqlDataReader = myCommand.ExecuteReader()

        If reader.HasRows Then
            Do While reader.Read()
                lbGetDateDue.Items.Add(New ListItem(reader.GetString(0).ToString, reader.GetDateTime(1).ToString))
            Console.WriteLine("No rows returned.")
        End If

        Dim ds As New DataSet

        Dim GetTitles = "select distinct strTitle, idTitle from FacilityTitles where FacilityID = 10159 order by strTitle;"
        GetTitles = GetTitles & "select ModuleName, moduleID from modules where moduleID > 0 order by ModuleID; "
        GetTitles = GetTitles & "select moduleID, idTitle, ReqModID from RequiredModules where dateDue = '" & lbGetDateDue.SelectedValue & "'  order by Moduleid "

        ds = SqlHelper.ExecuteDataset(connStr, CommandType.Text, GetTitles)

        ds.Tables(0).TableName = "Titles"
        ds.Tables(1).TableName = "Modules"
        ds.Tables(2).TableName = "FKey"

        'build table
        Dim tb As New HtmlTable
        tb.EnableViewState = False
        tb.CellSpacing = 1
        tb.Border = 1

        Dim tbr As New HtmlTableRow
        Dim tbc As New HtmlTableCell

        ' empty cell in the corner

        'build first row as
        Dim myCurModuleID As Integer
        For Each myModule As DataRow In ds.Tables("Modules").Rows
            tbc = New HtmlTableCell
            Dim lbl As New Label
            lbl.Text = myModule(0)

        tb.Rows.Add(tbr) ' Add the row to table

        Dim intRow As Integer = 0
        For Each myTitle As DataRow In ds.Tables("Titles").Rows

            Dim myCurTitleID = myTitle(1)
            tbr = New HtmlTableRow
            tbc = New HtmlTableCell
            Dim lbl As New Label
            lbl.Text = myTitle(0)
            tbr.Cells.Add(tbc)   ' Add Title A - Z to first cell of each row

            Dim i As Integer
            For i = 0 To ds.Tables("Modules").Rows.Count - 1
                myCurModuleID = ds.Tables("Modules").Rows(i).Item(1)
                ' each iteration adds row
                ' with an unchecked checkbox
                tbc = New HtmlTableCell
                Dim cb = New CheckBox
                cb.Checked = False
                cb.EnableViewState = False

                'iterate thru all records in FKeys table
                'to identify which rows have a idTitle field
                'that matches the current idTitle (myTitle(1))
                Dim blnChecked As Boolean = False
                For Each keyMapRow As DataRow In ds.Tables("FKey").Rows
                    If keyMapRow(1) = myCurTitleID And keyMapRow(0) = myCurModuleID Then
                        blnChecked = True
                        Exit For
                    End If

                cb.Checked = blnChecked

            ' add this row to table


    End Function
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

To persist the viewstate of dynamic webcontrols across the postback you need to create the control in onInit() procedure.

Please checkout which explains how to maintain the viewstate across postback.

juststeveAuthor Commented:
I'm not trying to maintain state...i've disabled it in the above code in an attempt to make sure the controls are properly initialized.
Could you, temporarily, disable the checkboxes using myCheckBox.Enabled?

Your problem is that you need ViewState in order to keep the original checked/nonchecked state of the checkboxes (as they are not defined in the aspx markup). So you either need to reset the user's changes (rebuild the table each time), or better still - prevent the user being able to make any changes.

Does that work? Or did I misinterpret the question ?

Introducing Cloud Class® training courses

Tech changes fast. You can learn faster. That’s why we’re bringing professional training courses to Experts Exchange. With a subscription, you can access all the Cloud Class® courses to expand your education, prep for certifications, and get top-notch instructions.

By the way, you said "The function's called at each Page_Load". Are you only calling it for the first call, or on every postback (using IsPostBack)?
juststeveAuthor Commented:

It should be more clear now...the checked/unchecked state should change depending on which quarter is select in the dropdown box. The fact that no changes occur (and I'm registering hits to the db so I know the query is re-running) is strange but not as strange as the fact that unchecking a box that's currently checked and re-posting the page (fired off a dropdown state change) will leave that box _unchecked. Even tho as each checkbox is explicitly set to unchecked when it's instantiated. I've put a breakpoint on that line .... it fire both at initial page load and after postback.

This is probably an important clue...

Originally I had the dropdown list box construction inside the same function as is generating the checkbox table.  So it would re-generate each time the page posted back. I noticed that entries would accumulate - on the first postback there would be a duplicate set of quarters in the dropdown list...after another postback there were 2 duplicate sets - 12 lines instead of 4. i've since move it to a separate function that only fires if NotPostBack and things work correctly.

The dropdown is defined as:
<asp:dropdownlist id="lbGetDateDue" runat="server" AutoPostBack="true" Height="12"></asp:dropdownlist>

Refreshing the page will correctly re-initialize any unchecked boxes....the problem only exhibits on a postback and at this point, changing the dropdown is the only way to fire postback.

I'm still not to the point of working on saving user changes but that's the next task so, yes, users should be able to change values.
This is tough. I think you have the right event handler bound to the DropDownList's SelectedIndexChanged event because you say that the breakpoint in CreateCheckBoxGrid fires on postback. Have you stepped through the entire method with a watch on the table being created? Does it complete, or does it throw any errors? I'm (again) guessing it completes.

Its possible that you need to first clear the table, or even delete it, from the control hierarchy. Could you do me a favour and post:
-your aspx file
-remind me what your .NET version (1.1/2.0?) and development program (Visual Studio 2003/2005?) is.

I think you might want to try declaring the table in the aspx, if it isn't already there, as a server-side control. Then at the top of CreateCheckBoxGrid method, remove all the rows and columns before refilling it. ALternatively, when you create the table, set it's id:

    Dim tb As New HtmlTable
    tb.EnableViewState = False
    tb.CellSpacing = 1
    tb.Border = 1
    tb.Id = "checkTable1"

and then when you start each time on the postback, try:
If Me.FindControls("checkTable1") != nothing Then
End If

That last one is a long shot, could you post your aspx and confirm that CreateCheckBoxGrid completes without any errors? I think it probably does as
Ultimately, I think you want to map your decision tree out:
 PageFirstFires (Not IsPostBack):
   -Grid fills
   -Some action

This would suggest that:
-You should call CreateCheckBoxGrid, with the Ddl fill from Page_Load when "Not IsPostBack"
-You should also call CreateCheckBoxGrid from the Ddl.SelectedIndexChanged even handler

This will set you up for your user changes submissions.

Then see if you can delete (if not declaring the table in the aspx)/clear (if declaring in aspx) the table at the top of every CreateCheckBoxGrid method (only if it already exists for the delete).


Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
enabling/disabling viewstate does not affect controls like textbox,checkbox etc .. it always maintains the state .. u will explicity have to uncheck the checkbox ..

It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today

From novice to tech pro — start learning today.

Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.