根据标签,这是一个实体框架,C#,Winforms问题。
我有一个文本框数据绑定到我的实体中可以为空的datetime字段。我想在删除文本框的内容时将空值传回实体,并将其留空。
Textbox CausesValidation property = true。当我删除文本框的内容时,如果没有输入有效日期,我将无法离开。
这是我的验证活动
private void txtDueDateDetail_Validating(object sender, CancelEventArgs e)
{
string errorMsg;
if (!ValidDate(txtDueDateDetail.Text, out errorMsg))
{
// Cancel the event and select the text to be corrected by the user.
e.Cancel = true;
txtDueDateDetail.Select(0, txtDueDateDetail.Text.Length);
// Set the ErrorProvider error with the text to display.
this.epNew.SetError(txtDueDateDetail, errorMsg);
}
Debug.Write("text: " + txtDueDateDetail.Text);
}
public bool ValidDate(string pTextDate, out string errorMessage)
{
DateTime tempDate;
errorMessage = "";
if (pTextDate.Length == 0)
{
//pass a null date...how?
return true;
}
DateTime.TryParse(pTextDate, out tempDate);
if (tempDate == DateTime.MinValue)
{
errorMessage = "date must be in format MM/dd/yyyy";
return false;
}
return true;
}
任何想法都会有所帮助。
答案 0 :(得分:3)
考虑到您的初始方法,您是否尝试将Binding.NullValue
设置为空字符串?您可以按以下方式以编程方式执行此操作:
txtDueDateDetail.DataBindings["Text"].NullValue = "";
根据docs,将空字符串分配给NullValue
与分配null
(这是默认值)不同。
你的最终解决方案没问题。在我阅读NullValue
属性之前,我考虑过实现它。对我来说,它的缺点是它会降低数据绑定的实用性,因为这样我最终会手动将更改后的值分配回数据源 - 我希望数据绑定能够为我做这件事。
答案 1 :(得分:1)
我无法绕过null日期时间验证,所以我关闭了[CausesValidation = FALSE]字段的验证并在Leave事件中执行了我自己的验证。
public bool ValidDate(string pTextDate, out DateTime? pDate, out string errorMessage)
{
DateTime tempDate;
errorMessage = "";
pDate = null;
if (pTextDate.Length == 0)
{
//pass null date here...
return true;
}
DateTime.TryParse(pTextDate, out tempDate);
if (tempDate == DateTime.MinValue)
{
errorMessage = "date must be in format MM/dd/yyyy";
return false;
}
pDate = tempDate;
return true;
}
private void txtDueDateDetail_Leave(object sender, EventArgs e)
{
string errorMsg;
DateTime? outDate;
if (!ValidDate(txtDueDateDetail.Text, out outDate, out errorMsg))
{
txtDueDateDetail.Select(0, txtDueDateDetail.Text.Length);
}
else
{
int CID = Convert.ToInt32(txtChargebackIDDetail.Text);
var temp = (from c in chg.ChargeBackks
where c.ID == CID
select c).FirstOrDefault();
temp.DueDate = outDate;
}
this.epNew.SetError(txtDueDateDetail, errorMsg);
}
功能......但不是IMO的最佳解决方案。
答案 2 :(得分:0)
我遇到了同样的问题,并提出了解决方案。绑定由向OnValidating添加事件处理程序的函数控制。通过反思,在此事件处理程序中,我们将基础实体属性设置为null或文本框中的值。这是允许通过验证的密钥-您必须将基础实体字段设置为null。即使处理e.Cancel也无济于事。
对绑定的调用如下:
AddDateBinding(Me.txtPhantomBlockIrrDate, Me.bsPhantomBlock, "IRRADIATE_DATE")
Public Sub AddDateBinding(control As Control, bs As BindingSource, field As String)
Dim controlProperty As String = ""
If TypeOf (control) Is TextBox Then
controlProperty = "Text"
End If
If TypeOf (control) Is ComboBox Then
controlProperty = "SelectedValue"
End If
control.DataBindings.Add(New System.Windows.Forms.Binding(controlProperty, bs, field, True, DataSourceUpdateMode.OnValidation, Nothing, "MM/dd/yyyy"))
AddHandler control.Validating, AddressOf DateValidating
End Sub
Public Sub DateValidating(sender As Object, e As System.ComponentModel.CancelEventArgs)
e.Cancel = False
Try
If CType(sender, Control).Text = "" Then
e.Cancel = False
Dim fieldName As String = CType(sender, Control).DataBindings(0).BindingMemberInfo.BindingField
Dim bs As BindingSource = CType(CType(sender, Control).DataBindings(0).DataSource, BindingSource)
Dim propInfo As Reflection.PropertyInfo = bs.Current.GetType().GetProperty(fieldName)
propInfo.SetValue(bs.Current, Nothing, Nothing)
Else
e.Cancel = False
Dim fieldName As String = CType(sender, Control).DataBindings(0).BindingMemberInfo.BindingField
Dim bs As BindingSource = CType(CType(sender, Control).DataBindings(0).DataSource, BindingSource)
Dim propInfo As Reflection.PropertyInfo = bs.Current.GetType().GetProperty(fieldName)
propInfo.SetValue(bs.Current, CType(sender, Control).Text, Nothing)
End If
Catch ex As Exception
End Try
End Sub