I spent the last hour or so searching for an answer to this question, but almost every result - either in ASP.NET, or talks about Code First approaches that are useless to me.
Basically, I got POCO objects for database entity objects that I provide to validate the use of IDataErrorInfo.
Now this works fine, except that I have a pointer that is 200 lines long with approximately 40 if-statements. (I'm serious.)
What I'm doing right now extends classes as follows:
public partial class MyPocoObject : IDataErrorInfo
{
public string Error
{
get { throw new NotImplementedException("IDataErrorInfo.Error"); }
}
public string this[string columnName]
{
get
{
string result = null;
}
}
}
This is clearly wrong, so I'm trying to use DataAnnotations.
This is what I understood so far.
I have created such metadata classes:
[MetadataType(typeof(MyObjectMetaData))]
public partial class MyObject { }
public class MyObjectMetaData
{
[Required(AllowEmptyStrings = false, ErrorMessage = "Forename is a required field.")]
public string Forename;
}
Then I have controls declared as such:
<TextBox Text="{Binding SelectedObject.Forename, NotifyOnValidationError=True, ValidatesOnDataErrors=True, UpdateSourceTrigger=PropertyChanged}"/>
:
<Style TargetType="TextBox" BasedOn="{StaticResource Global}">
<Style.Triggers>
<Trigger Property="Validation.HasError" Value="true">
<Setter Property="ToolTip" Value="{Binding RelativeSource={x:Static RelativeSource.Self},Path=(Validation.Errors)[0].ErrorContent}"/>
</Trigger>
</Style.Triggers>
</Style>
IDataErrorInfo, , . , .
? 40 if .
Update:
, , , , .
public partial class Member : IDataErrorInfo
{
[Required(AllowEmptyStrings = false, ErrorMessage = "Forename is a required field.")]
public string Forename;
private readonly Dictionary<string, object> _values = new Dictionary<string, object>();
public string Error
{
get { throw new NotImplementedException("IDataErrorInfo.Error"); }
}
public string this[string columnName]
{
get { return OnValidate(columnName); }
}
protected virtual string OnValidate(string propertyName)
{
if (string.IsNullOrEmpty(propertyName))
{
throw new ArgumentException("Invalid property name", propertyName);
}
string error = string.Empty;
var value = GetValue(propertyName);
var results = new List<System.ComponentModel.DataAnnotations.ValidationResult>(1);
var result = Validator.TryValidateProperty(
value,
new ValidationContext(this, null, null)
{
MemberName = propertyName
},
results);
if (!result)
{
var validationResult = results.First();
error = validationResult.ErrorMessage;
}
return error;
}
protected T GetValue<T>(string propertyName)
{
if (string.IsNullOrEmpty(propertyName))
{
throw new ArgumentException("Invalid property name", propertyName);
}
object value;
if (!_values.TryGetValue(propertyName, out value))
{
value = default(T);
_values.Add(propertyName, value);
}
return (T)value;
}
}
2:
, MVVM, , , , OnValidate .
- ... , , , GetValue, , , , .