C# MVVM WPF:验证自动生成列的datagrid行
我正在创建一个C# MVVM WPF:验证自动生成列的datagrid行,c#,wpf,mvvm,datagrid,C#,Wpf,Mvvm,Datagrid,我正在创建一个数据表,其列存储在列表中 public class CustomColumn { public string ColumnName { get; set; } public int MinLength { get; set; } public int MaxLength { get; set; } } public class ViewModel { public List<CustomColumn> Columns { get; se
数据表
,其列存储在列表中
public class CustomColumn
{
public string ColumnName { get; set; }
public int MinLength { get; set; }
public int MaxLength { get; set; }
}
public class ViewModel
{
public List<CustomColumn> Columns { get; set; }
public DataTable MyTable { get; set; }
public ViewModel()
{
InitializeCustomColumns();
MyTable = new DataTable();
foreach (CustomColumn column in Columns)
{
MyTable.Columns.Add(column.ColumnName, typeof(string));
}
}
}
我可以验证,但我想显示我的手机!如果
是有效的,则标记返回false。我设法解决了同样的问题
xaml
这将检测当前单元格是否是受影响的单元格,并根据错误状态返回可见性.Visible
如果为true,则返回可见性.Collapsed
,从而隐藏或显示额外的元素
CustomTable中的更改
public CustomTable()
{
...
Errors = new ObservableCollection<DataColumnChangeEventArgs>();
}
private void tableColumnChanging(object sender, DataColumnChangeEventArgs e)
{
if (!isValid(e))
{
object badValue = e.ProposedValue;
e.ProposedValue = "Bad Data";
e.Row.RowError = "The column contains an error";
e.Row.SetColumnError(e.Column, "Column cannot be " + badValue);
Errors.Add(e);
OnPropertyChanged("Errors");
}
else
{
DataColumnChangeEventArgs args = Errors.FirstOrDefault(ee => (ee.Row == e.Row) && (ee.Column == e.Column));
if (args != null)
{
Errors.Remove(args);
OnPropertyChanged("Errors");
}
//...
}
}
public ObservableCollection<DataColumnChangeEventArgs> Errors { get; set; }
publiccustomtable()
{
...
错误=新的ObservableCollection();
}
私有void tableColumnChanging(对象发送方、DataColumnChangeEventArgs e)
{
如果(!isValid(e))
{
对象badValue=e.建议值;
e、 ProposedValue=“坏数据”;
e、 Row.RowError=“该列包含错误”;
e、 Row.SetColumnError(例如,Column,“Column不能是”+badValue);
添加(e);
OnPropertyChanged(“错误”);
}
其他的
{
DataColumnChangeEventArgs args args=Errors.FirstOrDefault(ee=>(ee.Row==e.Row)&&(ee.Column==e.Column));
如果(args!=null)
{
错误。删除(args);
OnPropertyChanged(“错误”);
}
//...
}
}
公共ObservableCollection错误{get;set;}
结果
因此,整个想法是添加一个具有通知更改功能的额外属性,并将其用作触发器和其他属性来检测适当的列,而rest是我们额外属性的可见性!自定义模板中的元素-1阿披实,你现在应该知道,这不是一个你可以来说这是我想要的,并期望其他用户为你做工作的网站。。。你需要做的工作,只是来这里问你是否被困在一个特定的部分。因此,我建议你去尝试满足你的要求,如果你陷入困境,那么你应该提供证据来证明你的问题。@Sheridan我知道我问了很多问题。但我只是在做了充分的研究之后才提出这个问题。我当前的WPF应用程序有点复杂,因此我在提问之前尝试简化问题,并提供我问题的简化示例。有些事情是我无法理解的。阿披实,这不是问很多问题。。。它是关于询问代码,而不显示您自己已经尝试过。由于您现在已经提供了相关代码,我现在将删除我的否决票,尽管您的代码仍然不完整,不会重现您的问题。我们遇到了一种情况。由于DataRow
未实现INotifyPropertyChanged
,因此设置rowrerror
或任何其他属性不会传播到UI,因此我们无法直接执行任何触发。因此,想知道DataTable
是必要的,还是我们也可以使用其他一些集合类?@pushpraj从DataTable转移到其他集合确实很困难:(
<ScrollViewer xmlns:l="clr-namespace:CSharpWPF">
<ScrollViewer.Resources>
<DataTemplate DataType="{x:Type l:CustomTable}">
<DataTemplate.Resources>
<l:ErrorToVisibilityConverter x:Key="ErrorToVisibilityConverter" />
<Style TargetType="DataGridCell">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="DataGridCell">
<Grid Background="{TemplateBinding Background}">
<StackPanel Orientation="Horizontal">
<TextBlock Text=" ! "
FontWeight="Bold"
Foreground="Red">
<TextBlock.Visibility>
<MultiBinding Converter="{StaticResource ErrorToVisibilityConverter}"
Mode="OneWay">
<Binding RelativeSource="{RelativeSource FindAncestor,AncestorType=DataGridCell}" />
<Binding Path="Tag.Errors"
RelativeSource="{RelativeSource FindAncestor,AncestorType=DataGrid}" />
<Binding />
</MultiBinding>
</TextBlock.Visibility>
</TextBlock>
<ContentPresenter />
</StackPanel>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</DataTemplate.Resources>
<StackPanel>
...
</StackPanel>
</DataTemplate>
</ScrollViewer.Resources>
<ContentControl Content="{Binding TableCollection}" />
</ScrollViewer>
namespace CSharpWPF
{
public class ErrorToVisibilityConverter : IMultiValueConverter
{
public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
{
DataGridColumn column = values[0] as DataGridColumn;
ObservableCollection<DataColumnChangeEventArgs> errors = values[1] as ObservableCollection<DataColumnChangeEventArgs>;
DataRowView view = values[2] as DataRowView;
DataColumnChangeEventArgs args = errors.FirstOrDefault(e => (e.Row == view.Row) && (e.Column.Ordinal == column.DisplayIndex));
return view.Row.HasErrors && args != null ? Visibility.Visible : Visibility.Collapsed;
}
public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
}
public CustomTable()
{
...
Errors = new ObservableCollection<DataColumnChangeEventArgs>();
}
private void tableColumnChanging(object sender, DataColumnChangeEventArgs e)
{
if (!isValid(e))
{
object badValue = e.ProposedValue;
e.ProposedValue = "Bad Data";
e.Row.RowError = "The column contains an error";
e.Row.SetColumnError(e.Column, "Column cannot be " + badValue);
Errors.Add(e);
OnPropertyChanged("Errors");
}
else
{
DataColumnChangeEventArgs args = Errors.FirstOrDefault(ee => (ee.Row == e.Row) && (ee.Column == e.Column));
if (args != null)
{
Errors.Remove(args);
OnPropertyChanged("Errors");
}
//...
}
}
public ObservableCollection<DataColumnChangeEventArgs> Errors { get; set; }