WPF Datagrid:基于复选框条件禁用所有行的另一个单元格

时间:2015-12-22 10:28:21

标签: wpf wpfdatagrid

我开发了一个带有AutoGenerateColumns = false的自定义数据网格,在后面的代码中,我根据我需要的类型创建了列。我用过

对于DataGridTemplateColumn类型(包含cellTemplate和CellEditing模板),

string,对于复选框类型,我使用了DataGridCheckBoxColumn

现在我的要求是,在datagrid中,如果用户检查了2个以上的复选框(即每行只有一个复选框,每行复选框单击是一个计数),那么具有名称的特定列" DisplayName的"对于所有行,应禁用“文本框”类型。

我创建了一个属性来维护checkBoxClicked的计数,并且已根据chekbox的检查或取消检查进行了正确更新,现在我想使用此属性并禁用未选中复选框的所有行仅适用于列名称" DisplayName"。

任何建议都会有所帮助。

编辑:

我在代码中尝试了以下内容,但它无法正常工作。为DataGridCell创建了一个样式。并添加了一个转换器,它检查我想要禁用的列名称,下面是示例代码

<Style x:Key="DataGridCellStyle1" TargetType="{x:Type DataGridCell}">
<DataTrigger Binding="{Binding ElementName=DataGridUserControl, Path=MaxAddToLabelReached}" Value="true">
         <Setter Property="IsEnabled" Value="{Binding Path=Value, Converter={StaticResource ValueToBrushConverter}}" />
</DataTrigger>

我的转换器有逻辑

public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
 {

   try
   {
     DataGridCell dgc = (DataGridCell)value;

     if (dgc.Column.Header.ToString().Equals("Display Name"))
       return false;

   }
   catch (InvalidCastException )
   {
     return Boolean.FalseString;
   }


   return Boolean.TrueString;
 }

要求:

我的要求是 - 如果我有十行,那么每一行都会有一个名称为AddtoLabel的复选框类型列,在同一行中,将会有一个名称列和#34;显示名称&#34;,当用户选中复选框时,复选框的计数将为1,如果复选框的计数超过2,则我的属性&#34; MaxAddToLabelReached&#34;将被设置为true.Means我不应该允许用户检查未经检查的其他行中的复选框。我创建了一个样式来禁用所有其他未选中的复选框,因此&#34; Addtolabel&#34;未选中的列复选框将被禁用,

这很好用。当&#34; MaxAddToLabelReached&#34;时,每一行都以相同的方式然后在&#34; Displayname&#34;列,我必须检查未选中复选框的行,如果未选中它们,则禁用&#34; DisplayName&#34;该特定行的列单元格。

编辑:

我为数据网格创建列的方式是

我在XAML中创建了一个模板,如下所示

<DataGridTemplateColumn Header="CellTempalte" x:Key="DataGridTemplateColumn">
        <DataGridTemplateColumn.CellTemplate>
            <DataTemplate x:Name="DataGridCellTemplateColumn">
      <TextBlock  x:Name="textBlock" DataContextChanged="Cell_DataContextChanged" Margin="0, 0"  Loaded="Cell_Loaded" VerticalAlignment="Top"  
                  >

      </TextBlock>
            </DataTemplate>              
        </DataGridTemplateColumn.CellTemplate>
        <DataGridTemplateColumn.CellEditingTemplate>
            <DataTemplate x:Name="DataGridCellEditTemplateColumn">
                <TextBox   x:Name="celltext"  DataContextChanged="T_Cell_DataContextChanged" VerticalContentAlignment="Top" MinHeight="20" VerticalAlignment="Stretch" MouseEnter="datagrid_CellTextBoxEnter" 
                           MouseLeftButtonDown="TextBox_MouseLeftButtonDown_1" BorderBrush="{x:Null}" BorderThickness="0"/>
            </DataTemplate>
        </DataGridTemplateColumn.CellEditingTemplate>
    </DataGridTemplateColumn>

在Initialize Columns后面的代码中,我创建了如下列

       if (columnType == "Text")
        {

           DataGridTemplateColumn dataGridTemplateColumnForText = this.FindResource("DataGridTemplateColumn") as        DataGridTemplateColumn;
           DataGrid.Columns.Add(new DataGridTemplateColumn()
           {
              Header = columnHeadersInfo.colHeaderConfigInfoColl[i].nlsColumnName,
              CanUserSort = true,
              SortMemberPath = columnName,
              ClipboardContentBinding = binding,
              CellTemplate = dataGridTemplateColumnForText.CellTemplate,
              CellEditingTemplate = dataGridTemplateColumnForText.CellEditingTemplate,
              Width = gridColWidth,
              IsReadOnly = isReadOnly,
              Visibility = columnHeadersInfo.colHeaderConfigInfoColl[i].columnVisibility ? Visibility.Visible : Visibility.Hidden

           });


        }
 else if(columnType == "checkBox")
  {
     var CheckboxCol = new DataGridCheckBoxColumn
      {
          Header = columnHeader,
          Width = gridColWidth,
          IsReadOnly = isReadOnly,
          Binding = binding,
          ClipboardContentBinding = binding,
          CanUserSort = true,
          SortMemberPath = columnHeader,
          ElementStyle = this.Resources["CheckBoxStyle"] as Style,
          EditingElementStyle = this.Resources["CheckBoxEditingStyle"] as Style
      };

      this.DataGrid.Columns.Add(CheckboxCol);

}

因此,对于这种类型的列创建,我不确定,我如何使用您建议的示例代码。

2 个答案:

答案 0 :(得分:0)

您可以使用转换器类来实现此目的。 使用转换器并绑定count属性,如果计数大于2,则使用转换器,您可以返回bool,然后就可以在网格上实现启用和禁用操作。

答案 1 :(得分:0)

使用网格强制执行禁用的行为。如果MaxAddToLabelReached属性为false,则列将被禁用,反之亦然。

请确保您使用转换器,或者使MaxAddToLabelReached属性符合以下w.r.t代码。

在我的一个代码中,这种方法没有问题。

<DataGridTemplateColumn Header="DisplayName" >
    <DataGridTemplateColumn.CellTemplate>
        <DataTemplate>
            <Grid IsEnabled="{Binding MaxAddToLabelReached}">
                <TextBox x:Name="DisplayName" Text="{Binding DisplayName}" />
            </Grid>
        </DataTemplate>
    </DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>

根据CheckBox选中状态禁用列:

XAML:

  <DataGridTemplateColumn>
       <DataGridTemplateColumn.CellTemplate>
            <DataTemplate>
               <CheckBox Checked="CheckBox_Checked" Unchecked="CheckBox_Unchecked"/>
             </DataTemplate>
       </DataGridTemplateColumn.CellTemplate>
   </DataGridTemplateColumn>

代码:

private void CheckBox_Checked(object sender, RoutedEventArgs e)
        {
            /* apply your own condition here */

            Dgrd.Columns[0].IsReadOnly = true; // disable the entire column of all rows

            // to disable only the corresponding cell of the desired column
            CheckBox chk = (CheckBox)sender;
            DataGridRow row = (DataGridRow)Dgrd.ItemContainerGenerator.ContainerFromItem(chk.DataContext);
            DataGridCell p = (DataGridCell) ((TextBlock)Dgrd.Columns[0].GetCellContent(row)).Parent;
            p.IsEnabled = false;
        }

        private void CheckBox_Unchecked(object sender, RoutedEventArgs e)
        {
            /* apply your own condition here */

            // exact opposite of Checked event handler

            Dgrd.Columns[0].IsReadOnly = false; 

            CheckBox chk = (CheckBox)sender;
            DataGridRow row = (DataGridRow)Dgrd.ItemContainerGenerator.ContainerFromItem(chk.DataContext);
            DataGridCell p = (DataGridCell)((TextBlock)Dgrd.Columns[0].GetCellContent(row)).Parent;
            p.IsEnabled = true;
        }