好吧,伙计们,我一直在为这个问题疯狂地摸不着头脑,花了几个小时试图研究它是如何工作的但是我还没有找到答案,如果你希望看到我的任何一个SRC感到自由询问它,我会看看我是否能提供帮助。
基本上我遇到的问题是我的应用程序中有TreeView
个文件夹,即:
Catalog
Brands
Nike
Adidas
Lactose
Styles
Sandles
Trainers
Boots
我想解决的问题是,当我拖动文件夹时(这是在我的DragDropManager
课程中处理的),我无法向上或向下滚动(只是显示一个可爱的停止标志)。我也无法在树视图中找到卷轴,所以我不确定它是如何生成的(这不是我自己的软件,我最近开始为一家公司工作,所以我不熟悉代码而没有其他人似乎知道。)
如果我想从顶部移动到底部,这是一个问题。
滚动工作正常,无需拖动。
如果有人希望看到我的代码的任何部分随意问,因为我不确定该向您展示什么。
我已经阅读了很多文章,我只是在摸不着头脑。
答案 0 :(得分:20)
我已经为实现此行为创建了附加属性,请查看我的帖子 -
Attached Behavior for auto scrolling containers while doing Drag & Drop
主要逻辑是这样的 -
private static void OnContainerPreviewDragOver(object sender, DragEventArgs e)
{
FrameworkElement container = sender as FrameworkElement;
if (container == null) { return; }
ScrollViewer scrollViewer = GetFirstVisualChild<ScrollViewer>(container);
if (scrollViewer == null) { return; }
double tolerance = 60;
double verticalPos = e.GetPosition(container).Y;
double offset = 20;
if (verticalPos < tolerance) // Top of visible list?
{
//Scroll up
scrollViewer.ScrollToVerticalOffset(scrollViewer.VerticalOffset - offset);
}
else if (verticalPos > container.ActualHeight - tolerance) //Bottom of visible list?
{
//Scroll down
scrollViewer.ScrollToVerticalOffset(scrollViewer.VerticalOffset + offset);
}
}
关于SO的类似问题(虽然它们主要针对ListBox
/ ListView
,但也适用于TreeView
-
WPF Listbox auto scroll while dragging
答案 1 :(得分:1)
我知道这个问题确实很老,但这是MVVM的附加属性:
using System.Windows;
using System.Windows.Controls;
namespace AndroidCtrlUI.XTools.Behaviors
{
///<summary>
/// TreeItemAttach
///<para/> TreeViewItem
///</summary>
public sealed class TreeItemAttach
{
#region BringIntoView
///<summary>
/// DependencyProperty
///</summary>
public static readonly DependencyProperty BringIntoViewProperty = DependencyProperty.RegisterAttached("BringIntoView", typeof(bool), typeof(TreeItemAttach), new UIPropertyMetadata(false, (s, e) =>
{
if ((bool)e.NewValue != (bool)e.OldValue && s is TreeViewItem t)
{
if ((bool)e.NewValue)
{
t.Selected += BringIntoView;
}
else
{
t.Selected -= BringIntoView;
}
}
}));
///<summary>
/// Get
///</summary>
///<param name="target">DependencyObject</param>
///<returns>ICommand</returns>
public static bool GetBringIntoView(DependencyObject target)
{
return (bool)target.GetValue(BringIntoViewProperty);
}
///<summary>
/// Set
///</summary>
///<param name="target">DependencyObject</param>
///<param name="value">ICommand</param>
public static void SetBringIntoView(DependencyObject target, bool value)
{
target.SetValue(BringIntoViewProperty, value);
}
private static void BringIntoView(object sender, RoutedEventArgs e)
{
if (e.Source is TreeViewItem s)
{
double h = s.ActualHeight;
if (s.IsExpanded && s.Items.Count > 0)
{
h = s.ActualHeight / TreeWalker(s);
}
s.BringIntoView(new Rect(0, h * -1, s.ActualWidth, h * 2.5));
}
}
private static long TreeWalker(TreeViewItem item)
{
long c = item.Items.Count;
foreach (object i in item.Items)
{
if (i != null && item.ItemContainerGenerator.ContainerFromItem(i) is TreeViewItem t && t.IsExpanded && t.Items.Count > 0)
{
c += TreeWalker(t);
}
}
return c;
}
#endregion
}
}
它可以像这样使用:
<Style x:Key="TreeViewItemStyle" TargetType="{x:Type TreeViewItem}">
<Setter Property="tool:TreeItemAttach.BringIntoView" Value="True"/>
</Style>