c# - 如何在 Checkstate 中保存 ASP 复选框状态并在 postba 后检索值
问题描述
我正在开发一个 ASP Webform 应用程序,并在复选框 Viewstate 和 Postback 方面遇到一些挑战。我的应用程序有 2 个网格视图。Gridview 有大约 8 列,其中 3 列有 3 个 TemplateField,每个 TemplateField 都有自己的 ASP 复选框,具有不同的 ID。Gridview 显示来自 Active Directory 的已分配给用户的数据将被更新、删除或更改。我想使用复选框选中的状态或值进行更新。
请参阅 Gridview A 的标记
<asp:GridView ID="gv_ZugeteilteEmailverteiler" runat="server" AllowPaging ="true" PageSize="15" CssClass="table table-striped table-bordered" AutoGenerateColumns="false" Width="100%" BorderColor="#DEBA84" BackColor="Silver" HeaderStyle-Height="40px" OnPreRender="gv_ZugeteilteEmailverteiler_PreRender"
HorizontalAlign="Center" CellPadding="0">
<Columns>
<asp:TemplateField HeaderText="Reihe" ItemStyle-Width="200px" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center">
<ItemTemplate>
<%# Container.DataItemIndex + 1 %>
</ItemTemplate>
</asp:TemplateField>
<asp:BoundField DataField="gruppenname" HeaderText="Gruppenname" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="standort" HeaderText="Standort" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="beschreibung" HeaderText="Beschreibung" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="genehmigt" HeaderText="Genehmigt" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="400px"/>
<asp:BoundField DataField="zielobjekt" HeaderText="ZielObjekt" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="ACTION_CHECKED" HeaderText="Action_Checked" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px" />
<asp:TemplateField HeaderText="Neu-Hinzufügen" ItemStyle-Width="200px" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center">
<ItemTemplate>
<asp:CheckBox ID="cb_EmailverteilerHinzufuegen" runat="server" AutoPostBack="true" Checked="false" ItemStyle-HorizontalAlign="Center" CssClass="checkboxClass" onclick="CheckBoxCheck(this);" onchange="return javascript:CheckBoxCheck(this);" OnCheckedChanged="cb_EmailverteilerHinzufuegen_CheckedChanged"/>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderText="Entfernen" ItemStyle-Width="200px" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" >
<ItemTemplate>
<asp:CheckBox ID="cb_EmailverteilerEntfernen" runat="server" AutoPostBack="true" ItemStyle-HorizontalAlign="Center" CssClass="checkboxClass" onclick="CheckBoxCheck(this);" onchange="return javascript:CheckBoxCheck(this);" OnCheckedChanged="cb_EmailverteilerEntfernen_CheckedChanged"/>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField HeaderText="Bestätigen" ItemStyle-Width="200px" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center">
<ItemTemplate>
<asp:CheckBox ID="cb_EmailverteilerBestaetigen" runat="server" AutoPostBack="true" ItemStyle-HorizontalAlign="Center" class="checkboxClass" onclick="CheckBoxCheck(this);" onchange="return javascript:CheckBoxCheck(this);" OnCheckedChanged="cb_EmailverteilerBestaetigen_CheckedChanged"/>
</ItemTemplate>
</asp:TemplateField>
</Columns>
<HeaderStyle ForeColor="Black" Font-Bold="True" BackColor="#CCCC00"></HeaderStyle>
</asp:GridView>
Gridview B 在模板字段中也有大约 6 列和一个复选框。Gridview B 中的数据是来自 AD 的目录,可以添加到用户在 Gridview A 中显示的已给定目录列表中。因此,当单击 Gridview B 中的复选框时,选中或选中的整行将添加到 Gridview A。
请参阅 Gridview B 的标记
<asp:GridView ID="gv_MoeglicheEmailverteiler" runat="server" ClientIDMode="Static"
AutoGenerateColumns="false" BorderColor="#DEBA84" BackColor="Silver" HeaderStyle-Height="40px" OnPreRender="gv_MoeglicheEmailverteiler_PreRender"
HorizontalAlign="Center" CellPadding="3" CssClass="tablesorter">
<Columns>
<asp:TemplateField HeaderText="Reihe" ItemStyle-Width="200px" ItemStyle-HorizontalAlign="Center">
<ItemTemplate>
<%# Container.DataItemIndex + 1 %>
</ItemTemplate>
</asp:TemplateField>
<asp:BoundField DataField="gruppenname" HeaderText="Gruppenname" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="standort" HeaderText="Standort" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="beschreibung" HeaderText="Beschreibung" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="genehmigt" HeaderText="Genehmigt" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="zielobjekt" HeaderText="ZielObjekt" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px"/>
<asp:BoundField DataField="ACTION_CHECKED" HeaderText="Action_Checked" NullDisplayText="n/a" ItemStyle-HorizontalAlign="Center" HeaderStyle-HorizontalAlign="Center" ItemStyle-Width="250px" />
<asp:TemplateField ItemStyle-Width="300px" HeaderText="Action" ItemStyle-HorizontalAlign="Center">
<ItemTemplate>
<asp:CheckBox ID="cb_CheckOneMoglicheverteilerRow" runat="server" ItemStyle-HorizontalAlign="Center" class="checkboxClass" AutoPostBack="true" onclick = "Check_Click(this);" OnCheckedChanged="CheckBox_CheckChanged"/>
</ItemTemplate>
</asp:TemplateField>
</Columns>
<HeaderStyle ForeColor="Black" Font-Bold="True" BackColor="#CCCC00"></HeaderStyle>
</asp:GridView>
问题:两个 Gridview 中的每个复选框都会触发事件。示例 Gridview B 事件中的复选框是将选中的行添加到 Gridview A。我设法保存 Gridviews ViewState 并在每次回发或事件后检索它们并成功绑定它们。
我的问题是,Gridview A 中的复选框,我不能或不知道如何将它们的已检查状态保存在 ViewState 中,并在回发后或事件后或页面刷新后恢复它们。在页面刷新或回发后,它们都未选中。
以下是将 Gridview B 中的一行添加到 Gridview A 并从 Gridview A 中删除行的方法
// 创建数据表并保存在 Viewstate 中,我想我也可以在这里将复选框列添加到数据表中,但我不知道如何获取它们的值,因为 Gridview 列的值是从数据库绑定字段中获取的。
private DataTable CreateDataTable()
{
DataTable dt = new DataTable();
if (ViewState["SelectedRecords"] != null)
{
dt = (DataTable)ViewState["SelectedRecords"];
}
else
{
dt.Columns.Add("gruppenname");
dt.Columns.Add("standort");
dt.Columns.Add("beschreibung");
dt.Columns.Add("genehmigt");
dt.Columns.Add("zielobjekt");
dt.Columns.Add("Action_Checked");
dt.AcceptChanges();
}
return dt;
}
// 将行添加到从 Gridview A 到 Gridview B 的方法
private DataTable AddRow(GridViewRow gvRow, DataTable dt)
{
DataRow[] dr = dt.Select("gruppenname = '" + gvRow.Cells[1].Text + "'");
if (dr.Length <= 0)
{
dt.Rows.Add();
dt.Rows[dt.Rows.Count - 1]["gruppenname"] = gvRow.Cells[1].Text;
dt.Rows[dt.Rows.Count - 1]["standort"] = gvRow.Cells[2].Text;
dt.Rows[dt.Rows.Count - 1]["beschreibung"] = gvRow.Cells[3].Text;
dt.Rows[dt.Rows.Count - 1]["genehmigt"] = gvRow.Cells[4].Text;
dt.Rows[dt.Rows.Count - 1]["zielobjekt"] = gvRow.Cells[5].Text;
dt.Rows[dt.Rows.Count - 1]["Action_Checked"] = gvRow.Cells[6].Text;
dt.AcceptChanges();
}
return dt;
}
// 从 Gridview A 中移除 Row 的方法
private DataTable RemoveRow(GridViewRow gvRow, DataTable dt)
{
DataRow[] dr = dt.Select("gruppenname = '" + gvRow.Cells[1].Text + "'");
if (dr.Length > 0)
{
dt.Rows.Remove(dr[0]);
dt.AcceptChanges();
}
return dt;
}
// 现在这就是我如何称呼它们 // 从 Gridview Moglicheverteiler 中的选中行获取数据以添加到 Gridview Zugeteilte Emailverteiler 的方法
private void GetData()
{
DataTable dt;
if (ViewState["SelectedRecords"] != null)
dt = (DataTable)ViewState["SelectedRecords"];
else
dt = CreateDataTable();
for (int i = 0; i < gv_MoeglicheEmailverteiler.Rows.Count; i++)
{
CheckBox chk = (CheckBox)gv_MoeglicheEmailverteiler.Rows[i].Cells[6].FindControl("cb_CheckOneMoglicheverteilerRow"); string test = gv_MoeglicheEmailverteiler.Rows[i].Cells[1].Text;
if (gv_ZugeteilteEmailverteiler != null && chk.Checked)
{
for (int j = 0; j < gv_ZugeteilteEmailverteiler.Rows.Count; j++)
{
string actionChecked = gv_ZugeteilteEmailverteiler.Rows[j].Cells[6].Text;
if ((chk.Checked && actionChecked == "Bestaetigen")|| (chk.Checked && actionChecked == "Bestaetigt") || (chk.Checked && actionChecked == "TRUE") || (chk.Checked && actionChecked == "FALSE") || (chk.Checked && actionChecked == "Entfernen"))
{
dt = AddRow(gv_MoeglicheEmailverteiler.Rows[i], dt);
dt = AddRow(gv_ZugeteilteEmailverteiler.Rows[j], dt);
}
else if (chk.Checked)
{
dt = AddRow(gv_MoeglicheEmailverteiler.Rows[i], dt);
}
}
}
}
ViewState["SelectedRecords"] = dt;
}
private void SetData()
{
if (ViewState["SelectedRecords"] != null)
{
DataTable dt = (DataTable)ViewState["SelectedRecords"];
for (int i = 0; i < gv_MoeglicheEmailverteiler.Rows.Count; i++)
{
CheckBox chk = (CheckBox)gv_MoeglicheEmailverteiler.Rows[i].Cells[6].FindControl("cb_CheckOneMoglicheverteilerRow");
if (chk != null)
{
DataRow[] dr = dt.Select("gruppenname = '" + gv_MoeglicheEmailverteiler.Rows[i].Cells[1].Text + "'");
chk.Checked = dr.Length > 0;
}
}
}
}
所以简而言之,我试图弄清楚如何将复选框值保存到视图状态中,就像我对 Gridview Columns 所做的那样。任何想法都会非常感激。几个月来,我一直在解决这个问题。
// Bind ZugeteiltGridview For GetData Method
private void BindZugeteilteGridviewForGetDataMethod()
{
DataTable dt = (DataTable)ViewState["SelectedRecords"];
gv_ZugeteilteEmailverteiler.DataSource = dt;
gv_ZugeteilteEmailverteiler.DataBind();
//CheckAddedRowFromMoglicheEmailverteiler();
}
解决方案
你有AutoPostback=true
- 这就是问题所在。不要这样做。
相反,添加一个按钮来执行从 Grid A 到 Grid B 的更改。您应该能够访问复选框值,然后通过在 GridView 行被数据绑定之前循环它们 - 您可能需要一个隐藏字段来存储ID
项目的每一行。您应该(如果需要)从数据存储中获取该 ID 的数据,而不是尝试从 GridView 中获取数据。您当然可以尝试,但由于它们是 DataBound 控件,我相信您需要获取单元格的文本。
一旦完成,您就可以重新绑定网格。
确保在循环之前不要对网格 A 进行数据绑定,否则所有复选框都将消失。
推荐阅读
- sql - SQL return values from one table depending on another table
- c++ - 重载 new 和 delete 导致 valgrind 错误
- powershell - 如何在powershell上获取进程的父ID?
- kotlin - 在 Kotlin-way 中获取字符串中包含的子字符串的索引
- jquery - ASP.NET MVC 控制器的返回值字符串如何为空?
- asp.net-core - 如何在 ASP.NET Core 中自动触发电子邮件
- neo4j - 是否有与管道 (|) 类似的 & 符号?
- python - gspread 有没有办法在更新引用时复制粘贴公式?
- llvm - llvm 无需映射即可复制
- vue.js - 为什么 a-avatar 在 a-menu-item 内滑动一点