• 关于Bitmap的加载(二)


      接上节,上节记录了Bitmap的加载,用上节的方法,我们可以方便地压缩图片,进行加载。

      然而,有时候,当出来大量的图片或者是一张大图要加载时,这一过程所花的时间就会显得很长。甚至长到用户可以感觉出来,即UI的卡顿。因此,我们需要一个方法让图片自己加载去吧,不能干扰用户的操作。所以,我们需要用一个新的线程来完成图片加载的操作。其中最简单便捷的方法,就是Use an AsyncTask

      首先创建一个AsyncTask的子类:

        class BitmapWorkerTask extends AsyncTask<Integer, Void, Bitmap> {
            private final WeakReference<ImageView> imageViewReference;
            private int data = 0;
            private int width , height;
            public BitmapWorkerTask(ImageView imageView , int width , int height) {
                // Use a WeakReference to ensure the ImageView can be garbage collected
                imageViewReference = new WeakReference<ImageView>(imageView);
                this.width = width;
                this.height = height;
            }
            // Decode image in background.
            @Override
            protected Bitmap doInBackground(Integer... params) {
                data = params[0];
                return decodeSampledBitmapFromResource(getResources(), data, width, height);
            }
            // Once complete, see if ImageView is still around and set bitmap.
            @Override
            protected void onPostExecute(Bitmap bitmap) {
                if (imageViewReference != null && bitmap != null) {
                    final ImageView imageView = imageViewReference.get();
                    if (imageView != null) {
                        imageView.setImageBitmap(bitmap);
                    }
                }
            }
        }

      其中,第一个参数是需要加载的图片的Id;

      PS:WeakReference<ImageView> imageViewReference 为弱引用。  

    • WeakReference may be cleared and enqueued as soon as is known to be weakly-referenced.

      当GC启动时弱引用会自动被回收,这里使用弱引用,防止了内存溢出。

      然后,创建这个加载图片类的对象,并在合适的时候执行这个异步任务。

            testButton.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    int width = gridLayout.getWidth()/50;
                    int height = gridLayout.getHeight()/50;
                    Toast.makeText(getApplicationContext(),width+","+height,Toast.LENGTH_SHORT).show();
                    BitmapWorkerTask task = new BitmapWorkerTask(imageView1,width,height);
                    task.execute(R.drawable.ic_launcher_big);
                }
            });

      以上。

      然而,这也是有缺陷的。有时候我们需要加载的不只一张图。为了在存在多张图可能需要加载时,不影响系统的效率。组件回收器会在用户滑动屏幕时进行回收,将不出现在用户视野中的界面回收掉。在上面的方法中,每次加载都需要重开一个AsyncTask。有可能这张图还没有加载完,用户已经把这张图滑走了,我们需要用内存加载下一张图了。怎么处理?下回再写吧。。。

  • 相关阅读:
    JavaScript高级:JavaScript面向对象,JavaScript内置对象,JavaScript BOM,JavaScript封装
    JavaScript基础:javaScript基本语法,javaScript DOM,javaScript事件,javaScript综合案例
    Mybatis基础:Mybatis映射配置文件,Mybatis核心配置文件,Mybatis传统方式开发
    【笔记】Bagging和Pasting以及oob(Out-of-Bag)
    【笔记】集成学习入门之soft voting classifier和hard voting classifier
    8.23(day22)ATM+购物车系统
    Configure Dynamics 365 for Operations Virtual Machine/Virtual Hard Disk (VHD)
    Capture pictures to Power Platform
    How to convert HTML file to PDF using Power Automate
    Add B2B SSO to a Power Apps Portal
  • 原文地址:https://www.cnblogs.com/fishbone-lsy/p/4414670.html
Copyright © 2020-2023  润新知