ContextFlyout 和 SwipeControl 冲突

ContextFlyout and SwipeControl conflict

我有一个 ListView,它的 ItemTemplate 有一个 SwipeControl 和一个 ContextFlyout

但是,当我长按(我不是用鼠标,只是用手指)时 PlaylistControlItemSwipeControlLeftItems 出现而不是 ContextFlyout .

我应该如何让 ContextFlyout 显示出来?

下面是我的ListView:

<ListView
    SelectionMode="None">
    <ListView.ItemTemplate>
        <DataTemplate x:DataType="data:Music">
            <SwipeControl Loaded="SwipeControl_Loaded">
                <SwipeControl.LeftItems>
                    <SwipeItems Mode="Reveal">
                        <SwipeItem Text="Favorite">
                        </SwipeItem>
                    </SwipeItems>
                </SwipeControl.LeftItems>
                <SwipeControl.RightItems>
                    <SwipeItems Mode="Execute">
                        <SwipeItem Text="Remove">
                        </SwipeItem>
                    </SwipeItems>
                </SwipeControl.RightItems>
                <local:PlaylistControlItem DataContext="{x:Bind}" ShowAlbumText="{Binding ElementName=PlaylistController, Path=ShowAlbumText}">
                    <local:PlaylistControlItem.ContextFlyout>
                        <MenuFlyout Opening="OpenMusicMenuFlyout" />
                    </local:PlaylistControlItem.ContextFlyout>
                </local:PlaylistControlItem>
            </SwipeControl>
        </DataTemplate>
    </ListView.ItemTemplate>
</ListView>

更多源代码here

为不同的操作模式提供优化是个好主意,但也需要遵循一些设计原则。

但需要注意的是,ContextFlyoutSwipeControl都有自己的内部操作逻辑,比如SwipeControl是手指滑动,ContextFlyout是右单击或长按。你不能修改它。

您可以尝试将 ContextFlyout 绑定到更高级别,这可能会有所帮助。像这样:

<DataTemplate>
    <UserControl>
        <UserControl.ContextFlyout>
            <MenuFlyout Opening="OpenMusicMenuFlyout" />
        </UserControl.ContextFlyout>
        <SwipeControl>
            <SwipeControl.LeftItems>
                <SwipeItems Mode="Reveal">
                    <SwipeItem Text="Favorite">
                    </SwipeItem>
                </SwipeItems>
            </SwipeControl.LeftItems>
            <SwipeControl.RightItems>
                <SwipeItems Mode="Execute">
                    <SwipeItem Text="Remove">
                    </SwipeItem>
                </SwipeItems>
            </SwipeControl.RightItems>
            <local:PlaylistControlItem DataContext="{x:Bind}" ShowAlbumText="{Binding ElementName=PlaylistController, Path=ShowAlbumText}">
            </local:PlaylistControlItem>
        </SwipeControl>
    </UserControl>
</DataTemplate>

但是从用户体验的角度来说,我不建议混合使用ContextFlyoutSwipeControl。它们都是隐式操作,也就是说,UI 上没有明显的提示告诉用户这样做。

你正在做的是一个播放列表。我的建议是在 PlaylistControlItem 的末尾添加一个 MoreButton。这是一个明显的暗示。点击后可以显示Flyout并使用它代替隐含的ContextFlyout.

如果您仍打算通过长按来调用 ContextFlyout,请考虑在 UI 上明确提示以告诉用户 "can do this".

另外,可能会使用一些相同的程序处理逻辑来优化不同设备的体验。 UWP 有专门为此目的构建的设计模式。您可以参考 Commanding in Universal Windows Platform (UWP) apps using StandardUICommand, XamlUICommand, and ICommand 来优化您的代码并构建出色的跨设备体验


更新

我测试了你的代码并检查了问题的原因。你在设置 AllowReorder 属性 时省略了 ListView.CanDragItems 属性。

试试这个:

public bool AllowReorder
{
    get => SongsListView.CanReorderItems;
    set
    {
        SongsListView.CanReorderItems = SongsListView.AllowDrop = SongsListView.CanDragItems = SongsListView.CanDrag = value;
    }
}

此致。