Сбрасываемая RangeBase (Slider) в WPF

1

Я реализовал пользовательский слайдер, который происходит из RangeBase, который имеет добавленное свойство ResetValue, которое можно использовать для сброса значения в начальное значение. К сожалению, для этого требуется двойное связывание источника значений, а также использование режима привязки OneTime для ResetValue.

<ButtonSlider
        Minimum="0" Maximum="500" TickFrequency="1"
        Value="{Binding Path=MaxVoltageUv}"
        ResetValue="{Binding Path=MaxVoltageUv, Mode=OneTime}" />

В идеале у него было бы свойство логической зависимости CanReset, которое бы захватило ResetValue при первом связывании, если оно было включено. Я попытался реализовать его, захватив первый параметр Value, но по какой-то причине это работает только некоторое время.

Сначала он переопределяет метаданные в ValueProperty:

        ValueProperty.OverrideMetadata(typeof(ButtonSlider), new FrameworkPropertyMetadata(OnValueChanged, OnCoerceValue));

А затем реализует измененные обработчики пользовательских транзакций и значений.

    private static void OnValueChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        var buttonSlider = ((ButtonSlider)d);
        if (buttonSlider != null)
        {
            if (!buttonSlider.valueInitialized && e.NewValue is double)
            {
                buttonSlider.resetValue = (double)e.NewValue;
                buttonSlider.valueInitialized = true;
            }

            buttonSlider.CheckResetEnabled();
        }
    }

    private static object OnCoerceValue(DependencyObject d, object baseValue)
    {
        var buttonSlider = ((ButtonSlider)d);
        if (buttonSlider != null)
        {
            if(baseValue is double)
                return Math.Max(Math.Min((double)baseValue, buttonSlider.Maximum), buttonSlider.Minimum);
        }

        return DependencyProperty.UnsetValue;
    }

По какой-то причине OnValueChanged вызывается со значением 0, а исходное связывание должно быть равным 2. Это, по-видимому, связано с шаблонами данных. Элементы управления, которые не находятся в шаблоне данных, работают правильно.

Есть ли другой способ захватить начальное значение свойства зависимостей?

Теги:
wpf
custom-controls

2 ответа

0

Если в XAML установлены как контекст данных, так и привязка, вы можете использовать событие Loaded вашего настраиваемого элемента управления, чтобы сохранить текущее значение в качестве значения сброса. Это также будет работать, если ваш элемент управления находится в шаблоне данных, например.

Если контекст данных задан из кода, это будет работать, только если оно установлено до того, как элемент управления будет добавлен в логическое дерево.

0

Мои мысли

  • Убедитесь, что MaxVoltageUv которому вы привязываетесь, является двойным.
  • Удалите свойство зависимостей ResetValue это просто создает шум при попытке решить эту проблему.
  • 0 может быть значением по умолчанию для свойства зависимостей, которое устанавливается перед фактическим привязкой. Почему бы не поместить в -1.0 по умолчанию вместе с логикой в OnValueChanged чтобы обнаружить этот сценарий и проигнорировать до тех пор, пока не произойдет надлежащее значение.
  • 0
    Проблема тогда состоит в том, что начальное значение / значение сброса 0 не будет работать, потому что оно не различимо от значения 0, которое проявляется при использовании преобразования данных.
  • 0
    @Wouter Именно поэтому позже я указал, что элемент управления может установить свое начальное значение на -1, и если элемент управления видит это значение, он уходит в ноль для фактического отображения.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню