Присоединенное свойство не работает, если я не поставлю "Свойство" в конце его имени
У меня есть простое прикрепленное свойство:
class TestAttached
{
public static readonly DependencyProperty TestProperty = DependencyProperty.RegisterAttached("TestProperty", typeof(string), typeof(TestAttached));
public static string GetTest(DependencyObject d)
{
return (string)d.GetValue(TestProperty);
}
public static void SetTest(DependencyObject d, string value)
{
d.SetValue(TestProperty, value);
TextBox tb = d as TextBox;
tb.Text = value;
}
}
а также
<TextBox local:TestAttached.Test="Test" />
Ничего не происходит, и ни одна точка останова не достигнута SetTest
) если я не установил первый параметр RegisterAttached
"TestProperty" вместо "Test". Ни один учебник, который я нашел, в том числе и по MSDN, этого не делает, и, насколько я могу судить, мой код такой же, как у них, и должен работать. Что дает?
1 ответ
Когда свойство Dependency устанавливается / устанавливается через XAML, метод-обертка никогда не вызывается. Таким образом, вы должны избегать написания кода там.
Из MSDN:
Текущая реализация WPF поведения процессора XAML для установки свойств полностью обходит оболочки, вам не следует помещать какую-либо дополнительную логику в определения набора оболочек для вашего пользовательского свойства зависимости. Если вы поместите такую логику в определение набора, то эта логика не будет выполняться, когда свойство задано в XAML, а не в коде.
Вместо этого вы можете использовать PropertyChangedCallback
в случае, если вы хотите поместить некоторый код на изменение свойства DP.
public static readonly DependencyProperty TestProperty =
DependencyProperty.RegisterAttached("Test", typeof(string),
typeof(TestAttached),
new PropertyMetadata(TestChanged));
public static void TestChanged(DependencyObject d,
DependencyPropertyChangedEventArgs e)
{
// Place your code here
}
ОБНОВИТЬ
Но если я изменю имя на "TestProperty", то точка останова попадет в SetTest.
Причина этого заключается в следующем: Test
теперь ведет себя как обычное свойство CLR. Свойство - это не что иное, как методы Get/Set, когда вы переходите к IL-коду.
Вот почему сеттер получает удар, как и для обычного свойства CLR.
Если вы попытаетесь связать с каким-либо другим свойством,
<TextBox local:TestAttached.Test="{Binding SomeCLRProperty}" />
вы увидите сбой приложения, заявив:
"Связывание" не может быть установлено в свойстве "SetTest" типа "TextBox". "Связывание" может быть установлено только для свойства DependencyObject объекта DependencyObject.