简体   繁体   English

如何使用毕加索有效地加载大位图?

[英]How to load large bitmap efficiently with Picasso?

I am developing a Wallpaper app where I am showing the images with the help of firebase and Picasso in GridView. 我正在开发一个墙纸应用程序,在该应用程序中,我将借助Firebase和Picasso在GridView中显示图像。 I want to retrieve the image from the server and resize it as per the screen resolution. 我想从服务器检索图像并根据屏幕分辨率调整其大小。 Let the image size is 3000 * 5000 and the device screen size is 720 * 1280, then the image cropped to 720 * 1280. 假设图像大小为3000 * 5000,设备屏幕大小为720 * 1280,则图像裁切为720 * 1280。

https://developer.android.com/topic/performance/graphics/load-bitmap gives the solution but it resized the drawable file and with a fixed size. https://developer.android.com/topic/performance/graphics/load-bitmap提供了解决方案,但它调整了可绘制文件的大小并具有固定大小。

But I want to resize server image with the device screen size. 但是我想使用设备屏幕尺寸来调整服务器图像的大小。

RecyclerView ViewHolder RecyclerView ViewHolder

public void setDetails(Context ctx, String image){

        ImageView mImageTv = mView.findViewById(R.id.rImageView);

        Picasso.get().load(image).into(mImageTv);

    }

Passing image from Fragment to FullscreenActivity with putExtra 使用putExtra将图像从Fragment传递到FullscreenActivity

ViewHolder viewHolder = super.onCreateViewHolder(parent, viewType);
                viewHolder.setOnclickListener(new ViewHolder.ClickListener() {
                    @Override
                    public void onItemClick(View view, int position) {

                        ImageView mImageView = view.findViewById(R.id.rImageView);

                        Drawable mDrawable = mImageView.getDrawable();
                        Bitmap mBitmap = ((BitmapDrawable) mDrawable).getBitmap();

                        Intent intent = new Intent(view.getContext(), PostDetailsActivity2.class);
                        ByteArrayOutputStream stream = new ByteArrayOutputStream();

                        mBitmap.compress(Bitmap.CompressFormat.PNG, 100, stream);
                        byte[] bytes = stream.toByteArray();
                        intent.putExtra("image", bytes);
                        startActivity(intent);


                    }

Show image in FullScreen Activity 在全屏活动中显示图像

mImageTv = findViewById(R.id.full_imageView1);


        byte[] bytes = getIntent().getByteArrayExtra("image");
        Bitmap bmp = BitmapFactory.decodeByteArray(bytes, 0, bytes.length);

        mImageTv.setImageBitmap(bmp);

Please help me if you can....if anyone needs more details of code or about my problem, please comment for those....Thank you 如果可以,请帮助我。...如果有人需要更多代码详细信息或有关我的问题,请对此发表评论。...谢谢

Okay, since you're using the Picasso library to load your images, the library handles caching of the actual Bitmap for you automatically once the image is loaded. 好的,因为您正在使用Picasso库加载图像,所以一旦加载图像,该库将自动为您处理实际位图的缓存。 One glaring thing in your code is that you're trying to pass the Bitmap around via an Intent, that usually is a big no-no as Bitmap data is rather large and can incur a huge performance cost. 代码中的一件明显的事情是,您试图通过一种Intent传递Bitmap,这通常是一个很大的禁忌,因为Bitmap数据相当大,并且会产生巨大的性能成本。 Instead, the first time you call Picasso.get().load(image).into(mImageTv) Picasso will actually save that Bitmap (in an efficient manner) for you so the next time you call Picasso.get().load(image) the image will already be stored locally in your application and you won't actually have to make a network call again. 相反,第一次调用Picasso.get().load(image).into(mImageTv) Picasso实际上会(以一种有效的方式)为您保存该位图,因此下次调用Picasso.get().load(image)该图片已经存储在您的应用程序本地,实际上您无需再次进行网络调用。 So in your FullscreenActivity all you have to do is call Picasso.get().load(image).into(mImageTv) again. 因此,在FullscreenActivity您要做的就是Picasso.get().load(image).into(mImageTv)调用Picasso.get().load(image).into(mImageTv)

Now onto displaying the image in the correct way, if your server image is 3000x5000 and your device screen size is 720x1280 and you want to display the whole image you can use the centerCrop function provided by Picasso, Picasso.get().load(image).fit().centerCrop().into(mImageTv) . 现在以正确的方式显示图像,如果您的服务器图像为3000x5000,设备屏幕尺寸为720x1280,并且要显示整个图像,则可以使用Picasso提供的centerCrop函数, Picasso.get().load(image).fit().centerCrop().into(mImageTv) It will resize the image to fit the entire bounds of the screen and will ensure that the image retains its aspect ratio (since the server image's aspect ratio does not match up with the device screen's aspect ratio). 它将调整图像的大小以适合屏幕的整个边界,并确保图像保留其长宽比(因为服务器图像的长宽比与设备屏幕的长宽比不匹配)。

For getting screen width and height: 要获取屏幕的宽度和高度:

DisplayMetrics displayMetrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(displayMetrics);
int height = displayMetrics.heightPixels;
int width = displayMetrics.widthPixels;

Then resize using glide: 然后使用滑行调整大小:

GlideApp  
    .with(context)
    .load(url)
    .override(600, 200) // resizes the image to these dimensions (in pixel). resize does not respect aspect ratio
    .into(imageViewResize);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM