如何为ListBox的滚动设置动画?我知道我可以使用scrollIntoView,但我该如何设置它的动画?我想按箭头键从一个listBoxItem移动到另一个。
答案 0 :(得分:7)
以下是基于与以下链接相同的方法的粗略实现 http://aniscrollviewer.codeplex.com/
VerticalOffset
属性是只读的,因此您可以在VerticalOffset
上使用附加属性ScrollViewer
,ScrollToVerticalOffset
依次为ItemsControl
。此附加属性可以设置动画。
您还可以为名为AnimateScrollIntoView
的{{1}}创建扩展方法。
像这样称呼
listBox.AnimateScrollIntoView(yourItem);
ScrollViewerBehavior
public class ScrollViewerBehavior
{
public static 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)
{
ScrollViewer scrollViewer = target as ScrollViewer;
if (scrollViewer != null)
{
scrollViewer.ScrollToVerticalOffset((double)e.NewValue);
}
}
}
ItemsControlExtensions
public static class ItemsControlExtensions
{
public static void AnimateScrollIntoView(this ItemsControl itemsControl, object item)
{
ScrollViewer scrollViewer = VisualTreeHelpers.GetVisualChild<ScrollViewer>(itemsControl);
UIElement container = itemsControl.ItemContainerGenerator.ContainerFromItem(item) as UIElement;
int index = itemsControl.ItemContainerGenerator.IndexFromContainer(container);
double toValue = scrollViewer.ScrollableHeight * ((double)index / itemsControl.Items.Count);
Point relativePoint = container.TranslatePoint(new Point(0.0, 0.0), Window.GetWindow(container));
DoubleAnimation verticalAnimation = new DoubleAnimation();
verticalAnimation.From = scrollViewer.VerticalOffset;
verticalAnimation.To = toValue;
verticalAnimation.DecelerationRatio = .2;
verticalAnimation.Duration = new Duration(TimeSpan.FromMilliseconds(1000));
Storyboard storyboard = new Storyboard();
storyboard.Children.Add(verticalAnimation);
Storyboard.SetTarget(verticalAnimation, scrollViewer);
Storyboard.SetTargetProperty(verticalAnimation, new PropertyPath(ScrollViewerBehavior.VerticalOffsetProperty));
storyboard.Begin();
}
}
因为你还需要抓住ScrollViewer
,你需要这个
public static class VisualTreeHelpers
{
public static T GetVisualChild<T>(DependencyObject parent) where T : Visual
{
T child = default(T);
int numVisuals = VisualTreeHelper.GetChildrenCount(parent);
for (int i = 0; i < numVisuals; i++)
{
Visual v = (Visual)VisualTreeHelper.GetChild(parent, i);
child = v as T;
if (child == null)
{
child = GetVisualChild<T>(v);
}
if (child != null)
{
break;
}
}
return child;
}
}
答案 1 :(得分:0)
看看这个article,它解释了动画滚动和添加触摸手势的方式。下载页面底部的源代码并查看WpfScrollContent解决方案。我会扩展WPF ListBox并向其添加滚动动画,以便您可以重用该控件。