android开发杂记一
2017-01-07 17:25
369 查看
填坑一:
viewpager+fragment(3个fragment),其中有一个fragment内有listview,listeview内含有播放视频控件时,进入到界面会闪屏一次。原因是:listview内item的视频控件在fragment,fragment在activity是动态添加的,不会随着activity的初始化而刷新,只有在加载完fragment的时候加载刷新,所有会出现一次闪屏。这个时候只要在activityde xml界面内添加一段代码即可:
<SurfaceView android:layout_width="0dp" android:layout_height="0dp" />
填坑二:
从上一个坑爬出,继续下一个,listview内item视频控件需要显示缩略图,这里播放的是网络视频,所有是由url的,具体实现代码是:public Bitmap createVideoThumbnail(String url, int width, int height) { Bitmap bitmap = null; MediaMetadataRetriever retriever = new MediaMetadataRetriever(); int kind = MediaStore.Video.Thumbnails.MINI_KIND; try { if (Build.VERSION.SDK_INT >= 14) { retriever.setDataSource(url, new HashMap<String, String>()); } else { retriever.setDataSource(url); } bitmap = retriever.getFrameAtTime(); } catch (IllegalArgumentException ex) { // Assume this is a corrupt video file } catch (RuntimeException ex) { // Assume this is a corrupt video file. } finally { try { retriever.release(); } catch (RuntimeException ex) { // Ignore failures while cleaning up. } } if (kind == MediaStore.Images.Thumbnails.MICRO_KIND && bitmap != null) { bitmap = ThumbnailUtils.extractThumbnail(bitmap, width, height, ThumbnailUtils.OPTIONS_RECYCLE_INPUT); } return bitmap; }
但是会出现卡顿的情况,因为这里是listview在使用,而且
MediaMetadataRetriever retriever = new MediaMetadataRetriever();
是一个耗时操作,所有我们的第一个反应是把它加在子线程中实现,UI线程显示,代码如下:
1.创建一个子线程:
static class CreateVideoThumbnail extends Thread { private String url; private Handler handler; public CreateVideoThumbnail(String url, Handler handler) { this.url = url; this.handler = handler; } @Override public void run() { super.run(); handler.obtainMessage(0, createVideoThumbnail(url, 300, 300)).sendToTarget(); } public Bitmap createVideoThumbnail(String url, int width, int height) { Bitmap bitmap = null; MediaMetadataRetriever retriever = new MediaMetadataRetriever(); int kind = MediaStore.Video.Thumbnails.MINI_KIND; try { if (Build.VERSION.SDK_INT >= 14) { retriever.setDataSource(url, new HashMap<String, String>()); } else { retriever.setDataSource(url); } bitmap = retriever.getFrameAtTime(); } catch (IllegalArgumentException ex) { // Assume this is a corrupt video file } catch (RuntimeException ex) { // Assume this is a corrupt video file. } finally { try { retriever.release(); } catch (RuntimeException ex) { // Ignore failures while cleaning up. } } if (kind == MediaStore.Images.Thumbnails.MICRO_KIND && bitmap != null) { bitmap = ThumbnailUtils.extractThumbnail(bitmap, width, height, ThumbnailUtils.OPTIONS_RECYCLE_INPUT); } return bitmap; } }
2.子线程把耗时操作完成,通知ui线程,代码如下:
Handler handler = new Handler(Looper.getMainLooper()) { @Override public void handleMessage(Message msg) { super.handleMessage(msg); if (ok) { ivThumb.setImageBitmap((Bitmap) msg.obj); ok = false; } } };
3.现在准备工作完成,去调用子线程,代码:
t = new CreateVideoThumbnail(url, handler); t.start();
4.还没完成,因为这是是listview在用,listview有复用功能,而且,你的子线程会一直在线程池中,你必须在上一个view消失的时候把线程取消掉,要不然会有2种情况出现,(1)报错(2)现在view使用的还是上一个view的数据,所有要先reset,在你视频播放之前使用代码:
public void reset() { if (t != null) { t.interrupt(); } handler.removeMessages(0); ok = true; }
5.最后考虑到生命周期,在view消失的时候再reset一下,虽然有时不考虑生命周期不会出现问题,但是有可能会把你的内存往上调一下(就是占用内存),有时它会直接报错。这里小分队提示,最好去考虑下生命周期更好。
相关文章推荐
- [无线] Android 系统开发学习杂记
- android开发杂记(持续更新中)
- android 开发心得杂记
- Android 开发杂记——@, @+, ? 的介绍
- Android 开发杂记
- Android 系统开发学习杂记(转)
- android学习杂记(3)--百度地图开发环境的配置
- Android 系统开发学习杂记-基础
- Android 开发杂记
- Android开发------------杂记
- [杂记]Android开发一些容易忘记的API
- Android开发之杂记(3)
- Android 系统开发学习杂记-基础
- Android开发杂记
- android 开发笔记--杂记
- android 开发错误杂记
- Android之开发杂记(二)
- Android开发杂记(一)
- [无线] Android 系统开发学习杂记
- [无线] Android 系统开发学习杂记