Android 获取视频缩略图的 与播放视频的冲突

muximuxi525 2015-04-20 03:27:57
虽然不知道能不能获取到解答,但缘分谁知道呢。=_=

先发表我的疑问:
获取视频缩略图的asynctask任务怎样更好的暂停,和重新启动任务?如何才不会堵塞播放视频的UI线程?
即不会出现缓冲很长时间然后出现anr的现象。

我的需求是这样:
多页的gridview显示视频缩略图

APP写出来了,
主要技术是:
使用了单线程的asynctask异步加载视频缩略图(使用execute方法)

实现逻辑:
在某一页顺序加载缩略图,如果点击某个文件播放视频,暂停继续加载缩略图,等结束播放视频回到这一页重新启动任务加载缩略图。

但是出现各种问题
我的问题是这样的:
在某一页视频缩略图的加载过程中:视频缩略图是一个一个顺序加载出来的,我点击还没加载完缩略图的某个视频放,然后又快速关闭和快速播放另一个视频缩略图未加载完毕的视频,此时播放的视频会缓冲很长一段时间并且很大几率出现anr

简单的问的话:
怎么实现暂停和重新启动还未加载完毕的缩略图asynctask任务,而频繁暂停和启动不会出现anr。之所以暂停是因为播放视频的过程不能获取缩略图,否则会出错。

出现问题的疑因:
暂停task和重新启动task堵塞UI线程

我所做的工作:
我把暂停和重新启动的缩略图的操作放到子线程还是不能解决anr问题。



...全文
413 9 打赏 收藏 转发到动态 举报
写回复
用AI写文章
9 条回复
切换为时间正序
请发表友善的回复…
发表回复
看山似山 2017-06-28
  • 打赏
  • 举报
回复
你是怎么解决的,能分享一下代码吗
muximuxi525 2015-04-21
  • 打赏
  • 举报
回复
3、 "AsyncTask #2" prio=5 tid=17 Waiting | group="main" sCount=1 dsCount=0 obj=0x12d78580 self=0x7f7aba6000 | sysTid=2826 nice=10 cgrp=apps/bg_non_interactive sched=0/0 handle=0x7f7abf7600 | state=S schedstat=( 0 0 0 ) utm=1 stm=0 core=0 HZ=100 | stack=0x7f65bfe000-0x7f65c00000 stackSize=1036KB | held mutexes= at java.lang.Object.wait!(Native method) - waiting on <0x2083f03c> (a java.lang.Object) at java.lang.Thread.parkFor(Thread.java:1220) - locked <0x2083f03c> (a java.lang.Object) at sun.misc.Unsafe.park(Unsafe.java:299) at java.util.concurrent.locks.LockSupport.park(LockSupport.java:157) at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.await(AbstractQueuedSynchronizer.java:2016) at java.util.concurrent.LinkedBlockingQueue.take(LinkedBlockingQueue.java:410) at java.util.concurrent.ThreadPoolExecutor.getTask(ThreadPoolExecutor.java:1035) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1097) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587) at java.lang.Thread.run(Thread.java:818)
muximuxi525 2015-04-21
  • 打赏
  • 举报
回复
2、 "AsyncTask #1" prio=5 tid=16 Waiting | group="main" sCount=1 dsCount=0 obj=0x12d77c80 self=0x7f7aba4000 | sysTid=2814 nice=10 cgrp=apps/bg_non_interactive sched=0/0 handle=0x7f7abfbb00 | state=S schedstat=( 0 0 0 ) utm=5 stm=2 core=2 HZ=100 | stack=0x7f664be000-0x7f664c0000 stackSize=1036KB | held mutexes= at java.lang.Object.wait!(Native method) - waiting on <0x1168822f> (a java.lang.Object) at java.lang.Thread.parkFor(Thread.java:1220) - locked <0x1168822f> (a java.lang.Object) at sun.misc.Unsafe.park(Unsafe.java:299) at java.util.concurrent.locks.LockSupport.park(LockSupport.java:157) at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.await(AbstractQueuedSynchronizer.java:2016) at java.util.concurrent.LinkedBlockingQueue.take(LinkedBlockingQueue.java:410) at java.util.concurrent.ThreadPoolExecutor.getTask(ThreadPoolExecutor.java:1035) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1097) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587) at java.lang.Thread.run(Thread.java:818)
muximuxi525 2015-04-21
  • 打赏
  • 举报
回复
下面是traces文件,我贴出觉得是问题的几部分,但没看出什么问题。 1、 DALVIK THREADS (25): "main" prio=5 tid=1 Native | group="main" sCount=1 dsCount=0 obj=0x74b77fa8 self=0x7f7ab97000 | sysTid=2762 nice=0 cgrp=apps sched=0/0 handle=0x7f7e6c4150 | state=S schedstat=( 0 0 0 ) utm=213 stm=22 core=1 HZ=100 | stack=0x7fdc8c6000-0x7fdc8c8000 stackSize=8MB | held mutexes= kernel: __switch_to+0x74/0x8c kernel: binder_thread_read+0x8a8/0x1004 kernel: binder_ioctl+0x6b0/0x97c kernel: do_vfs_ioctl+0x34c/0x590 kernel: SyS_ioctl+0xa8/0x170 kernel: el0_svc_naked+0x34/0x38 native: #00 pc 00060524 /system/lib64/libc.so (__ioctl+4) native: #01 pc 00087e64 /system/lib64/libc.so (ioctl+100) native: #02 pc 000299d4 /system/lib64/libbinder.so (android::IPCThreadState::talkWithDriver(bool)+164) native: #03 pc 0002a434 /system/lib64/libbinder.so (android::IPCThreadState::waitForResponse(android::Parcel*, int*)+112) native: #04 pc 0002a6a8 /system/lib64/libbinder.so (android::IPCThreadState::transact(int, unsigned int, android::Parcel const&, android::Parcel*, unsigned int)+176) native: #05 pc 000223a8 /system/lib64/libbinder.so (android::BpBinder::transact(unsigned int, android::Parcel const&, android::Parcel*, unsigned int)+64) native: #06 pc 00086a20 /system/lib64/libmedia.so (???) native: #07 pc 00080034 /system/lib64/libmedia.so (android::MediaPlayer::setDataSource(int, long, long)+292) native: #08 pc 0002c70c /system/lib64/libmedia_jni.so (???) native: #09 pc 003ab610 /data/dalvik-cache/arm64/system@framework@boot.oat (Java_android_media_MediaPlayer__1setDataSource__Ljava_io_FileDescriptor_2JJ+184) at android.media.MediaPlayer._setDataSource(Native method) at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1109) at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1094) at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1073) at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1022) at android.media.MediaPlayer.setDataSource(MediaPlayer.java:974) at android.media.MediaPlayer.setDataSource(MediaPlayer.java:955) at com.jrm.localmm.business.video.VideoPlayView.openPlayer(VideoPlayView.java:503) at com.jrm.localmm.business.video.VideoPlayView.access$2000(VideoPlayView.java:135) at com.jrm.localmm.business.video.VideoPlayView$11.surfaceCreated(VideoPlayView.java:992) at android.view.SurfaceView.updateWindow(SurfaceView.java:579) at android.view.SurfaceView$3.onPreDraw(SurfaceView.java:176) at android.view.ViewTreeObserver.dispatchOnPreDraw(ViewTreeObserver.java:847) at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:1956) at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1054) at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:5779) at android.view.Choreographer$CallbackRecord.run(Choreographer.java:767) at android.view.Choreographer.doCallbacks(Choreographer.java:580) at android.view.Choreographer.doFrame(Choreographer.java:550) at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:753) at android.os.Handler.handleCallback(Handler.java:739) at android.os.Handler.dispatchMessage(Handler.java:95) at android.os.Looper.loop(Looper.java:135) at android.app.ActivityThread.main(ActivityThread.java:5221) at java.lang.reflect.Method.invoke!(Native method) at java.lang.reflect.Method.invoke(Method.java:372) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:902) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:697)
只为搞笑 2015-04-21
  • 打赏
  • 举报
回复
我感觉还是因为线程操作的问题,或者主线程逻辑有点问题,anr主要规避主线程做耗时任务,还是不容易出现的,要贴以下错误信息和代码,可能大家才能找到问题在那儿
muximuxi525 2015-04-21
  • 打赏
  • 举报
回复
引用 7 楼 u010668114 的回复:
at com.jrm.localmm.business.video.VideoPlayView.openPlayer(VideoPlayView.java:503) 感觉应该是调这个方法的时候出错了,可能是这样的,你的异步线程还在用视频资源来获取缩略图,然后你点击了播放视频,同时暂停异步线程,但是异步线程的暂停不是实时的,也就是说你的异步线程还没有释放资源,你的播放任务有要去取资源,然后互斥了。你这样试一下,确定异步线程暂停了,再播放视频。
你的办法挺有道理,就是感觉用户体验不是很好就是:在点击播放之后还有有一个提示现在在暂停其他任务的UI,然后等任务取消之后,这个UI才转向播放视频的UI。。 3Q all the same
只为搞笑 2015-04-21
  • 打赏
  • 举报
回复
at com.jrm.localmm.business.video.VideoPlayView.openPlayer(VideoPlayView.java:503) 感觉应该是调这个方法的时候出错了,可能是这样的,你的异步线程还在用视频资源来获取缩略图,然后你点击了播放视频,同时暂停异步线程,但是异步线程的暂停不是实时的,也就是说你的异步线程还没有释放资源,你的播放任务有要去取资源,然后互斥了。你这样试一下,确定异步线程暂停了,再播放视频。
muximuxi525 2015-04-20
  • 打赏
  • 举报
回复
引用 1 楼 u010668114 的回复:
话说,你的视频缩略图,是从媒体流里获取的?还是服务器给的url呢?
应该是属于前者,我是调用MediaMetadataRetriever 对象的getFrameAtTime方法获取缩略图的
只为搞笑 2015-04-20
  • 打赏
  • 举报
回复
话说,你的视频缩略图,是从媒体流里获取的?还是服务器给的url呢?

80,350

社区成员

发帖
与我相关
我的任务
社区描述
移动平台 Android
androidandroid-studioandroidx 技术论坛(原bbs)
社区管理员
  • Android
  • yechaoa
  • 失落夏天
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧