分类: C/C++
2011-12-31 17:59:04
转载请注明出处
音频波形绘制时,主要就是需要了解绘制原理。总的原则为:把多少个采样点绘制到多宽(像素)的界面上,此时绘制分2种情况:1 需要绘制的采样点数少于或等于显示宽度(像素),此时可以直接绘制;2 需要绘制的采样点数大于显示宽度(像素),此时涉及到抛弃些采样点,但不是简单从多少个采样点中取一个或多个,通过下面的代码,相信你能悟出其中的原理。
void CTransWaveShow::paintEvent(QPaintEvent *event)
{
QPainter painter(this);
painter.setRenderHint(QPainter::Antialiasing);
QColor hourColor(127, 0, 127);
int h = height() / 2;
painter.translate(0, h);
QPen vPen;
vPen.setColor(Qt::red);
vPen.setWidth(1);
painter.setPen(vPen);
painter.drawLine(0, 0, width(), 0);
if (!(m_AudioList.size() > 0))
{
return;
}
vPen.setColor(Qt::green);
painter.setPen(vPen);
int x1 = 0, y1 = 0, x2 = 0, y2 = 0;
int vPointStep = 1;
int vDataSetp = 1;
if (m_AudioList.size() >= width())
{
vPointStep = 1;
vDataSetp = m_AudioList.size() / width();
}
else
{
vPointStep = width() / m_AudioList.size();
vDataSetp = 1;
}
int vDataIdx = 0;
for (int i = 0; i < width(); )
{
int vPlusVal = 0;
int vNegaVal = 0;
for(int j = 0; j < vDataSetp; j ++)
{
int vIdx = vDataIdx * vDataSetp + j;
if (!(vIdx < m_AudioList.size()))
{
break;
}
int vCurVal = (m_AudioList[vIdx] * h) / (65535 / 2);
if (vCurVal > 0)
{
if (vCurVal > vPlusVal)
{
vPlusVal = vCurVal;
}
}
else if (vCurVal < 0)
{
if (vCurVal < vNegaVal)
{
vNegaVal = vCurVal;
}
}
}
if (vPlusVal > 0)
{
x2 = i;
y2 = - vPlusVal;
painter.drawLine(x1, y1, x2, y2);
x1 = x2;
y1 = y2;
}
if (vNegaVal < 0)
{
x2 = i;
y2 = - vNegaVal;
painter.drawLine(x1, y1, x2, y2);
x1 = x2;
y1 = y2;
}
i += vPointStep;
vDataIdx ++;
}
}