I love WPF

"jamais sans son interface"

I love WPF

"jamais sans son interface"

ToolTip on moving thumb for slider

I try to find a solution for having in slider a tooltip moving under thumb when i drag it

after reading somes post like :https://stackoverflow.com/questions/1178134/wpf-adding-a-tooltip-to-the-track-of-a-slider
i think that restyle slider is not a good solution when you using already restyled slider as mahapp for example
and microsoft good explain for tooltip position : https://docs.microsoft.com/fr-fr/dotnet/framework/wpf/controls/how-to-position-a-tooltip

So i find a better solution (more simple) with an attached property

 public class SliderHelper
    {
        #region ShowToolTipOnMoving (ATTACHED)
        public static bool GetShowToolTipOnMoving(DependencyObject obj) => (bool)obj.GetValue(ShowToolTipOnMovingProperty);
        public static void SetShowToolTipOnMoving(DependencyObject obj, bool value) => obj.SetValue(ShowToolTipOnMovingProperty, value);

        // Using a DependencyProperty as the backing store for ShowToolTipOnMoving.  This enables animation, styling, binding, etc...
        public static readonly DependencyProperty ShowToolTipOnMovingProperty =
            DependencyProperty.RegisterAttached(
                "ShowToolTipOnMoving",
                typeof(bool),
                typeof(SliderHelper),
                new FrameworkPropertyMetadata(false
            //,FrameworkPropertyMetadataOptions.AffectsRender
            , (d, e) =>
            {
                if (d is Slider slider)
                {
                    slider.Loaded += (ss, ee) =>
                    {
                        // find thumb
                        ToolTip tooltip = new ToolTip();
                        Thumb thumb = FindVisualChildren<Thumb>(slider).First();
                        thumb.DragStarted += (sss, eee) =>
                        {
                            tooltip.Content = (int)slider.Value;                           
                            tooltip.HorizontalOffset = 0;
                            tooltip.Placement = PlacementMode.Bottom;
                            tooltip.PlacementTarget = thumb;
                            tooltip.PlacementRectangle = new Rect(-(thumb.ActualWidth / 2), thumb.ActualHeight + 2, 0, 0);
                            tooltip.IsOpen = true;
                            tooltip.StaysOpen = true;                            
                        };
                        thumb.DragCompleted += (sss, eee) =>
                       {
                           tooltip.IsOpen = false;
                           tooltip.StaysOpen = false;
                       };
                        thumb.DragDelta += (sss, eee) =>
                        {
                            tooltip.Content = (int)slider.Value;
                            tooltip.HorizontalOffset += 0.1;
                            tooltip.HorizontalOffset -= 0.1;
                        };
                    };
                }
            }
            ));
        #endregion

        #region STATIC Functions
        public static IEnumerable<T> FindVisualChildren<T>(DependencyObject depObj) where T : DependencyObject
        {
            if (depObj != null)
            {
                for (int i = 0; i < VisualTreeHelper.GetChildrenCount(depObj); i++)
                {
                    DependencyObject child = VisualTreeHelper.GetChild(depObj, i);
                    if (child != null && child is T)
                    {
                        yield return (T)child;
                    }

                    foreach (T childOfChild in FindVisualChildren<T>(child))
                    {
                        yield return childOfChild;
                    }
                }
            }
        }
        #endregion
    }

and using like this

  <Slider HorizontalAlignment="Left"
                Height="29"
                Margin="37,293,0,0"
                TickFrequency="1"
                IsSnapToTickEnabled="True"
                VerticalAlignment="Top"
                Value="5"
                Width="350"
                local:SliderHelper.ShowToolTipOnMoving="true"
                ToolTip="{Binding Value, RelativeSource={RelativeSource Self}}" />

we can find many improvment about this helper, but this is the first draft

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Retour en haut