android开发之简单视频播放器(VideoView)

简单视频播放器的使用
一、简单使用videoView和MediaController实现播放控制
1、添加需要的权限

 <uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.CHANGE_CONFIGURATION"></uses-permission>

2、设置布局

 <VideoView
            android:id="@+id/main_video"
            android:layout_width="match_parent"
            android:layout_height="240dp"
            />

3、实例化VideoView

VideoView  videoView = (VideoView) findViewById(R.id.main_video);
      MediaController  controller = new MediaController(this);//实例化控制器
//        String path = Environment.getExternalStorageDirectory().getAbsolutePath()+"jiaoxue.mp4";
        /**
         * 本地播放
         */
//        videoView.setVideoPath("path");
        /**
         * 网络播放
         */
        videoView.setVideoURI(Uri.parse("http://192.168.1.109:8080/video/jiaoxue.mp4"));

        /**
         * 将控制器和播放器进行互相关联
         */
        controller.setMediaPlayer(videoView);
        videoView.setMediaController(controller);

二、自定义播放器 (贴上源码)

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    tools:context="com.zzj.myeasyvideoplaydemo.MainActivity">

    <RelativeLayout

        android:layout_width="match_parent"
        android:layout_height="240dp">
        <VideoView
            android:id="@+id/main_video"
            android:layout_width="match_parent"
            android:layout_height="240dp"
            />
        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="50dp"
            android:orientation="vertical"
            android:layout_alignParentBottom="true"
            >
            <SeekBar
                android:layout_width="match_parent"
                android:layout_height="5dp"
                android:layout_marginLeft="-20dp"
                android:layout_marginRight="-20dp"
                android:max="100"
                android:indeterminate="false"
                android:progress="20"
                />
            <RelativeLayout
                android:gravity="center_vertical"
                android:background="#101010"
                android:layout_width="match_parent"
                android:layout_height="match_parent">
                <LinearLayout
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:orientation="horizontal"
                    >
                    <ImageView
                        android:id="@+id/play_pasue_image"
                        android:layout_marginLeft="5dp"
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:background="@mipmap/video_play_blue"
                        />
                    <TextView
                        android:id="@+id/main_current_time"
                        android:layout_marginLeft="16dp"
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:text="00:00:00"
                        android:textSize="14dp"
                        android:textColor="#ffffff"
                        />
                    <TextView
                        android:layout_marginLeft="5dp"
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:text="/"
                        android:textSize="14dp"
                        android:textColor="#4c4c4c"
                        />
                    <TextView
                        android:id="@+id/main_totally_time"
                        android:layout_marginLeft="5dp"
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:text="00:00:00"
                        android:textSize="14dp"
                        android:textColor="#ffffff"
                        />
                </LinearLayout>
                <LinearLayout
                    android:layout_marginRight="5dp"
                    android:layout_alignParentRight="true"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content">
                    <ImageView
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:background="@mipmap/video_sound_switch"
                        />
                    <SeekBar
                        android:layout_width="100dp"
                        android:layout_height="5dp"
                        android:progress="20"
                        android:max="100"
                        />
                    <ImageView
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:background="@mipmap/play"
                        />
                </LinearLayout>
            </RelativeLayout>
        </LinearLayout>
    </RelativeLayout>

</RelativeLayout>

视频Java类:

public class TestMovieActivity extends BaseActivity {
    public static final int UPDATA_VIDEO_NUM = 1;
    private CustomVideoView videoView;
    private MediaController controller;//控制器
    private RelativeLayout videoLayout;
    private LinearLayout controllerLayout;//播放器的总控制布局
    private SeekBar play_seek, volume_seek;//播放进度和音量控制进度
    private ImageView play_controller_image, screen_image,volume_Image;
    private TextView current_time_tv, totally_time_tv;
    private String path;
    private int screen_width, screen_height;
    private AudioManager audioManager;//音量控制器
    private boolean screen_flag = true;//判断屏幕转向

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        //实例化音量控制器
        audioManager = (AudioManager) getSystemService(AUDIO_SERVICE);
        setContentView(R.layout.act_testmovie);

        initView();
        initData();
        initViewOnClick();
//        controller = new MediaController(this);//实例化控制器
//        path = Environment.getExternalStorageDirectory().getAbsolutePath()+"jiaoxue.mp4";
        /**
         * 本地播放
         */
//        videoView.setVideoPath("");
        /**
         * 网络播放
         */
        videoView.setVideoURI(Uri.parse("http://192.168.1.109:8080/video/jiaoxue.mp4"));
        //视频播放时开始刷新
//        videoView.start();
        play_controller_image.setImageResource(R.mipmap.video_play_blue);
//        handler.sendEmptyMessage(UPDATA_VIDEO_NUM);
        /**
         * 将控制器和播放器进行互相关联
         */
//        controller.setMediaPlayer(videoView);
//        videoView.setMediaController(controller);
    }

    @Override
    protected void onPause() {
        super.onPause();
        handler.removeMessages(UPDATA_VIDEO_NUM);
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        handler.removeMessages(UPDATA_VIDEO_NUM);
    }

    @Override
    public void onConfigurationChanged(Configuration newConfig) {
        super.onConfigurationChanged(newConfig);
        // 判断当前屏幕的横竖屏状态
        int screenOritentation = getResources().getConfiguration().orientation;
        if (screenOritentation == Configuration.ORIENTATION_LANDSCAPE) {
            //横屏时处理
            setVideoScreenSize(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
            volume_seek.setVisibility(View.VISIBLE);
            volume_Image.setVisibility(View.VISIBLE);
            screen_flag = false;
            //清除全屏标记,重新添加
            getWindow().clearFlags((WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN));
            getWindow().addFlags((WindowManager.LayoutParams.FLAG_FULLSCREEN));
        } else {
            //竖屏时处理
            setVideoScreenSize(ViewGroup.LayoutParams.MATCH_PARENT, DisplayUtils.dp2px(mContext,240));
            screen_flag = true;
            volume_seek.setVisibility(View.GONE);
            volume_Image.setVisibility(View.GONE);
            //清除全屏标记,重新添加
            getWindow().clearFlags((WindowManager.LayoutParams.FLAG_FULLSCREEN));
            getWindow().addFlags((WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN));
        }
    }

    /**
     * 通过handler对播放进度和时间进行更新
     */
    private Handler handler = new Handler() {
        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            if (msg.what == UPDATA_VIDEO_NUM) {
                //获取视频播放的当前时间
                int currentTime = videoView.getCurrentPosition();
                //获取视频的总时间
                int totally = videoView.getDuration();
                //格式化显示时间
                updataTimeFormat(totally_time_tv, totally);
                updataTimeFormat(current_time_tv, currentTime);
                //设置播放进度
                play_seek.setMax(totally);
                play_seek.setProgress(currentTime);
                //自己通知自己更新
                handler.sendEmptyMessageDelayed(UPDATA_VIDEO_NUM, 500);//500毫秒刷新
            }
        }
    };

    /**
     * 设置横竖屏时的视频大小
     *
     * @param width
     * @param height
     */
    private void setVideoScreenSize(int width, int height) {
        //获取视频控件的布局参数
        ViewGroup.LayoutParams videoViewLayoutParams = videoView.getLayoutParams();
        //设置视频范围
        videoViewLayoutParams.width = width;
        videoViewLayoutParams.height = height;
        videoView.setLayoutParams(videoViewLayoutParams);
        //设置视频和控制组件的layout
        ViewGroup.LayoutParams videoLayoutLayoutParams= videoLayout.getLayoutParams();
        videoLayoutLayoutParams.width = width;
        videoLayoutLayoutParams.height = height;
        videoLayout.setLayoutParams(videoLayoutLayoutParams);
    }

    /**
     * 时间格式化
     *
     * @param textView    时间控件
     * @param millisecond 总时间 毫秒
     */
    private void updataTimeFormat(TextView textView, int millisecond) {
        //将毫秒转换为秒
        int second = millisecond / 1000;
        //计算小时
        int hh = second / 3600;
        //计算分钟
        int mm = second % 3600 / 60;
        //计算秒
        int ss = second % 60;
        //判断时间单位的位数
        String str = null;
        if (hh != 0) {//表示时间单位为三位
            str = String.format("%02d:%02d:%02d", hh, mm, ss);
        } else {
            str = String.format("%02d:%02d", mm, ss);
        }
        //将时间赋值给控件
        textView.setText(str);
    }

    /**
     * 按钮点击事件
     */
    private void initViewOnClick() {
        //播放按钮事件
        play_controller_image.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                //判断播放按钮的状态
                if (videoView.isPlaying()) {
                    play_controller_image.setImageResource(R.mipmap.video_play_blue);
                    //视频暂停
                    videoView.pause();
                    //当视频处于暂停状态,停止handler的刷新
                    handler.removeMessages(UPDATA_VIDEO_NUM);
                } else {
                    play_controller_image.setImageResource(R.mipmap.video_pause_white);
                    videoView.start();
                    //当视频播放时,通知刷新
                    handler.sendEmptyMessage(UPDATA_VIDEO_NUM);
                }
            }
        });
        //播放进度条事件
        play_seek.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
            @Override
            public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
                //设置当前的播放时间
                updataTimeFormat(current_time_tv, progress);
                if (videoView.getDuration() == progress) {
                    play_controller_image.setImageResource(R.mipmap.video_play_blue);
                }
            }

            @Override
            public void onStartTrackingTouch(SeekBar seekBar) {
                //拖动视频进度时,停止刷新
                handler.removeMessages(UPDATA_VIDEO_NUM);
            }

            @Override
            public void onStopTrackingTouch(SeekBar seekBar) {
                //停止拖动后,获取总进度
                int totall = seekBar.getProgress();
                //设置VideoView的播放进度
                videoView.seekTo(totall);
                //重新handler刷新
                handler.sendEmptyMessage(UPDATA_VIDEO_NUM);

            }
        });
        //音量控制条事件
        volume_seek.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
            @Override
            public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
                //设置音量变动后系统的值
                audioManager.setStreamVolume(AudioManager.STREAM_MUSIC,progress,0);
            }

            @Override
            public void onStartTrackingTouch(SeekBar seekBar) {

            }

            @Override
            public void onStopTrackingTouch(SeekBar seekBar) {

            }
        });

        //设置全屏按钮点击事件
        screen_image.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                showLog("------当前屏幕标记----:"+screen_flag);
                if(screen_flag){
                    setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);//控制屏幕竖屏
                }else {
                    setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);//控制屏幕横屏
                }
            }
        });
    }

    @Override
    protected void initView() {
        videoView = (CustomVideoView) findViewById(R.id.main_video);
        videoLayout = (RelativeLayout) findViewById(R.id.act_testmovie_videolayout);
        controllerLayout = (LinearLayout) findViewById(R.id.main_controller_liner);
        play_seek = (SeekBar) findViewById(R.id.main_play_seek);
        volume_seek = (SeekBar) findViewById(R.id.main_volume_seek);
        current_time_tv = (TextView) findViewById(R.id.main_current_time);
        totally_time_tv = (TextView) findViewById(R.id.main_totally_time);
        play_controller_image = (ImageView) findViewById(R.id.play_pasue_image);
        screen_image = (ImageView) findViewById(R.id.main_screen_image);
        volume_Image = (ImageView) findViewById(R.id.act_testmovies_volume_image);
        DisplayMetrics metric = new DisplayMetrics();
        screen_width = metric.widthPixels;
        screen_height = metric.heightPixels;
    }

    @Override
    protected void initData() {
        //获取设置音量的最大值
        int volumeMax = audioManager.getStreamMaxVolume(AudioManager.STREAM_MUSIC);
        volume_seek.setMax(volumeMax);
        //获取设置当前音量
        int currentVolume = audioManager.getStreamVolume(AudioManager.STREAM_MUSIC);
        volume_seek.setProgress(currentVolume);
    }
}

补上CustomVideoView

public class CustomVideoView extends VideoView {
    //声明屏幕的大小
    int width = 1920;
    int height = 1080;
    public CustomVideoView(Context context) {
        super(context);
    }

    public CustomVideoView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    public CustomVideoView(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        //设置宽高
        int defaultWidth = getDefaultSize(width,widthMeasureSpec);
        int defaultHeight = getDefaultSize(height,heightMeasureSpec);
        setMeasuredDimension(defaultWidth,defaultHeight);
    }
}

https://github.com/z1060932884/VideoDemo

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 200,392评论 5 470
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 84,258评论 2 377
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 147,417评论 0 332
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 53,992评论 1 272
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 62,930评论 5 360
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,199评论 1 277
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,652评论 3 390
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,327评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,463评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,382评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,432评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,118评论 3 315
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,704评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,787评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,999评论 1 255
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,476评论 2 346
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,057评论 2 341

推荐阅读更多精彩内容

  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 171,282评论 25 707
  • 视频播放器在App是很常见的,有哪些视频播放器呢?具体情况该用哪款呢?这里我总结了常用的视屏播放Videoview...
    奔跑吧李博阅读 29,624评论 2 46
  • 一些肢体语言会泄露你内心的想法,即使这个想法你并不知道,这些,你都知道吗?据现在的科学研究来看,人们所知道的肢体语...
    岳小姐阅读 2,099评论 0 0
  • 什么状态 我也不知道 醒的时候很难睡着 熬夜熬的烦躁 每天躺在床上但都觉得好累好累 睡的时候 戴上眼罩 想着想着事...
    我叫什么不重要阅读 119评论 0 0
  • 昨晚朋友生日,家庭聚餐。餐后都约着去寿星家继续娱乐。 我们几个脾气相投的中年少女,凑在寿星婆的闺房拉呱...
    子信521阅读 306评论 0 0