这样我们就把第一步的功能实现了。
实现弹幕效果
接下来我们开始实现弹幕效果。弹幕其实也就是一个自定义的 View,它的上面可以显示类似于跑马灯的文字效果。观众们发表的评论都会在弹幕上显示出来,但又会很快地移出屏幕,既可以起到互动的作用,同时又不会影响视频的正常观看。
我们可以自己来编写这样的一个自定义 View,当然也可以直接使用网上现成的开源项目。那么为了能够简单快速地实现弹幕效果,这里我就准备直接使用由哔哩哔哩开源的弹幕效果库 DanmakuFlameMaster 了。
DanmakuFlameMaster 库的项目主页地址是:github.com/Bilibili/Da…
话说现在使用 Android Studio 来引入一些开源库真的非常方便,只需要在 build.gradle 文件里面添加开源库的依赖就可以了。那么我们修改 app/build.gradle 文件,并在 dependencies 闭包中添加如下依赖:
dependencies {
compile fileTree(dir: ‘libs’, include: [‘*.jar’])
compile ‘com.android.support:appcompat-v7:24.2.1’
testCompile ‘junit:junit:4.12’
compile ‘com.github.ctiao:DanmakuFlameMaster:0.5.3’
}
这样我们就将 DanmakuFlameMaster 库引入到当前项目中了。然后修改 activity_main.xml 中的代码,如下所示:
<master.flame.danmaku.ui.widget.DanmakuView
android:id=“@+id/danmaku_view”
android:layout_width=“match_parent”
android:layout_height=“match_parent” />
可以看到,这里在 RelativeLayout 中加入了一个 DanmakuView 控件,这个控件就是用于显示弹幕信息的了。注意一定要将 DanmakuView 写在 VideoView 的下面,因为 RelativeLayout 中后添加的控件会被覆盖在上面。
接下来修改 MainActivity 中的代码,我们在这里加入弹幕显示的逻辑,如下所示:
public class MainActivity extends AppCompatActivity {
private boolean showDanmaku;
private DanmakuView danmakuView;
private DanmakuContext danmakuContext;
private BaseDanmakuParser parser = new BaseDanmakuParser() {
@Override
protected IDanmakus parse() {
return new Danmakus();
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
VideoView videoView = (VideoView) findViewById(R.id.video_view);
videoView.setVideoPath(Environment.getExternalStorageDirectory() + “/Pixels.mp4”);
videoView.start();
danmakuView = (DanmakuView) findViewById(R.id.danmaku_view);
danmakuView.enableDanmakuDrawingCache(true);
danmakuView.setCallback(new DrawHandler.Callback() {
@Override
public void prepared() {
showDanmaku = true;
danmakuView.start();
generateSomeDanmaku();
}
@Override
public void updateTimer(DanmakuTimer timer) {
}
@Override
public void danmakuShown(BaseDanmaku danmaku) {
}
@Override
public void drawingFinished() {
}
});
danmakuContext = DanmakuContext.create();
danmakuView.prepare(parser, danmakuContext);
}
/**
- 向弹幕View中添加一条弹幕
- @param content
-
弹幕的具体内容
- @param withBorder
-
弹幕是否有边框
*/
private void addDanmaku(String content, boolean withBorder) {
BaseDanmaku danmaku = danmakuContext.mDanmakuFactory.createDanmaku(BaseDanmaku.TYPE_SCROLL_RL);
danmaku.text = content;
danmaku.padding = 5;
danmaku.textSize = sp2px(20);
danmaku.textColor = Color.WHITE;
danmaku.setTime(danmakuView.getCurrentTime());
if (withBorder) {
danmaku.borderColor = Color.GREEN;
}
danmakuView.addDanmaku(danmaku);
}
/**
- 随机生成一些弹幕内容以供测试
*/
private void generateSomeDanmaku() {
new Thread(new Runnable() {
@Override
public void run() {
while(showDanmaku) {
int time = new Random().nextInt(300);
String content = “” + time + time;
addDanmaku(content, false);
try {
Thread.sleep(time);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}).start();
}
/**
- sp转px的方法。
*/
public int sp2px(float spValue) {
final float fontScale = getResources().getDisplayMetrics().scaledDensity;
return (int) (spValue * fontScale + 0.5f);
}
@Override
protected void onPause() {
super.onPause();
if (danmakuView != null && danmakuView.isPrepared()) {
danmakuView.pause();
}
}
@Override
protected void onResume() {
super.onResume();
if (danmakuView != null && danmakuView.isPrepared() && danmakuView.isPaused()) {
danmakuView.resume();
}
}
@Override
protected void onDestroy() {
super.onDestroy();
showDanmaku = false;
if (danmakuView != null) {
danmakuView.release();
danmakuView = null;
}
}
…
}
可以看到,在 onCreate() 方法中我们先是获取到了 DanmakuView 控件的实例,然后调用了 enableDanmakuDrawingCache() 方法来提升绘制效率,又调用了 setCallback() 方法来设置回调函数。
接着调用 DanmakuContext.create() 方法创建了一个 DanmakuContext 的实例,DanmakuContext 可以用于对弹幕的各种全局配置进行设定,如设置字体、设置最大显示行数等。这里我们并没有什么特殊的要求,因此一切都保持默认。
另外我们还需要创建一个弹幕的解析器才行,这里直接创建了一个全局的 BaseDanmakuParser。
有了 DanmakuContext 和 BaseDanmakuParser,接下来我们就可以调用 DanmakuView 的 prepare() 方法来进行准备,准备完成后会自动调用刚才设置的回调函数中的 prepared() 方法,然后我们在这里再调用 DanmakuView 的 start() 方法,这样 DanmakuView 就可以开始正常工作了。
虽说 DanmakuView 已经在正常工作了,但是屏幕上没有任何弹幕信息的话我们也看不出效果,因此我们还要增加一个添加弹幕消息的功能。
观察 addDanmaku() 方法,这个方法就是用于向 DanmakuView 中添加一条弹幕消息的。其中首先调用了 createDanmaku() 方法来创建一个 BaseDanmaku 实例,TYPE_SCROLL_RL 表示这是一条从右向左滚动的弹幕,然后我们就可以对弹幕的内容、字体大小、颜色、显示时间等各种细节进行配置了。注意 addDanmaku() 方法中有一个 withBorder 参数,这个参数用于指定弹幕消息是否带有边框,这样才好将自己发送的弹幕和别人发送的弹幕进行区分。
这样我们就把最基本的弹幕功能就完成了,现在只需要当在接收到别人发送的弹幕消息时,调用 addDanmaku() 方法将这条弹幕添加到 DanmakuView 上就可以了。但接收别人发送来的消息又涉及到了即时通讯技术,显然这一篇文章中不可能将复杂的即时通讯技术也进行讲解,因此这里我专门写了一个 generateSomeDanmaku() 方法来随机生成一些弹幕消息,这样就可以模拟出和斗鱼类似的弹幕效果了。
除此之外,我们还需要在 onPause()、onResume()、onDestroy() 方法中进行一些逻辑处理,以保证 DanmakuView 的资源可以得到释放。
现在重新运行一下程序,效果如下图所示:
这样我们就把第二步的功能也实现了。
加入操作界面
那么下面我们开始进行第三步功能实现,加入发送弹幕消息的操作界面。
首先修改 activity_main.xml 中的代码,如下所示:
…
可以看到,这里我们加入了一个 LinearLayout 来作为操作界面。LinearLayout 中并没有什么复杂的控件,只有一个 EditText 用于输入内容,一个 Button 用于发送弹幕。注意我们一开始是将 LinearLayout 隐藏的,因为不能让这个操作界面一直遮挡着 VideoView,只有用户想要发弹幕的时候才应该将它显示出来。
接下来修改 MainActivity 中的代码,在这里面加入发送弹幕的逻辑,如下所示:
public class MainActivity extends AppCompatActivity {
…
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
…
final LinearLayout operationLayout = (LinearLayout) findViewById(R.id.operation_layout);
final Button send = (Button) findViewById(R.id.send);
final EditText editText = (EditText) findViewById(R.id.edit_text);
danmakuView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (operationLayout.getVisibility() == View.GONE) {
operationLayout.setVisibility(View.VISIBLE);
} else {
operationLayout.setVisibility(View.GONE);
}
}
});
send.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
String content = editText.getText().toString();
if (!TextUtils.isEmpty(content)) {
addDanmaku(content, true);
自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。
深知大多数初中级Android工程师,想要提升技能,往往是自己摸索成长或者是报班学习,但对于培训机构动则近万的学费,着实压力不小。自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!
因此收集整理了一份《2024年Android移动开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。
既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上Android开发知识点,真正体系化!
由于文件比较大,这里只是将部分目录截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且会持续更新!
如果你觉得这些内容对你有帮助,可以扫码获取!!(备注:Android)

最后
总而言之,Android开发行业变化太快,作为技术人员就要保持终生学习的态度,让学习力成为核心竞争力,所谓“活到老学到老”只有不断的学习,不断的提升自己,才能跟紧行业的步伐,才能不被时代所淘汰。
在这里我分享一份自己收录整理上述技术体系图相关的几十套腾讯、头条、阿里、美团等公司20年的面试题,把技术点整理成了视频和PDF(实际上比预期多花了不少精力),包含知识脉络 + 诸多细节,由于篇幅有限,这里以图片的形式给大家展示一部分。
还有高级架构技术进阶脑图、Android开发面试专题资料,高级进阶架构资料 帮助大家学习提升进阶,也节省大家在网上搜索资料的时间来学习,也可以分享给身边好友一起学习。
《Android学习笔记总结+移动架构视频+大厂面试真题+项目实战源码》,点击传送门即可获取!
[外链图片转存中…(img-HkQtk7ag-1712228713823)]
[外链图片转存中…(img-NPMSxWB2-1712228713823)]
[外链图片转存中…(img-kORyDTbu-1712228713823)]
还有高级架构技术进阶脑图、Android开发面试专题资料,高级进阶架构资料 帮助大家学习提升进阶,也节省大家在网上搜索资料的时间来学习,也可以分享给身边好友一起学习。