2014-04-03 84 views
0

我是WPF的新手,并试图解决看似简单的问题。在编辑中修改WPF DataGrid中的用户控件

我需要设计一个数据表并允许用户编辑它。当用户开始编辑单元格时,我需要在最右边的列中显示一组按钮[确定]和[取消]以接受或取消更改。当用户未编辑单元格时,应显示[删除]按钮供用户删除该行。

我写了一个自定义控件,可以根据自定义IsInEditMode属性显示[确定] [取消]或单个[删除]按钮。

public partial class RowEditControl : UserControl 
{ 
    public static DependencyProperty 
      IsInEditModeProperty = DependencyProperty.Register("IsInEditMode", 
                    typeof(bool), 
                    typeof(RowEditControl), 
                    new FrameworkPropertyMetadata(OnEditModeChanged)); 

    private static void OnEditModeChanged(DependencyObject aD, DependencyPropertyChangedEventArgs aE) 
    { 
     //depending on the value show [Delete] or [Ok][Cancel] buttons 
    } 
} 

当用户开始编辑单元格时,我需要以某种方式设置IsInEditMode。我一直在寻找所有的MSDN和这个论坛的例子/方式如何做到这一点,但找不到任何东西。

添加我的自定义控件的最后一列程序是这样的:

 { 
     mwTagList.Columns[1].Width = new DataGridLength(1, DataGridLengthUnitType.Star); 

     var fRowEditTemplate = new FrameworkElementFactory(typeof (RowEditControl)); 

     fRowEditTemplate.AddHandler(
            RowEditControl.DeleteClickedEvent, 
            new RoutedEventHandler(OnDeleteRowBtn) 
      ); 

     fRowEditTemplate.AddHandler(
           RowEditControl.OkClickedEvent, 
           new RoutedEventHandler(OnRowEditOk)); 

     fRowEditTemplate.AddHandler(
           RowEditControl.CancelClickedEvent, 
           new RoutedEventHandler(OnRowEditCancel)); 

     mwTagList.Columns.Add(
           new DataGridTemplateColumn() 
           { 
            Header = "Delete Row", 
            CellTemplate = new DataTemplate() {VisualTree = fRowEditTemplate} 
           } 
      ); 
    } 

非常感谢你的任何信息和提示!

回答

1

我解决了使用样式这个问题:

<Style x:Key="MwControlCellStyle" TargetType="{x:Type notesList:RowEditControl}"> 
     <Style.Triggers> 
      <MultiDataTrigger> 
       <MultiDataTrigger.Conditions> 
        <!-- find DataGridRow parent object and trigger if it is in editing mode --> 
        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type DataGridRow}}, Path=IsEditing}" Value="True"></Condition> 
       </MultiDataTrigger.Conditions> 
       <Setter Property="IsInEditMode" Value="True"></Setter> 
      </MultiDataTrigger> 
     </Style.Triggers> 
    </Style> 
0

DataGridRow上有一个IsEditing依赖项属性,所以你可以用XAML和几个转换器来做到这一点。在XAML的主要位是这个样子

<Window.Resources> 
<viewModel:BooleanVisibleConverter x:Key="boolVisConv"/> 
<viewModel:InverseBooleanVisibleConverter x:Key="invBoolVisConv"/> 

<DataTemplate x:Key="DataGridButtonsTemplate"> 
    <StackPanel > 
     <Button Content="Delete" Visibility ="{Binding IsEditing, Mode=OneWay, Converter={StaticResource invBoolVisConv}, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=DataGridRow}}"/> 
     <Button Content="OK" Visibility="{Binding IsEditing, Mode=OneWay, Converter={StaticResource boolVisConv},RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=DataGridRow}}"/> 
     <Button Content="Cancel" Visibility="{Binding IsEditing, Mode=OneWay, Converter={StaticResource boolVisConv},RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=DataGridRow}}"/> 
    </StackPanel> 
</DataTemplate> 
</Window.Resources> 

<DataGrid Grid.Row="1" ItemsSource="{Binding MyData}" AutoGenerateColumns="False"> 
    <DataGrid.Columns> 
     <DataGridTextColumn Binding="{Binding FirstField}" Header="First Property"></DataGridTextColumn> 
     <DataGridTextColumn Binding="{Binding SecondField}" Header="Second Property"></DataGridTextColumn> 
     <DataGridTextColumn Binding="{Binding ThirdField}" Header="Third Property"></DataGridTextColumn> 
     <DataGridTemplateColumn Header="Control" CellTemplate="{StaticResource DataGridButtonsTemplate}"></DataGridTemplateColumn> 
    </DataGrid.Columns> 
</DataGrid> 

一个例子转换器在这里,很明显,你将需要其中的两个,第二个将有返回值逆转

[ValueConversion(typeof(bool), typeof(Visibility))] 
public class BooleanVisibleConverter : IValueConverter 
{ 
    public object Convert(object value, Type targetType, object parameter, 
     System.Globalization.CultureInfo culture) 
    { 
     if (targetType != typeof(Visibility)) 
      throw new InvalidOperationException("The target must be a System.Windows.Visibility"); 

     return ((bool)value)? Visibility.Visible : Visibility.Collapsed; 
    } 

    public object ConvertBack(object value, Type targetType, object parameter, 
     System.Globalization.CultureInfo culture) 
    { 
     throw new NotSupportedException(); 
    } 
} 

您需要找出哪个按钮被按下,因为每行会有一个按钮被按下。有一对夫妇的想法,该怎么做,这里

WPF DataGrid - Button in a column, getting the row from which it came on the Click event handler

+0

谢谢!我使用上面的样式解决了这个问题,但是这看起来也很酷。这也是如何使用转换器的一个很好的例子,我是WPF的新手,从来没有使用它们。 –