c# UWP TreeView 在 ItemDrag 上自动滚动
Posted
技术标签:
【中文标题】c# UWP TreeView 在 ItemDrag 上自动滚动【英文标题】:c# UWP TreeView autoscroll on ItemDrag 【发布时间】:2021-08-07 00:57:36 【问题描述】:我面临一个非常简单且众所周知的问题。我的 UWP 应用程序中有一个树视图,用户可以通过拖放重新排序项目,但有一些限制。 d&d 本身就像预期的那样工作,但是现在,当我有一个很长的子项目列表要拖到树中非常高或低的地方时,我需要像每个用户从 Windows 资源管理器中知道的那样自动滚动,将光标向下移动到底部会激活滚动...但是...如何在 UWP 中实现它?我缺少任何默认属性吗?或者我什至如何滚动到树中的特定节点?有大量关于 Winform 甚至 WPF 的信息,但我卡在 UWP 上,无法将 WPF 解决方案转换为我的应用程序。
有人对这个问题有任何提示吗?
编辑:这是我的 XAML 的缩短版本:
<Page
x:Class="CookBook.Views.EditCategoryPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:templateSelectors="using:CookBook.TemplateSelectors"
xmlns:controls="using:Microsoft.Toolkit.Uwp.UI.Controls"
xmlns:models="using:CookBook.Core.Models.Entities"
xmlns:enums="using:CookBook.Core.Models"
xmlns:winui="using:Microsoft.UI.Xaml.Controls"
xmlns:behaviors="using:CookBook.Behaviors"
xmlns:helpers="using:CookBook.Helpers"
xmlns:interfaces="using:CookBook.Core.Models.Entities.Interfaces"
xmlns:converters="using:CookBook.Helpers.Converter" xmlns:viewcontrols="using:CookBook.Views.ViewControls" xmlns:treeviewdata="using:CookBook.Models.TreeViewData"
behaviors:NavigationViewHeaderBehavior.HeaderMode="Always"
NavigationCacheMode="Disabled"
Style="StaticResource PageStyle"
mc:Ignorable="d">
<Grid>
<Grid>
<Grid x:Name="mainGrid">
<Grid.ColumnDefinitions>
<ColumnDefinition x:Name="treeViewColumn" Width="350"/>
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup>
<VisualState>
<VisualState.StateTriggers>
<!--641 is the default CompactModeThresholdWidth in NavigationView -->
<AdaptiveTrigger MinWindowWidth="641" />
</VisualState.StateTriggers>
<VisualState.Setters>
<Setter Target="header.Margin" Value="0,0,0,0" />
<Setter Target="treeViewColumn.Width" Value="350" />
<Setter Target="treeViewColumn.MaxWidth" Value="500" />
</VisualState.Setters>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<Grid
Background="ThemeResource SystemChromeMediumLowColor">
<Grid.RowDefinitions>
<RowDefinition Height="40" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Grid
Margin="80,0,0,0"
x:Name="header">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<TextBlock
x:Uid="TreeViewTitle"
Margin="StaticResource SmallLeftMargin"
Style="StaticResource ListTitleStyle"
VerticalAlignment="Center" />
<!--Fold all-->
<Button
Grid.Column="1"
x:Uid="TreeView_CollapseAllButton"
Content=""
FontSize="14"
Padding="StaticResource SmallLeftRightMargin"
VerticalAlignment="Stretch"
VerticalContentAlignment="Center"
FontFamily="Segoe MDL2 Assets"
Background="Transparent"
Click="OnCollapseAll" />
<!--expand all-->
<Button
Grid.Column="2"
x:Uid="TreeView_ExpandAllButton"
FontSize="14"
Padding="StaticResource SmallLeftRightMargin"
VerticalAlignment="Stretch"
VerticalContentAlignment="Center"
FontFamily="Segoe MDL2 Assets"
Background="Transparent"
Click="OnExpandAll" >
<FontIcon FontFamily="Segoe MDL2 Assets" Glyph=""/>
</Button>
<!--Reorder Mode-->
<ToggleButton
Grid.Column="3"
Content=""
FontSize="14"
Padding="StaticResource SmallLeftRightMargin"
VerticalAlignment="Stretch"
VerticalContentAlignment="Center"
FontFamily="Segoe MDL2 Assets"
Background="Transparent"
IsThreeState="False"
RightTapped="ReorderModeRightClicked"
IsChecked="x:Bind ReorderMode, Mode=TwoWay" />
<!--Add-->
<Button
Grid.Column="4"
x:Name="foMenu"
x:Uid="Flyoutbutton"
Content=""
FontSize="14"
Padding="StaticResource SmallLeftRightMargin"
VerticalAlignment="Stretch"
VerticalContentAlignment="Center"
FontFamily="Segoe MDL2 Assets"
Background="Transparent">
<Button.Flyout>
<MenuFlyout>
<MenuFlyoutItem Text="Neue Kategorie" Click="AddCategory" ></MenuFlyoutItem>
<MenuFlyoutItem x:Name="btnCatIn" Text="x:Bind CategoryInText,Mode=OneWay" Click="AddCategory" />
<MenuFlyoutSeparator />
<MenuFlyoutItem x:Name="btnReceipeIn" Text="x:Bind ReceipeInText,Mode=OneWay" Click="AddReceipe" />
<MenuFlyoutSeparator />
<MenuFlyoutItem x:Name="btnImportFromCK" Text="Import aus Chefkoch" Click="BtnAddReceipeFromCK" />
<MenuFlyoutSeparator />
<MenuFlyoutItem x:Name="btnCBCut" Text="Ausschneiden" Click="CBCut" />
<!--<MenuFlyoutItem Text="Aus der Zwischenablage einfügen" Click="MoveReceipe" />-->
<MenuFlyoutSubItem x:Name="btnCBAdd" Text="Einträge einfügen">
</MenuFlyoutSubItem>
</MenuFlyout>
</Button.Flyout>
</Button>
</Grid>
<winui:TreeView
BorderBrush="Beige"
BorderThickness="1"
x:Name="treeView"
Grid.Row="1"
SelectionMode="Single"
CanBeScrollAnchor="True"
ItemsSource="x:Bind CategoryItems,Mode=TwoWay"
ItemInvoked="OnItemInvoked"
ItemTemplateSelector="StaticResource TreeViewTemplateSelector"
DragItemsStarting="TreeView_DragItemsStarting"
DragItemsCompleted="TreeView_DragItemsCompleted"
Width="auto">
<winui:TreeView.ItemContainerStyle>
<Style TargetType="winui:TreeViewItem">
<Setter Property="VerticalAlignment" Value="Stretch" />
<Setter Property="VerticalContentAlignment" Value="Stretch" />
</Style>
</winui:TreeView.ItemContainerStyle>
</winui:TreeView>
</Grid>
<ScrollViewer
Grid.Column="1" >
<ContentControl
Content="x:Bind SelectedItem, Mode=OneWay"
ContentTemplateSelector="StaticResource ContentTemplateSelector"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
VerticalContentAlignment="Stretch"
HorizontalContentAlignment="Stretch" />
</ScrollViewer>
<controls:GridSplitter
Grid.Column="1"
GripperCursor="Default"
HorizontalAlignment="Left"
ResizeDirection="Auto"
ResizeBehavior="BasedOnAlignment"
CursorBehavior="ChangeOnSplitterHover"
Width="16" />
</Grid>
<ScrollViewer x:Name="sViewerSingle" Visibility="Collapsed">
<ContentControl
Content="x:Bind SelectedItem, Mode=TwoWay"
ContentTemplateSelector="StaticResource ContentTemplateSelector"
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
VerticalContentAlignment="Stretch"
HorizontalContentAlignment="Stretch" />
</ScrollViewer>
</Grid>
</Grid>
</Page>
【问题讨论】:
你能分享你写的代码吗?你的意思是在放置完成时自动滚动到顶部还是底部? @NicoZhu-MSFT phu....也许我可以隔离我的 sn-p 并制作一个演示应用程序,否则我们将有很大的代码过载。但在以前:我的意思是在拖动时自动滚动,而不是在放置时。请在 Windows 资源管理器中测试此行为,将文件从目录列表的最顶部拖到最末尾,当光标碰到底部边框时,资源管理器将向下滚动 您可以参考这个案例reply。 是的,试过了,我在获取合适的父级时遇到了问题……我制作了一个小型示例存储库。您可以拖放每个组中的每一片叶子,但如何实现这种滚动行为:github.com/tzdlr/TreeViewReorderSample 我测试了你的代码,发现你的treeview不能正常滚动,请使用Grid替换默认的StackPanel作为treeview的父级,然后再次尝试拖动项目,你会发现结果。 【参考方案1】:c# UWP TreeView 在 ItemDrag 上自动滚动
TreeView
包含向下或向上拖动项目时的滚动行为。
在检查您的 xaml
代码期间,ScrollViewer
覆盖 TreeWiew,它将影响 TreeView
并防止滚动行为。请尝试将其移至其他区域。
【讨论】:
你是对的,我的 xaml 中有一个加倍...。一个滚动查看器已折叠,但似乎覆盖了整个页面并阻止滚动!感谢您指出!删除以上是关于c# UWP TreeView 在 ItemDrag 上自动滚动的主要内容,如果未能解决你的问题,请参考以下文章
在UWP应用程序中使用TreeView时如何处理命名空间冲突
UWP解析Windows.Storage.StorageFolder并添加TreeView
UWP - Flyout中的WinRT xaml工具包TreeView,在弹出窗口关闭后更改选择