概述

Android多媒体框架支持各种常见的媒体类型,可以很容易地将音频、视频和图像集成到App中。通过MediaPlayer Api,可以从应用程序资源(RAW)、文件系统或网络上数据流资源来播放音频或视频。本文演示了如何通过Api播放音频和视频文件,来获得良好性能和愉快的用户体验,仅供学习分享使用,如有不足之处,还请指正。

涉及知识点

  1. MediaPlayer 可以用来控制audio/video文件或流播放的类。通过此类,可以方便的控制音频/视频文件的播放,暂停和停止等操作。
  2. Uri 统一资源标识符(Uniform Resource Identifier,或URI)是一个用于标识某一互联网资源名称的字符串。
  3. VideoView 自带的一种播放视频的组件。
  4. SurfaceView 可以通过后台绘制显示的视图组件。

Activity中播放音频

页面上播放音频文件,步骤如下:

1. 准备资源文件,并播放

 private MediaPlayer mMediaPlayer;

     /**
* 开始
* @param v
*/
public void bn_start(View v){
if(mMediaPlayer==null) {
ready();
}
mMediaPlayer.start();
} /**
* 创建MediaPlayer并到prepare状态
*/
private void ready(){
if(mMediaPlayer==null){
mMediaPlayer=new MediaPlayer();//Idle
//Log.i("TAG", "ready: "+filePath);
File file=new File(Environment.getExternalStorageDirectory(),"goldfallen.mp3");
Log.i("TAG", "ready: "+file.getPath());
Log.i("TAG", "ready: "+file.exists());
Uri uri= Uri.fromFile(file);
try {
mMediaPlayer.setDataSource(AudioActivity.this,uri);
mMediaPlayer.prepare();//Prepared
} catch (IOException e) {
Log.i("TAG", "ready: "+ e.getMessage());
e.printStackTrace();
}
}
}

2. 暂停播放

 /**
* 暂停
* @param v
*/
public void bn_pause(View v){
if(mMediaPlayer!=null && mMediaPlayer.isPlaying()){
mMediaPlayer.pause();
}
}

3. 停止

   /**
* 停止
* @param v
*/
public void bn_stop(View v){
if(mMediaPlayer!=null && mMediaPlayer.isPlaying()){
mMediaPlayer.stop();
mMediaPlayer.release();
mMediaPlayer=null;
}
}

4. 释放资源(当页面销毁时,播放资源也要同时释放)

  @Override
protected void onDestroy() {
if(mMediaPlayer!=null && mMediaPlayer.isPlaying()){
mMediaPlayer.stop();
mMediaPlayer.release();
mMediaPlayer=null;
}
super.onDestroy();
}

5. 通过静态函数创建对象

 /**
* D:\Android\Project\DemoMedia\app\src\main\res\raw\A2012.mp3:
* Error: 'A' is not a valid file-based resource name character:
* File-based resource names must contain only lowercase a-z, 0-9, or underscore
*/
private void ready2(){
if(mMediaPlayer==null){
mMediaPlayer= MediaPlayer.create(this,R.raw.ab2012);
}
}

通过服务来播放音频

当页面关闭时,音频文件还可以在后台播放。步骤如下:

1. 定义后台服务,当服务启动时,创建MediaPlayer对象,并注册服务接收对象。

 public class AudioService extends Service {

     private MediaPlayer mMediaPlayer;

     private OperatorReceiver mReceiver;

     public AudioService() {
} @Override
public void onCreate() {
super.onCreate();
mMediaPlayer=new MediaPlayer();
mReceiver=new OperatorReceiver();
IntentFilter filter=new IntentFilter("operator.receiver");
registerReceiver(mReceiver,filter);
} @Override
public IBinder onBind(Intent intent) {
return null;
} @Override
public int onStartCommand(Intent intent, int flags, int startId) {
Log.i("TAG", "onStartCommand: ----ready ");
ready();
return super.onStartCommand(intent, flags, startId);
} @Override
public void onDestroy() {
if(mMediaPlayer!=null && mMediaPlayer.isPlaying()){
mMediaPlayer.stop();
}
if(mMediaPlayer!=null){
mMediaPlayer.release();
mMediaPlayer=null;
}
unregisterReceiver(mReceiver);
super.onDestroy();
} private void start(){
mMediaPlayer.start();
} private void pause(){
mMediaPlayer.pause();
} private void stop(){
mMediaPlayer.stop();
ready();
} private void ready(){
mMediaPlayer.reset();
try {
String filePath= Environment.getExternalStorageDirectory()+"/ab2012.mp3";
Log.i("TAG", "ready: "+filePath);
File file=new File(filePath);
if(file.exists()) {
mMediaPlayer.setDataSource(filePath);
mMediaPlayer.prepare();
}else{
Log.i("TAG", "ready: 文件不存在 ");
}
} catch (IOException e) {
Log.i("TAG", "ready: "+e.getMessage());
e.printStackTrace();
}
}
}

2. 操作接收者定义如下:

  /**
* 操作接收器
*/
class OperatorReceiver extends BroadcastReceiver
{
@Override
public void onReceive(Context context, Intent intent) {
int cmd=intent.getIntExtra("cmd",-1);
Log.i("TAG", "onReceive: "+cmd);
switch (cmd){
case Tools.PLAY:
start();
break;
case Tools.PAUSE:
pause();
break;
case Tools.STOP:
stop();
break;
default:
start();
break; }
}
}

3. 启动服务

   Intent intent =new Intent(this,AudioService.class);
startService(intent);

4. 前台Activity通过发送广播命令进行控制音频的播放与暂停

 /**
* 开始
* @param v
*/
public void bn_start(View v){
Intent intent=new Intent("operator.receiver");
intent.putExtra("cmd",Tools.PLAY);
sendBroadcast(intent);
Log.i("TAG", "bn_start: "+"service");
} /**
* 暂停
* @param v
*/
public void bn_pause(View v){
Intent intent=new Intent("operator.receiver");
intent.putExtra("cmd",Tools.PAUSE);
sendBroadcast(intent);
} /**
* 停止
* @param v
*/
public void bn_stop(View v){
Intent intent=new Intent("operator.receiver");
intent.putExtra("cmd",Tools.STOP);
sendBroadcast(intent);
}

5.通过后台服务的方式,需要在AndroidManifest.xml文件中进行注册

  <service
android:name=".AudioService"
android:enabled="true"
android:exported="true">
</service>

通过VideoView来播放视频

通过VideoView进行播放视频文件,只需要设置资源URI即可,具体如下:

  private VideoView mVideoView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_video);
mVideoView= (VideoView) this.findViewById(R.id.vv_info);
//设置路径
File file=new File(Environment.getExternalStorageDirectory(),"DCIM/Camera/VID20190629142614.mp4");
Log.i("TAG", "onCreate: "+file.getPath());
if(!file.exists()){
Log.i("TAG", "onCreate: 文件不存在");
}
Uri uri=Uri.fromFile(file);
mVideoView.setVideoURI(uri);
//设置Media Controller
MediaController controller=new MediaController(this);
mVideoView.setMediaController(controller);
//获取焦点
mVideoView.requestFocus();
mVideoView.start();
//设置播放完成事件
mVideoView.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
@Override
public void onCompletion(MediaPlayer mp) {
Toast.makeText(VideoActivity.this, "播放完毕", Toast.LENGTH_SHORT).show();
}
});
}

通过MediaPlayer来播放视频

通过MediaPlayer来播放视频文件,然后通过SurfaceView来显示视频内容,具体步骤如下:

1.启动,通过setDisplay来设置显示内容

 public  void bn_start(View view)  {
mMediaPlayer.reset();//到Idle状态
//设置路径
File file=new File(Environment.getExternalStorageDirectory(),"DCIM/Camera/VID20190629142614.mp4");
Log.i("TAG", "onCreate: "+file.getPath());
if(!file.exists()){
Log.i("TAG", "onCreate: 文件不存在");
} else {
Log.i("TAG", "onCreate: 文件存在 ");
}
Uri uri=Uri.fromFile(file);
try {
mMediaPlayer.setDataSource(this,uri);
mMediaPlayer.setDisplay(mSurfaceView.getHolder());
mMediaPlayer.prepare();
mMediaPlayer.start();
} catch (IOException e) {
e.printStackTrace();
}
}

2. 暂停与停止

  public  void bn_pause(View view){
if(mMediaPlayer.isPlaying()){
mMediaPlayer.pause();
}
} public void bn_stop(View view){
if(mMediaPlayer.isPlaying()){
mMediaPlayer.stop();
}
}

3. 资源释放

  @Override
protected void onDestroy() {
if(mMediaPlayer!=null && mMediaPlayer.isPlaying()){
mMediaPlayer.stop();
}
if(mMediaPlayer!=null){
mMediaPlayer.release();
mMediaPlayer=null;
}
super.onDestroy();
}

权限设置

如果要播放视频,需要相应的权限设置,并在安装时获取请求权限

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

备注

合抱之木,生于毫末;九层之台,起于垒土;千里之行,始于足下。

一起学Android之音频视频的更多相关文章

  1. 【转】android如何浏览并选择图片 音频 视频

    转自:http://www.cnblogs.com/top5/archive/2012/03/06/2381986.html   这几天 在学习并开发android系统的图片浏览 音频 视频 的浏览 ...

  2. 【视频】零基础学Android开发:蓝牙聊天室APP(四)

    零基础学Android开发:蓝牙聊天室APP第四讲 4.1 ListView控件的使用 4.2 BaseAdapter具体解释 4.3 ListView分布与滚动事件 4.4 ListView事件监听 ...

  3. 【视频】零基础学Android开发:蓝牙聊天室APP(二)

    零基础学Android开发:蓝牙聊天室APP第二讲 2.1 课程内容应用场景 2.2 Android UI设计 2.3 组件布局:LinearLayout和RelativeLayout 2.4 Tex ...

  4. android基础---->音频和视频的使用

    Android 在播放音频和视频方面也是做了相当不错的支持,它提供了一套较为完整的API,使得开发者可以很轻松地编写出一个简易的音频或视频播放器.今天我们开始android中音频和视频使用的学习. 目 ...

  5. 【视频】零基础学Android开发:蓝牙聊天室APP(三)

    零基础学Android开发:蓝牙聊天室APP第三讲 3.1 ImageView.ImageButton控件具体解释 3.2 GridView控件具体解释 3.3 SimpleAdapter适配器具体解 ...

  6. 【视频】零基础学Android开发:蓝牙聊天室APP(一)

    零基础学Android开发:蓝牙聊天室APP第一讲 1. Android介绍与环境搭建:史上最高效Android入门学习 1.1 Google的大小战略 1.2 物联网与云计算 1.3 智能XX设备 ...

  7. 学Android开发 这19个开发工具助你顺风顺水

    学Android开发 这19个开发工具助你顺风顺水 要想快速开发一个Android应用,通常会用到很多工具,巧妙利用这些工具,能让我们的开发工作事半功倍,节省大量时间,下面大连Android开发培训小 ...

  8. android平台短视频技术之 视频编辑的经验分享.

    android平台短视频技术之 视频编辑的经验分享. 提示一: 各位看官,这里分享的是视频编辑,即剪切/拼接/分离/合并/涂鸦/标记/叠加/滤镜等对视频的编辑操作.不是流媒体网络播放等功能,请注意. ...

  9. Android开发 获取视频中的信息(例如预览图或视频时长) MediaMetadataRetriever媒体元数据检索器

    前言 在Android里获取视频的信息主要依靠MediaMetadataRetriever实现 获取最佳视频预览图 所谓的最佳就是MediaMetadataRetriever自己计算的 /** * 获 ...

随机推荐

  1. 【程序人生】一个IT人的立功,立言,立德三不朽

    最近几个月很忙,忙着当奶爸,忙着做加班狗,忙着补裤裆学技术……以至于快忘了要思考人生了! 古人立志穷极一生追求“立德”,“立功”,“立言”,以求不朽,为万世所景仰,为后人所传颂,实现人生的意义.立德者 ...

  2. 使用saltstack自动部署K8S

    使用saltstack自动部署K8S 一.环境准备 1.1 规划 1. 操作系统 CentOS-7.x-x86_64. 2. 关闭 iptables 和 SELinux. 3. 所有节点的主机名和 I ...

  3. 知识图谱推理与实践(3) -- jena自定义builtin

    在第2篇里,介绍了jena的The general purpose rule engine(通用规则引擎)及其使用,本篇继续探究,如何自定义builtin. builtin介绍 先回顾builtin为 ...

  4. CefSharp禁止弹出新窗体,在同一窗口打开链接,或者在新Tab页打开链接,并且支持带type="POST" target="_blank"的链接

    说明:在同一窗口打开链接,只要稍加改造就可以实现,这里实现的是在新Tab页打开链接,并且支持带type="POST" target="_blank"的链接 gi ...

  5. HTML DOM 学习

    HTML DOM 学习 By: Mirror王宇阳 E-mail:2821319009@qq.com 博客主页:https://www.cnblogs.com/wangyuyang1016/ DOM ...

  6. JavaScript中常用的字符串方法

    1. charAt(x) charAt(x)返回字符串中x位置的字符,下标从 0 开始. //charAt(x) var myString = 'jQuery FTW!!!'; console.log ...

  7. Unity 依赖注入容器的AOP扩展

    使用EntLib\PIAB Unity 实现动态代理 using System; using Unity; using Unity.Interception; using Unity.Intercep ...

  8. WebShell代码分析溯源(十一)

    WebShell代码分析溯源(十一) 一.一句话变形马样本 <?php $e = $_REQUEST['e'];declare(ticks=1);register_tick_function ( ...

  9. PHP 字符串大全

    PHP字符串函数是核心的一部分.无需安装即可使用这些函数 函数名称 描述 addcslashes 以 C 语言风格使用反斜线转义字符串中的字符 addslashes 使用反斜线引用字符串 bin2he ...

  10. vue如何debugger源码

    在我们阅读vue源码时,一般引用vue的版本都是打包编译后的版本,无法debugger源码,要debugger源码,就需要给代码添加sourcemap,他存储源码与编译后代码的一种对应关系,详细内容可 ...