I found one bug, and I don't understand, why it's happening. I have DataGrid. On left mouse button click I want to open ContextMenu. I made it. It works fine until I start clicking on DataGrid's Cells on random (every time ContextMenu is closing and reappearing at new place). But at one moment something is happening and ContextMenu newer showing (and Window don't response to any Mouse events like clicking on buttons and so on)... until I move cursor out of window and return it (or clicking Alt or F10).
Here some code:
ContextMenu (inside <DataGrid.Resources>
)
<ContextMenu Style="{StaticResource DefaultContextMenuStyle}" x:Key="cm"
DataContext="{Binding Data, Source={StaticResource WindowViewModel}}">
</ContextMenu>
DataGrid column:
<DataGridTemplateColumn Header="TestHeader" Width="*">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<DockPanel ContextMenu="{StaticResource cm}" VerticalAlignment="Stretch" Background="Transparent">
<i:Interaction.Behaviors>
<local:OpenContextMenuLeftBehavior />
</i:Interaction.Behaviors>
<TextBlock Style="{StaticResource TextVCenteredCellStyle}" Text="{Binding LPU}" />
</DockPanel>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
And behavior to open ContextMenu:
public class OpenContextMenuLeftBehavior : Behavior<FrameworkElement>
{
protected override void OnAttached()
{
AssociatedObject.PreviewMouseUp += OpenContextMenu;
}
protected override void OnDetaching()
{
AssociatedObject.PreviewMouseUp -= OpenContextMenu;
}
void OpenContextMenu(object sender, MouseButtonEventArgs e)
{
if (e.ChangedButton == MouseButton.Left) {
FrameworkElement Sender = sender as FrameworkElement;
Sender.ContextMenu.PlacementTarget = Sender;
Sender.ContextMenu.IsOpen = true;
}
}
}
When I found that bug, I tried to find some info with Snoop WPF. And here some info from it:
Before bad thing happened one click on cell was like:
before bad thing
After bad thing:
after bad thing
First event happened at Popup (ContextMenu part?), it doesn't belong to window VisualTree. This Popup seems to stretch all over the main Window and closing, when i move mouse out of it.
So, I lost 2 days on that bug and this is all, that I can find.
Please help me.
EDIT: I created minimal example:
XAML:
<Window x:Class="WpfApplication1.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
xmlns:local="clr-namespace:WpfApplication1"
Title="MainWindow" Height="350" Width="525">
<Grid>
<DataGrid x:Name="dg1" IsReadOnly="True">
<DataGrid.Columns>
<DataGridTemplateColumn Width="*">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<DockPanel>
<i:Interaction.Behaviors>
<local:OpenContextMenuLeftBehavior />
</i:Interaction.Behaviors>
<DockPanel.ContextMenu>
<ContextMenu>
<MenuItem Header="123456"></MenuItem>
</ContextMenu>
</DockPanel.ContextMenu>
<TextBlock Text="123" />
</DockPanel>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
</Grid>
</Window>
Code behind:
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
dg1.ItemsSource = new List<int>()
{
1,2,3,4,5,6,7,8,9,0
};
}
}
public class OpenContextMenuLeftBehavior : Behavior<FrameworkElement>
{
protected override void OnAttached()
{
AssociatedObject.PreviewMouseUp += OpenContextMenu;
}
protected override void OnDetaching()
{
AssociatedObject.PreviewMouseUp -= OpenContextMenu;
}
void OpenContextMenu(object sender, MouseButtonEventArgs e)
{
if (e.ChangedButton == MouseButton.Left) {
FrameworkElement Sender = sender as FrameworkElement;
if (Sender != null) {
Sender.ContextMenu.PlacementTarget = Sender;
Sender.ContextMenu.IsOpen = true;
Sender.ContextMenu.UpdateLayout();
}
}
}
}
To reproduce this bug just click rapidly on different cells
答案 0 :(得分:0)
修订答案
在您发布完整,简单的示例后,我建议如下: 在您创建ContextMenu
之后 Sender.ContextMenu.IsOpen = true;
Sender.ContextMenu.PreviewMouseUp += ContextMenu_PreviewMouseUp;
已定义
private void ContextMenu_PreviewMouseUp(object sender, MouseButtonEventArgs e)
{
var Sender = (sender as ContextMenu);
if (Sender != null)
{
Sender.IsOpen = true;
e.Handled = true;
}
}
(你仍然需要管理网格线选择,但这就像这里的主题一样)