这看起来很简单,但绝对不能按预期工作。在WPF 4.0中,我正在尝试使用菜单栏创建一个窗口,该菜单栏接受键盘快捷键...只需一个简单的窗口,顶部的菜单栏和其他一些内容(在AvalonDock内部,可能是部分问题)。
有一个问题:菜单栏&内容是在另一个用户控件(让我们称之为SadPanda
,因为它让我成为一个悲伤的熊猫),这是窗口的直接内容。逻辑层次结构看起来像这样(不是实际的XAML):
<Window>
<UserControl x:Name="SadPanda" Focusable="True" FocusManager.IsFocusScope="True">
<Grid>
<MenuBar/>
<AvalonDock:DockingManager>
<PandaFood>
</AvalonDock:DockingManager>
</Grid>
</UserControl>
</Window>
窗口的内容需要访问窗口的Handle,所以在窗口加载之后设置就像这样:
window.Loaded += delegate { window.Content = new SadPanda(); };
菜单栏&amp;快捷键具有绑定到SadPanda的路由命令,当键盘焦点丢失时,输入手势不再起作用,因此悲伤的熊猫。我补充说:
LostKeyboardFocus += (sender, e) => Debug.WriteLine("Lost focus to " + e.NewFocus);
GotKeyboardFocus += (sender, e) => Debug.WriteLine("Got focus from " + e.OldFocus);
......似乎重点是回到Window,而不是回到SadPanda本身。如果我在窗口上设置Focusable =“False”,则焦点变为null;甚至从未考虑过控制。我尝试过(在评论中由alpha-mouse建议):
window.GotKeyboardFocus += delegate { Keyboard.Focus(sadPanda); };
即使这样也行不通 - 它会阻止菜单打开(它们会闪烁一秒钟,然后消失)或文本框变得焦点......不确定为什么;这似乎是完美的解决方案。
基本上,我希望用户控件具有顶级键盘焦点,而不是窗口。实现这一目标的最简单方法是什么?
答案 0 :(得分:3)
我仍然不确定为什么会这样,但这是我找到的解决方案:
Focusable="False"
和FocusManager.IsFocusScope="False"
。Focusable="True"
和FocusManager.IsFocusScope="True"
。三。使用以下内容:
PleasedPanda.LostKeyboardFocus += (sender, e) =>
{
if(e.NewFocus == null)
{
Keyboard.Focus(PleasedPanda);
}
}
我不确定为什么这会有效,而更明显的window.GotKeyboardFocus
没有,但那是你的WPF。
答案 1 :(得分:1)
在黑客的右边。您可以处理Window.GotKeyboardFocus
以立即关注SadPanda
。但可能有更好的解决方案。