APK应用程序为音乐和视频播放提供了完美解决方案
最编程
2024-01-09 09:59:17
...
#####1、实现功能
实现 音乐 或者 视频文件 点击 播放 暂停 停止 循环播放等
文件结构
#####3、string 文件
<resources>
<string name="app_name">AudioVideo</string>
<string name="music">音乐</string>
<string name="video">视频</string>
<string name="name">文件名</string>
<string name="play">播放</string>
<string name="stop">停止</string>
<string name="location">文件位置</string>
<string name="loopplay">重复播放</string>
<string name="kuaijin">快进</string>
<string name="kuaitui">快退</string>
<string name="mes">信息</string>
</resources>
#####3、xml 文件
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.lumeng.audiovideo.MainActivity">
<LinearLayout
android:layout_width="368dp"
android:layout_height="80dp"
android:layout_gravity="center"
android:orientation="horizontal"
tools:layout_editor_absoluteY="0dp"
tools:layout_editor_absoluteX="8dp">
<Button
android:id="@+id/bt_music"
android:layout_width="match_parent"
android:layout_height="fill_parent"
android:text="@string/music"
android:layout_weight="1"
android:textSize="40dp"/>
<Button
android:id="@+id/bt_video"
android:layout_width="match_parent"
android:layout_height="fill_parent"
android:text="@string/video"
android:layout_weight="1"
android:textSize="40dp"/>
</LinearLayout>
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="60dp"
android:layout_gravity="center"
android:orientation="vertical"
android:layout_marginTop="80dp"
tools:layout_editor_absoluteY="100dp"
tools:layout_editor_absoluteX="0dp">
<TextView
android:id="@+id/id_name"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:text="@string/name"
android:layout_weight="1"
android:textSize="20dp"
android:gravity="center" />
</LinearLayout>
<LinearLayout
android:layout_width="368dp"
android:layout_height="80dp"
android:layout_gravity="center"
android:orientation="horizontal"
android:layout_marginTop="150dp"
tools:layout_editor_absoluteY="0dp"
tools:layout_editor_absoluteX="8dp">
<Button
android:id="@+id/bt_play"
android:layout_width="match_parent"
android:layout_height="fill_parent"
android:text="@string/play"
android:layout_weight="1"
android:textSize="40dp"/>
<Button
android:id="@+id/bt_stop"
android:layout_width="match_parent"
android:layout_height="fill_parent"
android:text="@string/stop"
android:layout_weight="1"
android:textSize="40dp"/>
<CheckBox
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/chk_loop"
android:text="@string/loopplay"
android:layout_weight="1"
android:checked="false"
android:textSize="20dp"/>
</LinearLayout>
<LinearLayout
android:layout_width="368dp"
android:layout_height="80dp"
android:layout_gravity="center"
android:orientation="horizontal"
android:layout_marginTop="240dp"
tools:layout_editor_absoluteY="0dp"
tools:layout_editor_absoluteX="8dp">
<Button
android:id="@+id/bt_mes"
android:layout_width="match_parent"
android:layout_height="fill_parent"
android:text="@string/mes"
android:layout_weight="1"
android:textSize="40dp"/>
<Button
android:id="@+id/bt_kuaijin"
android:layout_width="match_parent"
android:layout_height="fill_parent"
android:text="@string/kuaitui"
android:layout_weight="1"
android:textSize="40dp"/>
<Button
android:id="@+id/bt_houtui"
android:layout_width="match_parent"
android:layout_height="fill_parent"
android:text="@string/kuaijin"
android:layout_weight="1"
android:textSize="40dp"/>
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:orientation="vertical"
android:layout_marginTop="320dp"
tools:layout_editor_absoluteY="100dp"
tools:layout_editor_absoluteX="0dp">
<TextView
android:id="@+id/id_location"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:text="@string/location"
android:textSize="20dp"
android:layout_weight="1"
android:singleLine="false"
android:gravity="left" />
</LinearLayout>
</RelativeLayout>
activity_video.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.lumeng.audiovideo.MainActivity">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:orientation="horizontal">
<VideoView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/videoView"/>
</LinearLayout>
</RelativeLayout>
#####5、功能代码
MainActivity.java
package com.example.lumeng.audiovideo;
import android.app.Activity;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.database.Cursor;
import android.media.MediaPlayer;
import android.net.Uri;
import android.provider.MediaStore;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.CheckBox;
import android.widget.CompoundButton;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends AppCompatActivity implements View.OnClickListener,
MediaPlayer.OnPreparedListener ,MediaPlayer.OnErrorListener,
MediaPlayer.OnCompletionListener, CompoundButton.OnCheckedChangeListener { //实现MediaPlayer的 3个事件监听事件
Uri uri; //存储影音文件的uri
TextView txvname, txvUri;
Button bt_Audio, bt_Video;
boolean isVideo = false; //记录是不是视频文件(否则是音乐文件)
Button btnPlay,btnStop;
CheckBox ckbLoop;
MediaPlayer mper;
Toast tos;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//设计屏幕不随手机旋转以及界面直像显示
setRequestedOrientation(ActivityInfo.
SCREEN_ORIENTATION_NOSENSOR);//设置屏幕不随手机旋转
setRequestedOrientation(ActivityInfo.
SCREEN_ORIENTATION_PORTRAIT);//设置屏幕直向显示
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);//保持屏幕常亮
bt_Audio = (Button) findViewById(R.id.bt_music);
bt_Video = (Button) findViewById(R.id.bt_video);
btnPlay = (Button) findViewById(R.id.bt_play);
btnStop = (Button) findViewById(R.id.bt_stop);
ckbLoop = (CheckBox) findViewById(R.id.chk_loop);
bt_Audio.setOnClickListener(this);
bt_Video.setOnClickListener(this);
btnPlay.setOnClickListener(this);
btnStop.setOnClickListener(this);
ckbLoop.setOnCheckedChangeListener(this);
txvname = (TextView)findViewById(R.id.id_name);
txvUri = (TextView)findViewById(R.id.id_location);
uri = Uri.parse("android.resource://" + getPackageName() +
"/" + R.raw.nlch);//默认播放程序内音乐 nlch
txvname.setText("nlch.mp3");//在界面显示名称
txvUri.setText("程序内的乐曲:" + uri.toString());//显示Uri
mper = new MediaPlayer(); //创建 MediaPlayer对象,设置三个监听事件
mper.setOnPreparedListener(this);
mper.setOnErrorListener(this);
mper.setOnCompletionListener(this);
tos = Toast.makeText(this,"",Toast.LENGTH_LONG); //创建Toast
prepareMusic();//准备默认的音乐(nlch.mp3)
}
void prepareMusic(){
btnPlay.setText("播放");
btnPlay.setEnabled(false);//使播放按钮不能按(要等该准备好才能用)
btnStop.setEnabled(false);//使停止按钮不能用
try {
mper.reset(); //若之前播放过歌曲,必须reset 才能换歌曲
mper.setDataSource(this,uri);//指定音乐来源
mper.setLooping(ckbLoop.isChecked());//是否循环播放
mper.prepareAsync();//要求MediaPlay播放准备的音乐
}catch (Exception e) {
tos.setText("指定音乐出错!" + e.toString());
tos.show();
}
}
@Override
protected void onPause() {
super.onPause();
if (mper.isPlaying()) { //如果正在播放就暂停
btnPlay.setText("继续");
mper.pause();//暂停播放
}
}
@Override
protected void onDestroy() {
mper.release();//释放MediaPlayer对象
super.onDestroy();
}
@Override
public void onClick(View view) {
Intent it = new Intent(Intent.ACTION_GET_CONTENT);//创建动作为选取内容的Intent
int id = view.getId();
switch (id) {
case R.id.bt_music: //如果是选取歌曲
it.setType("audio/*");//选取所有音乐类型
startActivityForResult(it, 100);
break;
case R.id.bt_video:
it.setType("video/*");//选取所有视频文件
startActivityForResult(it, 101);//
break;
case R.id.bt_play:
if (isVideo) {//如果是视频
Intent it_video = new Intent(this,Video.class);
//将视频的Uri以“uri”为名加入Intent中
it_video.putExtra("uri",uri.toString());
startActivity(it_video);
return ;
}
if (mper.isPlaying()) { //如果正在播放就暂停
mper.pause(); //暂停播放
btnPlay.setText("继续");
}else {//如果没有在播放,就开始播放
mper.start();//开始播放
btnPlay.setText("暂停"); //让播放按钮显示“暂停”
btnStop.setEnabled(true);//音乐已经播放,所以停止按钮有作用
}
break;
case R.id.bt_stop:
case R.id.videoView:
mper.pause();//暂停播放
mper.seekTo(0);//移到音乐0S位置
btnPlay.setText("播放");
btnStop.setEnabled(false); //让停止按钮不能用
break;
case R.id.bt_houtui:
if( !btnPlay.isEnabled()) {
return;//如果还没有准备好,不能回退
}
int len = mper.getDuration();//读取音乐长度
int pos =mper.getCurrentPosition();//读取当前播放的位置
pos -=10000; //倒退10s
if (pos < 0) {
pos=0;
}
mper.seekTo(pos);//将播放位置重新设置
tos.setText("倒退10S" + pos/1000 + "/" + len/1000);//显示信息
tos.show();
break;
case R.id.bt_kuaijin:
if(!btnPlay.isEnabled()){
return;
}
int lon = mper.getDuration();
int post = mper.getCurrentPosition();
post += 10000;
if (post > lon) {
mper.seekTo(post);
}
tos.setText("快进10S" + post/1000 + "/" + lon/1000);//显示信息
tos.show();
break;
case R.id.bt_mes:
if (!btnPlay.isEnabled()){
return;
}
int ln = mper.getDuration();//读取音乐长度
int po =mper.getCurrentPosition();//读取当前播放的位置
tos.setText("当前播放位置" + po/1000 + "/" + ln/1000);//显示信息
tos.show();
default:
break;
}
}
protected void onActivityResult (int requestcode , int resultcode, Intent data) {
super.onActivityResult(requestcode,resultcode,data);
if (resultcode == Activity.RESULT_OK) {//如果选项成功
isVideo = (requestcode == 101);//判断是否选择视频文件
uri = convertUri(data.getData()); //获取选取文件的 Uri,并进行 Uri 格式转换
txvname.setText((isVideo? "视频:":"歌曲:") +
uri.getLastPathSegment()); //显示文件名Uri最后一段文字
txvUri.setText("文件位置:" + uri.getPath());//显示文件路径
if(!isVideo) {
prepareMusic(); //如果是音乐文件就准备播放
}
}
}
Uri convertUri(Uri uri) { //将“content://类型的uri转换成file://类形的uri”
if (uri.toString().substring(0, 7).equals("content")) {//如果是以content开头
String[] colName = {MediaStore.MediaColumns.DATA};//声明要查询的字段
Cursor cursor = getContentResolver().
query(uri, colName, null, null, null);//以uri进行查询
cursor.moveToFirst(); //移到查询结果第一个记录
uri = Uri.parse("file://" + cursor.getString(0));//将路径转换成Uri
cursor.close();//关闭查询结果
}
return uri;
}
@Override
public void onPrepared(MediaPlayer mediaPlayer) {
btnPlay.setEnabled(true);//当准备好,让播放的按钮可以用
}
@Override
public void onCompletion(MediaPlayer mediaPlayer) {//当音乐播放完毕时
mper.seekTo(0);//将播放位置为0
btnPlay.setText("播放");
btnStop.setEnabled(false);//让停止按钮不能使用,因为已经停止播放
}
@Override
public boolean onError(MediaPlayer mediaPlayer, int i, int i1) {
tos.setText("发生错误,停止播放");
tos.show();
return true;
}
@Override
public void onCheckedChanged(CompoundButton compoundButton, boolean b) {
if (ckbLoop.isChecked()) {
mper.setLooping(true);//按下重复播放按钮。设置重复播放
}else {
mper.setLooping(false);
}
}
}
Video.java
package com.example.lumeng.audiovideo;
import android.content.Intent;
import android.media.MediaPlayer;
import android.net.Uri;
import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.view.View;
import android.view.WindowManager;
import android.widget.MediaController;
import android.widget.VideoView;
/**
* Created by lumeng on 18-1-26.
*/
public class Video extends ActionBarActivity implements MediaPlayer.OnCompletionListener {
VideoView vdv; //声明 VideoView 对象
int pos = 0; //用来记录前次的播放位置
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//隐藏系统的状态栏
getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
//隐藏Activity的标题栏
getSupportActionBar().hide();
setContentView(R.layout.activity_video); //上面两个函数 要在此函数之前
//保持屏幕常亮
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
Intent it = getIntent();//获取传入的Intent对象
//获取要播放视频的Uri
Uri uri = Uri.parse(it.getStringExtra("uri"));
//如果是因为旋转需要重启activity
if (savedInstanceState != null) {
pos = savedInstanceState.getInt("pos",0);//获得旋转前存储的播放位置
}
vdv = (VideoView) findViewById(R.id.videoView);
vdv.setOnClickListener((View.OnClickListener) this);
//建立播放器控制对象
MediaController mediaCtrl = new MediaController(this);
//设置播放器控制对象
vdv.setMediaController(mediaCtrl);
vdv.setVideoURI(uri); //设置播放的uri
vdv.setOnCompletionListener(this);//设置播放完毕的监听事件
}
@Override
protected void onResume() {
super.onResume(); //当Activity 启动或暂停状态回到互动状态
vdv.seekTo(pos); //移动pos位置
vdv.start();//开始播放
}
@Override
protected void onPause() {//当Activity 进入暂停状态
super.onPause();
pos = vdv.getCurrentPosition();//存储播放位置
vdv.stopPlayback();//停止播放
}
@Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
outState.putInt("pos",pos); //将onpause()中获得的播放位置存放到 bundle中
}
@Override
public void onCompletion(MediaPlayer mediaPlayer) {
finish(); //结束
}
}
文献参考:
android app开发入门 施威铭 编著
本人郑重声明,本博客所著文章、图片版权归权利人持有,本博只做学习交流分享所用,不做任何商业用途。访问者可將本博提供的內容或服务用于个人学习、研究或欣赏,不得用于商业使用。同時,访问者应遵守著作权法及其他相关法律的规定,不得侵犯相关权利人的合法权利;如果用于商业用途,须征得相关权利人的书面授权。若以上文章、图片的原作者不愿意在此展示內容,请及时通知在下,將及时予以刪除。