音乐播放器实现歌词同步
2011-01-14 21:25
801 查看
千千静听的歌词格式如下
[04:02.54][03:33.11][02:17.15][01:29.03]等 你 爱 我 爱 我
[00:26.86]等 你 爱 我
[03:40.75][02:24.74][01:37.65][00:35.58]哪怕只有一次也就足够
[03:48.06][02:31.78][01:44.36]等 你 爱 我 爱 我
所有我们可以用一个矩阵来存储歌词内容
TCHAR SongOn[MAX_PATH]; //正在播放的歌曲最短路径 TCHAR Lyric[120][100]; //歌词 TCHAR LyricOn[100]; //正要显示的歌词 int LyricIndex; //正在播放的歌的序号 int Lcount; //歌词句数 int NextSSends; //下一句播放的时间 void CALLBACK on_timer(HWND hwnd,UINT uMessage,UINT iTimerID,DWORD dwTime); //歌词显示 void LyricFront(HWND hwnd); //前进或者后退改变歌词 void LyricSort(); //歌词排序 bool ShowLyrics(HWND hwnd); //处理歌词
每50毫秒我们去检查一下是否下一句歌词可以显示了
由于我们在操作中不是只一直播放下去
这样,当我们在拖动进度条或快进快退时
要让歌词从头开始检查播放到那里来了
函数实现代码
bool ShowLyrics(HWND hwnd) {//播放当前歌曲的歌词 // KillTimer(hwnd,2); ZeroMemory(Lyric,sizeof(Lyric)); FILE *fp; TCHAR LPATH[MAX_PATH]; ZeroMemory(LPATH,sizeof(LPATH)); lstrcpy(LPATH,SongOn); lstrcpy(LPATH+strlen(LPATH)-3,TEXT("lrc")); //修改后缀 fp = fopen(LPATH,"r"); if(fp==NULL)return ERROR; //没有歌词或者打不开 TCHAR LyricLine[100]; Lcount=0; while(!feof(fp)) { ZeroMemory(LyricLine,sizeof(LyricLine)); fgets(LyricLine,sizeof(LyricLine),fp); if(isdigit(LyricLine[1])&&isdigit(LyricLine[2])) {//属于歌词 int rtimes=1; memcpy(Lyric[Lcount],LyricLine,10); while(10*rtimes<strlen(LyricLine)&&LyricLine[10*rtimes]=='[') {//加时间头 memcpy(Lyric[Lcount+rtimes],LyricLine+10*rtimes,10); rtimes++; } LyricLine[strlen(LyricLine)-1]='/0'; for(int i=0;i<rtimes;i++) { lstrcpy(Lyric[Lcount+i]+10,LyricLine+10*rtimes); //MessageBox(hwnd,Lyric[Lcount+i],0,0); } Lcount+=rtimes; //LyricLine[strlen(LyricLine)-1]='/0'; //lstrcpy(Lyric[Lcount++],LyricLine); //MessageBox(hwnd,Lyric[Lcount-1],0,0); } } LyricSort(); //歌词排序 LyricIndex=0; lstrcpy(LyricOn,Lyric[LyricIndex]); int minute=(LyricOn[1]-'0')*10+LyricOn[2]-'0'; int second=(LyricOn[4]-'0')*10+LyricOn[5]-'0'; int ssecond=(LyricOn[7]-'0')*10+LyricOn[8]-'0'; NextSSends=(minute*60+second)*1000+ssecond*10; SetTimer(hwnd,2,50,on_timer); return true; } void LyricFront(HWND hwnd) {//快进或者快退改变了歌词处理 TCHAR temp[20]; TCHAR temp1[MAX_PATH]; wsprintf(temp1,"status %s position",SongOn); mciSendString(temp1,temp,sizeof(temp)/sizeof(TCHAR),NULL); LyricIndex=0; int iNextSSends=0; int iLyricIndex=0; do{//播放时间到 int minute=(Lyric[iLyricIndex][1]-'0')*10+Lyric[iLyricIndex][2]-'0'; int second=(Lyric[iLyricIndex][4]-'0')*10+Lyric[iLyricIndex][5]-'0'; int ssecond=(Lyric[iLyricIndex][7]-'0')*10+Lyric[iLyricIndex][8]-'0'; NextSSends=iNextSSends; LyricIndex=iLyricIndex; iNextSSends=(minute*60+second)*1000+ssecond*10; iLyricIndex++; }while(iNextSSends<atoi(temp)); LyricIndex--; lstrcpy(LyricOn,Lyric[LyricIndex]); //SetDlgItemText(hwnd,IDC_EDITLyrics,LyricOn+10); } void LyricSort() {//歌词按时间排序 for(int i=1;i<Lcount;i++) { for(int j=0;j<Lcount-i;j++) { int minute=(Lyric[j][1]-'0')*10+Lyric[j][2]-'0'; int second=(Lyric[j][4]-'0')*10+Lyric[j][5]-'0'; int ssecond=(Lyric[j][7]-'0')*10+Lyric[j][8]-'0'; int iNextSSends=(minute*60+second)*1000+ssecond*10; minute=(Lyric[j+1][1]-'0')*10+Lyric[j+1][2]-'0'; second=(Lyric[j+1][4]-'0')*10+Lyric[j+1][5]-'0'; ssecond=(Lyric[j+1][7]-'0')*10+Lyric[j+1][8]-'0'; int jNextSSends=(minute*60+second)*1000+ssecond*10; if(iNextSSends>jNextSSends) {//交换 TCHAR TEMP[100]; ZeroMemory(TEMP,sizeof(TEMP)); lstrcpy(TEMP,Lyric[j]); lstrcpy(Lyric[j],Lyric[j+1]); lstrcpy(Lyric[j+1],TEMP); } } } }
原理比较简单,就是字符串处理麻烦点
相关文章推荐
- 原生JS实现网页手机音乐播放器 歌词同步播放的示例
- 基于jplayer实现歌词同步的JS音乐播放器效果
- Android中音乐播放器实现歌词同步显示
- 关于音乐播放器中歌词同步显示的实现
- Android 音乐播放器 实现歌词同步
- 歌词文件LRC的解析,可用于音乐播放器实现歌词同步操作
- 音乐播放器实现歌词同步
- Android 音乐播放器实现歌词显示
- Android 音乐播放器歌词列表式同步显示功能源码
- flash实现歌词同步
- 我的Android进阶之旅------>Android自定义View来实现解析lrc歌词并同步滚动、上下拖动、缩放歌词的功能
- HTML5实现歌词同步
- 歌词同步的实现(lrc)
- jquery+jplayer实现歌词同步的mp3音乐播放器效果
- 我的项目7 js 实现歌词同步(额,小小的效果)
- flash实现歌词同步
- 更新~音乐播放器的同步显示歌词
- Android关于音频歌词同步实现思路(一)
- 实现音乐播放器歌词显示效果
- Android 实现歌词同步