实现播放时的进度条显示,或是定时从service获取某些信息,是我们日常开发中经常遇到的需求,下面介绍当音乐再service中运行时,activity如果获取音乐进度信息的两种方式:

一、在activity中建立消息接收机制

我们需要在activity中建立一个用于接收信息的handler(handler简单的说是在android中可以发送消息和也可以处理消息的一种机制,当然它的用途更加强大,有时间可以去自己了解)

我们需要在onCreate方法之前添加handler,这样才能保证当我们的activity被destroy之后,再重建时可以第一时间获取当前音乐的进度。

下面是代码,有的同学可能看出来了,这个Handler的handleMessage被重写了,handleMessage写在了new Handler.Callback()回调函数中,返回值变成了boolean,其实这样做是为了防止内存泄漏,当然如果你能忍受Android Studio那一坨巨大的黄色警告你也可以选择用原本的handler方法,

//当前音乐播放进度    private static TextView nowTime;//音乐进度条    static SeekBar songseek;        //运用Handler中的handleMessage方法接收service传递的音乐播放进度信息    public static Handler handler = new Handler(new Handler.Callback() {        @Override        public boolean handleMessage(Message msg) {            // super.handleMessage(msg);            // 将SeekBar位置设置到当前播放位置,            // msg.arg1是service传过来的音乐播放进度信息,将其设置为进度条进度            songseek.setProgress(msg.arg1);            //将进度时间其转为mm:ss时间格式            nowTime.setText(new SimpleDateFormat("mm:ss",Locale.getDefault()).format(new Date(msg.arg1)));            return false;        }    });//下面才是android的onCreate方法protected void onCreate(Bundle savedInstanceState) {......}

二、在service中建立一个定时器来定时发送音乐进度信息

//开始播放音乐       mediaPlayer.start();      //每隔50毫秒发送音乐进度      Timer timer = new Timer();       timer.schedule(new TimerTask() {        @Override       public void run() {       //实例化一个Message对象Message msg = Message.obtain();//Message对象的arg1参数携带音乐当前播放进度信息,类型是int            msg.arg1 = mediaPlayer.getCurrentPosition();            //使用MainActivity中的handler发送信息            MainActivity.handler.sendMessage(msg);       }        }, 0, 50);

当然你也可以使用线程的方式来发现音乐进度信息,不过在这里并不推荐,因为单纯的音乐播放进度信息而已,没有必要用到线程来传信息,而已每一次执行都会创建一个线程,这样很浪费资源

//创建一个线程每隔100毫秒发送一次信息        Runnable runnable = new Runnable() {@Overridepublic void run() {while (true) {try {Thread.sleep(100);                    } catch (InterruptedException e) {                        e.printStackTrace();                    }                    Message msg = Message.obtain();                    msg.arg1 = mediaPlayer.getCurrentPosition();                    MainActivity.handler.sendMessage(msg);                    }                 }            };        Thread musicThread = new Thread(runnable);        musicThread.start();

附:MediaPlayer做音乐播放器采坑以及解决办法

1.千万不要把mediaPlayer.getDuration()放在定时任务里,线程和定时器都不能放

因为mediaPlayer.prepare()的执行速度很低,有概率出现mediaPlayer.prepare()还在执行中,突然定时器里刚刚好到时间该调用mediaPlayer.getDuration()这个方法,结果就是mediaPlayer.prepare()因为没有初始化成功就调用mediaPlayer.getDuration()而报下面的错误导致程序闪退。

java.lang.IllegalStateException android.media.MediaPlayer._prepare(Native Method)
(当然如果你的定时操作间隔越大出错的概率就越小,不过我强迫症就是忍不了)

2.上面提到mediaPlayer.prepare()的执行速度很低,如何解决

使用mediaPlayer.prepare()时,正常操作是:

mediaPlayer.prepare();mediaPlayer.start();

建议使用 mediaPlayer.prepareAsync()来代替mediaPlayer.prepare(),下面的代码可以取代上面

mediaPlayer.prepareAsync();//需要设置一个监听器mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {@Overridepublic void onPrepared(MediaPlayer mp) {mediaPlayer.start();}});

看一下效果

Android作业 音乐播放器

更多相关文章

  1. Android中解决破解签名验证之后导致的登录授权失效问题
  2. Android(安卓)Mms专题之:信息发送流程
  3. 基于android的网络音乐播放器-回调实现音乐播放及音乐收藏的实现
  4. greenhand起步之Android音乐播放器最终版
  5. android出现注: 某些输入文件使用或覆盖了已过时的 API。 注: 有
  6. 新建Android(安卓)AVD,点击start、launch,出现进度条后无任何反应,
  7. hook android api伪造设备信息做刷量
  8. Android(安卓)开启个人热点时 获取连接人数以及连接上的设备信息
  9. 在Android中自定义捕获Application全局异常,可以替换掉系统的强制

随机推荐

  1. Android天气预报之基于HttpGet对象解析天
  2. Android存储Json到本地,和读取本地Json
  3. Android获取窗体信息的Util方法
  4. Android仿“知乎”隐藏标题栏、回答详情
  5. android phoneGap 静态页面中简单的数据
  6. android 8 sdk源码编译时报错Try increas
  7. 新思路_Android同时显示多个跑马灯
  8. 转载:Android uses-permission大全
  9. 十二个android编程技巧
  10. Android 官方文档 Google Services