具有嵌套 ListView 双击事件的 ListView 会触发两次
ListView with nested ListView double click event fires twice
我设置了一个 WPF 应用程序,它显示应用程序的视图列表。
该应用程序使用绑定到 BrowserItem 的可观察集合的 ListView class(具有 Name 和 RelatedViewId 等属性)。
该应用程序有数百个视图,其中一些具有子视图 - 我通过 BrowserItem class 处理了这个问题,其中包含一个名为 'Children' 的 BrowserItem 属性 列表。
我已经设置了事件,因此当用户双击视图时 returns 来自浏览器的视图名称和相关元素 ID Class。
我通过为 ListViewItems 提供一个 TextBlock 和一个 ListView 来处理子视图 - 然后将 listView 绑定到 BrowserItem 的子列表。
这一切都很好:
Capture of application running
我遇到的问题是,当单击子项时,子项和父项 ListItem
的事件都会被触发。
有没有什么方法可以在双击子项目时只为子项目触发双击事件,而不是为它的父容器触发。
继承人 XAML:
<ListView Name="ViewList" ItemsSource="{Binding GroupItems}">
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<EventSetter Event="MouseDoubleClick"
Handler="ViewList_MouseDoubleClick" />
</Style>
</ListView.ItemContainerStyle>
<ListView.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<!--This is the child list, it visibility is set to collapsed if the child count = 0-->
<Expander>
<Expander.Style>
<Style>
<Style.Triggers>
<DataTrigger Binding="{Binding Path=Children.Count}"
Value="0">
<Setter Property="Expander.Visibility"
Value="Collapsed" />
</DataTrigger>
</Style.Triggers>
</Style>
</Expander.Style>
<ListBox ItemsSource="{Binding Children}">
<ListBox.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding Name}" />
</DataTemplate>
</ListBox.ItemTemplate>
<ListBox.ItemContainerStyle>
<Style TargetType="ListBoxItem">
<EventSetter Event="MouseDoubleClick"
Handler="ViewBox_MouseDoubleClickChild" />
</Style>
</ListBox.ItemContainerStyle>
</ListBox>
</Expander>
<TextBlock Text="{Binding Name}">
<TextBlock.Style>
<Style TargetType="{x:Type TextBlock}">
<Style.Triggers>
<DataTrigger Binding="{Binding Active}"
Value="true">
<Setter Property="Background"
Value="YellowGreen" />
</DataTrigger>
</Style.Triggers>
</Style>
</TextBlock.Style>
</TextBlock>
</StackPanel>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.GroupStyle>
<GroupStyle>
<GroupStyle.ContainerStyle>
<Style TargetType="{x:Type GroupItem}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate>
<Expander>
<Expander.Header>
<TextBlock Text="{Binding Name}" />
</Expander.Header>
<ItemsPresenter />
</Expander>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</GroupStyle.ContainerStyle>
</GroupStyle>
</ListView.GroupStyle>
</ListView>
事件调用的背后代码只是获取对象并显示其名称:
单击 ListItem 时的事件:
private void ViewList_MouseDoubleClick(object sender, MouseButtonEventArgs e)
{
ListViewItem picklv = sender as ListViewItem;
BrowserItem chosen = picklv.Content as BrowserItem;
MessageBox.Show("Clicked on View: " + chosen.Name + " Element Id: " + chosen.RelatedElement.ToString());
}
单击“查看子项”列表中的子项时的事件:
private void ViewBox_MouseDoubleClickChild(object sender, MouseButtonEventArgs e)
{
ListBoxItem picklb = sender as ListBoxItem;
BrowserItem pickedsub = picklb.Content as BrowserItem;
MessageBox.Show("Clicked on Child View: " + pickedsub.Name + " Element Id: " + pickedsub.RelatedElement.ToString());
}
通过子元素你必须监听 PreviewMouseDoubleClick
<EventSetter Event="PreviewMouseDoubleClick" Handler="ViewBox_MouseDoubleClickChild" />
并在子事件处理程序中添加 e.Handled = true;
:
private void ViewBox_MouseDoubleClickChild(object sender, MouseButtonEventArgs e)
{
var picklb = sender as ListBoxItem;
var pickedsub = picklb.Content as BrowserItem;
MessageBox.Show("Clicked on Child View: " + pickedsub.Name + " Element Id: " + pickedsub.RelatedElement.ToString());
e.Handled = true;
}
这将防止调用父元素的 MouseDoubleClick
事件处理程序。
我设置了一个 WPF 应用程序,它显示应用程序的视图列表。
该应用程序使用绑定到 BrowserItem 的可观察集合的 ListView class(具有 Name 和 RelatedViewId 等属性)。
该应用程序有数百个视图,其中一些具有子视图 - 我通过 BrowserItem class 处理了这个问题,其中包含一个名为 'Children' 的 BrowserItem 属性 列表。
我已经设置了事件,因此当用户双击视图时 returns 来自浏览器的视图名称和相关元素 ID Class。
我通过为 ListViewItems 提供一个 TextBlock 和一个 ListView 来处理子视图 - 然后将 listView 绑定到 BrowserItem 的子列表。
这一切都很好:
Capture of application running
我遇到的问题是,当单击子项时,子项和父项 ListItem
的事件都会被触发。
有没有什么方法可以在双击子项目时只为子项目触发双击事件,而不是为它的父容器触发。
继承人 XAML:
<ListView Name="ViewList" ItemsSource="{Binding GroupItems}">
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<EventSetter Event="MouseDoubleClick"
Handler="ViewList_MouseDoubleClick" />
</Style>
</ListView.ItemContainerStyle>
<ListView.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal">
<!--This is the child list, it visibility is set to collapsed if the child count = 0-->
<Expander>
<Expander.Style>
<Style>
<Style.Triggers>
<DataTrigger Binding="{Binding Path=Children.Count}"
Value="0">
<Setter Property="Expander.Visibility"
Value="Collapsed" />
</DataTrigger>
</Style.Triggers>
</Style>
</Expander.Style>
<ListBox ItemsSource="{Binding Children}">
<ListBox.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding Name}" />
</DataTemplate>
</ListBox.ItemTemplate>
<ListBox.ItemContainerStyle>
<Style TargetType="ListBoxItem">
<EventSetter Event="MouseDoubleClick"
Handler="ViewBox_MouseDoubleClickChild" />
</Style>
</ListBox.ItemContainerStyle>
</ListBox>
</Expander>
<TextBlock Text="{Binding Name}">
<TextBlock.Style>
<Style TargetType="{x:Type TextBlock}">
<Style.Triggers>
<DataTrigger Binding="{Binding Active}"
Value="true">
<Setter Property="Background"
Value="YellowGreen" />
</DataTrigger>
</Style.Triggers>
</Style>
</TextBlock.Style>
</TextBlock>
</StackPanel>
</DataTemplate>
</ListView.ItemTemplate>
<ListView.GroupStyle>
<GroupStyle>
<GroupStyle.ContainerStyle>
<Style TargetType="{x:Type GroupItem}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate>
<Expander>
<Expander.Header>
<TextBlock Text="{Binding Name}" />
</Expander.Header>
<ItemsPresenter />
</Expander>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</GroupStyle.ContainerStyle>
</GroupStyle>
</ListView.GroupStyle>
</ListView>
事件调用的背后代码只是获取对象并显示其名称:
单击 ListItem 时的事件:
private void ViewList_MouseDoubleClick(object sender, MouseButtonEventArgs e)
{
ListViewItem picklv = sender as ListViewItem;
BrowserItem chosen = picklv.Content as BrowserItem;
MessageBox.Show("Clicked on View: " + chosen.Name + " Element Id: " + chosen.RelatedElement.ToString());
}
单击“查看子项”列表中的子项时的事件:
private void ViewBox_MouseDoubleClickChild(object sender, MouseButtonEventArgs e)
{
ListBoxItem picklb = sender as ListBoxItem;
BrowserItem pickedsub = picklb.Content as BrowserItem;
MessageBox.Show("Clicked on Child View: " + pickedsub.Name + " Element Id: " + pickedsub.RelatedElement.ToString());
}
通过子元素你必须监听 PreviewMouseDoubleClick
<EventSetter Event="PreviewMouseDoubleClick" Handler="ViewBox_MouseDoubleClickChild" />
并在子事件处理程序中添加 e.Handled = true;
:
private void ViewBox_MouseDoubleClickChild(object sender, MouseButtonEventArgs e)
{
var picklb = sender as ListBoxItem;
var pickedsub = picklb.Content as BrowserItem;
MessageBox.Show("Clicked on Child View: " + pickedsub.Name + " Element Id: " + pickedsub.RelatedElement.ToString());
e.Handled = true;
}
这将防止调用父元素的 MouseDoubleClick
事件处理程序。