Reputation: 92
I have created many dynamic controls. I would now like to find those controls and review their contents on postback before proceeding with the database write.
Controls created as follows:
For i As Integer = 0 To numberOfSplitItems
Dim combo As New RadComboBox()
combo.ID = "MonthSpliCombo" & i
'Items then added to the combobox
monthDIV.Controls.Add(combo)
splitdiv.Controls.Add(MonthDIV)
PanelActualSplit.Controls.Add(splitdiv)
Next
This is working 100% and my controls are all added where they should be and are working. I can find all these controls in javascript no problem.
Protected Sub processSplitMonthsBTN_Click(sender As Object, e As EventArgs)
For i As Integer = 1 to numberOfSplitItems
Dim monthBox As New RadComboBox
Try
monthBox = DirectCast(PanelActualSplit.FindControl("MonthSpliCombo" & i), RadComboBox)
MsgBox(monthBox.ClientID)
Catch ex As Exception
MsgBox(ex.ToString)
End Try
Next
End Sub
Error it keeps showing: System.NullReferenceException: Object not set to an instance of an object.
I have adjusted as follows to try determine my error: taken out 'DirectCast' tried to use TryCast Dim monthBox as RadComboBox - leave out the 'As New'
I have tried multiple controls, but I cannot seem to get the control saved into the monthBox control so that I can start my validation.
Please could you assist.
Upvotes: 0
Views: 345
Reputation: 141
The answer is quite simple.
Upon each postback the controls are refreshed, thus losing the controls that were dynamically created on the last postback. Viewstate of the controls needs to be remembered and thus "recreated" on the next postback.
Move your procedure which created the controls into it's own sub and add the following overrides to your code.
Protected Overrides Function SaveViewState() As Object
Dim viewState = New Object(1) {}
viewState(0) = Integer.Parse(numberOfSplitItems)
viewState(1) = MyBase.SaveViewState()
Return viewState
End Function
Protected Overrides Sub LoadViewState(savedState As Object)
If TypeOf savedState Is Object() AndAlso DirectCast(savedState, Object()).Length = 2 Then
Dim viewState = DirectCast(savedState, Object())
Dim count = Integer.Parse(viewState(0).ToString())
yourAddcontrolsProceduresHere(count)
MyBase.LoadViewState(viewState(1))
Else
MyBase.LoadViewState(savedState)
End If
End Sub
That will solve the issue and reload the controls on your postback thus allowing the server to access find them and you will no longer have the Null reference exception.
Upvotes: 1
Reputation: 2862
Instead of PanelActualSplit.FindControl
you should use a function similar to this:
public static Control FindControlRecursive(Control ctl, string id) {
if (!ctl.HasControls())
return null;
Control res = null;
foreach(Control c in ctl.Controls) {
if (c.ID == id) {
res = c;
break;
} else {
res = FindControlRecursive(c, id);
if (res != null)
break;
}
}
return res;
}
in this way:
RadComboBox monthBox = (Table)FindControlRecursive(PanelActualSplit, "MonthSpliCombo" & i);
And you will find your control for sure.
Upvotes: 0