利用vitamio Mediaplayer 自定义了一个播放器

本人android初学者,学习了Vitamio Mediaplayer 的Demo,参考了农民伯伯大牛的文章,具体链接如下:

http://www.cnblogs.com/over140/archive/2012/05/22/2473019.html

实现了简单的功能:双击屏幕切换,点击显示进度条,暂停和播放。自己记录下,许多地方还有待优化的部分,请大家指点哈。

手机拍摄的真机效果不好请大家原谅

显示效果:

首先是XML布局:

这里增加了进度,播放,暂停等组件

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    >
    <RelativeLayout
        android:id="@+id/live_top"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@mipmap/top_bar_bg"
        >
        <ImageView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:src="@mipmap/detail_back_icon"
            android:layout_centerVertical="true"
            android:padding="5dp"
            />
        <TextView
            android:id="@+id/title"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_centerInParent="true"
            android:layout_marginLeft="85dp"
            android:layout_marginRight="85dp"
            android:textColor="#1c1c1c"
            android:textSize="25sp"
            android:text="测试视频"
            />
    </RelativeLayout>
    <RelativeLayout
        android:id="@+id/live_gl_rl"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:padding="@dimen/live_rl_padding"
        >
        <io.vov.vitamio.widget.CenterLayout
            android:id="@+id/live_cl"
            android:layout_width="match_parent"
            android:layout_height="220dp"
            >
            <ImageView
                android:id="@+id/live_iv_videoimage"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:visibility="gone"
                />
            <SurfaceView
                android:id="@+id/myvideo"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:layout_gravity="center"
                />
            <ImageView
                android:id="@+id/live_iv_play"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:src="@mipmap/play_btn"
                android:visibility="gone"
                />
            <ImageView
                android:id="@+id/live_iv_begin"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:src="@mipmap/play_btn"
                />
        </io.vov.vitamio.widget.CenterLayout>
        <RelativeLayout
            android:id="@+id/live_rl_clear"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_alignBottom="@+id/live_cl"
            android:visibility="gone"
            >
            <ImageButton
                android:id="@+id/live_imgbt_play"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginLeft="5dp"
                android:layout_centerVertical="true"
                android:background="@drawable/mediacontroller_button"
                android:src="@drawable/mediacontroller_pause"
                android:contentDescription="@string/mediacontroller_play_pause"
                />
            <TextView
                android:text="00:00:00"
                android:id="@+id/live_tv_current"
                style="@style/MediaController_Text"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_centerVertical="true"
                android:layout_toRightOf="@id/live_imgbt_play"
                />
            <TextView
                android:id="@+id/live_tv_end"
                style="@style/MediaController_Text"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_alignParentRight="true"
                android:layout_centerVertical="true"
                android:layout_marginRight="5dp"
                />
            <SeekBar
                android:id="@+id/live_seekbar"
                style="@style/MediaController_SeekBar"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_centerVertical="true"
                android:layout_toLeftOf="@+id/live_tv_end"
                android:layout_toRightOf="@+id/live_tv_current"
                android:focusable="true"
                android:max="1000" />
        </RelativeLayout>
    </RelativeLayout>

</LinearLayout>

JAVA代码,这里我仿照着农民伯伯的Demo,利用的GestureDetector(手势),触发双击和单击事件,还可以增加亮度和声音的手势调节,很可惜目前没有增加。利用Timer 与Handler每秒触发任务更新UI组件的进程。

package com.gmw.news.activity;
import android.content.pm.ActivityInfo;
import android.content.res.Configuration;
import android.graphics.PixelFormat;
import android.media.AudioManager;
import android.os.Bundle;
import android.os.Environment;
import android.os.Handler;
import android.os.Message;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import android.view.ViewGroup;
import android.view.WindowManager;
import android.widget.ImageButton;
import android.widget.ImageView;
import android.widget.RelativeLayout;
import android.widget.SeekBar;
import android.widget.TextView;

import com.gmw.news.R;

import java.util.Timer;
import java.util.TimerTask;

import io.vov.vitamio.LibsChecker;
import io.vov.vitamio.MediaPlayer;
import io.vov.vitamio.widget.CenterLayout;

public class LiveActivity extends BaseActivity implements SurfaceHolder.Callback,
        MediaPlayer.OnBufferingUpdateListener, MediaPlayer.OnCompletionListener,
        MediaPlayer.OnPreparedListener, MediaPlayer.OnVideoSizeChangedListener, View.OnTouchListener {
    private String PATH = Environment.getExternalStorageDirectory().getPath()+"/Movies/5.mkv";
    private static final String TAG = "MediaPlayerDemo";
    private int mVideoWidth;
    private int mVideoHeight;
    private MediaPlayer mMediaPlayer;
    private SurfaceView mPreview;
    private SurfaceHolder holder;
    private Bundle extras;
    private static final String MEDIA = "media";
    private static final int LOCAL_AUDIO = 1;
    private static final int STREAM_AUDIO = 2;
    private static final int RESOURCES_AUDIO = 3;
    private static final int LOCAL_VIDEO = 4;
    private static final int STREAM_VIDEO = 5;
    private boolean mIsVideoSizeKnown = false;
    private boolean mIsVideoReadyToBePlayed = false;
    private TextView txVideoTime;
    private SeekBar liveSeekBar;
    private Timer mTimer;
    private TextView txVideoCurrentTime;
    private long videoTime;
    private ImageView playBT;
    public final static int HANDER_UPDATE = 1;
    public final static int HANDER_HIDE = 2;
    private RelativeLayout liveRelative;
    private ImageButton liveImgbtPlay;
    private GestureDetector mGestureDetector;
    //屏幕的宽高
    private int windowWidth;
    private int windowHeight;
    //竖屏宽高
    private int glayoutHeight;
    private int glayoutWidth;
    private ViewGroup.LayoutParams layoutParams;
    private RelativeLayout liveTop;
    private CenterLayout glayout;
    //获取视频播放父类的padding,方便全屏的时候修改
    private RelativeLayout liveGlRl;
    private int liveGlRlPaddingBottom;
    private int liveGlRlPaddingLeft;
    private int liveGlRlPaddingRight;
    private int liveGlRlPaddingTop;

    @Override
    public void onConfigurationChanged(Configuration newConfig) {
        super.onConfigurationChanged(newConfig);
        Log.v(TAG,"onConfigurationChanged");
    }

    @Override
    public void initData() {
        //初始化库。若少了会报错!!
        if(!LibsChecker.checkVitamioLibs(this))
            return;
        //禁止休眠
        getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
        DisplayMetrics displayMetrics = getResources().getDisplayMetrics();
        windowWidth = displayMetrics.widthPixels;
        windowHeight = displayMetrics.heightPixels;
        mTimer = new Timer();
        mTimer.schedule(mTimerTask,0,1000);
    }
    private TimerTask mTimerTask = new TimerTask() {
        @Override
        public void run() {
            if(mMediaPlayer == null)
                return;
            if(mMediaPlayer.isPlaying()) {
                Message msg = Message.obtain();
                msg.what = HANDER_UPDATE;
                mHandler.sendMessage(msg);
            }
        }
    };
    private Handler mHandler = new Handler(){
        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            if(mMediaPlayer == null){
                return;
            }
            switch (msg.what){
                case HANDER_UPDATE:
                    long position = mMediaPlayer.getCurrentPosition();
                    long progress = liveSeekBar.getMax()*position/videoTime;
                    txVideoCurrentTime.setText(formatDuring(position));
                    liveSeekBar.setProgress((int) progress);
                    break;
                case HANDER_HIDE:

                    if(mMediaPlayer.isPlaying()){
                        playBT.setVisibility(View.GONE);
                        liveRelative.setVisibility(View.GONE);
                    }
                    break;
                default:
                    break;
            }

        }
    };
    @Override
    public void initView() {
        //加载布局文件
        setContentView(R.layout.activity_live);
        txVideoTime = (TextView) findViewById(R.id.live_tv_end);
        txVideoCurrentTime = (TextView) findViewById(R.id.live_tv_current);
        liveSeekBar = (SeekBar) findViewById(R.id.live_seekbar);
        playBT = (ImageView) findViewById(R.id.live_iv_play);
        liveRelative = (RelativeLayout) findViewById(R.id.live_rl_clear);
        liveImgbtPlay = (ImageButton) findViewById(R.id.live_imgbt_play);
        glayout = (CenterLayout) findViewById(R.id.live_cl);
        liveTop = (RelativeLayout) findViewById(R.id.live_top);
        layoutParams = glayout.getLayoutParams();
        glayoutHeight = layoutParams.height;
        glayoutWidth = layoutParams.width;

        liveGlRl = (RelativeLayout) findViewById(R.id.live_gl_rl);
        liveGlRlPaddingBottom = liveGlRl.getPaddingBottom();
        liveGlRlPaddingLeft = liveGlRl.getPaddingLeft();
        liveGlRlPaddingRight = liveGlRl.getPaddingRight();
        liveGlRlPaddingTop = liveGlRl.getPaddingTop();
        //注册手势时间
        mGestureDetector = new GestureDetector(this,new MyOnGestureListenner());
        //查找组件
        mPreview = (SurfaceView)findViewById(R.id.myvideo);

        //获取此surfaceView的holder对象。此holder对象即为mediaplayer显示的地方。
        holder = mPreview.getHolder();
        //设置回调。这里主要是surfaceChanged、surfaceDestroyed、surfaceCreated三个方法。
        holder.addCallback(this);
        holder.setFormat(PixelFormat.RGBA_8888);

        //获取数据
        //extras = getIntent().getExtras();
    }

    @Override
    public boolean onTouch(View v, MotionEvent event) {
        return mGestureDetector.onTouchEvent(event);
    }

    private class MyOnGestureListenner extends GestureDetector.SimpleOnGestureListener{
        @Override
        public boolean onSingleTapUp(MotionEvent e) {
            Log.v("onSingleTapUp","onSingleTapUp");
            liveRelative.setVisibility(View.VISIBLE);
            playBT.setVisibility(View.VISIBLE);
            Message msg = Message.obtain();
            msg.what = HANDER_HIDE;
            mHandler.sendMessageDelayed(msg, 3000);
            return super.onSingleTapUp(e);
        }

        @Override
        public boolean onDoubleTap(MotionEvent e) {
            Log.v("onDoubleTap", "onDoubleTap");
            if(mMediaPlayer == null){
                Log.v(TAG,"屏幕高:"+windowHeight+";屏幕宽:"+
                        windowWidth+"竖屏高:"+glayoutHeight+"宽:"+glayoutWidth);
            }
            int mCurrentOrientation = LiveActivity.this.getResources().getConfiguration().orientation;
            WindowManager.LayoutParams attrs = getWindow().getAttributes();
            //如果是横屏
            if(mCurrentOrientation == Configuration.ORIENTATION_LANDSCAPE){

                LiveActivity.this.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
                attrs.flags &= (~WindowManager.LayoutParams.FLAG_FULLSCREEN);
                getWindow().setAttributes(attrs);
                //取消全屏设置
                getWindow().clearFlags(WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS);
                liveTop.setVisibility(View.VISIBLE);
                layoutParams.height = glayoutHeight;
                layoutParams.width = glayoutWidth;
                liveGlRl.setPadding(liveGlRlPaddingLeft,liveGlRlPaddingTop,
                        liveGlRlPaddingRight,liveGlRlPaddingBottom);
                glayout.setLayoutParams(layoutParams);
            }
            //若果是竖屏
            if(mCurrentOrientation == Configuration.ORIENTATION_PORTRAIT){
                LiveActivity.this.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);
                attrs.flags |= WindowManager.LayoutParams.FLAG_FULLSCREEN;
                getWindow().setAttributes(attrs);
                //设置全屏
                getWindow().addFlags(WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS);
                liveTop.setVisibility(View.GONE);
                layoutParams.height = windowWidth;
                layoutParams.width = windowHeight;
                liveGlRl.setPadding(0,0,0,0);
                glayout.setLayoutParams(layoutParams);
            }
            //return super.onDoubleTap(e);
            return true;
        }
    }

    @Override
    public void initAction() {
        //设置触摸监听
        mPreview.setOnTouchListener(this);
        mPreview.setFocusable(true);//使能控件获得焦点
        mPreview.setClickable(true);//表明控件可以点击
        mPreview.setLongClickable(true);
        playBT.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if(mMediaPlayer.isPlaying()){
                    mMediaPlayer.stop();
                }else{
                    mMediaPlayer.start();
                }
            }
        });
        liveImgbtPlay.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if(mMediaPlayer.isPlaying()){
                    mMediaPlayer.stop();
                }else{
                    mMediaPlayer.start();
                }
            }
        });
    }
    private void doCleanUp() {
        mVideoWidth = 0;
        mVideoHeight = 0;
        mIsVideoReadyToBePlayed = false;
        mIsVideoSizeKnown = false;
    }

    @Override
    public void surfaceCreated(SurfaceHolder holder) {
        Log.d(TAG, "surfaceCreated called");
        final ImageView begin = (ImageView) findViewById(R.id.live_iv_begin);
        begin.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                begin.setVisibility(View.GONE);
                playVideo();
            }
        });

    }

    private void playVideo() {
        doCleanUp();
        try {
            //初始化mediaplayer。
            mMediaPlayer =new MediaPlayer(this);
            //设置数据源
            mMediaPlayer.setDataSource(PATH);
            //设置显示
            mMediaPlayer.setDisplay(holder);
            //准备
            mMediaPlayer.prepareAsync();
            //设置缓冲监听
            mMediaPlayer.setOnBufferingUpdateListener(this);
            //设置播放完毕监听
            mMediaPlayer.setOnCompletionListener(this);
            //设置准备完毕监听
            mMediaPlayer.setOnPreparedListener(this);
            //设置显示大小监听
            mMediaPlayer.setOnVideoSizeChangedListener(this);
            setVolumeControlStream(AudioManager.STREAM_MUSIC);
        }catch (Exception e) {
            Log.e(TAG, "error: " + e.getMessage(), e);
        }
    }

    @Override
    public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
        Log.d(TAG, "surfaceChanged called");
    }

    @Override
    public void surfaceDestroyed(SurfaceHolder holder) {
        Log.d(TAG, "surfaceDestroyed called");
    }

    @Override
    public void onBufferingUpdate(MediaPlayer mp, int percent) {
        //Log.d(TAG, "onBufferingUpdate percent:" + percent);
    }

    @Override
    public void onCompletion(MediaPlayer mp) {
        Log.d(TAG, "onCompletion called");
        mTimer.cancel();
    }

    @Override
    public void onPrepared(MediaPlayer mp) {
        Log.d(TAG, "onPrepared called");
        mIsVideoReadyToBePlayed = true;
        if (mIsVideoReadyToBePlayed && mIsVideoSizeKnown) {
            videoTime = mMediaPlayer.getDuration();
            txVideoTime.setText(formatDuring(videoTime));
            startVideoPlayback();
        }
    }

    @Override
    public void onVideoSizeChanged(MediaPlayer mp, int width, int height) {
        Log.v(TAG, "onVideoSizeChanged called");
        if (width == 0 || height == 0) {
            Log.e(TAG, "invalid video width(" + width + ") or height(" + height + ")");
            return;
        }
        mIsVideoSizeKnown = true;
        mVideoWidth = width;
        mVideoHeight = height;
        if (mIsVideoReadyToBePlayed && mIsVideoSizeKnown) {
            startVideoPlayback();
        }
    }
    @Override
    protected void onPause() {
        super.onPause();
        releaseMediaPlayer();
        doCleanUp();
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        releaseMediaPlayer();
        doCleanUp();
    }

    private void releaseMediaPlayer() {
        if (mMediaPlayer != null) {
            mMediaPlayer.release();
            mMediaPlayer = null;
        }
    }

    private void startVideoPlayback() {
        Log.v(TAG, "startVideoPlayback");

        holder.setFixedSize(mVideoWidth, mVideoHeight);
        mMediaPlayer.start();
    }
    //计算时间
    private  String formatDuring(long mss) {
        long hours = (mss % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60);
        long minutes = (mss % (1000 * 60 * 60)) / (1000 * 60);
        long seconds = (mss % (1000 * 60)) / 1000;
        String hour = "";
        if(hours < 10) {
            hour = "0" + hours;
        }else{
            hour = hours+"";
        }
        String minute = "";
        if(minutes < 10) {
            minute = "0" + minutes;
        }else{
            minute = hours+"";
        }
        String second = "";
        if(seconds < 10) {
            second = "0" + seconds;
        }else{
            second = seconds+"";
        }
        return hour + ":" + minute + ":"
                + second ;
    }
}

再来一个农民伯伯博客的传送门,里面详细的介绍了Vitamio:

http://www.cnblogs.com/over140/category/409230.html

时间: 2024-11-07 12:52:32

利用vitamio Mediaplayer 自定义了一个播放器的相关文章

095实现一个播放器的活动指示器

效果如下: ViewController.h 1 #import <UIKit/UIKit.h> 2 3 @interface ViewController : UIViewController 4 @property (strong, nonatomic) UIActivityIndicatorView *activityIndicatorView; 5 6 @end ViewController.m 1 #import "ViewController.h" 2 3 @i

使用纯css做一个播放器

首先,贴出成品图,如下: 可以发现播放器的基本形状有了,但是需要精确到每一个方向,不能溢出,就得以如下的方式写,贴出静态代码: html如下: <!DOCTYPE html><html lang="en"><head> <meta charset="UTF-8"> <title>Document</title> <link rel="stylesheet" href=&

如何用C#快速制作一个播放器

如何用VS快速制作一个播放器 本程序环境: 系统windows7 工具vs2012 语言c# 具体步骤如下: 1.  添加windowsmedia palyer组件 打开视图->工具箱 右键单击常规->选择项->COM组件->Windows Media Palyer 如图所示 新建winForm项目,打开form就可以看见工具箱常规下面有Windows Media Palyer组件了,如下图所示: 2.  在Form中添加WindowsMedia Palyer.OpenFileDi

使用VideoView自定义一个播放器控件

介绍 最近要使用播放器做一个简单的视频播放功能,开始学习VideoView,在横竖屏切换的时候碰到了点麻烦,不过在查阅资料后总算是解决了.在写VideoView播放视频时候定义控制的代码全写在Actvity里了,写完一看我靠代码好乱,于是就写了个自定义的播放器控件,支持指定大小,可以横竖屏切换,手动左右滑动快进快退.好了,下面开始. 效果图 效果图有点卡,我也不知道为啥..... VideoView介绍 这个是我们实现视频播放最主要的控件,详细的介绍大家百度就去看,这里介绍几个常用的方法. 用于

使用Mediaplay类写一个播放器

我们知道android本身播放视频的的能力是有限的..先来一个Demo 另附我的一个还未成熟的播放器,下载地址:http://www.eoemarket.com/soft/370334.html,正在完善中 package cn.marsXTU.mediaplayer; import android.media.AudioManager; import android.media.MediaPlayer; import android.media.MediaPlayer.OnCompletion

Android视频框架 Vitamio 打造自己的万能播放器

Vitamio 是一款 Android 与 iOS 平台上的全能多媒体开发框架,全面支持硬件解码与 GPU 渲染. Vitamio 功能强大,能够流畅播放720P甚至1080P高清MKV,FLV,MP4,MOV,TS,RMVB等常见格式的视频,还可以在 Android 与 iOS 上跨平台支持 MMS, RTSP, RTMP, HLS(m3u8) 等常见的多种视频流媒体协议,包括点播与直播. 1Vitamio的下载 官方下载: https://www.vitamio.org/Download/

利用js实现的音乐简易播放器

<html> <head> <meta charset="utf-8"> <meta name="author" content="dongfeng"> <title></title> <script> var musics = [ '1.mp3', '2.mp3', '3.mp3', '4.mp3', '2.mp3' ]; //定义正在播放的音频的索引 var

JavaScript自定义媒体播放器

使用<audio>和<video>元素的play()和pause()方法,可以手工控制媒体文件的播放.组合使用属性.事件和这两个方法,很容易创建一个自定义的媒体播放器,如下面的例子所示. 1 <div class="mediaplayer"> 2 <div class="video"> 3 <video id="player" src="movie.mov" poster=

如何写一个正经的Android音乐播放器 一

以前写过很多次音乐播放器,但是总有一些问题出现,例如: 1,音乐长时间播放问题(即便是放在service中去播放,依然会被杀死): 2,音乐的播放进度如何掌握?(如何利用mediaplayer.getCurrentPosition()来有效的通知界面变更进度?): 3,在我以往的经验中,音乐播放完毕下一曲时候,经常出现当前音乐播放还差几秒钟的时候就下一曲了的情况. 从网上找到教程中,通常都是一个播放器的demo,简单的直接把MediaPlayer放在了一个Activity中去操作,稍有良心的教程