手机影音第五天 视频列表的显示与播放以及个别牌子手机播放的问题

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了手机影音第五天 视频列表的显示与播放以及个别牌子手机播放的问题相关的知识,希望对你有一定的参考价值。

先展示下本次做好的效果:

    

技术分享

技术分享

  

  接着上次的说,上次说到了去获取手机里的视频信息,下面就用listview来展示视频列表与调用系统播放器来播放视频。

    1、根据获取到的视频列表,去设置适配器Adapter,然后利用前面写的listview的例子,来展示数据,这个就不详细说明了。

    2、点击单个listview的数据,来监听其事件,在监听的方法里,去调取播放方法。

        2.1利用隐式意图去调用所有符合要求的播放器。

        

    class MyOnItemClickListener implements AdapterView.OnItemClickListener {


        @Override
        public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
            //根据position获取list中的结果
            MediaItem item = mediaList.get(position);
            //Toast.makeText(context,"当前视频名称"+item.getName(),Toast.LENGTH_SHORT).show();

            //调取系统播放器  ---隐式意图
            Intent intent=new Intent(Intent.ACTION_VIEW);
           Uri uri=Uri.parse("file://"+item.getData());
            intent.setDataAndType(uri,"video/mp4"); //所有格式
            context.startActivity(intent);
        }
    }

    在这里就是要注意了,网上有的文章里,是这样写的

             Intent intent=new Intent(Intent.ACTION_VIEW);
            intent.setDataAndType(item.getData(),"video/mp4"); //所有格式
            context.startActivity(intent);

    这样写就导致无法弹出系统里符合播放条件的播放器,需要在URI做下处理,在前面加上file://这样才行。


    2.2 利用显示意图,直接调用mediaplayer来播放,自己封装了一下mediaplayer,以后可以自己定义播放器的样式,甚至打广告。这个SystemVideoPlayer是自己写的类。

Intent intent=new Intent(context,SystemVideoPlayer.class);
Uri uri=Uri.parse("file://"+item.getData());
intent.setDataAndType(uri,"video/mp4"); //所有格式
context.startActivity(intent);

    2.3 自定义的systemVideoPlayer,注意这个类继承Activity,要去androidManifext.xml里注册

    在这个类里,去监听videoView的准备播放状态,播放出错状态,播放完成状态,并且设置控制器来控制视频的暂停,快进,快退功能

package com.yuanlp.mobileplayer.activity;

import android.app.Activity;
import android.media.MediaPlayer;
import android.net.Uri;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.widget.MediaController;
import android.widget.Toast;
import android.widget.VideoView;

import com.yuanlp.mobileplayer.R;

/**
 * Created by 原立鹏 on 2017/7/16.
 * 系统播放器
 * 注意去Manifext.xml里注册
 */

public class SystemVideoPlayer extends Activity{
    private VideoView videoview;
    private Uri uri;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.system_video_player); //自定义的播放器样式,暂时为简单版    
        videoview= (VideoView) findViewById(R.id.videoview);

        //得到播放地址,从intent中获取
        uri = getIntent().getData();
        if (uri!=null){
            videoview.setVideoURI(uri);
        }

        //准备好的监听,监听是否视频准备好
        videoview.setOnPreparedListener(new MyOnPreparedListener());
        //播放出错了的监听
        videoview.setOnErrorListener(new MyOnErrorListener());
        //播放完成的监听
        videoview.setOnCompletionListener(new MyOnCompletionListener());

        //设置控制面板,系统自带的
        videoview.setMediaController(new MediaController(this));


    }
    /**
     * 准备好播放时的监听
     */
    class MyOnPreparedListener implements MediaPlayer.OnPreparedListener {

        @Override
        public void onPrepared(MediaPlayer mp) {
            videoview.start(); //开始播放

        }
    }

    /**
     * 播放出错
     */
    class MyOnErrorListener implements MediaPlayer.OnErrorListener {

        @Override
        public boolean onError(MediaPlayer mp, int what, int extra) {
            //出错后,系统会自动提示播放出错,同时自己也弹一个吐司
            Toast.makeText(SystemVideoPlayer.this,"播放出错",Toast.LENGTH_SHORT).show();
            return false;
        }
    }

    /**
     * 播放完成的监听
     */
    class MyOnCompletionListener implements MediaPlayer.OnCompletionListener {


        @Override
        public void onCompletion(MediaPlayer mp) {
            Toast.makeText(SystemVideoPlayer.this, "播放完成", Toast.LENGTH_SHORT).show();
        }
    }
}

    2.4 播放器样式布局

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
              android:orientation="vertical"
                android:gravity="center"
                android:background="#000000"
              android:layout_width="match_parent"
              android:layout_height="match_parent">

    <VideoView
        android:layout_centerInParent="true"
        android:id="@+id/videoview"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>
</RelativeLayout>


3、VideoPager的完整代码

package com.yuanlp.mobileplayer.pager;

import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.database.Cursor;
import android.net.Uri;
import android.os.Handler;
import android.os.Message;
import android.os.SystemClock;
import android.provider.MediaStore;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ListView;
import android.widget.ProgressBar;
import android.widget.TextView;
import android.widget.Toast;

import com.yuanlp.mobileplayer.R;
import com.yuanlp.mobileplayer.activity.SystemVideoPlayer;
import com.yuanlp.mobileplayer.adapter.MyAdapter;
import com.yuanlp.mobileplayer.base.BasePager;
import com.yuanlp.mobileplayer.bean.MediaItem;
import com.yuanlp.mobileplayer.utils.LogUtil;
import com.yuanlp.mobileplayer.utils.Utils;

import java.util.ArrayList;
import java.util.List;


/**
 * Created by 原立鹏 on 2017/7/13.
 * 本地视频的页面
 */

public class VideoPager extends BasePager {

    private ListView listview;
    private TextView nomedia;
    private ProgressBar pb_loding;
    private Utils utils;

    //保存所有的媒体信息的集合
    private List<MediaItem> mediaList;

    private MyAdapter myAdapter;

    public VideoPager(Context context) {
        super(context);
        utils=new Utils();

    }

    private Handler handler=new Handler(){
        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            if (mediaList!=null&&mediaList.size()>0){
                //有数据
                //设置适配器
                myAdapter=new MyAdapter(context,mediaList);
                listview.setAdapter(myAdapter);
               //Toast.makeText(context,"有数据",Toast.LENGTH_SHORT).show();
                nomedia.setVisibility(View.GONE);

            }else{
                //没有数据
                //文本显示
                Toast.makeText(context,"没有数据",Toast.LENGTH_SHORT).show();

            }
            pb_loding.setVisibility(View.GONE);
            //progressbar隐藏
        }
    };
    /**
     * 强制子类实现特定的效果
     *
     * @return
     */
    @Override
    public View initView() {
        LogUtil.e("本地视频被初始化了");
       View view=View.inflate(context, R.layout.video_pager,null);
        listview= (ListView) view.findViewById(R.id.listview);
        nomedia= (TextView) view.findViewById(R.id.tv_nomedia);
        pb_loding= (ProgressBar) view.findViewById(R.id.pb_loading);

        //设置listview的item的点击事件
        listview.setOnItemClickListener(new MyOnItemClickListener());

        return view;
    }

    @Override
    public void initData() {
        super.initData();
        LogUtil.e("本地视频页面的数据被初始化了");
        //加载本地数据
        getDataFromLocal();

    }

    class MyOnItemClickListener implements AdapterView.OnItemClickListener {


        @Override
        public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
            //根据position获取list中的结果
            MediaItem item = mediaList.get(position);
            //Toast.makeText(context,"当前视频名称"+item.getName(),Toast.LENGTH_SHORT).show();

//            //调取系统播放器  ---隐式意图
//            Intent intent=new Intent(Intent.ACTION_VIEW);
//           Uri uri=Uri.parse("file://"+item.getData());
//            intent.setDataAndType(uri,"video/mp4"); //所有格式
//            context.startActivity(intent);

            //调用自己写的播放器 ---显示意图

            Intent intent=new Intent(context,SystemVideoPlayer.class);
            Uri uri=Uri.parse("file://"+item.getData());
            intent.setDataAndType(uri,"video/mp4"); //所有格式
            context.startActivity(intent);

        }
    }

    /**
     * 从本地sd卡获取数据,有2中办法
     * 1、遍历sd卡,根据后缀名
     * 2、从内容提供者中获取,系统有自己会去扫描所有media信息。
     * 3/6.0后的系统,需要加上动态权限
     */
    private void getDataFromLocal() {
        mediaList=new ArrayList<>();

        new Thread(){
            @Override
            public void run() {
                super.run();
                SystemClock.sleep(2000);
                //根据上下文,去获取内容解析者
                ContentResolver resolver = context.getContentResolver();

                Uri uri= MediaStore.Video.Media.EXTERNAL_CONTENT_URI;
                String[] objs={
                       MediaStore.Video.Media.DISPLAY_NAME, //视频文件名称
                        MediaStore.Video.Media.DURATION,  //视频时长
                        MediaStore.Video.Media.SIZE, //文件大小
                        MediaStore.Video.Media.DATA, //视频的绝对地址
                        MediaStore.Video.Media.ARTIST,  //歌曲的演唱者,艺术家(音频可能会有该字段)
                };
                Cursor cursor = resolver.query(uri, objs, null, null, null);
                if (cursor!=null){
                    while(cursor.moveToNext()){
                        MediaItem item=new MediaItem();

                        String name=cursor.getString(0); //名称
                        item.setName(name);

                        long duration=cursor.getLong(1); //时长
                        item.setDuration(duration);

                        long size=cursor.getLong(2); //视频大小
                        item.setSize(size);

                        String data=cursor.getString(3); //视频的绝对地址
                        item.setData(data);

                        String artist=cursor.getString(4); //艺术家
                        item.setArtist(artist);

                        mediaList.add(item); //把每个item数据放到集合中
                    }
                    cursor.close();
                }

                //发消息,提示加载完media

                handler.sendEmptyMessage(0);
            }
        }.start();

    }



}

4、SystemVideoPlayer 自定义播放器类的代码

package com.yuanlp.mobileplayer.activity;

import android.app.Activity;
import android.media.MediaPlayer;
import android.net.Uri;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.widget.MediaController;
import android.widget.Toast;
import android.widget.VideoView;

import com.yuanlp.mobileplayer.R;

/**
 * Created by 原立鹏 on 2017/7/16.
 * 系统播放器
 * 注意去Manifext.xml里注册
 */

public class SystemVideoPlayer extends Activity{
    private VideoView videoview;
    private Uri uri;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.system_video_player);
        videoview= (VideoView) findViewById(R.id.videoview);

        //得到播放地址,从intent中获取
        uri = getIntent().getData();
        if (uri!=null){
            videoview.setVideoURI(uri);
        }

        //准备好的监听,监听是否视频准备好
        videoview.setOnPreparedListener(new MyOnPreparedListener());
        //播放出错了的监听
        videoview.setOnErrorListener(new MyOnErrorListener());
        //播放完成的监听
        videoview.setOnCompletionListener(new MyOnCompletionListener());

        //设置控制面板,系统自带的
        videoview.setMediaController(new MediaController(this));


    }
    /**
     * 准备好播放时的监听
     */
    class MyOnPreparedListener implements MediaPlayer.OnPreparedListener {

        @Override
        public void onPrepared(MediaPlayer mp) {
            videoview.start(); //开始播放

        }
    }

    /**
     * 播放出错
     */
    class MyOnErrorListener implements MediaPlayer.OnErrorListener {

        @Override
        public boolean onError(MediaPlayer mp, int what, int extra) {
            //出错后,系统会自动提示播放出错,同时自己也弹一个吐司
            Toast.makeText(SystemVideoPlayer.this,"播放出错",Toast.LENGTH_SHORT).show();
            return false;
        }
    }

    /**
     * 播放完成的监听
     */
    class MyOnCompletionListener implements MediaPlayer.OnCompletionListener {


        @Override
        public void onCompletion(MediaPlayer mp) {
            Toast.makeText(SystemVideoPlayer.this, "播放完成", Toast.LENGTH_SHORT).show();
        }
    }
}


本文出自 “YuanGuShi” 博客,请务必保留此出处http://cm0425.blog.51cto.com/10819451/1948069

以上是关于手机影音第五天 视频列表的显示与播放以及个别牌子手机播放的问题的主要内容,如果未能解决你的问题,请参考以下文章

手机影音第十四天,本地音乐列表的展示与播放(利用视频播放的布局)

手机影音第八天 控制视频播放页面的上面与下边的控制器布局的消失与隐藏

手机影音第十一天,显示视频缓冲,显示卡顿时的网速,播放系统视频时调用播放器的选择

手机影音第九天,控制视频全屏播放与退出全屏播放,音量调节按钮来控制视频音量与静音的实现

手机影音第七天 视频的播放下一个视频功能实现,视频进度电量变化的实现

手机影音第四天,顶部标题栏的布局实现与本地视频的搜索