Example #1
0
        void Remove(ToastAdorner toast)
        {
            var index = _adorners.IndexOf(toast) - 1;

            if (!_adorners.Remove(toast))
            {
                return;
            }

            RemoveDelegate del = _adornerLayer.Remove;

            Application.Current?.Dispatcher?.Invoke(del, toast);

            if (!_adorners.Any())
            {
                IsEmpty?.Invoke(this, new EventArgs());
                return;
            }

            if (index < 0)
            {
                return;
            }

            MoveBackwards(index);
        }
Example #2
0
        void ConfigureLeaveActions(ToastAdorner adorner, ToastAdornerSettings settings, int lifetime, Action leaveAction, Action cancelAction)
        {
            if (lifetime - settings.LeaveTime <= 0)
            {
                return;
            }

            var leaveTimer = new Timer(lifetime - settings.LeaveTime);

            leaveTimer.Elapsed += (s, e) =>
            {
                leaveTimer?.Dispose();
                leaveTimer = null;

                void Leave()
                {
                    leaveAction?.Invoke();
                }

                Application.Current?.Dispatcher?.Invoke((ActionDelegate)Leave);
            };

            if (settings.RefreshLifetimeOnMouseOver)
            {
                adorner.MouseEnter += (s, e) =>
                {
                    leaveTimer?.Dispose();
                    leaveTimer = null;

                    void Cancel()
                    {
                        cancelAction?.Invoke();
                    }

                    Application.Current?.Dispatcher?.Invoke((ActionDelegate)Cancel);
                };

                adorner.MouseLeave += (s, e) =>
                {
                    leaveTimer          = new Timer(lifetime - settings.LeaveTime);
                    leaveTimer.Elapsed += (sender, args) =>
                    {
                        leaveTimer?.Dispose();
                        leaveTimer = null;

                        void Leave()
                        {
                            leaveAction?.Invoke();
                        }

                        Application.Current?.Dispatcher?.Invoke((ActionDelegate)Leave);
                    };
                    leaveTimer.Start();
                };
            }

            leaveTimer.AutoReset = false;
            leaveTimer.Start();
        }
Example #3
0
        void Configure(ToastAdorner adorner, ToastAdornerSettings settings, Action clickAction, string title, string message)
        {
            ConfigureClose(adorner, settings);
            ConfigureClickAction(adorner, settings, clickAction);
            var lifetime = settings.DynamicLifetime ? GetDynamicLifetime(settings, title, message) : settings.Lifetime;

            ConfigureRemove(adorner, settings, lifetime);
            ConfigureLeave(adorner, settings, lifetime);
        }
Example #4
0
        void CancelFade(ToastAdorner adorner, double originalOpacity)
        {
            void Animate()
            {
                adorner.BeginAnimation(UIElement.OpacityProperty, null);
            }

            Application.Current?.Dispatcher?.Invoke((ActionDelegate)Animate);
            adorner.Opacity = originalOpacity;
        }
Example #5
0
 void ConfigureClickAction(ToastAdorner adorner, ToastAdornerSettings settings, Action clickAction)
 {
     adorner.ToastView.MouseLeftButtonUp += (s, e) =>
     {
         clickAction();
         if (settings.CloseAfterClickAction)
         {
             Remove(adorner);
         }
     };
 }
Example #6
0
        void GetLeaveActions(ToastAdorner adorner, ToastAdornerSettings settings, int lifetime, out Action leaveAction, out Action cancelAction)
        {
            if (settings.LeaveTime <= 0 || lifetime - settings.LeaveTime <= 0)
            {
                leaveAction  = null;
                cancelAction = null;
                return;
            }

            var    elapsedStopwatch = new Stopwatch();
            double originalOpacity  = adorner.Opacity;
            double originalLeft     = adorner.Left;
            double originalTop      = adorner.Top;
            var    isLeaving        = false;

            switch (LeaveStyle)
            {
            case LeaveStyle.FadeOut:
                leaveAction  = () => Fade(originalOpacity, settings, adorner);
                cancelAction = () => CancelFade(adorner, originalOpacity);
                break;

            case LeaveStyle.SlideOut:
                leaveAction = () =>
                {
                    originalLeft = adorner.Left;
                    originalTop  = adorner.Top;

                    Slide(adorner, settings);
                    elapsedStopwatch.Start();
                    isLeaving = true;
                };
                cancelAction = () =>
                {
                    if (!isLeaving)
                    {
                        return;
                    }
                    isLeaving = false;
                    var elapsed = (int)elapsedStopwatch.ElapsedMilliseconds;
                    elapsedStopwatch.Reset();
                    CancelSlide(adorner, originalLeft, originalTop, elapsed);
                };
                break;

            case LeaveStyle.None:
                leaveAction  = null;
                cancelAction = null;
                break;

            default:
                throw new ArgumentOutOfRangeException();
            }
        }
Example #7
0
        void AddToQueue(ToastAdorner adorner, ToastAdornerSettings toastSettings, Action clickAction, string title, string message)
        {
            var queueEntry = new ToastQueueEntry()
            {
                Adorner     = adorner,
                Settings    = toastSettings,
                ClickAction = clickAction,
                Title       = title,
                Message     = message
            };

            _queue.Enqueue(queueEntry);
        }
Example #8
0
        void ConfigureClose(ToastAdorner adorner, ToastAdornerSettings settings)
        {
            if (!settings.CanUserClose)
            {
                return;
            }

            adorner.CloseRequested += (s, e) => Remove(adorner);
            if (settings.CloseOnRightClick)
            {
                adorner.ToastView.MouseRightButtonUp += (s, e) => Remove(adorner);
            }
        }
Example #9
0
        void Fade(double originalOpacity, ToastAdornerSettings settings, ToastAdorner adorner)
        {
            void Animate()
            {
                var animation = new DoubleAnimation(
                    originalOpacity,
                    0,
                    GetLeaveTime(settings),
                    FillBehavior.Stop);

                adorner.BeginAnimation(UIElement.OpacityProperty, animation);
            }

            Application.Current?.Dispatcher?.Invoke((ActionDelegate)Animate);
        }
Example #10
0
        void Slide(ToastAdorner adorner, ToastAdornerSettings settings)
        {
            double targetTop  = 0;
            double targetLeft = 0;

            void SetTargets()
            {
                targetTop  = adorner.Top;
                targetLeft = adorner.Left;

                if (LeaveDirection == Direction.Left)
                {
                    targetLeft = -adorner.ActualWidth;
                }
                else if (LeaveDirection == Direction.Right)
                {
                    targetLeft = GetWidth();
                }
                else if (LeaveDirection == Direction.Up)
                {
                    targetTop = -adorner.ActualHeight;
                }
                else if (LeaveDirection == Direction.Down)
                {
                    targetTop = GetHeight();
                }
                else
                {
                    throw new ArgumentOutOfRangeException();
                }
            }

            Application.Current?.Dispatcher?.Invoke((ActionDelegate)SetTargets);

            void Animate()
            {
                var horizontal = LeaveDirection == Direction.Left || LeaveDirection == Direction.Right;
                var animation  = new DoubleAnimation(
                    horizontal ? adorner.Left : adorner.Top,
                    horizontal ? targetLeft : targetTop,
                    GetLeaveTime(settings),
                    FillBehavior.Stop);

                adorner.BeginAnimation(horizontal ? ToastAdorner.LeftProperty : ToastAdorner.TopProperty, animation);
            }

            Application.Current?.Dispatcher?.Invoke((ActionDelegate)Animate);
        }
Example #11
0
        void CancelSlide(ToastAdorner adorner, double originalLeft, double originalTop, int elapsedTime)
        {
            void Animate()
            {
                var horizontal = LeaveDirection == Direction.Left || LeaveDirection == Direction.Right;

                adorner.BeginAnimation(horizontal ? ToastAdorner.LeftProperty : ToastAdorner.TopProperty, null);
                var animation = new DoubleAnimation(
                    horizontal ? adorner.Left : adorner.Top,
                    horizontal ? originalLeft : originalTop,
                    GetCancelTime(elapsedTime));

                adorner.BeginAnimation(horizontal ? ToastAdorner.LeftProperty : ToastAdorner.TopProperty, animation);
            }

            Application.Current?.Dispatcher?.Invoke((ActionDelegate)Animate);
        }
Example #12
0
        public ToastAdorner Show(
            string message,
            string title,
            ToastAdornerSettings toastSettings = null,
            UIElement toastView = null,
            Action clickAction  = null)
        {
            if (toastSettings == null && DefaultToastSettings == null)
            {
                throw new ArgumentNullException(nameof(toastSettings), "Toast settings cannot be null if DefaultToastSettings has not been set.");
            }

            if (toastSettings == null)
            {
                toastSettings = DefaultToastSettings;
            }

            if (!toastSettings.CanUserClose && toastSettings.Lifetime <= 0)
            {
                throw new InvalidOperationException("Toast is configured to disallow user closing and to never expire.");
            }

            ToastAdorner adorner = null;

            void CreateAdorner()
            {
                adorner = new ToastAdorner(ElementToAdorn, toastView ?? _getDefaultView(title, message));
            }

            Application.Current?.Dispatcher?.Invoke((ActionDelegate)CreateAdorner);

            if (QueueToasts)
            {
                AddToQueue(adorner, toastSettings, clickAction, title, message);
                ProcessQueue();
            }
            else
            {
                Configure(adorner, toastSettings, clickAction, title, message);
                Add(adorner);
            }

            return(adorner);
        }
Example #13
0
        void ConfigureRemove(ToastAdorner adorner, ToastAdornerSettings settings, int lifetime)
        {
            if (lifetime <= 0)
            {
                return;
            }

            var lifetimeTimer = new Timer(lifetime);

            lifetimeTimer.Elapsed += (s, e) =>
            {
                Remove(adorner);
                lifetimeTimer.Dispose();
            };

            if (settings.RefreshLifetimeOnMouseOver)
            {
                adorner.MouseEnter += (s, e) => lifetimeTimer.Stop();
                adorner.MouseLeave += (s, e) => lifetimeTimer.Start();
            }

            lifetimeTimer.AutoReset = false;
            lifetimeTimer.Start();
        }
Example #14
0
        double GetEntryTop(ToastAdorner adorner)
        {
            double top = 0;

            void GetTop()
            {
                if (EnterLocation == Location.TopLeft)
                {
                    if (EnterFromDirection == Direction.Up)
                    {
                        top = -adorner.ActualHeight;
                    }
                    else if (EnterFromDirection != Direction.Left)
                    {
                        throw new InvalidOperationException();
                    }
                }

                if (EnterLocation == Location.TopRight)
                {
                    if (EnterFromDirection == Direction.Up)
                    {
                        top = -adorner.ActualHeight;
                    }
                    else if (EnterFromDirection != Direction.Right)
                    {
                        throw new InvalidOperationException();
                    }
                }

                if (EnterLocation == Location.BottomLeft)
                {
                    if (EnterFromDirection == Direction.Left)
                    {
                        top = GetHeight() - adorner.ActualHeight;
                    }
                    else if (EnterFromDirection == Direction.Down)
                    {
                        top = GetHeight();
                    }
                    else
                    {
                        throw new InvalidOperationException();
                    }
                }

                if (EnterLocation == Location.BottomRight)
                {
                    if (EnterFromDirection == Direction.Right)
                    {
                        top = GetHeight() - adorner.ActualHeight;
                    }
                    else if (EnterFromDirection == Direction.Down)
                    {
                        top = GetHeight();
                    }
                    else
                    {
                        throw new InvalidOperationException();
                    }
                }

                top += VerticalAdjustment;
            }

            Application.Current?.Dispatcher?.Invoke((ActionDelegate)GetTop);
            return(top);
        }
Example #15
0
        double GetEntryLeft(ToastAdorner adorner)
        {
            double left = 0;

            void GetLeft()
            {
                if (EnterLocation == Location.TopLeft)
                {
                    if (EnterFromDirection == Direction.Left)
                    {
                        left = -adorner.ActualWidth;
                    }
                    else if (EnterFromDirection != Direction.Up)
                    {
                        throw new InvalidOperationException();
                    }
                }

                if (EnterLocation == Location.BottomLeft)
                {
                    if (EnterFromDirection == Direction.Left)
                    {
                        left = -adorner.ActualWidth;
                    }
                    else if (EnterFromDirection != Direction.Down)
                    {
                        throw new InvalidOperationException();
                    }
                }

                if (EnterLocation == Location.TopRight)
                {
                    if (EnterFromDirection == Direction.Right)
                    {
                        left = GetWidth();
                    }
                    else if (EnterFromDirection == Direction.Up)
                    {
                        left = GetWidth() - adorner.ActualWidth;
                    }
                    else
                    {
                        throw new InvalidOperationException();
                    }
                }

                if (EnterLocation == Location.BottomRight)
                {
                    if (EnterFromDirection == Direction.Right)
                    {
                        left = GetWidth();
                    }
                    else if (EnterFromDirection == Direction.Down)
                    {
                        left = GetWidth() - adorner.ActualWidth;
                    }
                    else
                    {
                        throw new InvalidOperationException();
                    }
                }

                left += HorizontalAdjustment;
            }

            Application.Current?.Dispatcher?.Invoke((ActionDelegate)GetLeft);
            return(left);
        }
Example #16
0
        void Enter(ToastAdorner toast)
        {
            toast.Top  = GetEntryTop(toast);
            toast.Left = GetEntryLeft(toast);

            if (EnterStyle == EnterStyle.PopIn || EnterStyle == EnterStyle.FadeIn)
            {
                if (EnterLocation == Location.TopLeft ||
                    EnterLocation == Location.TopRight)
                {
                    toast.Top += toast.ActualHeight + VerticalPadding;
                }

                if (EnterLocation == Location.BottomLeft ||
                    EnterLocation == Location.BottomRight)
                {
                    toast.Top -= toast.ActualHeight + VerticalPadding;
                }

                if (EnterLocation == Location.TopLeft ||
                    EnterLocation == Location.BottomLeft)
                {
                    toast.Left += toast.ActualWidth + HorizontalPadding;
                }

                if (EnterLocation == Location.TopRight ||
                    EnterLocation == Location.BottomRight)
                {
                    toast.Left -= toast.ActualWidth + HorizontalPadding;
                }
            }

            if (EnterStyle == EnterStyle.FadeIn)
            {
                toast.Opacity = 0;

                void Animate()
                {
                    var animation = new DoubleAnimation(
                        0,
                        1,
                        MoveDuration,
                        FillBehavior.Stop);

                    toast.BeginAnimation(UIElement.OpacityProperty, animation);
                }

                Application.Current?.Dispatcher?.Invoke((ActionDelegate)Animate);
            }

            if (EnterStyle == EnterStyle.SlideIn)
            {
                double from;
                double target;
                if (EnterFromDirection == Direction.Left)
                {
                    from   = toast.Left;
                    target = toast.Left + toast.ActualWidth + HorizontalPadding + HorizontalAdjustment;
                }
                else if (EnterFromDirection == Direction.Right)
                {
                    from   = toast.Left;
                    target = GetWidth() - toast.ActualWidth - HorizontalPadding + HorizontalAdjustment;
                }
                else if (EnterFromDirection == Direction.Up)
                {
                    from   = toast.Top;
                    target = toast.Top + toast.ActualHeight + VerticalPadding + VerticalAdjustment;
                }
                else // Direction.Down
                {
                    from   = toast.Top;
                    target = GetHeight() - toast.ActualHeight - VerticalPadding + VerticalAdjustment;
                }

                var property =
                    EnterFromDirection == Direction.Left || EnterFromDirection == Direction.Right
                        ? ToastAdorner.LeftProperty
                        : ToastAdorner.TopProperty;

                var animation = new DoubleAnimation(
                    from,
                    target,
                    MoveDuration);

                void Animate()
                {
                    toast.BeginAnimation(property, animation);
                }

                Application.Current?.Dispatcher?.Invoke((ActionDelegate)Animate);
            }

            if (MoveStyle == MoveStyle.Stack)
            {
                if (MoveDirection == Direction.Left)
                {
                    foreach (var adorner in _adorners)
                    {
                        toast.Left -= adorner.ActualWidth + HorizontalPadding;
                    }
                }
                else if (MoveDirection == Direction.Right)
                {
                    foreach (var adorner in _adorners)
                    {
                        toast.Left += adorner.ActualWidth + HorizontalPadding;
                    }
                }
                else if (MoveDirection == Direction.Up)
                {
                    foreach (var adorner in _adorners)
                    {
                        toast.Top -= adorner.ActualHeight + VerticalPadding;
                    }
                }
                else if (MoveDirection == Direction.Down)
                {
                    foreach (var adorner in _adorners)
                    {
                        toast.Top += adorner.ActualHeight + VerticalPadding;
                    }
                }
            }

            if (MoveStyle == MoveStyle.Stack)
            {
                _adorners.Insert(0, toast);
            }
            else
            {
                _adorners.Add(toast);
            }

            if (MoveStyle == MoveStyle.Push)
            {
                MoveForward();
            }
        }
Example #17
0
        void Add(ToastAdorner toast)
        {
            toast.Loaded += (s, e) => { Enter(toast); };

            _adornerLayer.Add(toast);
        }
Example #18
0
 void ConfigureLeave(ToastAdorner adorner, ToastAdornerSettings settings, int lifetime)
 {
     GetLeaveActions(adorner, settings, lifetime, out var leaveAction, out var cancelAction);
     ConfigureLeaveActions(adorner, settings, lifetime, leaveAction, cancelAction);
 }