【问题标题】:DataGrid SelectionUnit=Cell disables all support for a selected row?DataGrid SelectionUnit=Cell 禁用对选定行的所有支持?
【发布时间】:2012-03-18 08:15:17
【问题描述】:

.Net 4 WPF DataGrid C# MMVM

当 DataGrid SelectionUnit 为整行时,wpf 数据绑定和 collectionview 负责通过视图的 currentitem 属性在视图模型中让我知道主动选择的项目是什么。这对于选择模式设置为全行的只读网格非常有用。

现在我有一个可编辑的网格。所以我设置了 SelectionUnit=Cell 以便更容易地发现其中一个单元格。现在突然之间,网格不再具有任何跟踪选择项的能力。设置为单元格模式时,我什至无法设置 SelectedItem。所以现在视图模型总是认为它在第一行。我可以在网格中处理 SelectedCellsChanged 以确定我在哪一行,我只是无法让 viewmodel 知道,因为网格的 SelectedItem 无法再设置!

我不明白为什么网格在单元格选择模式下仍然不能有 SelectedItem。

对我的网格进行硬编码以将 ItemSource 转换为我的 collectionview 以从 SelectedCellsChanged 事件调用 MoveCurrentTo,是否有任何其他 MVVM 真正的方法可以使视图的 CurrentItem 与网格保持同步?

要么这样,要么我更改网格样式以在我有可编辑网格时删除或减少行突出显示效果。

【问题讨论】:

  • 如果你必须“硬编码”,创建一个接口
  • 是的,这就是我现在所做的。
  • 我只是查看了DataGrid 源,在Cell 模式下,它们不与SelectedItem 同步

标签: wpf datagrid


【解决方案1】:

我正在寻找同样的问题,并找到了一个简单的解决方案

要访问SelectionUnit 设置为Cell 的行,您必须这样做:

DataGridXX.SelectedCells[0].item

仅当您一次只能选择一个单元格时才有效(不是在扩展模式下)。

【讨论】:

    【解决方案2】:

    我在MSDN 上使用附加属性找到了一个很好的解决方案:

    <DataGrid ItemsSource="{Binding}" IsReadOnly="True" SelectionUnit="Cell">
      <DataGrid.CellStyle>
        <Style TargetType="{x:Type DataGridCell}">
          <Style.Triggers>
            <Trigger Property="IsSelected" Value="True">
              <Setter Property="local:DataGridAttachedProperties.IsCellSelected" Value="True"/>
            </Trigger>
            <Trigger Property="IsSelected" Value="False">
              <Setter Property="local:DataGridAttachedProperties.IsCellSelected" Value="False"/>
            </Trigger>
          </Style.Triggers>
        </Style>
      </DataGrid.CellStyle>
      <DataGrid.ItemContainerStyle>
        <Style TargetType="{x:Type DataGridRow}">
          <Style.Triggers>
            <Trigger Property="local:DataGridAttachedProperties.IsCellSelected" Value="True">
              <Setter Property="BorderThickness" Value="2"/>
              <Setter Property="BorderBrush" Value="Red"/>
              <Setter Property="Background" Value="Yellow"/>
              <Setter Property="Opacity" Value="0.7"/>
            </Trigger>
          </Style.Triggers>
        </Style>
      </DataGrid.ItemContainerStyle>
    </DataGrid>
    

    还有 C#:

    public class DataGridAttachedProperties
    {
        public static bool GetIsCellSelected(DependencyObject obj)
        {
            return (bool)obj.GetValue(IsCellSelectedProperty);
        }
        public static void SetIsCellSelected(DependencyObject obj, bool value)
        {
            obj.SetValue(IsCellSelectedProperty, value);
        }
        public static readonly DependencyProperty IsCellSelectedProperty =
            DependencyProperty.RegisterAttached("IsCellSelected", typeof(bool), typeof(DataGridAttachedProperties), new UIPropertyMetadata(false,
            (o, e) =>
            {
                if (o is DataGridCell)
                {
                    DataGridRow row = VisualTreeHelperEx.FindVisualParent<DataGridRow>(o as DataGridCell);
                    row.SetValue(DataGridAttachedProperties.IsCellSelectedProperty, e.NewValue);
                }
            }));
    }
    public class VisualTreeHelperEx
    {
        public static T FindVisualParent<T>(DependencyObject child)
        where T : DependencyObject
        {
            DependencyObject parentObject = VisualTreeHelper.GetParent(child);
            if (parentObject == null) return null;
            T parent = parentObject as T;
            if (parent != null)
            {
                return parent;
            }
            else
            {
                return FindVisualParent<T>(parentObject);
            }
        }
    }
    

    【讨论】:

      【解决方案3】:

      我也有类似的问题,所以这里是我使用的样式(从网络复制)。 因此,您从http://datagridthemesfromsl.codeplex.com/ 复制 WhistlerBlue 主题并进行以下修改。希望这会有所帮助。

      <!--Cell-->
      <Style x:Key='CellStyle' TargetType="{x:Type controls:DataGridCell}" >
          <Setter Property="Foreground" Value="{StaticResource ThemeForegroundBrush}" />
          <Setter Property="Height" Value="Auto" />
          <Setter Property="HorizontalContentAlignment" Value="Stretch"/>
          <Setter Property="VerticalContentAlignment" Value="Stretch"/>
          <Setter Property="Cursor" Value="Arrow" />
          <Setter Property="BorderThickness" Value="1" />
          <!--Padding hack-->
          <Setter Property="Padding" Value="2 5 2 5" />
          <Setter Property="Template">
              <Setter.Value>
                  <ControlTemplate TargetType="{x:Type controls:DataGridCell}">
                      <Grid x:Name="Root" Background="Transparent">
                          <Grid.ColumnDefinitions>
                              <ColumnDefinition Width="*" />
                              <ColumnDefinition Width="Auto" />
                          </Grid.ColumnDefinitions>
                          <Rectangle x:Name="FocusVisual" Margin="0,-2,0,0" 
                                     Stroke="White"  Fill="White" 
                                     Opacity="0" IsHitTestVisible="false"/>
                          <ContentPresenter Margin="{TemplateBinding Padding}" HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}" 
                                            VerticalAlignment="{TemplateBinding VerticalContentAlignment}" Content="{TemplateBinding Content}" 
                                            ContentTemplate="{TemplateBinding ContentTemplate}" Cursor="{TemplateBinding Cursor}"/>
                          <Rectangle x:Name="RightGridLine" VerticalAlignment="Stretch" Width="1" Grid.Column="1" />
                      </Grid>
                  </ControlTemplate>
              </Setter.Value>
          </Setter>
      
      </Style>
      
      <!-- DataGridRow -->
      <Style x:Key='RowStyle' TargetType="{x:Type controls:DataGridRow}">
          <Setter Property="Background" Value="Transparent" />
          <Setter Property="SnapsToDevicePixels" Value="true"/>
          <Setter Property="Template">
              <Setter.Value>
                  <ControlTemplate TargetType="{x:Type controls:DataGridRow}">
                      <Border x:Name="DGR_Border"
                    Background="{TemplateBinding Background}"
                    BorderBrush="{TemplateBinding BorderBrush}"
                    BorderThickness="{TemplateBinding BorderThickness}"
                    SnapsToDevicePixels="True">
                          <primitives:SelectiveScrollingGrid>
                              <Grid.ColumnDefinitions>
                                  <ColumnDefinition Width="Auto"/>
                                  <ColumnDefinition Width="*"/>
                              </Grid.ColumnDefinitions>
      
                              <Grid.RowDefinitions>
                                  <RowDefinition Height="*"/>
                                  <RowDefinition Height="Auto"/>
                                  <RowDefinition Height='Auto' />
                              </Grid.RowDefinitions>
                              <Rectangle x:Name="Selected" Margin="0" Grid.RowSpan="2" Grid.ColumnSpan="2" 
                                     Fill="{StaticResource BtnOverFill}" Stroke="{StaticResource selectedStroke}" 
                                     Opacity="0"/>
                              <Rectangle x:Name="SelectedHighlight" Margin="1" Grid.RowSpan="2" Grid.ColumnSpan="2" 
                                     Stroke="#A0FFFFFF" 
                                     Opacity="0"/>
                              <primitives:DataGridRowHeader Grid.RowSpan="2"
                                                          primitives:SelectiveScrollingGrid.SelectiveScrollingOrientation="Vertical"                                       
                                                          Visibility="{Binding RelativeSource={RelativeSource AncestorType={x:Type controls:DataGrid}}, 
                                  Path=HeadersVisibility, 
                                  Converter={x:Static controls:DataGrid.HeadersVisibilityConverter},
                                  ConverterParameter={x:Static controls:DataGridHeadersVisibility.Row}}"/>
                              <Rectangle x:Name="Over" Margin="0" Grid.RowSpan="2" Grid.ColumnSpan="2" 
                                     Fill="{StaticResource hoverGradient}" 
                                     Stroke="{StaticResource hoverStroke}" 
                                     Opacity="0"/>
                              <primitives:DataGridCellsPresenter Grid.Column="1"
                                              ItemsPanel="{TemplateBinding ItemsPanel}"
                                              SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"/>
                              <primitives:DataGridDetailsPresenter Grid.Column="1" Grid.Row="1"
                                                                 x:Name='DetailsPresenter' 
                                                                 primitives:SelectiveScrollingGrid.SelectiveScrollingOrientation="{Binding RelativeSource={RelativeSource AncestorType={x:Type controls:DataGrid}}, Path=AreRowDetailsFrozen, Converter={x:Static controls:DataGrid.RowDetailsScrollingConverter}, ConverterParameter={x:Static controls:SelectiveScrollingOrientation.Vertical}}"                                                                                                                         
                                                                 Visibility="{TemplateBinding DetailsVisibility}"                                                               
                                                                 />
                              <Rectangle Height="1" HorizontalAlignment="Stretch" 
                                         x:Name="BottomGridLine" 
                                         Fill="{StaticResource HorizontalVerticalGridLinesBrush}" 
                                         Grid.Column="1" Grid.Row="2" />
                          </primitives:SelectiveScrollingGrid>
                      </Border>
                      <ControlTemplate.Triggers>
                          <Trigger Property='IsSelected' Value='True'>
                              <Trigger.EnterActions>
                                  <BeginStoryboard>
                                      <Storyboard>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="Selected" Storyboard.TargetProperty="Opacity" To="0.84"/>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="SelectedHighlight" Storyboard.TargetProperty="Opacity" To="1"/>
                                      </Storyboard>
                                  </BeginStoryboard>
                              </Trigger.EnterActions>
                              <Trigger.ExitActions>
                                  <BeginStoryboard>
                                      <Storyboard>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="Selected" Storyboard.TargetProperty="Opacity" To="0"/>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="SelectedHighlight" Storyboard.TargetProperty="Opacity" To="0"/>
                                      </Storyboard>
                                  </BeginStoryboard>
                              </Trigger.ExitActions>
                              <!--<Setter Property="DetailsVisibility" Value="Visible" />-->
                          </Trigger>
                          <MultiTrigger >
                              <MultiTrigger.Conditions>
                                  <Condition Property="IsMouseOver" Value="True" />
                                  <Condition Property="IsSelected" Value="False" />
                              </MultiTrigger.Conditions>
                              <MultiTrigger.EnterActions>
                                  <BeginStoryboard>
                                      <Storyboard>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="Over" Storyboard.TargetProperty="Opacity" To="0.73"/>
                                      </Storyboard>
                                  </BeginStoryboard>
                              </MultiTrigger.EnterActions>
                              <MultiTrigger.ExitActions>
                                  <BeginStoryboard>
                                      <Storyboard>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="Over" Storyboard.TargetProperty="Opacity" To="0"/>
                                      </Storyboard>
                                  </BeginStoryboard>
                              </MultiTrigger.ExitActions>
                          </MultiTrigger>
                          <MultiTrigger>
                              <MultiTrigger.Conditions>
                                  <Condition Property="IsSelected" Value="True" />
                                  <Condition Property="IsFocused" Value="False" />
                              </MultiTrigger.Conditions>
                              <MultiTrigger.EnterActions>
                                  <BeginStoryboard>
                                      <Storyboard>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="Selected" Storyboard.TargetProperty="Opacity" To="0.84"/>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="SelectedHighlight" Storyboard.TargetProperty="Opacity" To="1"/>
                                      </Storyboard>
                                  </BeginStoryboard>
                              </MultiTrigger.EnterActions>
                              <MultiTrigger.ExitActions>
                                  <BeginStoryboard>
                                      <Storyboard>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="Selected" Storyboard.TargetProperty="Opacity" To="0"/>
                                          <DoubleAnimation Duration="0" Storyboard.TargetName="SelectedHighlight" Storyboard.TargetProperty="Opacity" To="0"/>
                                      </Storyboard>
                                  </BeginStoryboard>
                              </MultiTrigger.ExitActions>
                          </MultiTrigger>
                      </ControlTemplate.Triggers>
                  </ControlTemplate>
              </Setter.Value>
          </Setter>
      </Style>
      

      【讨论】:

        猜你喜欢
        • 2016-07-24
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多