• Android 模仿bilibili弹幕


    运行效果
    这里写图片描述
    MainActivity.java

    package demo.ligong.sdut.danmutest;
    
    import android.graphics.Color;
    import android.os.Build;
    import android.os.Bundle;
    import android.os.Environment;
    import android.support.v7.app.AppCompatActivity;
    import android.text.TextUtils;
    import android.view.View;
    import android.widget.Button;
    import android.widget.EditText;
    import android.widget.LinearLayout;
    import android.widget.VideoView;
    
    import java.util.Random;
    
    import master.flame.danmaku.controller.DrawHandler;
    import master.flame.danmaku.danmaku.model.BaseDanmaku;
    import master.flame.danmaku.danmaku.model.DanmakuTimer;
    import master.flame.danmaku.danmaku.model.IDanmakus;
    import master.flame.danmaku.danmaku.model.android.DanmakuContext;
    import master.flame.danmaku.danmaku.model.android.Danmakus;
    import master.flame.danmaku.danmaku.parser.BaseDanmakuParser;
    import master.flame.danmaku.ui.widget.DanmakuView;
    
    public class MainActivity extends AppCompatActivity {
    
        private boolean showDanmaku;
    
        private DanmakuView danmakuView;
    
        private DanmakuContext danmakuContext;
         //创建一个弹幕的解析器才行,这里直接创建了一个全局的BaseDanmakuParser。
        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 = (VideoView) findViewById(R.id.video_view);
            //设置视频文件的地址
            videoView.setVideoPath(Environment.getDataDirectory() + "/Pixels.mp4");
            videoView.start();
            //我们先是获取到了DanmakuView控件的实例
            danmakuView = (DanmakuView) findViewById(R.id.danmaku_view);
            //然后调用了enableDanmakuDrawingCache()方法来提升绘制效率
            danmakuView.enableDanmakuDrawingCache(true);
            //又调用了setCallback()方法来设置回调函数。
            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.create()方法创建了一个DanmakuContext的实例
            danmakuContext = danmakuContext.create();
    
            danmakuView.prepare(parser,danmakuContext);
    
            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 v) {
                    if(operationLayout.getVisibility() == View.GONE){
                        operationLayout.setVisibility(View.VISIBLE);
                    }else {
                        operationLayout.setVisibility(View.GONE);
                    }
                }
            });
            send.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    String content = editText.getText().toString();
                    if (!TextUtils.isEmpty(content)){
                        addDanmaku(content,true);
                        editText.setText("");
                    }
                }
            });
            getWindow().getDecorView().setOnSystemUiVisibilityChangeListener(new View.OnSystemUiVisibilityChangeListener() {
                @Override
                public void onSystemUiVisibilityChange(int visibility) {
                    if (visibility == View.SYSTEM_UI_FLAG_VISIBLE){
                        onWindowFocusChanged(true);
                    }
                }
            });
        }
    //随机生成一些弹幕消息
        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();
        }
    
        /**
         * 向弹幕View中添加一条弹幕
         * @param content
         *   弹幕的具体内容
         * @param withBorder
         * DanmakuContext可以用于对弹幕的各种全局配置进行设定,如设置字体、设置最大显示行数等
         */
        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 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;
            }
        }
    
        @Override
        public void onWindowFocusChanged(boolean hasFocus) {
            super.onWindowFocusChanged(hasFocus);
            if (hasFocus && Build.VERSION.SDK_INT >= 19) {
                View decorView = getWindow().getDecorView();
                decorView.setSystemUiVisibility(
                        View.SYSTEM_UI_FLAG_LAYOUT_STABLE
                                | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
                                | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
                                | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
                                | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
                                | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
                );
            }
        }
    
    
    }
    

    manifest.xml

    <?xml version="1.0" encoding="utf-8"?>
    <manifest xmlns:android="http://schemas.android.com/apk/res/android"
        package="demo.ligong.sdut.danmutest">
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
        <application
            android:allowBackup="true"
            android:icon="@mipmap/ic_launcher"
            android:label="@string/app_name"
            android:roundIcon="@mipmap/ic_launcher_round"
            android:supportsRtl="true"
            android:theme="@style/AppTheme">
            <activity android:name=".MainActivity" android:screenOrientation="landscape"
                android:configChanges="orientation|keyboardHidden|screenLayout|screenSize"
                >
                <intent-filter>
                    <action android:name="android.intent.action.MAIN" />
    
                    <category android:name="android.intent.category.LAUNCHER" />
                </intent-filter>
            </activity>
        </application>
    
    </manifest>

    activity_main.xml

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="#000">
    
        <VideoView
            android:id="@+id/video_view"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_centerInParent="true" />
    
        <master.flame.danmaku.ui.widget.DanmakuView
            android:id="@+id/danmaku_view"
            android:layout_width="match_parent"
            android:layout_height="match_parent" />
    
        <LinearLayout
            android:id="@+id/operation_layout"
            android:layout_width="match_parent"
            android:layout_height="50dp"
            android:layout_alignParentBottom="true"
            android:background="#fff"
            android:visibility="gone">
    
            <EditText
                android:id="@+id/edit_text"
                android:layout_width="0dp"
                android:layout_height="match_parent"
                android:layout_weight="1" />
    
            <Button
                android:id="@+id/send"
                android:layout_width="wrap_content"
                android:layout_height="match_parent"
                android:text="Send" />
        </LinearLayout>
    </RelativeLayout>
    
  • 相关阅读:
    完美解决HTML5无法上传大文件方法
    完美解决jquery无法上传大文件方法
    Word图片上传控件+整合富文本
    ckeditor粘贴word文档图片的讨论
    python之理解super及MRO列表 ( 示例版 )
    JavaXXX成长直通车_汇总
    P75 验证码识别原理分析
    P74 复习
    P73 卷积神经网络识别手写数字
    P71 激活层与池化层
  • 原文地址:https://www.cnblogs.com/CCCrunner/p/11781787.html
Copyright © 2020-2023  润新知