SurfaceView播放视频发送弹幕并实现滚动歌词
本文实例为大家分享了SurfaceView播放视频发送弹幕,并实现滚动歌词,供大家参考,具体内容如下
SurfaceView使用步骤
使用SurfaceView的步骤:
- 首先要继承SurfaceView,实现SurfaceHolder.Callback接口。
- 重写方法:surfaceChanged:surface大小或格式发生变化时触发,在surfaceCreated调用后该函数至少会被调用一次。
- surfaceCreated:Surface创建时触发,一般在这个函数开启绘图线程(新的线程,不要再这个线程中绘制Surface)。
- surfaceDestroyed:销毁时触发,一般不可见时就会销毁。
- 利用getHolder()获取SurfaceHolder对象,调用SurfaceHolder.addCallback添加回调
- SurfaceHolder.lockCanvas获取Canvas对象并锁定画布,调用Canvas绘图,SurfaceHolder.unlockCanvasAndPost结束锁定画布,提交改变。
SurfaceHolder
SurfaceHolder回调自己的三个生命周期:
- surfaceCreated(SurfaceHolderholder)创建时
- surfaceChanged(SurfaceHolderholder,intformat,intwidth,intheight)改变时
- surfaceDestroyed(SurfaceHolderholder)销毁时
SurfaceView播放视频并可以发送弹幕
需要准备两个SurfaceView,一个是负责播放视频,一个负责展示弹幕。弹幕是展示在视频上面的,所以我们要给展示弹幕的SurfaceView设置两个方法:
surfaceView_danmu.setZOrderOnTop(true);——置于上方
surfaceView_danmuHolder.setFormat(PixelFormat.TRANSPARENT);——背景透明
publicclassMainActivityextendsAppCompatActivityimplementsSurfaceHolder.Callback{
publicstaticfinalintPROGRESS=101;
SurfaceViewsurfaceView,surfaceView_danmu;
SurfaceHoldersurfaceHolder,surfaceView_danmuHolder;
MediaPlayermediaPlayer=newMediaPlayer();
Stringpath="/sdcard/aa.mp4";
SeekBarseekBar;
Timertimer;
EditTexteditText;
Buttonbutton,bt_start,bt_stop;
intx=0;
ArrayListlist=newArrayList<>();
Handlerhandler=newHandler(){
@Override
publicvoidhandleMessage(Messagemsg){
super.handleMessage(msg);
if(msg.what==PROGRESS){
seekBar.setProgress((Integer)msg.obj);
mediaPlayer.setOnSeekCompleteListener(newMediaPlayer.OnSeekCompleteListener(){
@Override
publicvoidonSeekComplete(MediaPlayermp){
Toast.makeText(MainActivity.this,"播放完毕!",Toast.LENGTH_SHORT).show();
}
});
}
}
};
@Override
protectedvoidonCreate(BundlesavedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
surfaceView=findViewById(R.id.sufaceview);
surfaceView_danmu=findViewById(R.id.sufaceview_danmu);
editText=findViewById(R.id.et);
button=findViewById(R.id.bt_send);
seekBar=findViewById(R.id.bar);
bt_start=findViewById(R.id.bt_start);
bt_stop=findViewById(R.id.bt_stop);
surfaceHolder=surfaceView.getHolder();
surfaceHolder.addCallback(this);
surfaceView_danmuHolder=surfaceView_danmu.getHolder();
surfaceView_danmuHolder.addCallback(this);
surfaceView_danmu.setZOrderOnTop(true);
surfaceView_danmuHolder.setFormat(PixelFormat.TRANSPARENT);
if(mediaPlayer!=null){
try{
mediaPlayer.setDataSource(path);
mediaPlayer.prepareAsync();
mediaPlayer.setOnPreparedListener(newMediaPlayer.OnPreparedListener(){
@Override
publicvoidonPrepared(MediaPlayermp){
mediaPlayer.start();
intduration=mediaPlayer.getDuration();
seekBar.setMax(duration);
timer=newTimer();
timer.schedule(newTimerTask(){
@Override
publicvoidrun(){
intcurrentPosition=mediaPlayer.getCurrentPosition();
Messagemessage=Message.obtain();
message.what=PROGRESS;
message.obj=currentPosition;
handler.sendMessage(message);
}
},0,1000);
}
});
seekBar.setOnSeekBarChangeListener(newSeekBar.OnSeekBarChangeListener(){
@Override
publicvoidonProgressChanged(SeekBarseekBar,intprogress,booleanfromUser){
}
@Override
publicvoidonStartTrackingTouch(SeekBarseekBar){
}
@Override
publicvoidonStopTrackingTouch(SeekBarseekBar){
intprogress=seekBar.getProgress();
mediaPlayer.seekTo(progress);
}
});
}catch(IOExceptione){
e.printStackTrace();
}
}
button.setOnClickListener(newView.OnClickListener(){
@Override
publicvoidonClick(Viewv){
Strings=editText.getText().toString();
inty=(int)(Math.random()*300);
list.add(newDanMu(0,y,s,Color.RED));
}
});
bt_start.setOnClickListener(newView.OnClickListener(){
@Override
publicvoidonClick(Viewv){
mediaPlayer.start();
}
});
bt_stop.setOnClickListener(newView.OnClickListener(){
@Override
publicvoidonClick(Viewv){
mediaPlayer.pause();
}
});
}
@Override
publicvoidsurfaceCreated(SurfaceHolderholder){
if(holder==surfaceHolder){
mediaPlayer.setDisplay(holder);
}elseif(holder==surfaceView_danmuHolder){
newMyDanMuThread().start();
}
}
@Override
publicvoidsurfaceChanged(SurfaceHolderholder,intformat,intwidth,intheight){
}
@Override
publicvoidsurfaceDestroyed(SurfaceHolderholder){
}
classMyDanMuThreadextendsThread{
@Override
publicvoidrun(){
super.run();
Paintpaint=newPaint();
paint.setColor(Color.RED);
paint.setTextSize(40);
while(true){
try{
Thread.sleep(200);
}catch(InterruptedExceptione){
e.printStackTrace();
}
Canvascanvas=surfaceView_danmuHolder.lockCanvas();
canvas.drawColor(Color.TRANSPARENT,PorterDuff.Mode.CLEAR);
for(inti=0;i
实现滚动歌词
要准备一个装有时间和歌词的集合,准备一个Timer计时器和一个该展示第几个歌词。每隔一秒去拿该歌词的下一个歌词时间与进度匹配,如果进度>=该时间,那么就画该歌词在SurfaceView上;<则不画该歌词
一定要写SD卡读写权限!!!!!
publicclassMainActivityextendsAppCompatActivityimplementsSurfaceHolder.Callback{
SurfaceViewsurfaceView;
SurfaceHoldersurfaceHolder;
MediaPlayermediaPlayer=newMediaPlayer();
ArrayListlist=newArrayList<>();
Timertimer;
intcount=0;
@Override
protectedvoidonCreate(BundlesavedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
surfaceView=findViewById(R.id.sv);
surfaceHolder=surfaceView.getHolder();
surfaceHolder.addCallback(this);
timer=newTimer();
timer.schedule(newTimerTask(){
@Override
publicvoidrun(){
intcurrentPosition=mediaPlayer.getCurrentPosition();
if(list.size()>0){
if(currentPosition>=list.get(count+1).getTime()){
count++;
}
}
}
},0,500);
try{
mediaPlayer.setDataSource("/sdcard/凤凰传奇-最炫民族风(Live).mp3");
mediaPlayer.prepareAsync();
mediaPlayer.setOnPreparedListener(newMediaPlayer.OnPreparedListener(){
@Override
publicvoidonPrepared(MediaPlayermp){
mediaPlayer.start();
}
});
}catch(IOExceptione){
e.printStackTrace();
}
try{
StringBufferstringBuffer=newStringBuffer();
FileInputStreamfileInputStream=newFileInputStream("/sdcard/最炫民族风");
byte[]bytes=newbyte[1024];
intlen=0;
while((len=fileInputStream.read(bytes))!=-1){
stringBuffer.append(newString(bytes,0,len));
}
Gsongson=newGson();
JavaBeanjavaBean=gson.fromJson(stringBuffer.toString(),JavaBean.class);
JavaBean.LrcBeanlrc=javaBean.getLrc();
Stringlyric=lrc.getLyric();
String[]split=lyric.split("\n");
for(inti=0;i=2){
Strings=split1[0];
Stringsubstring1=s.substring(1,3);
Stringsubstring2=s.substring(4,6);
Stringsubstring3=s.substring(7,10);
longstart=Integer.parseInt(substring1)*60*1000+Integer.parseInt(substring2)*1000+Integer.parseInt(substring3);
Stringtext=split1[1];
list.add(newMusic(text,start));
}
}
}catch(FileNotFoundExceptione){
e.printStackTrace();
}catch(IOExceptione){
e.printStackTrace();
}
}
@Override
publicvoidsurfaceCreated(SurfaceHolderholder){
newMyThread().start();
}
@Override
publicvoidsurfaceChanged(SurfaceHolderholder,intformat,intwidth,intheight){
}
@Override
publicvoidsurfaceDestroyed(SurfaceHolderholder){
}
classMyThreadextendsThread{
@Override
publicvoidrun(){
super.run();
Paintpaint=newPaint();
paint.setColor(Color.RED);
paint.setTextSize(50);
while(true){
try{
Thread.sleep(100);
}catch(InterruptedExceptione){
e.printStackTrace();
}
Canvascanvas=surfaceHolder.lockCanvas();
if(canvas==null){
break;
}
canvas.drawColor(Color.TRANSPARENT,PorterDuff.Mode.CLEAR);
if(list.size()>0){
canvas.drawText(list.get(count).getTitle(),100,100,paint);
}
surfaceHolder.unlockCanvasAndPost(canvas);
}
}
}
}
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持毛票票。
声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。