我有一个asp.net页面,上面有两个控件,一个占位符和一个提交按钮。在Page_Load期间,我动态创建任务清单。每行包含一个描述,指向教程的链接和一个复选框。该行中的所有信息都保存在数据库中。如果数据库说已检查任务,则代码会将checked属性设置为true。我遇到的问题是,当单击提交按钮时,我无法找到页面上所有复选框的已检查属性的值(总共约23个)。
以下是创建复选框的代码......
checkbox = new CheckBox();
phChecklist.Controls.Add(checkbox);
if (item.Attributes.Contains("ree_completed"))
checkbox.Checked = (bool)item.Attributes["ree_completed"];
checkbox.EnableViewState = true;
checkbox.ClientIDMode = System.Web.UI.ClientIDMode.Static;
checkboxId = "checkbox" + (string)item.Attributes["ree_sectionnumber"].ToString() + (string)item.Attributes["ree_sequencenumber"].ToString();
checkbox.ID = checkboxId;
以下是尝试查找复选框值的代码...
foreach (Entity item in checklistCollection.Entities)
{
checkboxId = "checkbox" + (string)item.Attributes["ree_sectionnumber"].ToString() + (string)item.Attributes["ree_sequencenumber"].ToString();
itemChecked = (bool)ViewState[checkboxId];
if (itemChecked == "true")
** update database **
//CheckBox checkbox = (CheckBox)phchecklist.FindControl(checkboxId);
}
我想我已经阅读了关于这个主题的每一篇文章,并尝试了大部分内容。我也读过关于ViewState的内容,但我读过的建议没有用。正如您所看到的,我也尝试通过id找到控件集合中的复选框,但也无效。
回发到页面时,我不会重新创建复选框。有些帖子提到你必须重新创建控件但是当我尝试这样做时,我收到一条错误消息,说它是一个重复的id。我不希望重新创建页面的另一个原因是性能损失。该数据库位于远程的Microsoft Dynamic CRM数据库中。
如何在帖子后面保留checked属性的值?
更新:我更改了逻辑并修复了重复ID错误。该页面现在将在回发期间重新创建所有控件。单击提交按钮时,我仍然无法找到任何复选框控件的值。
加里
答案 0 :(得分:0)
您需要在创建复选框控件时为其提供ID。由于您要创建多个复选框;一个用于数据库中的每一行...您需要将唯一的行标识符添加到ID。因此,您需要从行ID(通常是IDENTITY)构建复选框ID。示例:">
然后,当您对表中的每一行进行后处理时,在回发时,您可以查询该特定键值对的请求。类似的东西:
foreach(DataTable.Rows中的DataRow博士) 响应[" CHK _" + dr(" ID")];
答案 1 :(得分:0)
使用Page Init作为page_Load事件。根据{{3}}"使用此事件来读取或初始化控件属性"
答案 2 :(得分:0)
如果要工作,您需要为动态添加的控件添加事件处理程序 在你的情况下
checkbox = new CheckBox();
phChecklist.Controls.Add(checkbox);
checkbox.CheckedChanged += checkBox_CheckedChanged;
然后你需要在方法中做什么
private void CheckBox_CheckedChanged(object sender, System.EventArgs e)
{
...
}
答案 3 :(得分:0)
正如我评论的那样,你肯定需要在Init事件期间创建控件,Load太晚了。有关详细信息,请查看asp.Net page life's cycle。
另外,您可能希望让ASP.NET处理控件的ID。你说你需要保留一些价值才能回到数据库,你可以wrap your checkboxes in a table。然后,您将能够遍历控件而无需猜测其名称。
例如,如果你的行有一个HiddenField,后跟你的实际CheckBox:
//Please call me during Init
protected void createTheControls() {
TableRow tr;
TableCell td;
CheckBox cb;
HiddenField section, sequence;
foreach (Object item in someList)
{
section = new HiddenField();
section.Value = item.Attributes["ree_sectionnumber"].ToString();
sequence = new HiddenField;
sequence.Value = item.Attributes["ree_sequencenumber"].ToString();
cb = new CheckBox();
cb.ID = String.Concat("checkbox", (String)sequence.Value);
if (item.Attributes.Contains("ree_completed"))
cb.Checked = (bool)item.Attributes["ree_completed"];
td = new TableCell();
td.Controls.Add(section);
td.Controls.Add(sequence);
td.Controls.Add(cb);
tr = new TableRow();
tr.Cells.Add(td);
}
}
protected void readTheControls()
{
foreach (TableRow tr in myTable.Rows)
{
HiddenField section = (HiddenField)tr.Cells[0].Controls[0];
HiddenField sequence = (HiddenField)tr.Cells[0].Controls[1];
CheckBox cb = (CheckBox)tr.Cells[0].Controls[2];
}
}
我注意到你试图明确地使用ViewState,我相信这里没有任何帮助。上面的解决方案可能看起来很麻烦,但它确保您在获取控件时不需要弄乱ID。
这里是thorough explanation from MSDN,这里有few short and sweet SO answers解释ViewState的目的。