We need certain vector graphics to change the color of certain elements in the graphics at runtime. It would seem that setting these colors based on static or dynamic resource values would not work. We want to have several versions of the same graphics, each of which has the ability to set certain graphic elements (Path, Line, etc.) to different colors, so I don’t think that a dynamic approach to resources will work. This leaves a data binding that seems correct. We are updating the graphics to use expr data binding instead of the hard-coded brush color:
<DrawingImage x:Key="Graphic1"> <DrawingImage.Drawing> <DrawingGroup> <DrawingGroup.Children> <GeometryDrawing Geometry="F1 M 8.4073,23.9233L"> <GeometryDrawing.Pen> <Pen LineJoin="Round" Brush="{Binding Line1Brush, Mode=OneWay}"/> </GeometryDrawing.Pen> </GeometryDrawing> <GeometryDrawing Geometry="F1 M 3.6875,2.56251L"> <GeometryDrawing.Pen> <Pen LineJoin="Round" Brush="{Binding Line2Brush, Mode=OneWay}"/> </GeometryDrawing.Pen> </GeometryDrawing> </DrawingGroup.Children> </DrawingGroup> </DrawingImage.Drawing> </DrawingImage>
Then we create an instance of the view model object (supporting INotifyPropertyChanged) for each instance of Graphic1 in this case and make sure that it has the Line1Brush and Line2Brush . Sounds good, but I can't get it to work. I assume this graphic, which is itself defined in the resource dictionary for Image objects, and I try to set their DataContext , and I get a data binding error in the Debug window. Here is the XAML image:
<Image x:Name="Pulse1" Grid.Column="0" Source="{StaticResource Graphic1}"/> <Image x:Name="Pulse2" Grid.Column="1" Source="{StaticResource Graphic1}"/>
And then in the Window Initialize method, I set my data context as follows:
public MainWindow() { InitializeComponent(); this.DataContext = this; this.PulseImage1 = new PulseImageViewModel(); this.PulseImage2 = new PulseImageViewModel(); this.PulseImage2.Line1Brush = Brushes.Green; this.PulseImage2.Line2Brush = Brushes.Red; this.Pulse1.DataContext = this.PulseImage1; this.Pulse2.DataContext = this.PulseImage2; }
Where PulseImageViewModel (shown below) defines two properties Line1Brush and Line2Brush , each of which fires a PropertyChanged event.
public class PulseImageViewModel : INotifyPropertyChanged { private Brush _line1Brush = Brushes.Yellow; private Brush _line2Brush = Brushes.Black; public event PropertyChangedEventHandler PropertyChanged; public Brush Line1Brush { get { return _line1Brush; } set { if (_line1Brush != value) { _line1Brush = value; NotifyPropertyChanged("Line1Brush"); } } } public Brush Line2Brush { get { return _line2Brush; } set { if (_line2Brush != value) { _line2Brush = value; NotifyPropertyChanged("Line2Brush"); } } } private void NotifyPropertyChanged(string propertyName) { var del = PropertyChanged; if (del != null) { del(this, new PropertyChangedEventArgs(propertyName)); } } }
However, I get data binding errors indicating that WPF is looking for Line1Brush in the top-level MainWindow object, and not on my PulseImageViewModel object. Any thoughts on what I'm doing wrong, or if there is a better way to accomplish my task of dynamically changing colors on a vector graphic? In addition, it would be nice if, by default, the graphics could have a good static set of colors, if the user had not connected the view model object.