WPF UserControl中按钮执行命令或点击事件后修改文本的实现疑问
实现方案
核心问题本质是需要捕获第三步业务逻辑的执行完成信号,根据你使用Command还是自定义点击事件,有两种常用实现方式:
1. 绑定Command场景
优先推荐使用异步Command实现,你可以直接在按钮的点击事件中等待Command执行完成后修改文本:
第一步:定义异步Command接口(如果没有使用自带异步Command的第三方MVVM框架)
public interface IAsyncCommand : ICommand { Task ExecuteAsync(object parameter); }
第二步:编写按钮点击事件逻辑
private async void YourButton_Click(object sender, RoutedEventArgs e) { // 第二步:立刻修改文本为等待状态 YourButton.Content = "please wait"; // 第三步:执行绑定的Command if (YourButton.Command is ICommand command && command.CanExecute(YourButton.CommandParameter)) { if (command is IAsyncCommand asyncCommand) { // 等待异步命令执行完成 await asyncCommand.ExecuteAsync(YourButton.CommandParameter); } else { // 兼容同步Command,耗时逻辑避免阻塞UI线程 await Task.Run(() => command.Execute(YourButton.CommandParameter)); } } // 第四步:执行完成后修改文本 YourButton.Content = "it's done"; }
注:代码中
YourButton替换为你UserControl内按钮的x:Name属性值。
2. 自定义点击事件场景
如果是对外暴露自定义点击事件给外部使用,将事件委托修改为异步委托即可:
第一步:在UserControl中定义自定义点击事件
// 对外暴露的异步点击事件 public event Func<object, RoutedEventArgs, Task> CustomClick;
第二步:编写按钮点击事件逻辑
private async void YourButton_Click(object sender, RoutedEventArgs e) { YourButton.Content = "please wait"; // 第三步:执行所有外部订阅的点击事件逻辑 var handlers = CustomClick?.GetInvocationList(); if (handlers != null) { foreach (var handler in handlers) { if (handler is Func<object, RoutedEventArgs, Task> asyncHandler) { await asyncHandler(sender, e); } else { // 兼容同步事件处理逻辑 handler.DynamicInvoke(sender, e); } } } YourButton.Content = "it's done"; }
注意:如果你的业务逻辑包含UI操作,不要使用
Task.Run包裹执行,否则会触发跨线程访问异常,直接同步执行即可。
内容的提问来源于stack exchange,提问作者Hossein
相关产品推荐
相关产品推荐

