# MessageBox 使用文档 本文档介绍 AtomUI MessageBox 控件的各种使用方式,示例代码摘自 Gallery 演示程序。 > 📖 Gallery 源码位置:`controlgallery/AtomUIGallery/ShowCases/Views/Feedback/ModalShowCase.axaml`("MessageBox Style" 部分) --- ## 前置准备 在 AXAML 中使用 MessageBox,需要引入以下命名空间: ```xml xmlns:atom="https://atomui.net" ``` 在 C# 代码中引入: ```csharp using AtomUI.Desktop.Controls; // MessageBox, MessageBoxOptions, MessageBoxStyle using Avalonia.Controls; // TopLevel, Control ``` > ⚠️ **前提条件**:使用静态 API 时,应用程序必须使用 `atom:Window` 作为顶级窗口,因为 MessageBox 需要通过 `GlobalDialogManager` 管理弹窗,而该管理器仅在 `atom:Window` 中自动注册。 --- ## 1. 声明式使用(AXAML) 在 AXAML 中直接声明 ``,通过 `IsOpen` 双向绑定控制开关状态: ### 基本 Confirm 弹框 ```xml Some descriptions Confirm ``` ### 不同消息样式 ```xml some messages...some messages... some messages...some messages... Information some messages...some messages... Success some messages... Error some messages... Warning ``` **声明式使用要点**: - MessageBox 与触发按钮放在同一个 `Panel` 中 - `PlacementTarget` 指向触发按钮的 `Name`,用于定位弹窗位置 - `IsOpen` 必须使用 `Mode=TwoWay` 双向绑定,以便弹框关闭时自动重置为 `false` - 消息内容作为 MessageBox 的子内容(`Content` 属性标记了 `[Content]`) --- ## 2. 命令式使用(静态 API) 通过静态方法在代码中快速弹出消息弹框,无需在 AXAML 中预先声明: ### 异步模态调用(推荐) ```csharp private async void HandleCreateConfirmMessageBox(object? sender, RoutedEventArgs e) { await Dispatcher.UIThread.InvokeAsync(() => { }, DispatcherPriority.Background); var content = new StackPanel { Orientation = Orientation.Vertical, Spacing = 5, Children = { new TextBlock { Text = "Some contents..." }, new TextBlock { Text = "Some contents..." } } }; var options = new MessageBoxOptions { Title = "Do you want to delete these items?", IsDragMovable = true, IsCenterOnStartup = true, Style = MessageBoxStyle.Confirm }; await MessageBox.ShowMessageModalAsync(content, null, options); } ``` ### 不同样式的静态调用 ```csharp // Information 样式 private async void ShowInfoMessage(object? sender, RoutedEventArgs e) { await Dispatcher.UIThread.InvokeAsync(() => { }, DispatcherPriority.Background); var content = BuildContent(); var options = new MessageBoxOptions { Title = "This is a notification message", Style = MessageBoxStyle.Information, IsDragMovable = true }; await MessageBox.ShowMessageModalAsync(content, null, options); } // Success 样式 private async void ShowSuccessMessage(object? sender, RoutedEventArgs e) { await Dispatcher.UIThread.InvokeAsync(() => { }, DispatcherPriority.Background); var content = BuildContent(); var options = new MessageBoxOptions { Title = "Operation successful", Style = MessageBoxStyle.Success, IsDragMovable = true }; await MessageBox.ShowMessageModalAsync(content, null, options); } // Error 样式 private async void ShowErrorMessage(object? sender, RoutedEventArgs e) { await Dispatcher.UIThread.InvokeAsync(() => { }, DispatcherPriority.Background); var content = BuildContent(); var options = new MessageBoxOptions { Title = "This is an error message", Style = MessageBoxStyle.Error, IsDragMovable = true }; await MessageBox.ShowMessageModalAsync(content, null, options); } ``` **静态 API 使用要点**: - 在事件处理器中使用 `await Dispatcher.UIThread.InvokeAsync(() => { }, DispatcherPriority.Background)` 确保 UI 线程完成当前布局后再弹出 - `ShowMessageModalAsync` 是最常用的方法——模态弹出并返回用户操作结果 - 静态方法会自动查找 `GlobalDialogManager` 并管理弹窗的创建和清理 - 弹窗关闭后自动从 `GlobalDialogManager` 中移除 --- ## 3. 获取操作结果 ### 模态方式获取结果 ```csharp var result = await MessageBox.ShowMessageModalAsync(content, null, options); // result 包含用户的操作结果 if (result != null) { // 用户点击了确认 } ``` ### 回调方式获取结果 ```csharp await MessageBox.ShowMessageBoxAsync( viewModel, options, closed: (actionResult) => { var result = actionResult.Result; // 处理关闭后的逻辑 } ); ``` --- ## 4. 使用 Window 宿主模式 默认使用 Overlay 模式(页面内浮层),可以切换为 Window 模式(独立原生窗口): ```xml 这将在独立窗口中显示。 ``` ```csharp // 静态 API 中指定 Window 模式 var options = new MessageBoxOptions { Title = "原生窗口弹框", Style = MessageBoxStyle.Information, HostType = DialogHostType.Window }; await MessageBox.ShowMessageModalAsync(content, null, options); ``` --- ## 5. 拖拽移动 ```xml 拖拽标题栏移动此弹框。 ``` --- ## 6. 轻量关闭(点击遮罩关闭) 仅 Overlay 模式有效: ```xml 点击弹框外部区域即可关闭。 ``` --- ## 7. 自定义尺寸 ```csharp var options = new MessageBoxOptions { Title = "固定尺寸弹框", Style = MessageBoxStyle.Information, Width = 500, Height = 300, MinWidth = 400, MaxWidth = 600 }; await MessageBox.ShowMessageModalAsync(content, null, options); ``` --- ## 8. 监听事件 ```csharp // 声明式使用时,在 Code-behind 中订阅事件 var messageBox = new MessageBox { Title = "确认操作", Style = MessageBoxStyle.Confirm }; messageBox.Confirmed += (sender, e) => { // 用户点击了确认按钮 Console.WriteLine("Confirmed!"); }; messageBox.Cancelled += (sender, e) => { // 用户点击了取消按钮 Console.WriteLine("Cancelled!"); }; messageBox.Closed += (sender, e) => { // 弹框关闭(无论确认还是取消) Console.WriteLine("Closed!"); }; ``` --- ## 9. MVVM 绑定模式 MessageBox 天然支持 MVVM 模式——内容通过 `Content` 属性传入,DataContext 可以绑定到 ViewModel: ### 泛型方式(推荐) ```csharp // 自动创建 TView 实例并设置 DataContext await MessageBox.ShowMessageBoxModalAsync( viewModel, new MessageBoxOptions { Title = "确认操作", Style = MessageBoxStyle.Confirm } ); ``` ### 自定义内容方式 ```csharp var content = new ConfirmView(); await MessageBox.ShowMessageModalAsync( content, viewModel, // 设置为 content.DataContext new MessageBoxOptions { Title = "确认操作", Style = MessageBoxStyle.Confirm } ); ``` --- ## 常见使用模式 ### 删除确认 ```csharp private async void OnDeleteClick(object? sender, RoutedEventArgs e) { await Dispatcher.UIThread.InvokeAsync(() => { }, DispatcherPriority.Background); var content = new TextBlock { Text = "确定要删除选中的项目吗?此操作不可恢复。" }; var options = new MessageBoxOptions { Title = "确认删除", Style = MessageBoxStyle.Confirm, IsCenterOnStartup = true }; var result = await MessageBox.ShowMessageModalAsync(content, null, options); // 根据 result 判断用户操作 } ``` ### 操作成功提示 ```csharp private async void ShowSuccessNotice() { await Dispatcher.UIThread.InvokeAsync(() => { }, DispatcherPriority.Background); var content = new TextBlock { Text = "数据已成功保存到服务器。" }; var options = new MessageBoxOptions { Title = "保存成功", Style = MessageBoxStyle.Success }; await MessageBox.ShowMessageModalAsync(content, null, options); } ``` ### 错误详情展示 ```csharp private async void ShowError(Exception ex) { await Dispatcher.UIThread.InvokeAsync(() => { }, DispatcherPriority.Background); var content = new StackPanel { Spacing = 8, Children = { new TextBlock { Text = ex.Message }, new TextBlock { Text = ex.StackTrace, FontSize = 10, Opacity = 0.6 } } }; var options = new MessageBoxOptions { Title = "操作失败", Style = MessageBoxStyle.Error, MaxWidth = 600 }; await MessageBox.ShowMessageModalAsync(content, null, options); } ```