Finding Controls in a Table

J

JDavies

Hi All

I am dynamically Creating DropDownList boxes for a Survey form. These
DropdownLists are added to Table Cells programatically.

I tried to loop thru the controls on the form but it doesnt seem to work
right, the loop appears below:

for each cntl in page.controls(1).controls
ddlId = cntl.Id
debug.write(ddlID)

next


nothing Fancy i am just trying to find the controls and then later on get
the value from the selection.

However, i can find the Table they are on but i never see the control it
self?????

How do i get the DropdownList when it is in a Table cell?

Any help is greatly Appreciated

TIA
Samantha
 
M

Mike Moore [MSFT]

Hi Samantha,

Dynamically added controls are tricky. The first time they're usually added
in the grid's ItemDataBound event. Further, DataBind is usually called in
Page_Load with If not IsPostBack.

So, the first visit to the page triggers DataBind which includes
dynamically adding the controls.

Next, we post back the form. The datagrid is defined in the HTML page. So,
it is automatically recreated and repopulated with the viewstate data.
However, your dynamically added controls are not defined in the HTML. So,
they are not recreated. They're gone.

The solution is that you need to recreate them in the Page_Load event,
including populating them with data. After the load event, ASP.NET will use
the posted data to set these controls to the state that the user gave them.

If you try my code below and remove the call to "Bind" in the button click
event, you will see that the various drop lists maintain whatever you
select. Try it. It's when you call Bind, which recreates all these
controls, that they loose they're state.

To get access to the values entered by the user, access the grid before
calling Bind. I've included that in my button click event below.

This sample is based on the Pubs database. Only the first, or top most,
drop list is set to be monitored when you click the button.

Here's my HTML

<form id="Form1" method="post" runat="server">
<asp:button id="Button1" runat="server" Text="Button"></asp:button><BR>
<BR>
<asp:datagrid id="DataGrid1" runat="server" AutoGenerateColumns="False"
ShowHeader="False">
<Columns>
<asp:BoundColumn DataField="au_id"
HeaderText="au_id"></asp:BoundColumn>
<asp:BoundColumn DataField="au_fname"
HeaderText="au_fname"></asp:BoundColumn>
<asp:BoundColumn DataField="au_lname"
HeaderText="au_lname"></asp:BoundColumn>
<asp:TemplateColumn></asp:TemplateColumn>
</Columns>
</asp:datagrid>
</form>


Here is my code.

Private Sub Page_Load(ByVal sender As System.Object, ByVal e As
System.EventArgs) Handles MyBase.Load
If Not IsPostBack Then
Bind()
Else
Dim i
For i = 0 To DataGrid1.Items.Count - 1
Dim d As New WebControls.DropDownList
d.Items.Add(DataGrid1.Items(i).Cells(0).Text)
d.Items.Add(DataGrid1.Items(i).Cells(1).Text)
d.Items.Add(DataGrid1.Items(i).Cells(2).Text)
DataGrid1.Items(i).Cells(3).Controls.Add(d)
Next
End If
End Sub

Private Sub Bind()
Dim Qry1 As System.Data.SqlClient.SqlDataReader
Dim connectionString As String = "server='localhost';
trusted_connection=true; Database='pubs'"
Dim sqlConnection As System.Data.SqlClient.SqlConnection = New
System.Data.SqlClient.SqlConnection(connectionString)
Dim queryString As String = "SELECT au_id, au_lname, au_fname FROM
authors"
Dim sqlCommand As System.Data.SqlClient.SqlCommand = New
System.Data.SqlClient.SqlCommand(queryString, sqlConnection)
sqlConnection.Open()
Qry1 =
sqlCommand.ExecuteReader(System.Data.CommandBehavior.CloseConnection)
DataGrid1.DataSource = Qry1
DataGrid1.DataBind()
Qry1.Close()
sqlCommand.Dispose()
sqlConnection.Close()
sqlConnection.Dispose()
End Sub

Private Sub DataGrid1_ItemDataBound(ByVal sender As Object, ByVal e As
System.Web.UI.WebControls.DataGridItemEventArgs) Handles
DataGrid1.ItemDataBound
If e.Item.ItemType = ListItemType.Item Or e.Item.ItemType =
ListItemType.AlternatingItem Then
Dim d As New WebControls.DropDownList
d.Items.Add(e.Item.Cells(0).Text)
d.Items.Add(e.Item.Cells(1).Text)
d.Items.Add(e.Item.Cells(2).Text)
e.Item.Cells(3).Controls.Add(d)
End If
End Sub

Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As
System.EventArgs) Handles Button1.Click
Response.Write(CType(DataGrid1.Items(0).Cells(3).Controls(0),
DropDownList).SelectedValue)
Bind()
End Sub


Thank you, Mike
Microsoft, ASP.NET Support Professional

Microsoft highly recommends to all of our customers that they visit the
http://www.microsoft.com/protect site and perform the three straightforward
steps listed to improve your computer’s security.

This posting is provided "AS IS", with no warranties, and confers no rights.


--------------------
 
J

JDavies

Mike

thanks for your very concise response, and offering me an alternative to my
form.

What i have done is programmatically is added a table using the codebehind
of a user control.

I Query a Database to get the questionairre questions, then have to mix in
the type of DropDownList box that the question deserves, either a Yes No, or
a Multiple Choice answer.

I do not need to maintain state as i will insert and Response.Redirect to
another page like a review page.

What i cant see to do is find these DropDownLists, each with their own
unique id, tucked away in a table Cell, in a Table called CHF_Table1


I need to be able to iterate thru the table to capture the resposnses to
send to a database.

I Tried Page.Controls(1).Controls and can only find the table id and nothing
else.

Any Help with cycling thru the Table Cells to find the DropDownLists would
be greatly appreciated

But once again thanks for your excellent response

TIA
Samantha


"Mike Moore [MSFT]" said:
Hi Samantha,

Dynamically added controls are tricky. The first time they're usually added
in the grid's ItemDataBound event. Further, DataBind is usually called in
Page_Load with If not IsPostBack.

So, the first visit to the page triggers DataBind which includes
dynamically adding the controls.

Next, we post back the form. The datagrid is defined in the HTML page. So,
it is automatically recreated and repopulated with the viewstate data.
However, your dynamically added controls are not defined in the HTML. So,
they are not recreated. They're gone.

The solution is that you need to recreate them in the Page_Load event,
including populating them with data. After the load event, ASP.NET will use
the posted data to set these controls to the state that the user gave them.

If you try my code below and remove the call to "Bind" in the button click
event, you will see that the various drop lists maintain whatever you
select. Try it. It's when you call Bind, which recreates all these
controls, that they loose they're state.

To get access to the values entered by the user, access the grid before
calling Bind. I've included that in my button click event below.

This sample is based on the Pubs database. Only the first, or top most,
drop list is set to be monitored when you click the button.

Here's my HTML

<form id="Form1" method="post" runat="server">
<asp:button id="Button1" runat="server"
 
M

Mike Moore [MSFT]

Hi Samantha,

1) The typical method
If you add a break point to your code-behind and use the watch window to
evaluate datagrid1.items(0).cells(3).controls, you will find that this
controls collection has a count of zero, even though it previously had a
drop list in it. At this point, the drop list no longer exists and it is of
no use to cycle through the cells and controls.

To get the values, you need to re-add the controls as my sample
demonstrated.

2) What may work better for you
In the HTML for your page, in the @ Page line, add trace="true". Then
browse your page, make some selections, and submit the page (turn off an
redirects or transfers so that the page redisplays).

Look in the "form collection" and you will see all your controls along with
the selected values. Rather than recreate the form, we will get the values
from the form collection. One problem though, look at the really odd
control names we need to use to extract these values.

Here's a code sample that you may like. It stores the control names in a
hidden field and then uses these values in the hidden field to extract the
values. I chose not to hard code the control names because these names
change so easily. Unfortunately, the control number can also change if you
make changes to the cell.

Notice that I've added a runat=server hidden field to my grid.
Also notice that my drop list is now controls(3) instead of 0. You may have
to experiment to see what control number your controls are. Break mode is
good for this. Type "DataGrid1.Items(i).Cells(3).Controls(1)" in the watch
window to see what type of control "(1)" is.

Here's my HTML

<form id="Form1" method="post" runat="server">
<asp:button id="Button1" runat="server" Text="Button"></asp:button><BR>
<BR>
<asp:datagrid id="DataGrid1" runat="server" ShowHeader="False"
AutoGenerateColumns="False">
<Columns>
<asp:BoundColumn DataField="au_id"
HeaderText="au_id"></asp:BoundColumn>
<asp:BoundColumn DataField="au_fname"
HeaderText="au_fname"></asp:BoundColumn>
<asp:BoundColumn DataField="au_lname"
HeaderText="au_lname"></asp:BoundColumn>
<asp:TemplateColumn>
<ItemTemplate>
<INPUT id=h name=h type="hidden" runat=server>
</ItemTemplate>
</asp:TemplateColumn>
</Columns>
</asp:datagrid>
</form>

Here's my code

Private Sub Page_Load(ByVal sender As System.Object, ByVal e As
System.EventArgs) Handles MyBase.Load
If Not IsPostBack Then
Bind()
Else
Dim i
For i = 0 To DataGrid1.Items.Count - 1
Dim s As String
s = CType(DataGrid1.Items(i).Cells(3).Controls(1),
HtmlControls.HtmlInputHidden).Value
s = Request.Form(s)
Response.Write(s & "<br>")
Next
End If
End Sub

Private Sub Bind()
Dim Qry1 As System.Data.SqlClient.SqlDataReader
Dim connectionString As String = "server='localhost';
trusted_connection=true; Database='pubs'"
Dim sqlConnection As System.Data.SqlClient.SqlConnection = New
System.Data.SqlClient.SqlConnection(connectionString)
Dim queryString As String = "SELECT au_id, au_lname, au_fname FROM
authors"
Dim sqlCommand As System.Data.SqlClient.SqlCommand = New
System.Data.SqlClient.SqlCommand(queryString, sqlConnection)
sqlConnection.Open()
Qry1 =
sqlCommand.ExecuteReader(System.Data.CommandBehavior.CloseConnection)
DataGrid1.DataSource = Qry1
DataGrid1.DataBind()
Qry1.Close()
sqlCommand.Dispose()
sqlConnection.Close()
sqlConnection.Dispose()
End Sub

Private Sub DataGrid1_ItemDataBound(ByVal sender As Object, ByVal e As
System.Web.UI.WebControls.DataGridItemEventArgs) Handles
DataGrid1.ItemDataBound
If e.Item.ItemType = ListItemType.Item Or e.Item.ItemType =
ListItemType.AlternatingItem Then
Dim d As New WebControls.DropDownList
d.Items.Add(e.Item.Cells(0).Text)
d.Items.Add(e.Item.Cells(1).Text)
d.Items.Add(e.Item.Cells(2).Text)
e.Item.Cells(3).Controls.Add(d)
CType(e.Item.Cells(3).Controls(1),
HtmlControls.HtmlInputHidden).Value = e.Item.Cells(3).Controls(3).UniqueID()
End If
End Sub

Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As
System.EventArgs) Handles Button1.Click
Bind()
End Sub


Thank you, Mike
Microsoft, ASP.NET Support Professional

Microsoft highly recommends to all of our customers that they visit the
http://www.microsoft.com/protect site and perform the three straightforward
steps listed to improve your computer’s security.

This posting is provided "AS IS", with no warranties, and confers no rights.


--------------------
From: "JDavies" <[email protected]>
References: <[email protected]>
Subject: Re: Finding Controls in a Table
Date: Tue, 11 Nov 2003 18:32:45 -0500
Lines: 213
X-Priority: 3
X-MSMail-Priority: Normal
X-Newsreader: Microsoft Outlook Express 6.00.2800.1158
X-MimeOLE: Produced By Microsoft MimeOLE V6.00.2800.1165
Message-ID: <[email protected]>
Newsgroups: microsoft.public.dotnet.framework.aspnet.webcontrols
NNTP-Posting-Host: 249.113.26.24.cfl.rr.com 24.26.113.249
Path: cpmsftngxa06.phx.gbl!cpmsftngxa10.phx.gbl!TK2MSFTNGXA05.phx.gbl!TK2MSFTNGP08
.phx.gbl!tk2msftngp13.phx.gbl
Xref: cpmsftngxa06.phx.gbl microsoft.public.dotnet.framework.aspnet.webcontrols:16087
X-Tomcat-NG: microsoft.public.dotnet.framework.aspnet.webcontrols

Mike

thanks for your very concise response, and offering me an alternative to my
form.

What i have done is programmatically is added a table using the codebehind
of a user control.

I Query a Database to get the questionairre questions, then have to mix in
the type of DropDownList box that the question deserves, either a Yes No, or
a Multiple Choice answer.

I do not need to maintain state as i will insert and Response.Redirect to
another page like a review page.

What i cant see to do is find these DropDownLists, each with their own
unique id, tucked away in a table Cell, in a Table called CHF_Table1


I need to be able to iterate thru the table to capture the resposnses to
send to a database.

I Tried Page.Controls(1).Controls and can only find the table id and nothing
else.

Any Help with cycling thru the Table Cells to find the DropDownLists would
be greatly appreciated

But once again thanks for your excellent response

TIA
Samantha


"Mike Moore [MSFT]" said:
Hi Samantha,

Dynamically added controls are tricky. The first time they're usually added
in the grid's ItemDataBound event. Further, DataBind is usually called in
Page_Load with If not IsPostBack.

So, the first visit to the page triggers DataBind which includes
dynamically adding the controls.

Next, we post back the form. The datagrid is defined in the HTML page. So,
it is automatically recreated and repopulated with the viewstate data.
However, your dynamically added controls are not defined in the HTML. So,
they are not recreated. They're gone.

The solution is that you need to recreate them in the Page_Load event,
including populating them with data. After the load event, ASP.NET will use
the posted data to set these controls to the state that the user gave them.

If you try my code below and remove the call to "Bind" in the button click
event, you will see that the various drop lists maintain whatever you
select. Try it. It's when you call Bind, which recreates all these
controls, that they loose they're state.

To get access to the values entered by the user, access the grid before
calling Bind. I've included that in my button click event below.

This sample is based on the Pubs database. Only the first, or top most,
drop list is set to be monitored when you click the button.

Here's my HTML

<form id="Form1" method="post" runat="server">
<asp:button id="Button1" runat="server"
Text="Button"> said:
<BR>
<asp:datagrid id="DataGrid1" runat="server" AutoGenerateColumns="False"
ShowHeader="False">
<Columns>
<asp:BoundColumn DataField="au_id"
HeaderText="au_id"></asp:BoundColumn>
<asp:BoundColumn DataField="au_fname"
HeaderText="au_fname"></asp:BoundColumn>
<asp:BoundColumn DataField="au_lname"
HeaderText="au_lname"></asp:BoundColumn>
<asp:TemplateColumn></asp:TemplateColumn>
</Columns>
</asp:datagrid>
</form>


Here is my code.

Private Sub Page_Load(ByVal sender As System.Object, ByVal e As
System.EventArgs) Handles MyBase.Load
If Not IsPostBack Then
Bind()
Else
Dim i
For i = 0 To DataGrid1.Items.Count - 1
Dim d As New WebControls.DropDownList
d.Items.Add(DataGrid1.Items(i).Cells(0).Text)
d.Items.Add(DataGrid1.Items(i).Cells(1).Text)
d.Items.Add(DataGrid1.Items(i).Cells(2).Text)
DataGrid1.Items(i).Cells(3).Controls.Add(d)
Next
End If
End Sub

Private Sub Bind()
Dim Qry1 As System.Data.SqlClient.SqlDataReader
Dim connectionString As String = "server='localhost';
trusted_connection=true; Database='pubs'"
Dim sqlConnection As System.Data.SqlClient.SqlConnection = New
System.Data.SqlClient.SqlConnection(connectionString)
Dim queryString As String = "SELECT au_id, au_lname, au_fname FROM
authors"
Dim sqlCommand As System.Data.SqlClient.SqlCommand = New
System.Data.SqlClient.SqlCommand(queryString, sqlConnection)
sqlConnection.Open()
Qry1 =
sqlCommand.ExecuteReader(System.Data.CommandBehavior.CloseConnection)
DataGrid1.DataSource = Qry1
DataGrid1.DataBind()
Qry1.Close()
sqlCommand.Dispose()
sqlConnection.Close()
sqlConnection.Dispose()
End Sub

Private Sub DataGrid1_ItemDataBound(ByVal sender As Object, ByVal e As
System.Web.UI.WebControls.DataGridItemEventArgs) Handles
DataGrid1.ItemDataBound
If e.Item.ItemType = ListItemType.Item Or e.Item.ItemType =
ListItemType.AlternatingItem Then
Dim d As New WebControls.DropDownList
d.Items.Add(e.Item.Cells(0).Text)
d.Items.Add(e.Item.Cells(1).Text)
d.Items.Add(e.Item.Cells(2).Text)
e.Item.Cells(3).Controls.Add(d)
End If
End Sub

Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As
System.EventArgs) Handles Button1.Click
Response.Write(CType(DataGrid1.Items(0).Cells(3).Controls(0),
DropDownList).SelectedValue)
Bind()
End Sub


Thank you, Mike
Microsoft, ASP.NET Support Professional

Microsoft highly recommends to all of our customers that they visit the
http://www.microsoft.com/protect site and perform the three straightforward
steps listed to improve your computer's security.

This posting is provided "AS IS", with no warranties, and confers no rights.
 

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

No members online now.

Forum statistics

Threads
473,766
Messages
2,569,569
Members
45,042
Latest member
icassiem

Latest Threads

Top