Home > Software design >  Picasso performance issues when resizing multiple images
Picasso performance issues when resizing multiple images

Time:01-14

I have an activity that need to load multiples images and resize them so that they fit screen width.

I try to load the images into this.frameHolder which is a LinearLayout inside a NestedScrollView and do match the screen width.

The code below is working but make the application very slow as soon as there is more than few images.

    public void displayImages(List<ImageContent> images) {
        for(ImageContent img:images) {
            //Create an new view for image
            ImageView imgView = new ImageView(this);
            this.frameHolder.addView(imgView);

            //Create a client with custom header for this image
            OkHttpClient client = new OkHttpClient.Builder()
                    .addInterceptor(chain -> {
                        Request.Builder newRequest = chain.request().newBuilder();
                        newRequest.addHeader(img.getHeaderKey(), img.getHeaderValue());
                        return chain.proceed(newRequest.build());
                    }).build();
            
            //Create a picasso instance for this client
            Picasso.Builder builder = new Picasso.Builder(this).downloader(new OkHttp3Downloader(client));
            Picasso pic = builder.build();

            //Load and resize the image to fit screen width
            pic.load(img.getUrlContentData()).resize(frameHolder.getWidth(), 0).into(imgView);
        }
    }

How can I load multiple images and make them fit the screen width, without degrading performance too much ? I'm open to other solution than Picasso if that make it possible.

CodePudding user response:

I ended giving up on using a library, as @Qasim Malik suggested I've tried Glide and Fresco as alternatives, but I still got similar issues.

So since I wasn't able to do it with a library, I did it myself by handling the request and image resizing directly :

private final static OkHttpClient client = new OkHttpClient();
public void displayImages(List<ImageContent> images) {
        for(ImageContent img:images) {
            ImageView imgView = new ImageView(this);
            this.frameHolder.addView(imgView);

            Request.Builder requestBuilder = new Request.Builder()
                .addHeader(img.getHeaderKey(), img.getHeaderValue())
                .url(content.getUrlContentData());


            client.newCall(requestBuilder.build()).enqueue(new Callback() {
                @Override
                public void onFailure(Call call, IOException e) {
                    loadFailed();
                }

                @Override
                public void onResponse(Call call, Response response) throws IOException {
                    Bitmap bitmap = BitmapFactory.decodeStream(response.body().byteStream());
                    float widthInitial =  bitmap.getWidth() ;
                    float heightInitial =  bitmap.getHeight() ;
                    Bitmap resizedImage = Bitmap.createScaledBitmap(bitmap, frameHolder.getWidth(), Math.round(frameHolder.getWidth() * (heightInitial / widthInitial)), true);
                    
                    imgView.setImageBitmap(resizedImage);
                }
        });
        }
    }

This work fine, and there are no more performance issues, but I'm still unsure of why the libraries are so slow at it...

  • Related