您的位置:首页 > 产品设计 > UI/UE

【Espruino】NO.16 使用VS1003播放音乐

2014-07-07 22:55 399 查看
http://blog.csdn.net/qwert1213131/article/details/37512497
本文属于个人理解,能力有限,纰漏在所难免,还望指正!
【小鱼有点电】
【Espruino中文社区】

想当年mp3正起步的时候,好几百的软妹币买的mp3播放器连个屏幕都没有,简直就是享受啊,现在这东西满大街都是,倒是不稀罕了,但是自己做个mp3玩玩应该还是比较有乐趣的吧。本文引用的VS1003是一个多功能的MP3和WMA解码芯片,它来自芬兰VLSI半导体公司,功能强大但价格便宜,并且简单易用,非常符合DIYer的口味。使用SPI接口协议,附上器数据手册一份点击打开链接,因此我们只需要将Espruino板上具有SPI功能的引脚与VS1003连接上即可.目前只能解码32kbps之内的mp3文件,码率高的会卡额,转换方式可以用千千静听搞定或者百度额。
附上视频地址:点击打开链接



/*vs1003引脚定义*/
var pin_MISO = B4;
var pin_MOSI = B5;
var pin_CLK = B3;
var pin_CS = C12;
var pin_DCS = A8;
var pin_RST = C11;
var pin_DREQ = C10;
/* VS1003B(音频解码芯片) 命令 */
/*写操作  | 命令   |   地址   |   数据  |
|  02H   |   0xH    |  xxxxH  | */
var VS_WRITE_COMMAND = 0x02;

/*读操作  | 命令   |   地址   |   数据  |
|  03H   |   0xH    |  xxxxH  | */
var VS_READ_COMMAND =	0x03;

var SPI_MODE				=0x00;  //模式控制
var SPI_STATUS			=0x01;  //VS10XX的状态寄存器
var SPI_BASS				=0x02;  //高低音控制
var SPI_CLOCKF  		=0x03;  //时钟频率倍乘寄存器
var SPI_DECODE_TIME =0x04;  //解码时间长度
var SPI_AUDATA     	=0x05;  //各种音频数据
var SPI_WRAM      	=0x06;  //RAM 写/读
var SPI_WRAMADDR  	=0x07;  //RAM 写/读的起始地址
var SPI_HDAT0     	=0x08;  //流数据标头0
var SPI_HDAT1     	=0x09;  //流数据标头1
var SPI_AIADDR    	=0x0a;  //应用程序的起始地址
var SPI_VOL      		=0x0b;  //音量控制
var SPI_AICTRL0  		=0x0c;  //应用程序控制寄存器0
var SPI_AICTRL1  		=0x0d;  //应用程序控制寄存器1
var SPI_AICTRL2  		=0x0e;  //应用程序控制寄存器2
var SPI_AICTRL3  		=0x0f;  //应用程序控制寄存器3

function delay(x) //delay x ms
{
var time0 = getTime();
var time1 = 0;
while(1)
{
time1 = getTime();
if((time1-time0)*1000>=x)
break;
}
}
function VS10XX_Init(){
SPI1.setup({ sck:pin_CLK, mosi:pin_MOSI, miso: pin_MISO,order: "msb", baud: 1000000 ,mode:0});
//reset vs1003
digitalWrite(pin_RST,HIGH);
delay(100);
digitalWrite(pin_RST,LOW);
delay(100);
digitalWrite(pin_RST,HIGH);

digitalWrite(pin_CS,HIGH);
digitalWrite(pin_DCS,HIGH);
while(!digitalRead(pin_DREQ));

SPI1.send(0xff,pin_CS);//启动传输

var VS10XX_ID=VS10XX_ReadReg(SPI_STATUS);//读取状态寄存器
VS10XX_ID>>=4;//得到VS10XX的芯片信号

if(VS10XX_ID==VS1053)
{
VS10XX_WriteReg(SPI_MODE,0x0816);//软件复位,新模式
}
else
{
VS10XX_WriteReg(SPI_MODE,0x0804);//软件复位,新模式
}
while(!digitalRead(pin_DREQ));

VS10XX_WriteReg(SPI_CLOCKF,0x9800);//设置VS10XX的时钟,3.5倍频 ,2xADD
VS10XX_WriteReg(SPI_AUDATA,0xbb81);// 采样率48k,立体声
VS10XX_WriteReg(SPI_BASS,0x00f6);// 设置重低音,0x00F6对60HZ以下的音频信号进行15dB的增强,0x7A00对10KHZ以上的信号进行10.5dB的增强
VS10XX_WriteReg(SPI_VOL,0x4040);// VS10XX 音量

while(!digitalRead(pin_DREQ));
SPI1.setup({ sck:pin_CLK, mosi:pin_MOSI, miso: pin_MISO,order: "msb", baud: 16000000 ,mode:0});

}

function VS10XX_WriteReg( addr, data){
digitalWrite(pin_DCS,HIGH);//关闭数据片选
digitalWrite(pin_CS,LOW);//打开片选,可对功能寄存器读写

SPI1.send(VS_WRITE_COMMAND);//写入操作码0x02
SPI1.send(addr);//写入寄存器地址
SPI1.send(data>>8);//写入高字节
SPI1.send(data&0xff);//写入低字节

digitalWrite(pin_CS,HIGH);
}

function VS10XX_ReadReg( addr)
{
var temp = 0;
digitalWrite(pin_DCS,HIGH);//关闭数据片选
digitalWrite(pin_CS,LOW);//打开片选,可对功能寄存器读写

SPI1.send(VS_READ_COMMAND);//写入操作码0x02
SPI1.send(addr);//写入寄存器地址
temp = (SPI1.send(0xa5)<<8);//读取高字节
temp |= SPI1.send(0xa5);//读取低字节

digitalWrite(pin_CS,HIGH);
return temp;
}

/******************************************************************
向VS1003写入2048个0,用于清空VS1003的数据缓冲区注:在播放完一个完整
的音频(如一首完整的MP3)后,调用此函数,清空VS1003数据缓冲区,为下
面的音频数据(如下一首MP3)作准备。
******************************************************************/
function VS_Flush_Buffer()
{
var i = 0;
var j = 0;
digitalWrite(pin_DCS,LOW); //打开数据片选
while(i<2048)
{
if ( digitalRead(pin_DREQ) !== 0 )
{
for ( j=0; j<32; j++ )
{
SPI1.send( 0 );
i++;
}
}
}
digitalWrite(pin_DCS,HIGH);
}

var file=["0:/1.mp3","0:/2.mp3","0:/3.mp3","0:/32.mp3"];

var button=0;//控制歌曲的结束
//播放名为filename的文件
function play(filename){

var fd = E.openFile(filename,'r') ;
var i=0,j=0;
var data="",xx="";
digitalWrite(pin_DCS,LOW);
while(1)
{
data=fd.read(512);

for(j=0;j<16;j++)
{
xx=data.slice(j*32,(1+j)*32);
digitalWrite([LED1,LED2,LED3],xx[0]);
while(digitalRead(pin_DREQ) !== 1);
SPI1.send(xx);
if(xx.length<32)
return;
if(digitalRead(BTN1)==1)
{
button=0;
digitalWrite(pin_DCS,HIGH);
VS_Flush_Buffer();
fd.close();
return;
}

}
}
digitalWrite(pin_DCS,HIGH);
VS_Flush_Buffer();
fd.close();
}
//播放卡里的音乐
function xxplay()
{
var cnt=0;
while(1)
{
for(cnt=0;cnt<4;cnt++)
{
play(file[cnt]);
}
}
}

VS10XX_Init();

//加入10ms去抖,按下按键BTN2开始播放
var l=0;
function start() {
l = !l;
digitalWrite(LED1,l);
xxplay();
}

setWatch(start,C5,{repeat:true,edge:'rising',debounce:10});
save();
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: