我已编程多年,在旧版本的.NET中大约有10个,因此我是LINQ,UpdatePanels和Ajax的新手以及他们的工作方式。
以下代码正常工作
数据库字段定义为:
rptPriority INT NOT NULL DEFAULT(0)
一个非常简化的页面存根有效:
<asp:UpdatePanel ID="upReport" runat="server" UpdateMode="Conditional">
<ContentTemplate>
<fieldset>
<asp:DetailsView ID="dvReport" runat="server" DataSourceID="ldsReport" CssClass="reset"
AutoGenerateRows="False" DefaultMode="Edit" Width="100%">
<Fields>
<asp:TemplateField>
<ItemTemplate>
<asp:DynamicControl ID="Priority" runat="server" DataField="rptPriority" Mode="Edit" CssClass="general" />
等
我需要做的是将动态控制作为文本框更改为可更新并由相同数据驱动的复选框。以下给出了正确的数据,但没有更新
如果我使用直接SQL或PROCEDURES这样做,这不会是一个大问题。 (也不是一种选择)
<asp:CheckBox ID="Priority" runat="server" Checked='<%# Convert.ToBoolean(Eval("rptPriority")) %>' />
我将“Eval”更改为“Bind”并获得“ERROR CS0103:当前上下文中不存在名称'Bind'”
我怀疑“Convert.ToBoolean”是问题的一部分
有很多页面我试图获取我需要的信息。其中How to add checkbox to datagrid in vb.net,Html.CheckBox returns false if disabled, even if seleced和Checkbox server/client events,How do you know to use Container.DataItem when data binding in ASP.NET? Is there a reference?,The databind bind() function belongs to which class?更不用说还有50多个栈外溢出让我到了现在的位置。
修改
根据Rob的建议,我添加了以下内容,但无法获得/找到使用“DetailsViewUpdateEventArgs”的任何方法。
protected void dvReport_ItemUpdating(object sender, DetailsViewUpdateEventArgs e)
{
DetailsView dv = sender as DetailsView;
CheckBox ctlPriority = dv.FindControl("Priority") as CheckBox;
e.NewValues["rptPriority"] = ctlPriority.Checked ? 1 : 0;
}
以下是来自后面的保存/更新代码的存根。
protected void btnSave_OnCLick(object sender, EventArgs e)
{
RadioButtonList rblReportStatus = (RadioButtonList)dvReport.FindControl("rblReportStatus");
using (RiderReportDataContext db = new RiderReportDataContext())
{
Report report = null;
Contact contact = null;
DateTime now = DateTime.Now;
bool doUpdate = false;
ldsContact.Updating += (o, ea) =>
{
Contact original = (Contact)ea.OriginalObject;
contact = (Contact)ea.NewObject;
if (
original.FirstName != contact.FirstName ||
...
original.Email != contact.Email)
{
doUpdate = true;
}
db.Contacts.Attach(contact, original);
ea.Cancel = true;
};
// force the update procedure
dvContact.UpdateItem(true);
ldsReport.Updating += (o, ea) =>
{
Report original = ea.OriginalObject as Report;
report = ea.NewObject as Report;
if (rblReportStatus.SelectedItem != null)
{
report.ReportStatusId = int.Parse(rblReportStatus.SelectedValue);
}
if (
original.ReportStatusId != report.ReportStatusId ||
original.SourceId != report.SourceId ||
...
original.ReportTypeID != report.ReportTypeID ||
original.rptPriority != report.rptPriority || // The value here doesn't change
original.SupervisorId != report.SupervisorId)
{
doUpdate = true;
}
db.Reports.Attach(report, original);
ea.Cancel = true;
};
// force the update procedure
dvReport.UpdateItem(true);
// Other Search For Updates
if (doUpdate)
{
contact.ChangedOn = now;
report.ChangedOn = now;
Log log = new Log();
log.ReportId = report.Id;
log.UserId = MembershipClass.User.Id;
log.Text = "The report updated.";
log.CreatedOn = now;
report.Logs.Add(log);
db.SubmitChanges();
}
}
if (Page.IsValid)
{
Response.Redirect("~/default.aspx" /*table.ListActionPath */);
}
}
答案 0 :(得分:1)
正如您所发现的,Bind()
并未提供转换数据类型的简便方法。您会发现其他答案建议更改您绑定的数据类型,但我知道这不是您的选择。
我认为您最好的解决方案是回到单向绑定。例如使用现有代码:
<asp:CheckBox ID="Priority" runat="server"
Checked='<%# Convert.ToBoolean(Eval("rptPriority")) %>' />
在呈现DetailsView
时,将正确设置复选框的值,但在更新详细信息时不会为rptPriority提供值。为此,您需要向OnItemUpdating
添加DetailsView
事件处理程序,以便您执行所需的自定义转换。 e.g。
<asp:DetailsView ID="dvReport" runat="server"
onitemupdating="dvReport_ItemUpdating"
您的代码隐藏中的实现将如下所示: -
protected void dvReport_ItemUpdating(object sender, DetailsViewUpdateEventArgs e)
{
DetailsView dv = sender as DetailsView;
CheckBox ctlPriority = dv.FindControl("Priority") as CheckBox;
e.NewValues["rptPriority"] = ctlPriority.Checked ? 1 : 0;
}
希望这有帮助。