(背景:我正在分阶段将 WinForms 应用程序移植到 WPF。目前,我仍然有一个 WinForms 主窗体,其中包含一个包含 WPF 内容的 ElementHost。)
我希望在某些ApplicationCommand(例如Cut、Copy和Paste )更改其 .CanExecute 的值时告知我的应用程序。我认为订阅像 ApplicationCommands.Cut.CanExecuteChanged 这样的全局事件很简单,但我注意到一些奇怪的行为,它似乎并没有被一致地调用。
例如,我创建了一个简化的 WinForms 测试应用程序,它只有一个 ElementHost。然后我向它添加了一个 WPF 文本框并将 CanExecuteChanged 处理程序附加到它:
public Form1()
{
InitializeComponent();
var tb = new System.Windows.Controls.TextBox {Text = "WPF Inside ElementHost"};
ApplicationCommands.Cut.CanExecuteChanged += Cut_CanExecuteChanged;
ApplicationCommands.Cut.CanExecuteChanged +=
(s, e) => Debug.WriteLine("CanExecute Changed=" + ApplicationCommands.Cut.CanExecute(null, s as IInputElement));
elementHost1.Child = tb;
}
private void Cut_CanExecuteChanged(object sender, System.EventArgs e)
{
Debug.WriteLine("CanExecute Method for Cut = " + ApplicationCommands.Cut.CanExecute(null, sender as IInputElement));
}
奇怪的是,当我执行诸如在文本框中选择文本之类的操作时,会调用使用内联 lambda/delegate 的处理程序。但是,使用实例方法订阅的那个不会被调用。
此外,在我更复杂的应用程序中,我根本没有看到 CanExecute 被调用,即使我为处理程序使用内联委托也是如此。