开源代码分享: GoldArch.TaskWrapperReport task执行生命周期封装,处理过程报告

GoldArch TaskWrapper 和 UI 控件

开源地址:https://github.com/goldarch/GoldArch.TaskWrapperReport

.NET Windows 窗体库用于简化后台任务管理,并带有用于进度报告和状态显示的集成 UI 控件。

概述

GoldArch.TaskWrapper库(位于GoldArch.TaskWrapperReport代码中的命名空间结构中)提供了一个强大的TaskWrapper类来执行异步操作,同时提供对进度报告、取消、状态管理和错误处理的细粒度控制。它由一套自定义 UI 控件补充,旨在有效地可视化任务进度和日志。

所提供的解决方案包括:

  • GoldArch.TaskWrapper(类库组件):包含核心TaskWrapper逻辑和可重用的 UI 控件。它们组织在GoldArch.TaskWrapperReport.TaskWrapperCoreGoldArch.TaskWrapperReport.TaskReportControl和 等命名空间中GoldArch.TaskWrapperReport.Common
  • GoldArch.TaskWrapper.Simple(WinForms 应用程序):一个展示该库的各种功能和 UI 控件的演示项目。

特征

核心任务包装器(GoldArch.TaskWrapperReport.TaskWrapperCore.TaskWrapper

  • 异步任务执行:在后台线程上运行长时间运行的操作,而不会冻结 UI。
  • 进度报告:任务可以使用对象报告进度更新包括消息、百分比值和严重性级别(Information、、、等)WarningErrorSuccessTaskProgressInfo
  • CancellationToken 支持:通过 优雅地取消任务CancellationTokenSource
  • 状态管理:任务通过枚举中定义的明确状态,,,,,,Idle进行转换StartingRunningCancellingCompletedFaultedCancelledTaskExecutionState
  • 错误处理:捕获并报告任务中的异常,并提供TaskStateChangedEventArgs包含异常详细信息的事件。
  • 生命周期操作:定义在任务开始之前(BeforeDoWorkAction)和任务完成之后(AfterCompletionAction)要执行的操作。
  • 可配置堆栈跟踪显示:在报告中显示或隐藏错误堆栈跟踪的选项(ShowErrorStackTrace属性)。

UI 控件(GoldArch.TaskWrapperReport.TaskReportControl

  • TextProgressBarProgressBar可直接在其上显示文本的自定义,具有可配置的文本/进度颜色和CustomText属性。
  • RichTextBoxEx增强了RichTextBox自动滚动行为,尤其是在用户可能已滚动到其他位置时追加文本。它使用 Win32 消息(例如EM_GETSCROLLPOS和 )EM_SETSCROLLPOS进行滚动管理。
  • StatusProgressBar一个紧凑的用户控件,使用TextProgressBar将所有任务状态(空闲、运行、已完成、错误等)和进度信息以格式化文本的形式显示在进度条上。提供针对不同状态(例如TextFormatIdleProgressBarRunningColor)的丰富颜色和文本自定义功能。
  • StatusProgressDisplay一个用户控件,具有Label状态文本(lblStatus)和TextProgressBar进度条可视化效果。它清晰地区分了状态信息和进度条可视化效果,并可自定义不同状态的颜色和文本(例如StatusTextIdleProgressBarIdleColor)。
  • TaskReportRichTextBox一个全面的用户控件,集成了TextProgressBar用于RichTextBoxEx详细日志记录的 和取消按钮。它内部管理TaskWrapperInstance,并提供丰富的任务报告界面,并可根据不同的日志级别(例如InfoTextColorErrorTextColor)自定义文本颜色。

辅助类

  • TaskExecutionHelper提供静态辅助方法(ExecuteAction, ),以便使用更简洁的语法ExecuteAsyncFunc快速运行任务。TaskWrapper
  • ControlInvokeHelperControl.Invoke使用和从非 UI 线程安全地调用 UI 控件上的操作的实用程序Control.BeginInvoke
  • TaskReportUtil简单的实用程序,例如,用于格式化时间戳(例如Now年月日时分秒)。

数据结构

  • TaskProgressInfo封装进度更新细节(内容消息、进度文本、进度值、报告级别)。
  • ReportLevel(枚举):定义进度消息的性质(例如,,,,,InformationWarningErrorSuccessDetail
  • TaskExecutionState(枚举):表示任务的当前状态(例如Idle,,,,RunningCompletedFaulted

项目结构(基于提供的文件)

  • GoldArch.TaskWrapper/(概念库根)
    • Common/ControlInvokeHelper.cs
    • Properties/(AssemblyInfo.cs、Resources.Designer.cs、Settings.Designer.cs)
    • TaskReportControl/(TextProgressBar.cs、RichTextBoxEx.cs、StatusProgressBar.cs、StatusProgressDisplay.cs、TaskReportRichTextBox.cs 及其 .designer.cs 文件)
    • TaskWrapperCore/(TaskWrapper.cs、TaskProgressInfo.cs、TaskReportUtil.cs、TaskExecutionHelper.cs)
  • GoldArch.TaskWrapper.Simple/(演示应用程序)
    • Properties/(AssemblyInfo.cs、Resources.Designer.cs、Settings.Designer.cs)
    • Program.cs
    • MainForm.cs
    • SimpleProgressForm.cs
    • SimpleProgressForm02.cs
    • SimpleProgressForm03.cs
    • App.config

如何使用

1.使用TaskReportRichTextBox(推荐用于详细日志)

此控件是独立的并管理其自己的TaskWrapperInstance

// In your Form:
// Add TaskReportRichTextBox control (e.g., taskReportControl1) via designer or code.

// Configure in MainForm.cs or similar:
private void SetupTaskReportControl()
{
    taskReportControl1.ShowCancelButton = true;
    taskReportControl1.ShowErrorStackTraceInWrapper = true; 
    taskReportControl1.IsScrollToEndAfterReport = true;   

    taskReportControl1.TaskWrapperInstance.StateChanged += (s, e) => {
        // Custom logic based on task state
    };
}

private void BtnStartComplexTask_Click(object sender, EventArgs e)
{
    var wrapper = taskReportControl1.TaskWrapperInstance;
    // Check if task is already running
    if (wrapper.CurrentState == TaskExecutionState.Running || wrapper.CurrentState == TaskExecutionState.Starting)
    {
        MessageBox.Show("A task is already running.");
        return;
    }
    taskReportControl1.ResetReportControl(); 

    wrapper.DoWorkFuncAsync = async (token, progress) =>
    {
        for (int i = 0; i <= 10; i++)
        {
            token.ThrowIfCancellationRequested();
            await Task.Delay(500, token).ConfigureAwait(false);

            progress.Report(new TaskProgressInfo(
                content: $"Step {i + 1} logged. Details...\n",
                progressText: $"Processing item {i + 1} of 11",
                progressValue: (i + 1) * (100 / 11), // Example calculation
                level: i > 7 ? ReportLevel.Warning : ReportLevel.Information
            ));
        }
        progress.Report(new TaskProgressInfo("All steps processed successfully!", ReportLevel.Success));
        return null; // Success
    };
    
    wrapper.StartTaskAsync();
}

// To report messages not directly tied to the TaskWrapper's current task:
private void BtnReportDirectly_Click(object sender, EventArgs e)
{
    taskReportControl1.ReportDirectContent(
        $"This is a direct informational message.\n", ReportLevel.Information);
    taskReportControl1.ReportDirectProgress("Direct Update", 50, ReportLevel.StatusUpdate);
}
 

2. 使用 TaskWrapper 和 StatusProgressDisplay 或 StatusProgressBar

(示例改编自 SimpleProgressForm02.cs 和 SimpleProgressForm03.cs)

// In your Form (e.g., for StatusProgressDisplay):
// private StatusProgressDisplay statusProgressDisplayControl;
// private TaskWrapper _taskWrapper;

private void InitializeMyForm()
{
    _taskWrapper = new TaskWrapperReport.TaskWrapperCore.TaskWrapper();
    statusProgressDisplayControl.ResetDisplay(_taskWrapper.TextProgressBarMinimum, _taskWrapper.TextProgressBarMaximum);

    _taskWrapper.ProgressReporter.ProgressChanged += (s, progressInfo) => {
        statusProgressDisplayControl.ReportProgress(progressInfo, _taskWrapper.CurrentState);
    };
    _taskWrapper.StateChanged += (s, stateArgs) => {
        ControlInvokeHelper.ControlInvoke(this, () => { 
            statusProgressDisplayControl.SetVisualState(stateArgs.NewState, stateArgs.Exception);
            // Update other UI like button states
        });
    };
}

private void BtnStartTask_Click(object sender, EventArgs e)
{
    // Check if task is runnable and reset display
    statusProgressDisplayControl.ResetDisplay(_taskWrapper.TextProgressBarMinimum, _taskWrapper.TextProgressBarMaximum);

    _taskWrapper.DoWorkFuncAsync = async (token, progress) =>
    {
        // Your task logic here, reporting progress via progress.Report(...)
        return null; // On success
    };
    _taskWrapper.StartTaskAsync(reportWrapperStatusMessages: false); // Let the control handle status messages
}

// Remember to dispose _taskWrapper in FormClosing event
 

构建并运行演示

克隆代码库https://github.com/goldarch/GoldArch.TaskWrapperReport。在 Visual Studio 中打开解决方案(可能是 GoldArch.TaskWrapperReport.sln 或类似文件)。将 GoldArch.TaskWrapper.Simple 设置为启动项目。构建并运行。演示应用程序将会出现,您可以测试各种任务报告场景。

依赖项

.NET Framework 4.5.2

posted @ 2025-06-05 09:34  GoldArch  阅读(18)  评论(1)    收藏  举报