2012-11-06 229 views
0

我有一個WPF數據網格,我已經綁定了一個observablecollection。它工作正常,但問題是我在運行時在單元級別應用樣式。下面提到了一個示例方法ApplyStyleAtCellLevelInDataGrid()。我必須調用這個方法兩次才能顯示WPF DataGrid中的樣式的效果。爲什麼會這樣......WPF Datagrid WPF樣式問題

這裏是XAML

<Style x:Key="BaseStyle" TargetType="{x:Type TextBlock}"> 
    <Setter Property="Background" Value="Transparent"/> 
    <Setter Property="Foreground" Value="Black"/>   
    <Setter Property="FontSize" Value="10"/> 
    <Setter Property="TextAlignment" Value="Center"/> 
</Style> 

<Style TargetType="{x:Type TextBlock}" x:Key="Col1Style" BasedOn="{StaticResource BaseStyle}"> 

     <Setter Property="Background"> 
      <Setter.Value> 
       <SolidColorBrush Color="Tomato"/> 
      </Setter.Value> 
     </Setter>    

     <Style.Triggers> 
      <EventTrigger RoutedEvent="Binding.TargetUpdated"> 
       <BeginStoryboard HandoffBehavior="Compose"> 
        <Storyboard TargetProperty="(TextBlock.Background).(SolidColorBrush.Color)"> 
        <ColorAnimation Duration="0:0:1.5" To="DarkRed" AutoReverse="True" RepeatBehavior="1" /> 
        </Storyboard> 
       </BeginStoryboard> 
      </EventTrigger> 
     </Style.Triggers> 
    </Style> 

<風格X:鍵= 「DGCellStyle」 的TargetType = 「{x:類型DataGridCell}」>

 <Setter Property="BorderThickness" Value="0" /> 
     <Setter Property="FontSize" Value="10"></Setter> 
     <Setter Property="Foreground" Value="Black"></Setter>   
    </Style> 

電網宣言在XAML

<DataGrid Name="dataGrid1" ItemsSource="{Binding Values}" CellStyle="{StaticResource DGCellStyle}" SnapsToDevicePixels="True" UseLayoutRounding="False"> 

    <DataGrid.Columns> 
     <DataGridTextColumn Header="Value" Binding="{Binding Value1, Mode=OneWay, NotifyOnTargetUpdated=True}" Width="0.25*"/> 
     <DataGridTextColumn Header="Value 1" Binding="{Binding Value2, Mode=OneWay, NotifyOnTargetUpdated=True}" Width="0.25*"/> 
     <DataGridTextColumn Header="Value 2" Binding="{Binding Value3, Mode=OneWay, NotifyOnTargetUpdated=True}" Width="0.25*"/> 
     <DataGridTextColumn Header="Value 3" Binding="{Binding Value4, Mode=OneWay, NotifyOnTargetUpdated=True}" Width="0.25*"/> 
    </DataGrid.Columns>   
</DataGrid> 

代碼

private void ApplyStyleAtCellLevelInDataGrid() 

    { 
     if (Values == null || Values.Count == 0) 
     { 
      Values = new ObservableCollection<MyClass>(); 
      Values.Add(new MyClass { Value1 = "1", Value4 = "2", Value2 = "4", Value3 = "3" }); 
      Values.Add(new MyClass { Value1 = "2", Value4 = "3", Value2 = "5", Value3 = "7" }); 
      Values.Add(new MyClass { Value1 = "3", Value4 = "4", Value2 = "7", Value3 = "2" }); 
      Values.Add(new MyClass { Value1 = "4", Value4 = "4", Value2 = "8", Value3 = "6" }); 
     } 
     else 
     { 
      foreach (var item in Values) 
      { 
       MyClass c = item as MyClass; 
       c.Value1 = _rand.Next(0, 100).ToString();   
       c.Value2 = _rand.Next(0, 100).ToString(); 
       c.Value3 = _rand.Next(0, 100).ToString(); 
       c.Value4 = _rand.Next(0, 100).ToString(); 
      } 
     } 

     ////////////// 

     DataGridCell cell = GetCell(1, 1); 

     Style defaultStyle = (Style)FindResource("NewStyle"); 
     ((TextBlock)cell.Content).Style = defaultStyle; 

     cell = GetCell(1, 2); 
     defaultStyle = (Style)FindResource("NewStyleExtended"); 
     ((TextBlock)cell.Content).Style = defaultStyle; 

     cell = GetCell(2, 2); 
     defaultStyle = (Style)FindResource("NewStyle"); 
     ((TextBlock)cell.Content).Style = defaultStyle; 

     cell = GetCell(2, 3); 
     defaultStyle = (Style)FindResource("Col1Style"); 
     ((TextBlock)cell.Content).Style = defaultStyle; 
    } 


private void Window_Loaded(object sender, RoutedEventArgs e) 
    {   
// Single call of this method does not work, 

I have to call two times then it shows the effect 

     ApplyStyleAtCellLevelInDataGrid(); 
     ApplyStyleAtCellLevelInDataGrid(); 
    } 

回答

0

將您的Style的TargetTypeTextBlock更改爲DataGridCell,然後將樣式應用爲DataGrid.CellStyle。由於您已將CellStyle設置爲DGCellStyle,因此您可能必須合併這兩種樣式。

另外,你需要在你的基本樣式改變TextAlignmentHorizontalAlignment因爲TextAlignment是不是你可能會感興趣的實施DataTemplateSelector的DataGridCell

<Style x:Key="BaseStyle" TargetType="{x:Type DataGridCell}"> 
    <Setter Property="Background" Value="Transparent"/> 
    <Setter Property="Foreground" Value="Black"/>   
    <Setter Property="FontSize" Value="10"/> 
    <Setter Property="HorizontalAlignment" Value="Center"/> 
</Style> 

<Style TargetType="{x:Type DataGridCell}" x:Key="Col1Style" BasedOn="{StaticResource BaseStyle}"> 
    <Setter Property="Background"> 
     <Setter.Value> 
      <SolidColorBrush Color="Tomato"/> 
     </Setter.Value> 
    </Setter>    

    <Style.Triggers> 
     <EventTrigger RoutedEvent="Binding.TargetUpdated"> 
      <BeginStoryboard HandoffBehavior="Compose"> 
       <Storyboard TargetProperty="(DataGridCell.Background).(SolidColorBrush.Color)"> 
       <ColorAnimation Duration="0:0:1.5" To="DarkRed" AutoReverse="True" RepeatBehavior="1" /> 
       </Storyboard> 
      </BeginStoryboard> 
     </EventTrigger> 
    </Style.Triggers> 
</Style> 

而且

<DataGrid CellStyle="{StaticResource Col1Style}" ... /> 
+0

感謝您的回答,但我的郵件的問題是,爲什麼我叫ApplyStyleAtCellLevelInDataGrid() ;在Window_Loaded事件中使用2次來顯示樣式的效果?調用它一次不會在屏幕上顯示任何東西 –

+0

@AsadNaeem我最好的猜測是它與WPF的[DispatcherPriority](http://msdn.microsoft.com/en-us/library/system.windows.threading)有關。 dispatcherpriority.aspx),並且第一次運行是創建'Grid'綁定的'Values'集合,並且DataGrid項目還沒有完成渲染,或者在渲染過程和覆蓋過程中應用了默認樣式你的自定義風格,所以這就是爲什麼需要第二次運行。不過,如果不設置測試場景,我也不會知道。 – Rachel

0

屬性。該對象用於在任何數據項上提供顯示邏輯。

這裏有一個快速教程:​​

+0

感謝您的答案,但我的郵件問題是,爲什麼我要調用ApplyStyleAtCellLevelInDataGrid();在Window_Loaded事件中顯示風格的效果?調用一次在屏幕上不顯示任何內容 –

+0

我不知道。但是在WPF中有一些接口是爲了修改基於自定義邏輯的樣式而不使用它們。我的回答是:如果您在處置時使用了工具而不是繞過它,那麼您甚至不需要使用「ApplystyleAtCellLevel」函數。 – Joe

0

在App.xaml中的應用程序標記添加

"xmlns:dg="http://schemas.microsoft.com/wpf/2008/toolkit"

<Application.Resources>標籤中添加代碼

<Style x:Key="ColumnHeaderStyle" TargetType="{x:Type dg:DataGridColumnHeader}"> 
    <Setter Property="HorizontalAlignment" Value="Center" /> 
</Style> 

<Style x:Key="CellRightAlign" TargetType="{x:Type dg:DataGridCell}"> 
    <Setter Property="HorizontalAlignment" Value="Right" /> 
</Style> 

現在落後的AutoGeneratedColumns事件添加到您的DataGrid

Style RightAlign = (Style)FindResource("CellRightAlign"); 
yourGrid.Columns[0].CellStyle = RightAlign;