Search code examples
windows-8winrt-xaml

How can I detect when the XAML Slider is Completed?


In XAML I have the <Slider />. It has the ValueChanged event. This event fires with every change to Value. I need to detect when the value change is over. LostFocus, PointerReleased are not the correct event. How can I detect this?


Solution

  • You can create a new class and inherit from Slider. From there on, you can look for the Thumb control & listen for the events you want.

    Something like this should work:

    public class SliderValueChangeCompletedEventArgs : RoutedEventArgs
    {
        private readonly double _value;
    
        public double Value { get { return _value; } }
    
        public SliderValueChangeCompletedEventArgs(double value)
        {
            _value = value;
        }
    }
    public delegate void SlideValueChangeCompletedEventHandler(object sender, SliderValueChangeCompletedEventArgs args);
    
    public class ExtendedSlider : Slider
    {
        public event SlideValueChangeCompletedEventHandler ValueChangeCompleted;
        private bool _dragging = false;
    
        protected void OnValueChangeCompleted(double value)
        {
            if (ValueChangeCompleted != null)
            {
                ValueChangeCompleted(this, new SliderValueChangeCompletedEventArgs(value) );
            }
        }
    
        protected override void OnApplyTemplate()
        {
            base.OnApplyTemplate();
            var thumb = base.GetTemplateChild("HorizontalThumb") as Thumb;
            if (thumb != null)
            {
                thumb.DragStarted += ThumbOnDragStarted;
                thumb.DragCompleted += ThumbOnDragCompleted;
            }
            thumb = base.GetTemplateChild("VerticalThumb") as Thumb;
            if (thumb != null)
            {
                thumb.DragStarted += ThumbOnDragStarted;
                thumb.DragCompleted += ThumbOnDragCompleted;
            }
        }
    
        private void ThumbOnDragCompleted(object sender, DragCompletedEventArgs e)
        {
            _dragging = false;
            OnValueChangeCompleted(this.Value);
        }
    
        private void ThumbOnDragStarted(object sender, DragStartedEventArgs e)
        {
            _dragging = true;
        }
    
        protected override void OnValueChanged(double oldValue, double newValue)
        {
            base.OnValueChanged(oldValue, newValue);
            if (!_dragging)
            {
                OnValueChangeCompleted(newValue);
            }
        }
    }