关于PowerImageView使用问题总结

来源:互联网 发布:网络统考时间 编辑:程序博客网 时间:2024/06/16 09:23

       最近在练习一个项目,需要写一个聊天室模块;因此需要实现发表情与发gif图片的功能。刚开始用Github上的开源框架gif_drawable里的gifImageView,可是加载总是出问题;网上查了很久,试了很多方法也没解决;最后放弃了,就选用了大神郭霖写的PowerImageView那个自定义View来实现。

       PwerImageView源码博客:http://blog.csdn.net/guolin_blog/article/details/11100315

       在阅读了PowerImageView源码与看了相关评论后,对郭大神写的这个自定义View有了初步的了解;知道这个类还存在一些Bug,根据网友的评论和自己使用的情况进行一些总结:

       1、在获取到src指定图片资源所对应的id这一块,郭霖是通过Java底层反射机制来获得,以下是方法代码:

             

private int getResourceId(TypedArray a, Context context, AttributeSet attrs) {try {Field field = TypedArray.class.getDeclaredField("mValue");field.setAccessible(true);TypedValue typedValueObject = (TypedValue) field.get(a);return typedValueObject.resourceId;} catch (Exception e) {e.printStackTrace();} finally {if (a != null) {a.recycle();}}

         有细心的网友指出,这个为获取资源id调用反射机制来做把问题复杂化了点,且有一些网友发现这个方法会导致一些Bug出来;可以用atts里一个方法直接获取到资源id:

            //使用for循环逐个取出attrs里的元素名跟src比较,如果符合,则取出对应的值(id);

          

    for (int i = 0; i < attrs.getAttributeCount(); i++) { if(attrs.getAttributeName(i).equals("src")) { resourceId= attrs.getAttributeResourceValue(i, 0); } }

            两个方法我都试过了,都可以用;但第二个方法相对简单明了,因此我选择了网友提供的这个方法。

     2、关于文中提到的android4.0版本以上因为默认开启了硬件加速功能会导致gif动画播放不出来,需要在注册清单中通过将hardwareAccelerated属性设置为”false“来禁用硬件加速功能;但有网友发现这种做法会导致整个应用运行效率降低,会使用一些页面加载时特别卡;建议使用另一个方法:

         在构造函数中增加一行代码(红色字体代码):

public PowerImageView(Context context, AttributeSet attrs, int defStyle) {super(context, attrs, defStyle);TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.PowerImageView);//int resourceId = getResourceId(a, context, attrs);for (int i = 0; i < attrs.getAttributeCount(); i++) { if(attrs.getAttributeName(i).equals("src")) { resourceId= attrs.getAttributeResourceValue(i, 0); } }if (resourceId != 0) {// 当资源id不等于0时,就去获取该资源的流InputStream is = getResources().openRawResource(resourceId);// 使用Movie类对流进行解码mMovie = Movie.decodeStream(is);if (mMovie != null) {// 如果返回值不等于null,就说明这是一个GIF图片,下面获取是否自动播放的属性<span style="color:#ff0000;">this.setLayerType(View.LAYER_TYPE_SOFTWARE, null);</span>isAutoPlay = a.getBoolean(R.styleable.PowerImageView_auto_play, false);Bitmap bitmap = BitmapFactory.decodeStream(is);mImageWidth = bitmap.getWidth();mImageHeight = bitmap.getHeight();bitmap.recycle();if (!isAutoPlay) {// 当不允许自动播放的时候,得到开始播放按钮的图片,并注册点击事件mStartButton = BitmapFactory.decodeResource(getResources(),R.drawable.start_play);setOnClickListener(this);}}}}

  

3、加载了gif图片后,很多gif动画却只是加载的时候执行一次,并不会反复循环播放,但有一些图片又是可以循环播放的;源码中在onDraw方法中调用了playMovie方法后,调用了invalidate()方法;按理来说调用了invalidate方法后会重复执行onDraw方法,网上查找了相关的分享后发现,高版本的android系统可能进行了一些优化,view的invalidate方法不一定会触发onDraw方法重新执行;但问题点是,为何是固定的图片不会触发ondraw方法,而不是随机性产生的?




0 0
原创粉丝点击