Soteriologist
Programmer
I have a datatable that I'm trying to use for storing a matchup between two columns of dynamic controls (a span holding data on the left is matched up to choices from dropdownlists on the right).
I want the datable to save and store the data between postbacks but it seems to be resetting/not-saving.
The code I'm providing is a full working example (aspx and vb). On the page try picking something from one dropdownlist and see that it saves; then choose something from another dropdownlist and see that your new choice saves BUT your old choice for the other dropdownlist does not stay saved. Also try picking something in a dropdownlist (notice that it saves to the datable), then click the "div 2" button and notice that the data resets. (I'm talking about what data that is shown in the gridview and not by the controls themselves... actually this bring up another problem: I'm trying to have the dynamic controls display what is saved in datatable, but they don't seem to be.)
Essentially what I'm trying to accomplish is the following:
If the datatable is empty (a.k.a. the page is loading for the first time) build the dynamic controls and try to automatch values.
If the datatable is filled with data, then build the dynamic controls and select values for the dropdownlist based off of what is saved in the datatable.
When a user chooses something in one of the dropdownlists AND that value hasn't already been picked in another dropdownlist save that value to the datatable
If the user chooses something that already has been picked, then display an error message and don't save the value to the datatable.
Here's the ASPX:
Here's the VB.NET:
I want the datable to save and store the data between postbacks but it seems to be resetting/not-saving.
The code I'm providing is a full working example (aspx and vb). On the page try picking something from one dropdownlist and see that it saves; then choose something from another dropdownlist and see that your new choice saves BUT your old choice for the other dropdownlist does not stay saved. Also try picking something in a dropdownlist (notice that it saves to the datable), then click the "div 2" button and notice that the data resets. (I'm talking about what data that is shown in the gridview and not by the controls themselves... actually this bring up another problem: I'm trying to have the dynamic controls display what is saved in datatable, but they don't seem to be.)
Essentially what I'm trying to accomplish is the following:
If the datatable is empty (a.k.a. the page is loading for the first time) build the dynamic controls and try to automatch values.
If the datatable is filled with data, then build the dynamic controls and select values for the dropdownlist based off of what is saved in the datatable.
When a user chooses something in one of the dropdownlists AND that value hasn't already been picked in another dropdownlist save that value to the datatable
If the user chooses something that already has been picked, then display an error message and don't save the value to the datatable.
Here's the ASPX:
Code:
<%@ Page Language="VB" AutoEventWireup="false" CodeFile="Default.aspx.vb" Inherits="Testing_Default" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "[URL unfurl="true"]http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">[/URL]
<html xmlns="[URL unfurl="true"]http://www.w3.org/1999/xhtml">[/URL]
<head runat="server">
<title>Untitled Page</title>
</head>
<body>
<form id="form1" runat="server">
<div>
<div id="Div1_div" runat="server" visible="false">
<asp:Button ID="Div1_btn" runat="server" Text="Div 2" /><br />
<asp:GridView ID="Page1_gv" runat="server">
<AlternatingRowStyle BackColor="#F5F5F5" />
<SelectedRowStyle BackColor="#FFFF00" />
</asp:GridView>
Left Index:<asp:TextBox ID="LeftIndex_txtbx" runat="server"></asp:TextBox>
Right DDL Index:<asp:TextBox ID="RightIndex_txtbx" runat="server"></asp:TextBox>
Right Number:<asp:TextBox ID="RightNumber_txtbx" runat="server"></asp:TextBox><br />
<p id="DuplicateNumberWarning_p" runat="server" style="color:#ff0000; display:none;">     
The column that you chose is already in use.
</p>
<asp:PlaceHolder ID="Numbers_ph" runat="server" />
</div>
<div id="Div2_div" runat="server" visible="false">
<asp:Button ID="Div2_btn" runat="server" Text="Div 1" /><br />
<asp:GridView ID="Div2_gv" runat="server">
<AlternatingRowStyle BackColor="#F5F5F5" />
<SelectedRowStyle BackColor="#FFFF00" />
</asp:GridView>
</div>
</div>
</form>
</body>
</html>
Here's the VB.NET:
Code:
Imports System.Data
Imports System.Data.SqlClient
Partial Class Testing_Default
Inherits System.Web.UI.Page
Protected Numbers_dt As DataTable = New DataTable("Numbers")
Protected Number_nr As DataRow
Protected Sub Page_Init(ByVal sender As Object, ByVal e As EventArgs) Handles MyBase.Init
With Numbers_dt
.Columns.Add("u_LeftNumber", System.Type.GetType("System.String"))
.Columns.Add("i_RightIndex", System.Type.GetType("System.Int32"))
.Columns.Add("u_RightNumber", System.Type.GetType("System.String"))
End With
End Sub
Protected Sub Page_Load(ByVal sender As Object, ByVal e As EventArgs) Handles MyBase.Load
If Not (Page.IsPostBack) Then
Div1_div.Visible = True
End If
End Sub
#Region " Div 1 "
Protected Sub Div1_div_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Div1_div.Load
GenerateNumbersList()
Page1_gv.DataSource = Numbers_dt
Page1_gv.DataBind()
End Sub
Protected Sub GenerateNumbersList()
Dim Counter As Integer
Dim Number As String
Dim LeftNumber_sp As New HtmlGenericControl
Dim RightNumbers_ddl As New DropDownList
Dim Numbers_dtEmpty As Boolean
If (Numbers_dt.Rows.Count > 0) Then
Numbers_dtEmpty = False
Else
Numbers_dtEmpty = True
End If
While (Counter < 5)
Number = (Counter + 1).ToString()
LeftNumber_sp = New HtmlGenericControl
With LeftNumber_sp
.ID = "LeftNumber" & Number & "_sp"
.InnerText = Number
End With
RightNumbers_ddl = GenerateNumbers_ddl(Counter, Number, Numbers_dtEmpty)
Numbers_ph.Controls.Add(LeftNumber_sp)
Numbers_ph.Controls.Add(RightNumbers_ddl)
Numbers_ph.Controls.Add(New LiteralControl("<br /><br />"))
Counter += 1
End While
End Sub
Protected Function GenerateNumbers_ddl(ByVal IDCounter As Integer, ByVal LeftNumber As String, ByVal Numbers_dtEmpty As Boolean) As DropDownList
Dim Blank_li As ListItem = New ListItem("", "")
Dim One_li As ListItem = New ListItem("One", "One")
Dim Two_li As ListItem = New ListItem("2", "2")
Dim Three_li As ListItem = New ListItem("Three", "Three")
Dim Four_li As ListItem = New ListItem("4", "4")
Dim Five_li As ListItem = New ListItem("Five", "Five")
Dim ddl As New DropDownList
With ddl
.ID = "RightNumbers" & IDCounter.ToString() & "_ddl"
.CssClass = "float_l"
.Style.Item("width") = "50px"
.AutoPostBack = True
.Items.Add(Blank_li)
.Items.Add(One_li)
.Items.Add(Two_li)
.Items.Add(Three_li)
.Items.Add(Four_li)
.Items.Add(Five_li)
End With
If (Numbers_dtEmpty = True) Then
Number_nr = Numbers_dt.NewRow()
Number_nr("u_LeftNumber") = IDCounter.ToString()
For Each ListItem In ddl.Items
If (ListItem.Text.Length > 0) And (LeftNumber.Length > 0) Then
If (ListItem.Text.Substring(0, 1).ToLower = LeftNumber.Substring(0, 1).ToLower) Then
ListItem.Selected = True
Exit For
End If
End If
Next
If (ddl.SelectedIndex <> 0) Then
Number_nr("i_RightIndex") = ddl.SelectedIndex
Else
Number_nr("i_RightIndex") = 0
End If
Number_nr("u_RightNumber") = ddl.SelectedValue
Numbers_dt.Rows.Add(Number_nr)
Else
ddl.SelectedIndex = Numbers_dt.Rows(IDCounter).Item("i_RightIndex")
End If
AddHandler ddl.SelectedIndexChanged, AddressOf DBHeader_ddl_SelectedIndexChanged
Return ddl
End Function
Protected Sub DBHeader_ddl_SelectedIndexChanged(ByVal sender As Object, ByVal e As System.EventArgs)
Dim ddl As DropDownList = DirectCast(sender, DropDownList)
Dim selectedIndex, rowNumber As Integer
Dim selectedValue, selectedText As String
With ddl
selectedIndex = .SelectedIndex
selectedValue = .SelectedValue
selectedText = .SelectedItem.Text
rowNumber = CInt(.ClientID.ToString().Replace("RightNumbers", "").Replace("_ddl", ""))
End With
Dim rowCounter As Integer
Dim foundMatch As Boolean
If (selectedIndex <> 0) Then
While (rowCounter < Numbers_dt.Rows.Count())
If (Numbers_dt.Rows(rowCounter).Item("i_RightIndex") = selectedIndex) And (Numbers_dt.Rows(rowCounter).Item("u_LeftNumber") <> (rowNumber.ToString())) Then
foundMatch = True
Exit While
Else
foundMatch = False
End If
rowCounter += 1
End While
Else
foundMatch = False
End If
If (foundMatch = True) Then
DuplicateNumberWarning_p.Style("display") = "block"
DuplicateNumberWarning_p.InnerText = "Your selection was found to exist already in the datatable."
Numbers_dt.Rows(rowNumber).BeginEdit()
Numbers_dt.Rows(rowNumber).Item("i_RightIndex") = 0
Numbers_dt.Rows(rowNumber).Item("u_RightNumber") = ""
Numbers_dt.Rows(rowNumber).EndEdit()
Numbers_dt.Rows(rowNumber).AcceptChanges()
Else
DuplicateNumberWarning_p.Style("display") = "none"
Numbers_dt.Rows(rowNumber).BeginEdit()
Numbers_dt.Rows(rowNumber).Item("i_RightIndex") = selectedIndex
Numbers_dt.Rows(rowNumber).Item("u_RightNumber") = selectedValue
Numbers_dt.Rows(rowNumber).EndEdit()
Numbers_dt.Rows(rowNumber).AcceptChanges()
End If
LeftIndex_txtbx.Text = Numbers_dt.Rows(rowNumber).Item("u_LeftNumber")
RightIndex_txtbx.Text = Numbers_dt.Rows(rowNumber).Item("i_RightIndex")
RightNumber_txtbx.Text = Numbers_dt.Rows(rowNumber).Item("u_RightNumber")
Page1_gv.DataBind()
End Sub
Protected Sub Page1_btn_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles Div1_btn.Click
Div1_div.Visible = False
Div2_div.Visible = True
End Sub
#End Region
#Region " Div 2 "
Protected Sub Page2_div_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Div2_div.Load
Div2_gv.DataSource = Numbers_dt
Div2_gv.DataBind()
End Sub
Protected Sub Div2_btn_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles Div2_btn.Click
Div1_div.Visible = True
Div2_div.Visible = False
End Sub
#End Region
End Class