在DataTemplate中更改ELEMENT的背景

时间:2017-04-27 05:56:09

标签: c# wpf xaml

我看过网上发现了一些与我的问题有关的话题,虽然他是XAML和WPF的新手,但是我很难做出我想要的工作。

我有一个自定义的TimeLineControl StackPanel,它包含TimeLineFunctionControl类型的'Items',其中Items使用DataTemplate来定义'Items'的显示方式。

  <!-- Static Resource = BgColor -->
  <Color R="255" G="255" B="255" A="180" x:Key="BgColor" />

  <!-- Static Resource = BgBrush -->
  <SolidColorBrush Color="{DynamicResource BgColor}" x:Key="BgBrush" />

  <!-- DataTemplate = TimeLineFunctionDataTemplate -->
  <DataTemplate  DataType="{x:Type tt:FunctionDataType}" 
                 x:Key="TimeLineFunctionDataTemplate">
     <Border x:Name="DataContainer"
        BorderThickness="0.3"
        BorderBrush="Black" 
        CornerRadius="2" 
        Margin="0,20,0,10" 
        Height="50" 
        Background="{DynamicResource BgBrush}">
        <StackPanel Orientation="Vertical">
           <TextBlock Text="{Binding Path=Name}" FontWeight="Bold"/>
           <TextBlock Text="{Binding Path=StartTime.TotalMilliseconds, StringFormat={}{0} ms}" FontSize="8"/>
           <TextBlock Text="{Binding Path=EndTime.TotalMilliseconds, StringFormat={}{0} ms}" FontSize="8"/>
        </StackPanel>
     </Border>
  </DataTemplate>

public class FunctionDataType : ITimeLineDataItem
{
    public TimeSpan? StartTime { get; set; }
    public TimeSpan? EndTime { get; set; }
    public Boolean TimelineViewExpanded { get; set; }
    public String Name { get; set; }
}

我希望能够在代码中动态更改Border(DataContainer)的背景颜色。

我尝试了以下内容;

1 - 不起作用,我已经了解到,一旦应用了模板,就不再使用Background属性了。

titem.Background = (Brush)FindResource("BgBrushTriggered");

2 - Works,虽然我需要在XAML中定义两(2)个DataTemplate,每个都有不同的背景颜色,但似乎必须有更好的方法来实现它。

titem.ContentTemplate = (DataTemplate)FindResource("TimeLineFunctionDataTriggeredTemplate");

3 - Works,虽然它会更改所有项目,因为我正在更改DynamicResource值。

this.Resources["BgBrush"] = new SolidColorBrush((Color)FindResource("BgColorTriggered"));

4 - 不起作用,XAML报告“会员”背景“无法识别或无法访问”;

Background="{TemplateBinding Background}"


Background="{Binding Background, RelativeSource={RelativeSource TemplatedParent}"

问:我的选择是什么?

问:是否有一个很好的在线资源来正确学习XAML,现在应用绑定,样式,模板等......

2 个答案:

答案 0 :(得分:1)

执行此操作的正确方法是将Background的{​​{1}}属性绑定到Border对象的属性,然后设置您想要的特定项的此属性变化

您既可以直接绑定到FunctionDataType属性,也可以定义其他类型的属性,并使用转换器将此值转换为Brush。 FunctionDataType必须实现INotifyPropertyChanged接口才能使其正常工作。

请参阅以下示例代码。

Brush
<DataTemplate DataType="{x:Type tt:FunctionDataType}" 
              x:Key="TimeLineFunctionDataTemplate">
    <Border x:Name="DataContainer"
        BorderThickness="0.3"
        BorderBrush="Black" 
        CornerRadius="2" 
        Margin="0,20,0,10" 
        Height="50" 
        Background="{Binding BgBrush}">
        <StackPanel Orientation="Vertical">
            <TextBlock Text="{Binding Path=Name}" FontWeight="Bold"/>
            <TextBlock Text="{Binding Path=StartTime.TotalMilliseconds, StringFormat={}{0} ms}" FontSize="8"/>
            <TextBlock Text="{Binding Path=EndTime.TotalMilliseconds, StringFormat={}{0} ms}" FontSize="8"/>
        </StackPanel>
    </Border>
</DataTemplate>
public class FunctionDataType : ITimeLineDataItem, INotifyPropertyChanged
{
    public TimeSpan? StartTime { get; set; }
    public TimeSpan? EndTime { get; set; }
    public Boolean TimelineViewExpanded { get; set; }
    public String Name { get; set; }

    private Brush _bgBrush;
    public Brush BgBrush
    {
        get { return _bgBrush; }
        set { _bgBrush = value; NotifyPropertyChanged(); }
    }

    public event PropertyChangedEventHandler PropertyChanged;
    private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
    {
        if (PropertyChanged != null)
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }
}

答案 1 :(得分:0)

你可以在你的模型ItemColorIndex中使用一个属性,然后通过转换器将背景绑定到它背景=“{Binding ItemColorIndex,Converter = XXX}