8.4 KiB
8.4 KiB
通用窗体使用指南 | General Form Usage Guide
概述 | Overview
XP.Common.GeneralForm 提供 XplorePlane 项目中可复用的通用 WPF 窗体组件。当前包含以下窗体:
| 窗体 | 说明 |
|---|---|
ProgressWindow |
模态进度条窗口,支持线程安全的进度更新和关闭操作 |
InputDialog |
通用输入对话框,支持单行文本输入、可选验证和多语言按钮 |
目录结构 | Directory Structure
XP.Common/GeneralForm/
├── ViewModels/
│ ├── InputDialogViewModel.cs # 输入对话框 ViewModel
│ └── ProgressWindowViewModel.cs # 进度窗口 ViewModel
└── Views/
├── InputDialog.xaml # 输入对话框 XAML 视图
├── InputDialog.xaml.cs # 输入对话框 Code-Behind
├── ProgressWindow.xaml # 进度窗口 XAML 视图
└── ProgressWindow.xaml.cs # 进度窗口 Code-Behind
ProgressWindow 进度条窗口
功能特性 | Features
- 模态进度条窗口,居中显示,不可调整大小
- 线程安全:
UpdateProgress()和Close()可从任意线程调用,内部自动通过Dispatcher调度 - 可配置是否允许用户手动关闭窗口(
isCancelable参数) - 不可取消时,通过 Win32 API 禁用窗口关闭按钮(灰色不可点击)
- 进度值自动 Clamp 到
[0, 100]范围,超出范围时记录 Warn 日志 - 自动继承主窗口图标
- 使用 Telerik
RadProgressBar控件(Crystal 主题)
构造函数参数 | Constructor Parameters
public ProgressWindow(
string title = "操作进行中", // 窗口标题
string message = "请稍候...", // 提示信息
bool isCancelable = true, // 是否允许用户关闭窗口
ILoggerService? logger = null // 日志服务(可选)
)
| 参数 | 类型 | 默认值 | 说明 |
|---|---|---|---|
title |
string |
"操作进行中" |
窗口标题栏文本 |
message |
string |
"请稍候..." |
进度条上方的提示信息 |
isCancelable |
bool |
true |
true:用户可手动关闭;false:禁用关闭按钮 |
logger |
ILoggerService? |
null |
传入日志服务后自动记录窗口生命周期日志 |
公开方法 | Public Methods
UpdateProgress - 更新进度
// 线程安全,可从任意线程调用
void UpdateProgress(string message, double progress)
message:更新提示信息文本progress:进度值(0-100),超出范围自动修正
Close - 关闭窗口
// 线程安全,可从任意线程调用(隐藏基类 Window.Close())
new void Close()
基本用法 | Basic Usage
using XP.Common.GeneralForm.Views;
using XP.Common.Logging.Interfaces;
public class SomeService
{
private readonly ILoggerService _logger;
public SomeService(ILoggerService logger)
{
_logger = logger?.ForModule<SomeService>()
?? throw new ArgumentNullException(nameof(logger));
}
public async Task ExecuteLongOperation()
{
// 创建进度窗口(不可取消)
var progressWindow = new ProgressWindow(
title: "数据处理中",
message: "正在初始化...",
isCancelable: false,
logger: _logger);
// 显示模态窗口(需在 UI 线程调用)
// 注意:ShowDialog() 会阻塞,通常配合 Task 使用
_ = Task.Run(async () =>
{
try
{
progressWindow.UpdateProgress("正在加载数据...", 20);
await Task.Delay(1000); // 模拟耗时操作
progressWindow.UpdateProgress("正在处理数据...", 60);
await Task.Delay(1000);
progressWindow.UpdateProgress("即将完成...", 90);
await Task.Delay(500);
progressWindow.UpdateProgress("完成", 100);
}
finally
{
// 关闭窗口(线程安全)
progressWindow.Close();
}
});
progressWindow.ShowDialog();
}
}
允许用户取消的用法 | Cancelable Usage
// 创建可取消的进度窗口
var progressWindow = new ProgressWindow(
title: "文件导出",
message: "正在导出文件...",
isCancelable: true, // 用户可以点击关闭按钮取消
logger: _logger);
progressWindow.ShowDialog();
ViewModel 绑定属性 | ViewModel Binding Properties
ProgressWindowViewModel 继承自 BindableBase,提供以下可绑定属性:
| 属性 | 类型 | 说明 |
|---|---|---|
Title |
string |
窗口标题(只读) |
Message |
string |
提示信息文本(可通知) |
Progress |
double |
进度值 0-100(可通知) |
ProgressText |
string |
百分比显示文本,如 "75%"(只读,自动计算) |
IsCancelable |
bool |
是否允许用户关闭(只读) |
注意事项 | Notes
ShowDialog()必须在 UI 线程调用,它会阻塞当前线程直到窗口关闭UpdateProgress()和Close()内部已处理跨线程调度,可安全地从后台线程调用- 当
isCancelable = false时,窗口关闭按钮会被 Win32 API 禁用(灰色),用户无法通过 Alt+F4 或点击关闭 - 进度值超出
[0, 100]范围时会自动修正并记录 Warn 级别日志 Close()使用new关键字隐藏基类方法(因Window.Close()非虚方法),确保通过ProgressWindow类型引用调用
InputDialog 输入对话框
功能特性 | Features
- 模态输入对话框,居中于父窗口显示,不可调整大小
- 自动继承主窗口图标
- 按钮文本支持多语言(使用
Button_OK/Button_Cancel资源键) - 可选的输入验证委托(
Func<string, string?>),验证失败时在输入框下方显示红色错误提示 - 输入内容变化时自动清除验证错误
- 使用 Telerik
RadWatermarkTextBox和RadButton控件(Crystal 主题) - 提供静态
Show()便捷方法,一行代码即可调用
静态方法 | Static Method
public static string? Show(
string prompt, // 提示文本
string title, // 窗口标题
string defaultValue = "", // 默认值
Func<string, string?>? validate = null, // 验证委托(可选)
Window? owner = null // 父窗口(可选)
)
| 参数 | 类型 | 默认值 | 说明 |
|---|---|---|---|
prompt |
string |
必填 | 输入框上方的提示文本 |
title |
string |
必填 | 窗口标题栏文本 |
defaultValue |
string |
"" |
输入框的初始值 |
validate |
Func<string, string?>? |
null |
验证委托:返回 null 表示通过,返回错误信息则阻止确认 |
owner |
Window? |
null |
父窗口,设置后对话框居中于父窗口 |
返回值:用户输入的字符串,取消时返回 null。
基本用法 | Basic Usage
using XP.Common.GeneralForm.Views;
// 最简用法,无验证
var name = InputDialog.Show("请输入名称:", "新建项目");
if (name == null) return; // 用户取消
// 带默认值
var port = InputDialog.Show("请输入端口号:", "配置", "8080");
带验证的用法 | Usage with Validation
// 验证委托:返回 null 表示通过,返回错误信息则显示在输入框下方
var groupId = InputDialog.Show(
"请输入 Group ID:",
"新增 Group",
validate: input =>
{
if (string.IsNullOrWhiteSpace(input))
return "ID 不能为空";
if (existingIds.Contains(input))
return "ID 已存在,请使用不同的 ID";
return null; // 验证通过
});
// 验证非负整数
var dbNumber = InputDialog.Show(
"请输入 DB 块号(非负整数):",
"新增 Group",
"0",
validate: input =>
{
if (!int.TryParse(input, out int val) || val < 0)
return "必须为非负整数";
return null;
});
注意事项 | Notes
Show()必须在 UI 线程调用(内部使用ShowDialog())- 验证委托在用户点击确定按钮时执行,验证失败不会关闭对话框
- 用户修改输入内容时会自动清除上一次的验证错误提示
- 按钮文本从 XP.Common 资源文件读取(
Button_OK/Button_Cancel),自动跟随应用语言