问题:事件处理程序quantity_TextChanged
不会更改会话变量“列表”以反映当前状态。事件处理程序将附加到addItemRowToTable
生成的所有文本框中,并通过其分配的ID进行区分。
我肯定会丢失一些东西,但不确定。
其他信息:我需要这样一种方式:对多个文本框所做的更改都被保存到1个Session变量中,以供以后在会话中进一步使用(按表中显示的顺序)。然后,每个文本框的值将在其旁边的标签中使用(每个文本框1个标签)。
所需结果:
Header Header2
[TextBox with value of 42] [Label displaying 42]
[TextBox with value of 76] [Label displaying 76]
[TextBox with value of 105] [Label displaying 105]
WebForm1.aspx.cs
protected void Page_LoadComplete(object sender, EventArgs e)
{
if (Session["list"] != null)
{
List<int> numbers = Session["list"] as List<int>;
int index = 0;
foreach (int item in numbers)
{
tblItems.Rows.AddAt(index + 1, addItemRowToTable(item, index));
// For debugging purposes
Response.Write("<script>console.log(\"" + item.ToString() + "\");</script>");
index++;
}
}
}
private TableRow addItemRowToTable(int item, int index)
{
TableCell[] cells = { new TableCell(), new TableCell() };
TableRow row = new TableRow();
TextBox box = new TextBox();
box.ID = String.Format("{0}_q", index);
box.Attributes["type"] = "number";
box.Attributes["min"] = "1";
box.Attributes["width"] = "60px";
box.TextChanged += new EventHandler(quantity_TextChanged);
box.AutoPostBack = true;
cells[0].Controls.Add(box);
Label lbl = new Label();
lbl.ID = String.Format("{0}_l", index);
lbl.Text = item.ToString();
cells[1].Controls.Add(lbl);
foreach (TableCell cell in cells)
row.Cells.Add(cell);
return row;
}
protected void Button1_Click(object sender, EventArgs e)
{
if (Session["list"] != null)
{
List<int> numbers = Session["list"] as List<int>;
numbers.Add(0);
Session["list"] = numbers;
}
else
{
List<int> numbers = new List<int>();
numbers.Add(0);
Session["list"] = numbers;
}
}
private void quantity_TextChanged(object sender, EventArgs e)
{
if (Session["list"] != null)
{
TextBox item = sender as TextBox;
int position = Convert.ToInt32(item.ID.Split('_')[0]);
List<int> numbers = Session["list"] as List<int>;
numbers[position] = Convert.ToInt32(item.Text);
Session["list"] = numbers;
}
}
WebForm1.aspx
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="WebForm1.aspx.cs" Inherits="Assignment2.WebForm1" %>
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
<title></title>
</head>
<body>
<form id="form1" runat="server">
<div>
<asp:Button ID="Button1" runat="server" Text="Button" OnClick="Button1_Click" />
<br />
<br />
<asp:Table ID="tblItems" runat="server">
<asp:TableHeaderRow>
<asp:TableHeaderCell>Header</asp:TableHeaderCell>
<asp:TableHeaderCell>Header2</asp:TableHeaderCell>
</asp:TableHeaderRow>
</asp:Table>
</div>
</form>
</body>
</html>
答案 0 :(得分:1)
首先,您不需要进入Page_LoadComplete
。我认为您可能试图在单击按钮后添加正确数量的文本框。但是单击按钮应该只添加一个新的TextBox,仅此而已。在Page_Load中,您需要添加存储在Session中的TextBox。
请参见下面的示例,获取具有TextChanged事件的可行解决方案,该事件之所以有效,是因为所有正确的控件都是在回发时重新创建的。
protected void Page_Load(object sender, EventArgs e)
{
if (IsPostBack == false)
{
//do not add or manipulate dynamic controls inside an ispostback check
}
//check if the session exists
if (Session["list"] != null)
{
//add the correct number of textboxes from session
for (int i = 1; i <= Convert.ToInt32(Session["list"]); i++)
{
addTextBox(i);
}
}
}
private void addTextBox(int index)
{
//create a new textbox
TextBox tb = new TextBox();
tb.ID = "DynamicTextBox" + index;
tb.AutoPostBack = true;
//add an event to the textbox
tb.TextChanged += new EventHandler(quantity_TextChanged);
//add the textbox to the page
PlaceHolder1.Controls.Add(tb);
}
protected void Button1_Click(object sender, EventArgs e)
{
int index = 1;
//get the current textbox count if it exists
if (Session["list"] != null)
{
index = Convert.ToInt32(Session["list"]) + 1;
}
//add a new textbox
addTextBox(index);
//upate the session with the new value
Session["list"] = index;
}
private void quantity_TextChanged(object sender, EventArgs e)
{
//display the textbox value in a label for testing
Label1.Text = ((TextBox)sender).Text;
}