Failed to load viewstate - user controls

R

Rotsey

Hi,

I have a web site that uses user controls to display different formats of
timesheets.

I have a browse page that has prev/next buttons to browse through a set of
timesheets.

As I say they can be different user controls for each timesheet type.

The problem is when I navigate (prev/next) from one type of user control to
the next type
I get this error

System.Web.HttpException: Failed to load viewstate. The control tree into
which viewstate is being loaded must match the control tree that was used to
save viewstate during the previous request. For example, when adding
controls dynamically, the controls added during a post-back must match the
type and position of the controls added during the initial request.

The thing is strange is that say the first user control is for monthly
timesheets and then I click next to goto
a weekly timesheet (different user control) it is fine. But when i go back
to the first monthly timsheet
again it gives this error.

Help!!
rotsey
 
B

bruce barker

when viewstate is loaded after a postback, it looks for controls with
the same name and type to load.

if you dynamically change the user control you can get this error. you
should keep track of which control you rendered (say a flag in
viewstate) and recreate the control in oninit. then in onload/prerender
if you change the control, delete the old one and add the new one.

-- bruce (sqlwork.com)
 
S

SMiGL

Hi,

I have a web site that uses user controls to display different formats of
timesheets.

I have a browse page that has prev/next buttons to browse through a set of
timesheets.

As I say they can be different user controls for each timesheet type.

The problem is when I navigate (prev/next) from one type of user control to
the next type
I get this error

System.Web.HttpException: Failed to load viewstate. The control tree into
which viewstate is being loaded must match the control tree that was used to
save viewstate during the previous request. For example, when adding
controls dynamically, the controls added during a post-back must match the
type and position of the controls added during the initial request.

The thing is strange is that say the first user control is for monthly
timesheets and then I click next to goto
a weekly timesheet (different user control) it is fine. But when i go back
to the first monthly timsheet
again it gives this error.

Help!!
rotsey

This problem arise when you dynamic create child control and for this
create use some variable. After postback this variable has old value
that give at Initialize method. To fix this problem need recover this
varible, for this use SaveControlState, LoadControlState.

Example
public class UniversalFilterControl1 : WebControl
{

protected override void OnInit(EventArgs e)
{
base.OnInit(e);
Page.RegisterRequiresControlState(this);
}

protected override void LoadControlState(object savedState)
{
object[] list = savedState as object[];
base.LoadControlState(list[0]);
if (list[1] != null)
<some varible> = list[1];
}

protected override object SaveControlState()
{
object[] list = new object[2];
list[0] = base.SaveControlState();
list[1] = <some varible>;
}
}
 
R

Rotsey

This was working fine before I made some styling changes to the page.

Can you please take a look at this code and offer suggestins how to alter
it???

I added a OnInit and got a stackoverflow exception.

Private Sub Page_Load(ByVal sender As System.Object, ByVal e As
System.EventArgs) Handles MyBase.Load

'Put user code to initialize the page here

If Not Me.Request.Params("Browse") Is Nothing Then

lstType = CInt(Me.Request.Params("Browse"))

Else

lstType = EnumListType.TimesheetAwaiting

Session("EmployeeID") = 1

End If

If Not IsPostBack Then

GetDocumentList()

Session("DocIndex") = 0

End If

BuildPage()

LoadDocument()

If Not IsPostBack Then

'GetDocumentList()

'Session("DocIndex") = 0

End If

End Sub

Public Sub BuildPage()

Dim tbl As New Table

Dim r As New TableRow

Dim c As TableCell

tbl.Width = Unit.Pixel(660)

tbl.Rows.Add(r)

c = New TableCell

If InStr(GetTypeDescription(lstType), "Awaiting Authorisation") Then

c.Controls.Add(New LiteralControl("<H4>" + GetTypeDescription(lstType) + "
(" + CType(Session("DocCount"), String) + ")</H4>"))

Else

c.Controls.Add(New LiteralControl("<H3>" + GetTypeDescription(lstType) + "
(" + CType(Session("DocCount"), String) + ")</H3>"))

End If

c.ColumnSpan = "2"

r.Cells.Add(c)

c = New TableCell

c.HorizontalAlign = HorizontalAlign.Right

Dim lnk As New HyperLink

lnk.Text = "&lt;Printable Version&gt;"

lnk.NavigateUrl = "#"

'lnk.ForeColor = Color.Blue

lnk.Attributes("onclick") = "new_window('" &
Page.ResolveUrl("~/frmPrintDocument.aspx") & "');"

c.Controls.Add(lnk)

c.Controls.Add(New LiteralControl("&nbsp;&nbsp;&nbsp;"))

c.Controls.Add(NewHyperLink("frmUserHome.aspx", "&lt;Back to Home&gt;", ""))

r.Cells.Add(c)

ContentArea.Controls.Add(New LiteralControl("<br><center>"))

ContentArea.Controls.Add(tbl)

ContentArea.Controls.Add(New LiteralControl("</center><br>"))

tbl = New Table

tbl.Width = Unit.Pixel(660)

r = New TableRow

tbl.Rows.Add(r)

btnPrev = New LinkButton

btnPrev.Text = "&lt;Previous " & GetDocumentDescription(lstType) & "&gt;"

btnPrev.ID = "btnPrev"

AddHandler btnPrev.Click, AddressOf ButtonClick

c = New TableCell

c.HorizontalAlign = HorizontalAlign.Left

c.Controls.Add(btnPrev)

c.Width = Unit.Pixel(280)

r.Cells.Add(c)

btnNext = New LinkButton

btnNext.Text = "&lt;Next " & GetDocumentDescription(lstType) & "&gt;"

btnNext.ID = "btnNext"

AddHandler btnNext.Click, AddressOf ButtonClick

c = New TableCell

c.HorizontalAlign = HorizontalAlign.Center

'_pageIndex.ForeColor = Color.DarkBlue

c.Width = Unit.Pixel(100)

c.Controls.Add(_pageIndex)

r.Cells.Add(c)

c = New TableCell

c.HorizontalAlign = HorizontalAlign.Right

c.Controls.Add(btnNext)

c.Width = Unit.Pixel(280)

r.Cells.Add(c)

Dim objTBR As New TBRDocuments(lstType, Session("EmployeeID"),
Session("UserID"))

ContentArea.Controls.Add(New LiteralControl("<br><center>"))

ContentArea.Controls.Add(tbl)

ContentArea.Controls.Add(New LiteralControl("</center><br>"))

End Sub

Public Sub GetDocumentList()

Dim objTBR As New TBRDocuments(lstType, Session("EmployeeID"),
Session("UserID"))

Session("Documents") = objTBR

Session("DocCount") = objTBR.Count

End Sub

Public Sub LoadDocument()

Dim doc As TBRDocuments

doc = CType(Session("Documents"), TBRDocuments)

If Session("DocCount") > 0 Then

_pageIndex.Text = "(" & (Session("DocIndex") + 1).ToString & " of " &
Session("DocCount") & ")"

End If

If doc.Count > 0 Then

CallControl(doc.Documents(Session("DocIndex")))

Else

btnPrev.Visible = False

btnNext.Visible = False

End If

End Sub

Public Sub CallControl(ByVal doc As Document)

Select Case doc.DocumentType

Case enumDocType.Invoice

ctlDoc = Page.LoadControl(Page.ResolveUrl("~/Secure/ctlinvoice.ascx"))

ctlDoc.id = "ctlInvoice"

Case enumDocType.TimesheetMonthly

ctlDoc =
Page.LoadControl(Page.ResolveUrl("~/Secure/ctlTimesheetMonthly.ascx"))

ctlDoc.id = "ctlTimesheetMonthly"

Case enumDocType.TimesheetWeekly

ctlDoc =
Page.LoadControl(Page.ResolveUrl("~/Secure/ctlTimesheetWeekly.ascx"))

ctlDoc.id = "ctlTimesheetWeekly"

End Select

viewstate("docType") = doc.DocumentType

Session("PrintDoc") = doc 'So it can be printed

ctlDoc.CtlDocument = doc

ctlDoc.LoadTimesheet = True

ctlDoc.ListType = lstType

ContentArea.Controls.Add(New LiteralControl("<center>"))

ContentArea.Controls.Add(ctlDoc)

ContentArea.Controls.Add(New LiteralControl("</center>"))

SetNavControls(Session("DocIndex"), Session("DocCount"))

End Sub

Public Sub ButtonClick(ByVal sender As System.Object, ByVal e As
System.EventArgs)

Select Case sender.id

Case "btnPrev"

If Session("DocIndex") > 0 Then

Session("DocIndex") -= 1

RemoveControl(ContentArea.Controls, ctlDoc.id)

LoadDocument()

End If

Case "btnNext"

If Session("DocIndex") + 1 < Session("DocCount") Then

Session("DocIndex") += 1

RemoveControl(ContentArea.Controls, ctlDoc.id)

LoadDocument()

End If

End Select

End Sub

Public Sub SetNavControls(ByVal idx As Integer, ByVal max As Integer)

If max < 2 Then

btnPrev.Visible = False

btnNext.Visible = False

ElseIf idx = 0 Then

btnPrev.Visible = False

btnNext.Visible = True

ElseIf idx < max - 1 Then

btnPrev.Visible = True

btnNext.Visible = True

Else

btnPrev.Visible = True

btnNext.Visible = False

End If

End Sub
 

Ask a Question

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

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,968
Messages
2,570,154
Members
46,702
Latest member
LukasConde

Latest Threads

Top