2015-12-08 3 views
0

Итак, моя проблема в том, что у меня есть пользовательский элемент управления. В xaml я привязываю некоторые цвета к свойствам цвета, которые я создал, как показано ниже.User Control DataContext/Binding Issue with Dependency Property WPF

<GradientStop x:Name="stop1" Color="{Binding Color1}" Offset="0"/> 
<GradientStop x:Name="stop2" Color="{Binding Color2}" Offset="1"/> 

В моем коде позади у меня есть DependencyProperty, который я объявил, как показано ниже.

public static readonly DependencyProperty IsActiveProperty = DependencyProperty.Register("IsActive", typeof(bool), typeof(Bin), 
new PropertyMetadata(new PropertyChangedCallback(Bin.IsActivePropertyChanged))); 

Свойство зависимость имеет PropertyChangedCallback, что он называет называемый IsActivePropertyChanged, как показано ниже.

private static void IsActivePropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) 
{ 
      Bin b = (Bin)d; 
      if((bool)e.NewValue) 

      { 
       b.Color1 = Color.FromArgb(0xFF, 0x3E, 0x3E, 0x3E); 
       b.Color2 = Colors.Red; 
       b.Color3 = Colors.Red; 
       b.Color4 = Color.FromArgb(0xFF, 0xFF, 0xFF, 0xFF); 
      } 
      else 
      { 
       b.Color1 = Color.FromArgb(0xFF, 0x3E, 0x3E, 0x3E); 
       b.Color2 = Color.FromArgb(0xFF, 0x83, 0x83, 0x83); 
       b.Color3 = Color.FromArgb(0xFF, 0x63, 0x63, 0x63); 
       b.Color4 = Color.FromArgb(0xFF, 0xFF, 0xFF, 0xFF); 
      } 
     } 

Если я использую конструктор ниже, цвет меняется внутри конструктора прекрасно работают, однако, мой IsActivePropertyChangedEvent никогда не увольняют. Я предполагаю из-за назначения DataContext в конструкторе.

public Bin() 
     { 
      Color1 = Color.FromArgb(0xFF, 0x3E, 0x3E, 0x3E); 
      Color2 = Color.FromArgb(0xFF, 0x83, 0x83, 0x83); 
      Color3 = Color.FromArgb(0xFF, 0x63, 0x63, 0x63); 
      Color4 = Color.FromArgb(0xFF, 0xFF, 0xFF, 0xFF); 
      InitializeComponent(); 
      DataContext = this; 
     } 

Если я закомментируйте задание DataContext и использовать конструктор ниже, мои цвета задание не работает, но IsActivePropertyChanged событие срабатывает отлично.

public Bin() 
      { 
       Color1 = Color.FromArgb(0xFF, 0x3E, 0x3E, 0x3E); 
       Color2 = Color.FromArgb(0xFF, 0x83, 0x83, 0x83); 
       Color3 = Color.FromArgb(0xFF, 0x63, 0x63, 0x63); 
       Color4 = Color.FromArgb(0xFF, 0xFF, 0xFF, 0xFF); 
       InitializeComponent(); 
       //DataContext = this; 
      } 

Мой вопрос в том, как я могу заставить привязку работать правильно и у меня есть огонь по событию. Я попытался установить DataContext="{Binding RelativeSource={RelativeSource Self}}" (вместо установки DataContext в коде позади) элементов, привязанных к свойствам цвета в XAML, прямоугольнику и полигону, но это, похоже, не работает. Заранее благодарю за любую помощь.

+1

При написании собственного контроля вы не должны связываться с 'DataContext' самого элемента управления. Вместо этого, при связывании GradientStop вы можете использовать 'RelativeSource = {RelativeSource AncestorType = Bin}' (предполагая, что 'Bin' является вашим контролем). Или вы можете определить шаблон и использовать 'TemplateBinding'. Проверьте [этот ответ] (http://stackoverflow.com/questions/30476263/dependency-property-datacontext/30496202#30496202) Я написал некоторое время назад для аналогичного вопроса. – vesan

+0

_ «мой IsActivePropertyChangedEvent никогда не срабатывает» _ - тогда никто его не меняет. Невозможно сказать, действительно ли это имеет какое-либо отношение к вашему «DataContext», поскольку вы не показали, как свойство будет изменено. Я могу сказать, что из небольшого кода, который вы опубликовали, кажется, что вы должны использовать триггер XAML для изменения значений цвета, а не кода. Пожалуйста, предоставьте хороший [mcve], который надежно воспроизводит вашу проблему, а также точное описание того, что делает этот код и как это отличается от того, что вы хотите. –

+0

Я изменяю свойство IsActive из своего видаModel в своем основном приложении. Как я уже сказал выше, он срабатывает каждый раз, если я удаляю строку dataContext в конструкторе, но не тогда, когда я держу эту строку. @vesan Я попробую это, когда я получу сегодня утром. – ProgrammingDude

ответ

1

При написании собственного контроля вы не должны связываться с самим элементом управления DataContext.

Вместо этого, при привязке GradientStop, вы можете использовать RelativeSource={RelativeSource AncestorType=Bin} (предполагая, что Bin - ваш контроль). Или вы можете определить шаблон и использовать TemplateBinding. Check this answer Я написал некоторое время назад для аналогичного вопроса - он имеет более подробное описание того, как это работает.