using System;
|
using System.Windows;
|
using System.Windows.Controls;
|
using System.Windows.Media.Animation;
|
|
namespace HMI.UI
|
{
|
public class ScrollLabel : Control
|
{
|
static ScrollLabel()
|
{
|
DefaultStyleKeyProperty.OverrideMetadata(typeof(ScrollLabel), new FrameworkPropertyMetadata(typeof(ScrollLabel)));
|
}
|
|
private DoubleAnimation animation;
|
|
public override void OnApplyTemplate()
|
{
|
base.OnApplyTemplate();
|
|
// 在模板应用后启动初始动画
|
var scrollViewer = GetTemplateChild("slv") as ScrollViewer;
|
var label = GetTemplateChild("label") as Label;
|
if (scrollViewer != null)
|
{
|
// 等待布局完成后再启动动画
|
scrollViewer.Loaded += (s, e) =>
|
{
|
var storyboard = new Storyboard();
|
animation = new DoubleAnimation
|
{
|
From = 0,
|
To = scrollViewer.ScrollableWidth,
|
Duration = new Duration(TimeSpan.FromSeconds(3)),
|
AutoReverse = true,
|
RepeatBehavior = RepeatBehavior.Forever,
|
BeginTime = TimeSpan.FromSeconds(0.2)
|
};
|
|
Storyboard.SetTarget(animation, scrollViewer);
|
Storyboard.SetTargetProperty(animation, new PropertyPath(ScrollViewerBehavior.HorizontalOffsetProperty));
|
|
storyboard.Children.Add(animation);
|
scrollViewer.Resources["ScrollAnimation"] = storyboard;
|
storyboard.Begin();
|
};
|
}
|
}
|
|
private void ScrollViewer_ScrollChanged(object sender, ScrollChangedEventArgs e)
|
{
|
//RefreshAnimation();
|
}
|
|
private void RefreshAnimation()
|
{
|
// 查找ScrollViewer并重新启动动画
|
var scrollViewer = GetTemplateChild("slv") as ScrollViewer;
|
|
if (scrollViewer != null)
|
{
|
scrollViewer.Dispatcher.BeginInvoke(new Action(() =>
|
{
|
// 停止当前动画
|
var storyboard = scrollViewer.Resources["ScrollAnimation"] as Storyboard;
|
if (storyboard != null)
|
{
|
storyboard.Stop();
|
if (animation != null)
|
{
|
animation.To = scrollViewer.ScrollableWidth;
|
}
|
storyboard.Begin();
|
}
|
|
}), System.Windows.Threading.DispatcherPriority.Background);
|
}
|
}
|
|
public static readonly DependencyProperty ValueProperty =
|
DependencyProperty.RegisterAttached("Value", typeof(string), typeof(ScrollLabel),
|
new FrameworkPropertyMetadata(null, new PropertyChangedCallback(OnValueChanged)));
|
|
private static void OnValueChanged(DependencyObject obj, DependencyPropertyChangedEventArgs e)
|
{
|
var scrollLabel = obj as ScrollLabel;
|
scrollLabel?.RefreshAnimation();
|
}
|
|
public event EventHandler<string> ValueChanged;
|
|
public string Value
|
{
|
get { return (string)GetValue(ValueProperty); }
|
set
|
{
|
SetValue(ValueProperty, value);
|
}
|
}
|
}
|
|
public static class ScrollViewerBehavior
|
{
|
public static readonly DependencyProperty HorizontalOffsetProperty =
|
DependencyProperty.RegisterAttached("HorizontalOffset", typeof(double), typeof(ScrollViewerBehavior),
|
new UIPropertyMetadata(0.0, OnHorizontalOffsetChanged));
|
public static void SetHorizontalOffset(FrameworkElement target, double value)
|
{
|
target.SetValue(HorizontalOffsetProperty, value);
|
}
|
public static double GetHorizontalOffset(FrameworkElement target)
|
{
|
return (double)target.GetValue(HorizontalOffsetProperty);
|
}
|
private static void OnHorizontalOffsetChanged(DependencyObject target, DependencyPropertyChangedEventArgs e)
|
{
|
var view = target as ScrollViewer;
|
if (view != null)
|
{
|
view.ScrollToHorizontalOffset((double)e.NewValue);
|
}
|
}
|
|
public static readonly DependencyProperty VerticalOffsetProperty = DependencyProperty.RegisterAttached("VerticalOffset", typeof(double), typeof(ScrollViewerBehavior), new UIPropertyMetadata(0.0, OnVerticalOffsetChanged));
|
public static void SetVerticalOffset(FrameworkElement target, double value)
|
{
|
target.SetValue(VerticalOffsetProperty, value);
|
}
|
public static double GetVerticalOffset(FrameworkElement target)
|
{
|
return (double)target.GetValue(VerticalOffsetProperty);
|
}
|
private static void OnVerticalOffsetChanged(DependencyObject target, DependencyPropertyChangedEventArgs e)
|
{
|
var view = target as ScrollViewer;
|
if (view != null)
|
{
|
view.ScrollToVerticalOffset((double)e.NewValue);
|
}
|
}
|
}
|
|
}
|