带用户控制的垂直左侧菜单(内部扩展器)必须在您打开一个时关闭其他菜单 XAML
Vertical Left Menu with User Control (Expander inside) must close others when you open one XAML
我正在实现一个带有用户控件的垂直左下拉菜单,它在扩展器中。 UserControl 有一个 DependencyProperty,它需要一个 ListView(菜单项),还有一个依赖项 属性“IsSelected”,它与 Expander 属性“IsExpanded”绑定。我喜欢在用户单击 UserControlMenu 时实现一个功能,打开它(如果已关闭)并关闭其他功能。我附上了我的 类 和 UserControl,但是,现在只有当您单击 UserControlMenu 时,我才能看到它打开并立即关闭。
用户控件XAML
<UserControl x:Class="DropDownMenuExpander.UserControlMenuItem"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:md="http://materialdesigninxaml.net/winfx/xaml/themes"
mc:Ignorable="d" >
<Grid>
<md:PackIcon Kind="{Binding Path=Icon}" Width="15" Height="15" Margin="10 16"/>
<Expander x:Name="ExpanderMenu" Header="{Binding Path=Header}" IsExpanded="{Binding Path=IsSelected}" Width="210" HorizontalAlignment="Right" Background="{x:Null}">
<ContentControl Content="{Binding ListView}"/>
</Expander>
</Grid>
</UserControl>
用户控件.cs
public partial class UserControlMenuItem : UserControl
{
public static readonly DependencyProperty HeaderProperty = DependencyProperty.Register("Header", typeof(string), typeof(UserControlMenuItem));
public string Header
{
get
{
return (string)GetValue(HeaderProperty);
}
set
{
SetValue(HeaderProperty, value);
}
}
public static readonly DependencyProperty IsSelectedProperty = DependencyProperty.Register("IsSelected", typeof(bool), typeof(UserControlMenuItem));
public bool IsSelected
{
get
{
return (bool)GetValue(IsSelectedProperty);
}
set
{
SetValue(IsSelectedProperty, value);
}
}
public static readonly DependencyProperty IconProperty = DependencyProperty.Register("Icon", typeof(PackIconKind), typeof(UserControlMenuItem));
public PackIconKind Icon
{
get
{
return (PackIconKind)GetValue(IconProperty);
}
set
{
SetValue(IconProperty, value);
}
}
public static readonly DependencyProperty ListViewProperty = DependencyProperty.Register("ListView", typeof(ListView), typeof(UserControlMenuItem), new UIPropertyMetadata(null));
public ListView ListView
{
get
{
return (ListView)GetValue(ListViewProperty);
}
set
{
SetValue(ListViewProperty, value);
}
}
public UserControlMenuItem()
{
InitializeComponent();
DataContext = this;
}
}
在主窗口中调用用户控件
<StackPanel x:Name="st_menu" Margin="10" Orientation="Vertical" ScrollViewer.CanContentScroll="True">
<local:UserControlMenuItem x:Name="MenuItemHome" Header="Home" Icon="Home" PreviewMouseDown="MenuItemHome_PreviewMouseDown">
<local:UserControlMenuItem.ListView>
<ListView SelectionMode="Single" Margin="0 16 0 16">
<ListViewItem>
<TextBlock Text="Item1"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="Item2"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="Item3"/>
</ListViewItem>
</ListView>
</local:UserControlMenuItem.ListView>
</local:UserControlMenuItem>
<local:UserControlMenuItem x:Name="MenuItem2" Header="User" Icon="User" PreviewMouseDown="MenuItemHome_PreviewMouseDown">
<local:UserControlMenuItem.ListView>
<ListView SelectionMode="Single" Margin="0 16 0 16">
<ListViewItem>
<TextBlock Text="User1"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="User2"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="User3"/>
</ListViewItem>
</ListView>
</local:UserControlMenuItem.ListView>
</local:UserControlMenuItem>
<local:UserControlMenuItem x:Name="MenuMes2" Header="Messages" Icon="Chat" PreviewMouseDown="MenuItemHome_PreviewMouseDown">
<local:UserControlMenuItem.ListView>
<ListView SelectionMode="Single" Margin="0 16 0 16">
<ListViewItem>
<TextBlock Text="Message1"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="Message2"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="Message3"/>
</ListViewItem>
</ListView>
</local:UserControlMenuItem.ListView>
</local:UserControlMenuItem>
</StackPanel>
MainWindow.cs
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
MenuItemHome.IsSelected = true;
}
private void MenuItemHome_PreviewMouseDown(object sender, MouseButtonEventArgs e)
{
foreach (var item in st_menu.Children)
{
if (item is UserControlMenuItem menuItem)
{
if (menuItem.Equals(sender as UserControlMenuItem))
{
menuItem.IsSelected = true;
}
else
{
menuItem.IsSelected = false;
}
}
}
}
}
你应该设置eventArgs.Handled = true;
,它会阻止事件冒泡,比如:
private void MenuItemHome_PreviewMouseDown(object sender, MouseButtonEventArgs e)
{
foreach (var item in st_menu.Children)
{
if (item is UserControlMenuItem menuItem && sender is UserControlMenuItem senderItem)
{
menuItem.IsSelected = menuItem.Equals(senderItem) && !senderItem.IsSelected;
e.Handled = true; //Tells to the visual tree that event was already handled
}
}
}
我正在实现一个带有用户控件的垂直左下拉菜单,它在扩展器中。 UserControl 有一个 DependencyProperty,它需要一个 ListView(菜单项),还有一个依赖项 属性“IsSelected”,它与 Expander 属性“IsExpanded”绑定。我喜欢在用户单击 UserControlMenu 时实现一个功能,打开它(如果已关闭)并关闭其他功能。我附上了我的 类 和 UserControl,但是,现在只有当您单击 UserControlMenu 时,我才能看到它打开并立即关闭。
用户控件XAML
<UserControl x:Class="DropDownMenuExpander.UserControlMenuItem"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:md="http://materialdesigninxaml.net/winfx/xaml/themes"
mc:Ignorable="d" >
<Grid>
<md:PackIcon Kind="{Binding Path=Icon}" Width="15" Height="15" Margin="10 16"/>
<Expander x:Name="ExpanderMenu" Header="{Binding Path=Header}" IsExpanded="{Binding Path=IsSelected}" Width="210" HorizontalAlignment="Right" Background="{x:Null}">
<ContentControl Content="{Binding ListView}"/>
</Expander>
</Grid>
</UserControl>
用户控件.cs
public partial class UserControlMenuItem : UserControl
{
public static readonly DependencyProperty HeaderProperty = DependencyProperty.Register("Header", typeof(string), typeof(UserControlMenuItem));
public string Header
{
get
{
return (string)GetValue(HeaderProperty);
}
set
{
SetValue(HeaderProperty, value);
}
}
public static readonly DependencyProperty IsSelectedProperty = DependencyProperty.Register("IsSelected", typeof(bool), typeof(UserControlMenuItem));
public bool IsSelected
{
get
{
return (bool)GetValue(IsSelectedProperty);
}
set
{
SetValue(IsSelectedProperty, value);
}
}
public static readonly DependencyProperty IconProperty = DependencyProperty.Register("Icon", typeof(PackIconKind), typeof(UserControlMenuItem));
public PackIconKind Icon
{
get
{
return (PackIconKind)GetValue(IconProperty);
}
set
{
SetValue(IconProperty, value);
}
}
public static readonly DependencyProperty ListViewProperty = DependencyProperty.Register("ListView", typeof(ListView), typeof(UserControlMenuItem), new UIPropertyMetadata(null));
public ListView ListView
{
get
{
return (ListView)GetValue(ListViewProperty);
}
set
{
SetValue(ListViewProperty, value);
}
}
public UserControlMenuItem()
{
InitializeComponent();
DataContext = this;
}
}
在主窗口中调用用户控件
<StackPanel x:Name="st_menu" Margin="10" Orientation="Vertical" ScrollViewer.CanContentScroll="True">
<local:UserControlMenuItem x:Name="MenuItemHome" Header="Home" Icon="Home" PreviewMouseDown="MenuItemHome_PreviewMouseDown">
<local:UserControlMenuItem.ListView>
<ListView SelectionMode="Single" Margin="0 16 0 16">
<ListViewItem>
<TextBlock Text="Item1"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="Item2"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="Item3"/>
</ListViewItem>
</ListView>
</local:UserControlMenuItem.ListView>
</local:UserControlMenuItem>
<local:UserControlMenuItem x:Name="MenuItem2" Header="User" Icon="User" PreviewMouseDown="MenuItemHome_PreviewMouseDown">
<local:UserControlMenuItem.ListView>
<ListView SelectionMode="Single" Margin="0 16 0 16">
<ListViewItem>
<TextBlock Text="User1"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="User2"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="User3"/>
</ListViewItem>
</ListView>
</local:UserControlMenuItem.ListView>
</local:UserControlMenuItem>
<local:UserControlMenuItem x:Name="MenuMes2" Header="Messages" Icon="Chat" PreviewMouseDown="MenuItemHome_PreviewMouseDown">
<local:UserControlMenuItem.ListView>
<ListView SelectionMode="Single" Margin="0 16 0 16">
<ListViewItem>
<TextBlock Text="Message1"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="Message2"/>
</ListViewItem>
<ListViewItem>
<TextBlock Text="Message3"/>
</ListViewItem>
</ListView>
</local:UserControlMenuItem.ListView>
</local:UserControlMenuItem>
</StackPanel>
MainWindow.cs
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
MenuItemHome.IsSelected = true;
}
private void MenuItemHome_PreviewMouseDown(object sender, MouseButtonEventArgs e)
{
foreach (var item in st_menu.Children)
{
if (item is UserControlMenuItem menuItem)
{
if (menuItem.Equals(sender as UserControlMenuItem))
{
menuItem.IsSelected = true;
}
else
{
menuItem.IsSelected = false;
}
}
}
}
}
你应该设置eventArgs.Handled = true;
,它会阻止事件冒泡,比如:
private void MenuItemHome_PreviewMouseDown(object sender, MouseButtonEventArgs e)
{
foreach (var item in st_menu.Children)
{
if (item is UserControlMenuItem menuItem && sender is UserControlMenuItem senderItem)
{
menuItem.IsSelected = menuItem.Equals(senderItem) && !senderItem.IsSelected;
e.Handled = true; //Tells to the visual tree that event was already handled
}
}
}