在WPF开发中,按钮的点击和不可点击常用命令绑定来自动完成。例如下面的示例:
xmal代码:
后台窗体Load 事件中绑定命令代码:
bool isUndo=true;
CommandBinding cmdBinding
= new CommandBinding(ApplicationCommands.Undo,
(s1, exeArgs) =>
{
RoutedCommand cmd = exeArgs.Command as RoutedCommand;
if (cmd != null)
{
string cmdName = cmd.Name;
MessageBox.Show(cmdName);
}
},
(s2, canExeArgs) =>
{
canExeArgs.CanExecute = isUndo;
}
);
this.CommandBindings.Add(cmdBinding);
此时运行程序,按组合快捷键ctrl+z ,会弹出“undo”字样,
如果在this.CommandBindings.Add(cmdBinding) 后加入如下代码:
Thread td = new Thread(new ThreadStart(() =>
{
Thread.Sleep(1000*5);
isUndo = false;
}));
td.Start();
窗体Load后,不做任何操作,包括移动鼠标或按住某个键盘键,理论上5秒后按钮会变为不可用。但实际上需要触碰下界面或移动鼠标,按住键盘等才可以使按钮反灰不可用。
此时解决办法是: CommandManager.InvalidateRequerySuggested();
Thread td = new Thread(new ThreadStart(() =>
{
Thread.Sleep(1000*10);
isUndo = false;
CommandManager.InvalidateRequerySuggested();
}));
再次运行程序(切记:不做任何操作,包括移动鼠标或按住某个键盘键)发现5s后按钮还未变灰。问题在哪里?
原因在于CommandManager.InvalidateRequerySuggested()需要在UI线程中运行,该如下方式即可:
this.Dispatcher.BeginInvoke(new Action(() =>
{
CommandManager.InvalidateRequerySuggested();
}));