简单的libmad封装类LibMP3:
// LibmadMP3.h: interface for the LibmadMP3 class.
//
//
#if !defined(AFX_LIBMADMP3_H__0363C03A_CE0B_45E2_BA2D_EB73AB15B66C__INCLUDED_)
#define AFX_LIBMADMP3_H__0363C03A_CE0B_45E2_BA2D_EB73AB15B66C__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
#include "mad.h"
class LibmadMP3
{
public:
LibmadMP3(const char* filename);
virtual ~LibmadMP3();
long ReadFrame(unsigned char* pcm);
private:
int Setup();
private:
struct mad_stream stream;
struct mad_frame frame;
struct mad_synth synth;
struct mad_header header;
mad_timer_t timer;
FILE* file;
long readsize;
long freq;
long bitrate;
int channel;
};
#endif // !defined(AFX_LIBMADMP3_H__0363C03A_CE0B_45E2_BA2D_EB73AB15B66C__INCLUDED_)
cpp文件:
// LibmadMP3.cpp: implementation of the LibmadMP3 class.
//
//
#include "LibmadMP3.h"
//
// Construction/Destruction
//
static unsigned char inputBuffer[4096 + MAD_BUFFER_GUARD];
signed short to_short(mad_fixed_t fixed)
{
if(fixed >= MAD_F_ONE)
return (SHRT_MAX);
if(fixed <= -MAD_F_ONE)
return (-SHRT_MAX);
fixed = fixed>>(MAD_F_FRACBITS-15);
return ((signed short)fixed);
}
LibmadMP3::LibmadMP3(const char* filename):
freq(0),
bitrate(0),
channel(2),
frameCount(0)
{
file = fopen(filename,"rb");
mad_stream_init(&stream);
mad_frame_init(&frame);
mad_synth_init(&synth);
mad_timer_reset(&timer);
}
LibmadMP3::~LibmadMP3()
{
mad_synth_finish(&synth);
mad_frame_finish(&frame);
mad_stream_finish(&stream);
fclose(file);
}
int LibmadMP3::Setup()
{
size_t remaining;
unsigned char* read;
if(stream.next_frame != NULL)
{
remaining = stream.bufend - stream.next_frame;
memmove(inputBuffer, stream.next_frame, remaining);
read = inputBuffer + remaining;
readsize = 4096 - remaining;
}
else
{
readsize = 4096;
read = inputBuffer;
remaining=0;
}
readsize = fread(read,1,readsize,file);
if(readsize <= 0)
{
return -1;
}
mad_stream_buffer(&stream, inputBuffer, readsize+remaining);
//char dest[100];
//mad_timer_string(timer, dest, "%02lu:%02u:%02u", MAD_UNITS_HOURS, MAD_UNITS_MILLISECONDS, 0);
stream.error=(mad_error)0;
return 0;
}
long LibmadMP3::ReadFrame(unsigned char* pcm)
{
if(stream.buffer == NULL)
{
if(Setup() == -1)
return -1;
}
mad_header_decode(&frame.header,&stream);
while(mad_frame_decode(&frame,&stream) == -1)
{
if(MAD_RECOVERABLE(stream.error))
{
if(stream.error!=MAD_ERROR_LOSTSYNC)
{
}
continue;
}
else
{
if(stream.error == MAD_ERROR_BUFLEN)
{
if (Setup() == -1)
return -1;
continue;
}
return -1;
}
}
mad_synth_frame(&synth,&frame);
if(bitrate < 128000)
{
//获取频率
freq = synth.pcm.samplerate; ///采样频率44100
bitrate = frame.header.bitrate; ///比特率128000
channel = (frame.header.mode == MAD_MODE_SINGLE_CHANNEL) ? 1 : 2; ///声道2 立体声
}
mad_timer_add(&timer,frame.header.duration);
int j = 0;
for(int i=0; i<synth.pcm.length; i++)
{
signed short sample;
sample=to_short(synth.pcm.samples[0][i]);
pcm[j++] = sample & 0xff;
pcm[j++] = sample >> 8;
if(MAD_NCHANNELS(&frame.header)==2)
sample=to_short(synth.pcm.samples[1][i]);
pcm[j++] = sample & 0xff;
pcm[j++] = sample >> 8;
}
//char dest[120];
//mad_timer_string(timer,dest, "%lu:%02lu.%03u", MAD_UNITS_MINUTES, MAD_UNITS_MILLISECONDS, 0);
return j;
}
long LibmadMP3::GetPlayTime()
{
return mad_timer_count(timer,MAD_UNITS_MILLISECONDS);
}
截图以及链接地址,百度盘:http://pan.baidu.com/s/1eQlPTmy
CSDN资源:http://download.csdn.net/detail/c_tianzi/8970807