You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在C#中实现Timer与Bitmap刷新的同步?

解决Timer与相机帧接收的同步问题,稳定更新直方图

我完全懂你的困扰——一边是相机后台线程不停推送新帧,一边是Timer定时要更新直方图,两个操作碰在一起就容易因为共享资源冲突导致图表抽风。别着急,咱们一步步来解决这个线程同步的问题:

核心思路

问题根源在于两个线程(相机回调线程 + Timer触发的UI线程)同时访问/修改同一份图像数据,导致数据不一致。我们需要做两件事:

  1. 用线程安全的方式保存最新的帧数据,避免冲突
  2. 把直方图计算放到后台线程,别卡UI,计算完再回到UI线程更新图表

具体代码修改

首先,先定义一个线程安全的变量来存最新的帧,加锁保护:

// 锁对象,用来保护帧数据的访问
private readonly object _frameLock = new object();
// 保存最新收到的相机帧,只存最新的,旧的直接覆盖
private Frame _latestFrame;

然后修改OnFrameReceived回调,只负责更新最新帧,不要在这里计算直方图(之前卡就是因为这个):

private void OnFrameReceived(Camera camera, Frame frame)
{
    // 加锁确保只有一个线程能修改_latestFrame
    lock (_frameLock)
    {
        // 注意:这里一定要复制帧数据!相机可能会复用Frame对象,直接赋值会导致后续处理时数据被覆盖
        // 如果你的Frame类有Clone方法,直接用;没有的话就手动复制像素数据到新的容器(比如字节数组/Bitmap)
        _latestFrame = frame.Clone(); 
    }

    // 把帧放回队列,让相机继续采集
    camera.QueueFrame(frame);
}

接下来修改Timer的Tick事件,安全获取最新帧后,后台计算直方图再更新UI:

private void histTimer_Tick(object sender, EventArgs e)
{
    Frame frameToProcess = null;

    // 加锁安全取出最新帧,取出后清空_latestFrame,避免重复处理同一帧
    lock (_frameLock)
    {
        if (_latestFrame != null)
        {
            frameToProcess = _latestFrame;
            _latestFrame = null;
        }
    }

    if (frameToProcess == null)
        return; // 没有新帧就直接返回

    // 用Task.Run把直方图计算放到后台线程,不卡UI
    Task.Run(() =>
    {
        // 这里写你的直方图计算逻辑,比如从frameToProcess提取像素值统计
        int[] histogramData = CalculateHistogram(frameToProcess);

        // 计算完必须回到UI线程更新图表(WinForms控件只能在UI线程操作)
        this.Invoke((MethodInvoker)delegate
        {
            // 替换成你实际更新图表的代码,比如设置Series数据、刷新控件
            UpdateHistogramChart(histogramData);
        });

        // 记得释放帧资源,避免内存泄漏
        frameToProcess.Dispose();
    });
}

额外注意事项

  • 帧数据复制:一定要确保你处理的是帧的副本,而不是相机正在使用的原对象,否则相机回收/复用帧时会导致数据错乱。如果Frame没有Clone方法,就手动把像素数据复制到一个独立的字节数组或Bitmap里。
  • 资源释放:用完Frame后一定要调用Dispose,不然会内存泄漏,长时间运行程序会越来越卡。
  • UI线程更新:WinForms的所有控件操作必须在UI线程,所以计算完直方图后一定要用Invoke或BeginInvoke回到UI线程再更新图表。

这样修改后,Timer和相机回调就不会再抢着访问同一份数据了,直方图更新会稳定很多~

内容的提问来源于stack exchange,提问作者Trion

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.27 06:35:45