歌词算是分析完了.当然,歌词头的信息没有分析,这些内容将在显示中被忽略,读者有兴趣的话可以自己分析,文件头的意义大概如下:
[ar:周杰伦]艺术家为周杰伦
[al:Jap]专辑为JAP
[by:歌词吾爱http://www.51lrc.com]来源为歌词吾爱http://www.51lrc.com
[offset:400]笔者不太清楚,大概是缓冲时间为400毫秒吧,有错的话请指出来。
接着就是让歌词显示在MC中,在预览图的歌词显示器里,播到哪句歌词,哪句就会闪烁;点击一句歌词,音乐会跳到相应位置。这是怎么做的呢?
首先,每一行字都是一个影片剪辑实例,在库里是同一影片剪辑.该剪辑有两帧,第一帧是正常时的状态,第二帧是音乐播到该歌词时的状态。此外,影片剪辑里还有一按钮,用于点击歌词。
下面就一起做这个MC:
新建一个MC,命名为ITEMBUTTON,在该MC里做一个动态文本,变量名为caption1,
然后在文本相应的图层插入一个关键帧,改变一下文本的颜色,使音乐播放到该歌词时有变色的效果.变量名改为caption2.(本来这是多此一举的事情,但不知为什么,变量名相同的话,第二帧老是显示不出文字,所以笔者被迫这样做)。
然后新建一个图层,在该图层新建一按钮,命名为ITEMBUTTON_BUTTON
接着新建一图层,在第一帧输入AS:
至此,显示歌词的MC单元完成了。
把该MC拖到先前创建的LYRICSITEMS剪辑中.实例名为ITEMBUTTON0,假如你需要显示N行歌词,就复制N个,最后就是有N+1个ITEMBUTTON影片剪辑,实例名分别为ITEMBUTTON1,ITEMBUTTON2,...."ITEMBUTTON"+N(为什么是N+1个,在后面会解释).把这些剪辑按顺序从上到下排列好。
当然,这也可以用DUPLICATEMOVIECLIP来实现,但是笔者的机器太慢了,导致这样运行经常出问题,在各位的机里应该不会有此问题(笔者的机:C4,1.0G,内存128MB)
在LRC列表框里,定义一个函数MOVEUP(因为歌词向上移动所以就这样命名该函数),该函数要显示的只是跟时间有关的内容,而且其它内容对歌词主体播放会有影响,主要是数据类型不统一。
因为数组是经过排序的,根据ASCII排列规则,时间集中在一个区域(前提是歌词信息也标准,即变量名不以数字开头),这区域的两头都可能有跟时间没关的信息。
所以显示前先去掉前面和后面的歌词信息。
去掉方法,定义两个变量,STARTING,ENDING,表示歌词从哪句开始显示,哪句结束.
在LYRICSITEMS添加一个函数:
var starting
var ending
for (i=0; i>=timeValue.length-1; i++) {//从时间数组的前面读起
if (!isNaN(timeValue[i])) {//读到数据类型为数字的时候
starting = i;//表示到了时间的开始
break;//退出循环
}
}
for (i=timeValue.length-1; i>=0; i--) {//从时间数组的后面读起
if (!isNaN(timeValue[i])) {//读到数据类型为数字的时候
ending = i;//表示到了时间的末端
break;//退出循环
}//第二次循环也可以从STARTING开始,不过一般来说,从STARTING开始,循环的次数要多一些,所以就从TIMEVALUE.LENGTH-1开始往上循环.
}
}
下一步,让歌词随着歌曲的播放而进行高亮显示(其实就是让相应歌词的MC跳到第二帧)
根据TIMEVALUE数组的值来定位:
比如说:下面是一段歌词:
[00:21.18]是因为想了太多
[00:24.91]是心理起了作用
在15秒84和21秒18之间,第一句歌词处于高亮状态
在21秒18和24秒91之间,第二句歌词处于高亮状态
据此定义一变量TEMPPOS定位歌词.
在MOVEUP函数里追加:
for (i=starting; i<=ending; i++) {//从歌词的时间信息项开始循环
if (i == ending || pos<=timeValue[i+1]*1000) {//当歌曲的时间处在两个相邻时间值之间或者播到末尾,简单地说就是歌词时间跟歌曲时间相对应的时候
temppos = i;//获得要高亮显示的歌词的位置
break;//并退出循环
}
}
预览图中,列表所显示的是高亮歌词及其上下4句歌词,这里涉及一个问题,就是该从哪句开始显示.为此定义一变量STARTPOINT,追加代码:
var startpoint=temppos-Math.floor(shownum/2);//该数值使高亮歌词显示在列表框中间.
for(var i=0;i<=shownum-1;i++){
this["itembutton"+i].caption1=LyricsText[i+startpoint]
this["itembutton"+i].caption2=this["itembutton"+i].caption1
}//随着歌曲的播放,重置歌词的内容.
this["itembutton"+(temppos-startpoint)].gotoAndStop(2)//让播到的歌词高亮显示
this["itembutton"+(temppos-startpoint-1)].gotoAndStop(1);//让刚才高亮的歌词恢复原来的状态
函数主要部分是这样。
让MOVEUP函数在歌曲播放时不断执行,以同步显示歌词,加入:
moveUp()
}
如果大家按着笔者的教程来做,现在基本的效果应该出来了.先测试一下。
怎么让歌词平滑滚动呢?
在整个容器里,只显示了SHOWNUM行歌词,所以,不可能就是简单地让歌词在播放过程中一直地上升。
我们主要是让两句歌词之间能够缓慢地上升,而不是播到相应歌词才让歌词跳动.
以以下两句歌词为例:
[00:21.18]是因为想了太多
在15秒84和21秒18之间,我们让列表框的所有项目匀速移动一个列表框项目的高度.这样,当时间无限接近21秒18的时候,列表框的所有项目移动的距离接近于一个列表框项目的高度.当时间到21秒18,ONENTERFRAME事件响应时,列表框的内容恰好要更改,因为高亮显示的歌词发生改变.更改是原列表框第一项去掉,其它项目相应地往上移动,最后追加后面还没显示的歌词的第一行.所以,假如列表框项目实际上不移动的话,就会给人一种刚好移动了也恰好是一个列表框项目高度.因此,此时让列表框的位置恢复到原来15秒84时的位置,就不会有跳动的感觉。
知道了这个原理以后,就开始写这段匀速移动的代码了。这是个初中的物理问题,解决起来应该不难。
我们主要是要求出列表框项目移动的距离△S,然后求出列表框项目的位置.这时,可能会有读者问:那不就是要设置SHOWNUM个列表框的位置吗?从上面的分析可见,所有列表框项目的△S值是相同的,所以,我们干脆控制整个列表框的位置属性。
根据匀速运动的公式,有
其中△T就是当前歌曲时间与歌词时间信息的差值,即当前时间(T-15.84).那么V怎么求呢?
我们刚才说了,在两句歌词的时间差里,我们需要移动一个列表框项目的距离S,代入上述公式,得
V=S/(21,18-15.84)
解出了V以后,就可以把距离跟时间的关系写出来:
把该函数用于AS中:
S就是一个列表框的高度itembutton0._height,15.84就是以当前歌词位置TEMPPOS为下标的数组项的值timeValue[temppos],21,18就是当前歌词下一项的时间信息值timeValue[temppos+1],当前歌曲位置T就是歌曲位置pos/1000(因为上面设置了pos=_parent.song.duration,而duration是以毫秒为单位的,TIMEVALUE数组是以秒为单位,所以需要转换一下单位)
于是,控制列表框位置的代码就写出来了:
该代码添加在MOVEUP函数里。然后列表框的位置就等于列表框初始值减去DELTA(因为往上为负,所以是减)。
为了获得初始值,在MOVEUP函数的外面追加:
接着就可以在MOVEUP函数里追加:
此时,测试影片,就可以看到平滑移动的效果了.但是,当歌词高亮显示发生改变的时候,你会看到列表框上面一项突然消失,同时下面弹出下一项.这个该怎么消除呢?
很简单,就在主场景画两块颜色跟背景颜色一样,大小跟列表框项目相同的矩形方块,一块放在列表框的上面,底线与列表框顶断对齐,另一块放在列表框下面,底线跟列表框底线对齐.这样就看不到这种突然消失的现象了。
效果是达到了,但是可能有些读者还会有疑问:要遮住上下两个项目,用遮罩不是更方便吗,为什么要这么麻烦呢?
原因在于:这样做会让被遮罩层有动态文本,这就需要嵌入字体轮廓才能显示文字,而且文字是从歌词文件那里读取的,什么字符都可能有,于是,就要为所有字符嵌入字体轮廓.也就是需要导入整个字体文件,结果就是导致文件很大(一般是几M到十多M),使得加载的时间大大增加,浏览者会等得不耐烦.所以建议读者还是不使用遮罩为佳.
接着就是制作鼠标点击控制歌词的效果了。
要实现点击歌词的跳转功能,在ITEMBUTTON按钮里添加代码:
pos=_parent.timeValue[_name.slice(10)+_parent.startpoint] //获得被点击歌词的相应时间,其中,SLICE(10)是把ITEMBUTTON十个字符去掉,以获得被点击按钮所在的索引.
_parent._parent.song.start(pos,1) //从点击时间开始播放
gotoAndPlay(2) //表示高亮显示被点击的歌词
}
大家现在可以下载源文件了:
Player.rar
不过声音文件太大,没放到压缩包里.大家可以从别处下载,或者点击:
然后也告诉大家声音文件地址的通式:
download.incoo.com/blueidea/hbro/player/sound/歌名.mp3
声音文件下载后,解压上面的RAR文件.把它们放到SOUND文件夹下,注意声音文件名要跟歌词文件名一致喔(当然不包括扩展名).歌词文件放在LYRICS文件夹下。
[1] [2]
