VB.Net函数阻塞UI求助:需保留UI操作权限以终止任务
问题分析与解决方案
你的代码核心问题在于线程和异步逻辑混用导致的混乱,加上缺少任务取消机制,具体问题包括:
- 手动创建
Thread后,内部调用Task.WhenAll却没有Await,线程会提前结束,异步任务脱离控制 refreshRichTextBox里用Task.Run包裹Invoke完全多余,Invoke本身就是切换回UI线程,多此一举反而增加开销- 所有行的处理任务并行执行,短时间内大量UI更新请求可能导致UI线程阻塞
- 没有提供任务终止的入口,无法中途停止处理
修正后的代码
首先在窗体类里定义一个取消令牌源:
Private cts As CancellationTokenSource
然后重写按钮点击事件和相关方法:
Private Async Sub Button2_Click(sender As Object, e As EventArgs) Handles Button2.Click ' 先停止之前的任务(如果有的话) cts?.Cancel() cts?.Dispose() cts = New CancellationTokenSource() Try ' 初始化日志分隔线 AppendToRichTextBox(RichTextBox1, vbCrLf & "======================================================") ' 拆分GCode行,过滤空行 Dim GCODES As String() = GCode.Split({vbCrLf}, StringSplitOptions.RemoveEmptyEntries) ' 逐行异步处理(如果需要并行,可限制并发数,比如用SemaphoreSlim) For Each line In GCODES ' 检查是否取消 cts.Token.ThrowIfCancellationRequested() ' 处理单行(后续可加入SerialPort发送逻辑) Await ProcessLineAsync(line) ' 可选:如果需要控制处理速度,加个延迟 ' Await Task.Delay(100, cts.Token) Next Catch ex As OperationCanceledException AppendToRichTextBox(RichTextBox1, vbCrLf & "任务已终止") Catch ex As Exception AppendToRichTextBox(RichTextBox1, vbCrLf & $"出错:{ex.Message}") Finally cts.Dispose() cts = Nothing End Try End Sub Private Async Function ProcessLineAsync(line As String) As Task ' 这里后续加入SerialPort发送逻辑,比如: ' Await serialPort.WriteLineAsync(line) ' 更新RichTextBox AppendToRichTextBox(RichTextBox1, line) End Function Private Sub AppendToRichTextBox(rtextBox As RichTextBox, str As String) ' 如果不在UI线程,切换过去 If rtextBox.InvokeRequired Then rtextBox.Invoke(Sub() AppendToRichTextBox(rtextBox, str)) Return End If rtextBox.AppendText(str & vbCrLf) rtextBox.SelectionStart = rtextBox.Text.Length rtextBox.ScrollToCaret() End Sub
关键改进点
- 使用
CancellationTokenSource实现任务取消,点击按钮时会先终止之前的任务,再启动新任务 - 去掉多余的
Thread和嵌套异步逻辑,直接用Async/Await让UI线程保持响应 - 逐行处理(如果需要并行,可添加
SemaphoreSlim控制并发数,避免UI被大量更新请求阻塞) - 简化UI更新逻辑,仅在需要时才切换到UI线程
终止任务的实现
你可以添加一个“终止”按钮,点击时执行:
Private Sub ButtonCancel_Click(sender As Object, e As EventArgs) Handles ButtonCancel.Click cts?.Cancel() End Sub
内容的提问来源于stack exchange,提问作者Fabian Q
相关产品推荐
相关产品推荐

