Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Wpf-АК11.doc
Скачиваний:
3
Добавлен:
01.03.2025
Размер:
3.47 Mб
Скачать

4. Метаданныесвойствзависимости

Класс FrameworkPropertyMetadata наследуетсяоткласса PropertyMetadata, идлябольшинствацелейразработкиприложенийуровняплатформы WPF вкачествеметаданныхсвойствиспользуетсятип FrameworkPropertyMetadata, анебазовыетипыметаданных PropertyMetadata или UIPropertyMetadata. Это касается сценариев как с имеющимися, так и с пользовательскими свойствами зависимости.

При каждом определении регистрации и добавления или присоединения свойства зависимости необходимо предоставить экземпляр класса FrameworkPropertyMetadata. Так мы информируем систему свойств WPF о необходимости особым образом обращаться со свойством зависимости, использующим этот экземпляр FrameworkPropertyMetadata. (рис. 6.10)

Рис. 6.10 - …

С помощью класса FrameworkPropertyMetadata можно предоставить системе свойств следующую информацию:

  • значения по умолчанию;

  • одноиззначений FrameworkPropertyMetadataOptions, например AffectsMeasure/AffectsArrange/AffectsRender/Inherits ит. д.;

  • делегаты обратного вызова измененных свойств;

  • приведенные значения;

  • отмена поддержки анимации для свойства;

  • предоставление одного из событий UpdateSourceTrigger, например PropertyChanged, LostFocus, Explicit и т. д.

Всего один экземпляр FrameworkPropertyMetadata дает жесткий контроль над множеством метаданных свойства зависимости.

Проверка и обратные вызовы свойства зависимости и приведенные значения. У вас, наверное, могло сложиться мнение, что свойства зависимости довольно сложные и мощные. Но не следует забывать еще о нескольких принципах. Вот они:

  • обратные вызовы для тех случаев, когда изменяется свойство зависимости;

  • приведенные значения для изменения неприемлемого значения свойства зависимости;

  • проверка допустимости значения.

Использование делегатов при первой регистрации свойства зависимости решает большинство из перечисленных задач. В состав прилагаемого решения (вверху статьи) входит проект Callback_Validation_DPs, демонстрирующий эти принципы. По сути, есть класс Gauge, наследуемый от класса Control, с тремя свойствами зависимости:

  • CurrentReading

  • MinReading

  • MaxReading

Каждое из них предназначено для проверки допустимости. Значение CurrentReading сравнивается со значениями свойств зависимости MinReading и MaxReading и при необходимости приводится. Рассмотрим пример применения этих свойств.

Рис. 6.11 - Демонстрационное приложение

При работе демонстрационное приложение выглядит так (рис. 6.11).

Обратные вызовы и приведенные значения для случаев, когда изменяется свойство зависимости. Свойствозависимости CurrentReading объявляетсятак.

public static readonly DependencyProperty CurrentReadingProperty =

   DependencyProperty.Register(

   "CurrentReading",

   typeof(double),

   typeof(Gauge),

   new FrameworkPropertyMetadata(

       Double.NaN,

       FrameworkPropertyMetadataOptions.None,

       new PropertyChangedCallback(OnCurrentReadingChanged),

       new CoerceValueCallback(CoerceCurrentReading)

   ),

   new ValidateValueCallback(IsValidReading)

);

Объект объявляется CoerceValueCallbackс делегатом, указывающим на метод CoerceCurrentReading, при объявлении которого свойство CurrentReadingсравнивается со свойствами зависимости Min/Maxи приводится при необходимости. Также обратите внимание на объявление объекта PropertyChangedCallbackс делегатом, указывающим на метод OnCurrentReadingChanged, который, в свою очередь, обеспечивает при необходимости приведение свойств зависимости Min/Max. В основном это делается для того, чтобы свойство зависимости Minбыло меньше Max и аналогично для свойства зависимости Max. В моем примере свойства зависимости Min/Maxна самом деле не изменяются, но я хотел показать, как это делается на случай, если это вам понадобится.

private static void OnCurrentReadingChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)

{

   d.CoerceValue(MinReadingProperty); //вызовделегата CoerceValueCallback ("CoerceMinReading")

   d.CoerceValue(MaxReadingProperty); //вызовделегата CoerceValueCallback ("CoerceMaxReading")

}

...

...

...

///

/// Приведение значения Coerce CurrentReading, если оно выходит за допустимые пределы

///

private static object CoerceCurrentReading(DependencyObject d, object value)

{

   Gauge g = (Gauge)d;

   double current = (double)value;

   if (current < g.MinReading) current = g.MinReading;

   if (current > g.MaxReading) current = g.MaxReading;

   return current;

}

Здесь происходит приведение значения свойства зависимости CurrentReading в диапазоне от MinReadingи MaxReading, при этом выполняется условие Min < Max и Max > Min. Так что мы никогда не выйдем за привязанные значения для любого из этих трех свойств зависимости.

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]