В течение многих часов я исследовал следующую ситуацию: у меня есть окно, определенное xaml, которое использует usercontrol (ToggleButton) с некоторыми свойствами зависимостей.
Базовая модель представления окна содержит некоторые логические объекты, которые представляют состояние устройств (вкл / выкл), а другие представляют запрос на переключение устройства с истинным / ложным флангом (к ним подключен ПЛК, и связь работает нормально ).
Следовательно, в пользовательском контроле есть 2 DP:
Тот, который переключает устройства (режим привязки OneWayToSource с UpdateSourceTrigger.Explicit работает нормально (показывая мне, что основы, такие как общий DataContext, хороши и нигде не "нарушены").
Однако привязка, указывающая другой DP (состояние устройства с режимом привязки OneWay), показывает следующие признаки:
Устройство (PLC-) выключено (ложно) перед запуском программы
Результат: По умолчанию для свойства DeviceState установлено значение false.
Set вызывается впервые при включении устройства
(базовый объект viewmodel изменяется на true, сообщает об этом через
PropertyChanged уведомление) и DependencyPropertyChanged является
вызывается правильно. Далее переключается на выкл / вкл (ложь / истина)
снова не приводит к повторному вызову "set" (хотя
PropertyChanged на базовый объект снова вызывается).
Устройство включено (true) перед запуском программы
Результат: Обработчик DP запускается в
начало программы и без изменений
false или true позволяет вызывать его снова.
Я уже пытался отследить это:
Реализован DummyDebugConverter .
Результат: я вижу, что он также выстрелил только один раз. Так что не давая мне никакой дополнительной подсказки
Проанализировал окно вывода и обнаружил следующее сообщение:
Информация System.Windows.Data: 21: BindingExpression не может получить значение из нулевого элемента данных. Это может произойти, когда привязка отсоединена или когда связывается с типом Nullable, который не имеет значения. BindingExpression: Path = bLightState.Value; DataItem = 'ControlPanelModel' (HashCode = 45596481); целевой элемент - AdsButton (Name = 'btnLight'); Свойство target - DeviceState (тип Boolean)
Отладка этого не дала мне подсказку. Мои контрольные точки, например в отладочном конвертере или методе set нигде не показывал мне нулевое значение. Все значения в конструкторе viewmodel инициализируются значениями по умолчанию. Но я вижу сообщение всегда только один раз и полагаю, что оно как-то связано с проблемой.
Использовал то же выражение привязки для целей тестирования на некоторых других элементах (метка и кнопка переключения) помимо моего usercontrol. Они работают хорошо и обновляют свои значения, как и ожидалось, как только объект в модели представления изменяется (желаемое поведение). Сообщение в 2 не удовлетворяет, если я удалю свой пользовательский контроль.
Итак, я прихожу к выводу, что ошибка в моем определении DP.
Вот соответствующие фрагменты кода:
AdsButton.xaml.cs
[Description("When set to true the device is shown as on"), Category("Default")]
public bool DeviceState
{
get { return (bool)GetValue(DeviceStateProperty); }
set { SetValue(DeviceStateProperty, value); }
}
public static readonly DependencyProperty DeviceStateProperty =
DependencyProperty.Register(
"DeviceState", typeof(bool),
typeof(AdsButton),
new FrameworkPropertyMetadata(
false,
FrameworkPropertyMetadataOptions.None,
DeviceStateChanged,
CoerceDeviceStateProperty,
true,
UpdateSourceTrigger.Explicit));
private static void DeviceStateChanged(DependencyObject d,
DependencyPropertyChangedEventArgs e)
{
(d as AdsButton).DeviceState = (bool) e.NewValue;
}
private static object CoerceDeviceStateProperty(DependencyObject d, object value)
{
return value ?? false;
}
ControlPanel.xaml
<src:AdsButton x:Name="btnLight"
Value="{Binding Path=bLight.Value, Mode=OneWayToSource}"
DeviceState="{Binding Path=bLightState.Value, Mode=OneWay}" />
<Label Content="{Binding bLightState.Value, Mode=OneWay}" />
<ToggleButton Content="Button" IsChecked="{Binding bLightState.Value, Mode=OneWay}" />
Так кто-нибудь знает: почему мой собственный DP реагирует иначе, чем в стандартных элементах управления?