因为做老师留的大作业时要做音频波形图接触了FMOD引擎,感觉FMOD功能真的是强大,不过大部分较新的学习资源都是外国的,对英语不好的新手来说也有些困难。我在此分享一下自己的学习成果,希望对大家有写帮助和启发。这也是本人第一次写博客,写得不好请见谅。
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include
#include
#include
#include
#include
#include "fmod.hpp"
#include "fmod_dsp.h"
#include "fmod_errors.h"
#include "fmod_dsp_effects.h"
#include "curveplot.h"
namespace Ui {
class MainWindow;
}
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = 0);
~MainWindow();
FMOD::System* mSystem=NULL;
FMOD::Channel* mChannel;
FMOD::DSP* mDsp;
FMOD::Sound* mSound;
FMOD_RESULT mResult;
FMOD::ChannelGroup *mChannelGroup;
FMOD_DSP_PARAMETER_FFT *fftparameter;
QTimer timer;
private slots:
void onTimer();
void on_toolButton_clicked();
void on_toolButton_2_clicked();
void on_horizontalSlider_sliderMoved(int position);
private:
Ui::MainWindow *ui;
CurvePlot *_curvePlot=nullptr;
QVectorwav;
};
#endif // MAINWINDOW_H
//构造函数:
ui->setupUi(this);
wav.resize(2048);
mResult=FMOD::System_Create(&mSystem);
connect(&timer, SIGNAL(timeout()), SLOT(onTimer()));
if(mResult!=FMOD_OK)
{
qDebug()<<"error:System_Create";
exit(-1);
}
mResult=mSystem->init(32,FMOD_INIT_NORMAL,0);
if(mResult!=FMOD_OK)
{
qDebug()<<"error:System->init";
exit(-1);
}
ui->toolButton->setIcon(QPixmap(":/images/play.png"));
ui->toolButton_2->setIcon(QPixmap(":/images/file.png"));
_curvePlot=new CurvePlot(this);
ui->content->addWidget(_curvePlot);
_curvePlot->setAdjustVal(0.5);
_curvePlot->outPut();
//打开文件按钮
QString filename = QFileDialog::getOpenFileName();
mResult=mSystem->createSound(filename.toLocal8Bit(),FMOD_LOOP_NORMAL|FMOD_2D,0,&mSound);
if(mResult!=FMOD_OK)
{
qDebug()<<"error:System->createSound";
exit(-1);
}
mResult=mSystem->playSound(mSound,0,false,&mChannel);
if(mResult!=FMOD_OK)
{
qDebug()<<"error:System->playSound";
exit(-1);
}
ui->toolButton->setIcon(QPixmap(":/images/pause.png"));
mSound->setMode(FMOD_LOOP_OFF);
mResult=mSystem->createDSPByType(FMOD_DSP_TYPE_FFT,&mDsp);
mResult=mChannel->addDSP(0,mDsp);
uint length;
mSound->getLength(&length,FMOD_TIMEUNIT_MS);
ui->horizontalSlider->setMaximum(length);
length/=1000;
ui->label->setText(QString().sprintf("%02d:%02d ", length/60, length%60));
mSystem->update();
timer.start(400);
//实时刷新void onTimer()
mDsp->getParameterData(FMOD_DSP_FFT_SPECTRUMDATA,(void **)&fftparameter,0,0,0);
for(int j=0;jlength;j++)
{
//一倍不太明显,将其放大十倍
wav[j]=fftparameter->spectrum[0][j]*10;
}
_curvePlot->outPut(wav);
uint pos;
mChannel->getPosition(&pos,FMOD_TIMEUNIT_MS);
ui->horizontalSlider->setValue(pos);
pos/=1000;
ui->label_2->setText(QString().sprintf(" %02d:%02d", pos/60, pos%60));
bool isPlay;
mChannel->isPlaying(&isPlay);
if(!isPlay)
timer.stop();
绘制图形部分:
#ifndef CURVEPLOT_H
#define CURVEPLOT_H
#include
#include
#include
//边缘
class QMargin
{
public:
QMargin(int left,int top,int right,int bottom):
Left(left),Top(top),Right(right),Bottom(bottom){}
QMargin(int h,int v):
Left(h),Top(v),Right(h),Bottom(v){}
QMargin(int d=0):
Left(d),Top(d),Right(d),Bottom(d){}
int Left;
int Top;
int Right;
int Bottom;
};
//波形图
class CurvePlot : public QWidget
{
Q_OBJECT
public:
explicit CurvePlot(QWidget *parent=0);
void outPut();
void outPut(QVector &data);
void setAdjustVal(float val){iAdjustVal = val;}
QSize minimumSizeHint() const;
QMargin Margin;
QPen pen;
QBrush Background;
protected:
void paintEvent(QPaintEvent *paint);
void resizeEvent(QResizeEvent *);
private:
void transformPoints(QVector &data, int w, int h, QVector &points);
QPixmap pixmap;
float iAdjustVal;
};
#endif // CURVEPLOT_H
//构造函数
Margin = QMargin(2);
Background = QBrush(QColor(Qt::black));
pen = QPen(QBrush(QColor(Qt::red)), 3);
iAdjustVal = 0;
//坐标转换
//void transformPoints(QVector &data, int w, int h, QVector &points)
//获取极值
float max=data[0],min=data[0];
for(int i=1;idata[i])
min=data[i];
}
//转化成当前屏幕的内的坐标大小
max+=iAdjustVal;
min-=iAdjustVal;
float diffVal=max-min;
for(int i=0;i &data)
int w = width() - Margin.Left - Margin.Right;
int h = height() - Margin.Top - Margin.Bottom;
pixmap = QPixmap(":/images/timg.jpg");
pixmap.scaled(w,h);
QPainter painter(&pixmap);
painter.setRenderHints(QPainter::SmoothPixmapTransform);
//painter.fillRect(QRectF(0, 0, w, h), Background);
QVector points;
transformPoints(data, w, h+this->height()*0.3, points);
painter.setPen(pen);
for (int i= 0; i< points.size()-1; i++)
painter.drawLine(points[i], points[i+1]);
update();
源码下载链接:https://download.csdn.net/download/qq_36166213/10823109