2011-11-17 49 views
4

我有一个名为item的类,它只包含两个属性。我将在屏幕上将它们显示为具有样式的按钮。这个问题涉及我如何根据IsSelected值来设置按钮的样式,当我想要影响的元素的样式不是数据模板时。我已经尝试过使用触发器,但无法启动它。使用数据模板中的样式

该课程如下。

public class Item : ObservableObject 
{ 
    private string _title; 
    private bool _isSelected; 

    public string Title 
    { 
     get { return _title; } 
     set 
     { 
      _title = value; 
      RaisePropertyChanged("Title"); 
     } 
    } 

    public bool IsSelected 
    { 
     get { return _isSelected; } 
     set 
     { 
      _isSelected = value; 
      RaisePropertyChanged("IsSelected"); 
     } 
    } 
} 

我使用数据模板在ItemsControls中显示这些项目。

<ItemsControl ItemsSource="{Binding Path=Items}" ItemTemplate="{StaticResource ResourceKey=ItemTemplate}"> 
     <ItemsControl.ItemsPanel> 
      <ItemsPanelTemplate> 
       <StackPanel Orientation="Horizontal" /> 
      </ItemsPanelTemplate> 
     </ItemsControl.ItemsPanel> 
    </ItemsControl> 

使用以下样式和数据模板。

<Style x:Key="ItemButton" TargetType="Button"> 
    <Setter Property="Template"> 
     <Setter.Value> 
      <ControlTemplate TargetType="{x:Type Button}"> 
       <Border Name="ButtonBorder" BorderThickness="2,2,2,0" BorderBrush="#AAAAAA" CornerRadius="6,6,0,0" Margin="2,20,0,0" Background="Black"> 
        <ContentPresenter 
          VerticalAlignment="Center" 
          HorizontalAlignment="Center"/> 
       </Border> 
      </ControlTemplate> 
     </Setter.Value> 
    </Setter> 
</Style> 
<DataTemplate x:Key="ItemTemplate"> 
    <Button Height="60" Style="{StaticResource ItemButton}" Name="Button"> 
     <StackPanel Orientation="Horizontal"> 
      <TextBlock Text="{Binding Path=Title}" 
         HorizontalAlignment="Left" Margin="5,5,5,3" FontSize="25" Foreground="#6B6B6B" FontFamily="Arial" /> 
       <Button Style="{StaticResource NoChromeButton}" Margin="0,0,5,0"> 
       <Button.Content> 
        <Image Height="20" Source="/WpfApplication1;component/Image/dialogCloseButton.png"></Image> 
       </Button.Content> 
       <Button.ToolTip> 
        Close  
       </Button.ToolTip> 
      </Button> 
     </StackPanel> 
    </Button> 
</DataTemplate> 

我需要在IsSelected为True时将对象Item中的“ButtonBorder”背景从黑色更改为白色。

我已经在触发加在数据模板 这是不行的,我想它,因为样式覆盖DataTemplate中,因此背景保持白色。但是,当我尝试在样式中执行触发器时,我无法访问IsSelected属性?

的DataTemplate触发

<DataTemplate.Triggers> 
     <DataTrigger Binding="{Binding IsSelected}" Value="True"> 
      <Setter TargetName="Button" Property="Background" Value="White"/> 
     </DataTrigger> 
    </DataTemplate.Triggers> 

风格触发

<Style.Triggers> 
     <DataTrigger Binding="{Binding IsSelected}" Value="True"> 
      <Setter Property="Background" Value="White"/> 
     </DataTrigger> 
    </Style.Triggers> 

我这么想吗?

+0

如果'ItemButton'仅用于'Item'对象,那么你为什么不只是巩固风格融入'Item'的DataTemplate? –

+0

这是一个公平的评论,我已经习惯了将所有东西都分开到个人资源的习惯,不确定它是否是一种好习惯,但我坚持认为:) – JonWillis

+0

@jberger它也使得资源和UI布局更易于阅读并修改它们是否与内嵌模板和样式不混淆。 – Rachel

回答

8

让你ButtonBorder.Background{TemplateBinding Background},这意味着它将使用任何背景颜色被分配到模板按钮,然后就可以根据触发

<Style x:Key="ItemButton" TargetType="Button"> 
    <Setter Property="Background" Value="Black" /> 
    <Setter Property="Template"> 
     <Setter.Value> 
      <ControlTemplate TargetType="{x:Type Button}"> 
       <Border Name="ButtonBorder" Background="{TemplateBinding Background}" ... > 
        <ContentPresenter ... "/> 
       </Border> 
      </ControlTemplate> 
     </Setter.Value> 
    </Setter> 
</Style> 

<Style x:Key="SelectableItemButton" TargetType="Button" BasedOn="{StaticResource ItemButton}"> 
    <Setter Property="Background" Value="Black" /> 
    <Style.Triggers> 
     <DataTrigger Binding="{Binding IsSelected}" Value="True"> 
      <Setter Property="Background" Value="White"/> 
     </DataTrigger> 
    </Style.Triggers> 
</Style> 

<DataTemplate x:Key="ItemTemplate"> 
    <Button Height="60" Style="{StaticResource SelectableItemButton}"> 
     ... 
    </Button> 
</DataTemplate> 
更改按钮的背景

我也做一个SelectableItemButton风格,从ItemButton继承,并刚刚实现了扳机

+0

这工作的一种享受,我忘了TemplateBinding来自有限的时间与WPF一起工作。但是{Binding IsSelected}是如何知道它与我的对象相关的,而不是像其他GUI控件一样被选中,如复选框。 – JonWillis

+1

@JonWillis由于您使用的是DataTrigger,如果该值存在并且为True,则该绑定将查看'Button.DataContext.IsSelected'并更改背景颜色。你可以在技术上做一个Button并给它一个CheckBox对象的DataContext,它可能会工作,虽然我不会推荐:) – Rachel

0

不宜目标是“ButtonBorder”,而不是“按钮”中:

<Setter TargetName="Button".... 

此外,要访问IsSelected你需要设置样式中TargetType财产....

+0

你是对的我错了,但是。 TargetName不起作用。在DataTemplate中ButtonBorder不存在,因为该名称在样式中定义。在样式中,TargetName不是在触发器中使用的有效属性(所以Visual Studio告诉我)。 – JonWillis

+0

TargetType在样式上设置,它被设置为“Button”。数据模板创建一个按钮及其中的内容,然后它创建的按钮将应用ItemButton样式。 – JonWillis

相关问题