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

QPainter绘制双通道波形:第二通道Y轴位置异常问题

QPainter绘制双通道波形位置偏移问题解决

问题描述

用QPainter实现波形绘制,从单通道改为双通道显示后,第一通道(上半区)绘制正常,但第二通道的位置严重偏离画布底部。

单通道波形居中的代码:

painter.drawRect(i * xScale, center - (m_samplesL[i] * center), 2, (m_samplesL[i] * center) * 2);

双通道第一通道(上半区)正常工作的代码:

painter.drawRect(i * xScale, (center / 2) - (m_samplesL[i] * (center / 2)), 2, (m_samplesL[i] * (center / 2)) * 2);

错误的第二通道代码(位置偏离底部):

painter.drawRect(i * xScale, ((center * 2)) - (m_samplesR[i] * (center / 2)), 2, (m_samplesR[i] * (center / 2)) * 2);

问题原因

center是画布高度的一半(m_height/2),center*2等于整个画布的高度,以此为基准计算Y坐标,会导致波形顶部超出画布底部边界,自然无法在预期位置显示波形。

双通道需要将画布上下均分:

  • 上半区范围:0 ~ center(画布高度的一半),第一通道以center/2为中线绘制
  • 下半区范围:center ~ m_height,第二通道需要以center + center/2(即画布高度的3/4处)为中线绘制

修正代码

修改run()函数中双通道的绘制逻辑:

else if (m_channelCount == 2)
{
    // 第一通道:上半区,中线为画布高度的1/4处
    painter.drawRect(i * xScale, (center / 2) - (m_samplesL[i] * (center / 2)), 2, (m_samplesL[i] * (center / 2)) * 2);
    // 第二通道:下半区,中线为画布高度的3/4处
    painter.drawRect(i * xScale, (3 * center / 2) - (m_samplesR[i] * (center / 2)), 2, (m_samplesR[i] * (center / 2)) * 2);
}

另外注意代码中的拼写错误:成员变量m_heihgt应为m_height,建议修正避免后续混淆。

完整修正后的run函数

void WaveformThread::run()
{
    int numberOfSamples = m_samplesL.size();
    float xScale = (float)m_width / (numberOfSamples);
    float center = (float)m_heihgt / 2; // 建议将m_heihgt改为m_height
    QImage waveImage = QImage(m_width, m_heihgt, QImage::Format_RGB16);
    waveImage.fill(m_background_color);
    QPainter painter(&waveImage);
    painter.setPen(QPen(m_wave_color, 1, Qt::SolidLine, Qt::RoundCap));
    int counter = 0;

    for(int i = 0; i < numberOfSamples; i++){
        if (m_abort)
            break;
        if (m_channelCount == 1)
            painter.drawRect(i * xScale, center - (m_samplesL[i] * center), 2, (m_samplesL[i] * center) * 2);
        else if (m_channelCount == 2)
        {
            painter.drawRect(i * xScale, (center / 2) - (m_samplesL[i] * (center / 2)), 2, (m_samplesL[i] * (center / 2)) * 2);
            painter.drawRect(i * xScale, (3 * center / 2) - (m_samplesR[i] * (center / 2)), 2, (m_samplesR[i] * (center / 2)) * 2);
        }
        counter++;
    }
    emit waveformReady(waveImage);
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.09 15:20:36