using System.ComponentModel; using System.Runtime.CompilerServices; using System.Windows.Threading; namespace ShrlAlgoToolkit.RevitAddins.Common.Controls { // WPF 的 ViewModel public class ProgressViewModel : INotifyPropertyChanged { private readonly CancellationTokenSource _cts; public Dispatcher UIDispatcher { get; set; } public Action CloseAction { get; set; } public ProgressViewModel(string title, CancellationTokenSource cts) { Title = title; _cts = cts; } private string _title; public string Title { get => _title; set => SetProperty(ref _title, value); } private string _message = "正在准备..."; public string Message { get => _message; set => SetProperty(ref _message, value); } private double _progressValue; public double ProgressValue { get => _progressValue; set => SetProperty(ref _progressValue, value); } private double _maximum = 100; public double Maximum { get => _maximum; set => SetProperty(ref _maximum, value); } public void Cancel() { if (!_cts.IsCancellationRequested) { Message = "正在取消任务,请稍候..."; _cts.Cancel(); } } // 跨线程更新 UI public void Update(int current, int total, string message) { UIDispatcher?.InvokeAsync(() => { ProgressValue = current; Maximum = total; if (!string.IsNullOrEmpty(message)) Message = message; }); } public void UpdateMessage(string message) { UIDispatcher?.InvokeAsync(() => Message = message); } public event PropertyChangedEventHandler PropertyChanged; protected void SetProperty(ref T field, T value, [CallerMemberName] string propertyName = null) { field = value; PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName)); } } }