Android imageview shows greenish image - android

This is the original image:
This is the rendered image using ImageView:
However, sometimes when the image is in a carousel, swiping back to the image may cause the image to render correctly, which is even more weird...
This behavior is observed both on an LG G3 (Android 5.1) and Genymotion (Android 4.4.4). I'm using the Glide library for loading images, using the ARGB_8888 decode format:
new GlideBuilder(this).setDecodeFormat(DecodeFormat.PREFER_ARGB_8888);

This is a resolved issue 305. Here is a quick recap:
This issue appears only with images with JPEG format (the quality is irrelevant). It looks like it affects RGB_565 much more significantly than ARGB_8888, so you may want to switch the DecodeFormat to ARGB_8888 (clear the app data to check if the issue is resolved). But it can appear even with ARGB_8888, so use one of the following solutions:
Use DiskCacheStrategy.NONE (for local images) or DiskCacheStrategy.SOURCE (for remote images) to prevent Glide from re-compressing the images:
Glide.with(this)
.load(url)
.diskCacheStrategy(DiskCacheStrategy.SOURCE)
.into(imageView);
Use asBitmap() and a custom BitmapEncoder to always compress affected images as PNGs:
Glide.with(this)
.fromResource()
.asBitmap()
.encoder(new BitmapEncoder(Bitmap.CompressFormat.PNG,100))
.load(R.drawable.testimg)
.into(imageView);

Just in case someone tried all that is listed above and none of it worked (like in my case), there is another workaround. Since greenish colour happens during transformation, we can avoid transformation.
Glide.with(context)
.load(url)
.dontTransform()
.into(holder.productImage);

This issue may happen on few devices not all like one plus 3 or 3T and some LG devices when fetching imageUrl from server to your android project.
public static void loadImageWith(Context context, String imageUrl, ImageView imageView) {
Glide.with(context)
.load(imageUrl)
.diskCacheStrategy(DiskCacheStrategy.SOURCE)
.dontTransform()
.placeholder(R.drawable.empty_photo)
.into(imageView);
}
centerCrop() may create issue, so avoid to use centerCrop().

Related

Glide and image resolution

I'm loading an image from a file. It's a photo gallery so I don't want the image resolution to be scaled down. I've found this code snippet that seems to work great on my devices but I've had users complain about low res images before (That I've been unable to replicate but have confirmed they're real issues) so I want to play it safe.
Will this code snippet load the full resolution image or does it require more than this?
File pageFile = getPageFile();
Glide.with(mPhotoView).load(pageFile)
.apply(new RequestOptions()
.override(Target.SIZE_ORIGINAL))
.into(mPhotoView);
For clarity:
Previously, we were creating our own bitmap from the file input stream and applying it like this:
Glide.with(mPhotoView).load(bitmap).into(mImageView);
This is when users started complaining about image resolution
Please try below:-
Glide.with(imageView).load(url)
.apply(new RequestOptions()
.fitCenter()
.format(DecodeFormat.PREFER_ARGB_8888)
.override(Target.SIZE_ORIGINAL))
.into(imageView);
Also, add this android:adjustViewBounds="true" to your ImageView in XML.
You can use centerCrop() instead of fitCenter() to scale. If used centerCrop(), it scales the image so that it fills the requested bounds and then crops the extra.

Bitmaps lose transparency when downloaded with Glide

I am trying to download a bitmap image in an android app using the Glide library (version 4), but when I do that the transparency of the image is lost and it is replaced by a white background.I tried using the commands:
Glide.with(this).load(url).into(imageView);
Glide.with(this).asBitmap().load(url).into(imageView);
and
Glide.with(this).load(url).apply( new RequestOptions().format(DecodeFormat.PREFER_ARGB_8888).encodeFormat(Bitmap.CompressFormat.PNG)).into(imageView);
However nothing seems to work.
The image url is: https://s151.convertio.me/p/HwxwbAP4nbAyKsEmdn7ORw/1dc5e4a91d3de94ef6c5fcd51b0fb79d/yellow_circle_1.bmp
And here are some screenshots of the app:
This is how it should look.
(It looks like that when I use a png image, the red background is the ImageView's background and the image background is transparent.)
This is how it looks with a bitmap
(The transparent background became white.)
Thanks a lot.
There is no alpha channel in BMP format, as far as I know
https://en.wikipedia.org/wiki/BMP_file_format
Glide.with(context).load(dataModel.getImgurl())
.thumbnail(0.5f)
.fitCenter()
.centerCrop()
.diskCacheStrategy(DiskCacheStrategy.ALL)
.into(imageView);

Using high definition pictures in android

I'm having some trouble when uploading high definition pictures in my app.
I have a Grid View and when I add the photo the app crashes stating that its a memory problem.
One solution I did was to decrease the size of the image through a website (https://www.befunky.com/create/resize-image/) but the image gets blurie.
Also used a solution that is present on the official Android developers' website (https://developer.android.com/topic/performance/graphics/load-bitmap.html), unsuccessfully (the app gets too slow and I have the previous result).
I've seen many applications where this is not a issue and I want to learn the way they do it correctly.
Try Picasso, it can load an image into your imageView from your drawable (or url), and its fit() method allows you to reduce the image to the lowest possible resolution, without affecting quality.
Basically, it measures the dimensions of the target ImageView and uses resize() to reduce the image size to the dimensions of your ImageView:
High quality picture in drawable folder:
Picasso.with(context)
.load(R.drawable.image)
.fit()
.into(imageView);
High quality picture from a url:
Picasso.with(context)
.load("www.url.com/image.jpg")
.fit()
.into(imageView);
You can find more details on how to use fit, resizing and scaling with Picasso here.

Android Glide: Show a blurred image before loading actual image

I am developing an Android app which displays full screen images to the user. Images are fetched from the server. I am using Glide to show the image. But I want to display a very small size blurred image before displaying the actual image. Once the image is cached, directly full sized image should be shown.
Image Displaying flows goes like this:
- If image is downloaded for the first time, first download a small scaled image, and then download full resolution image.
- If image has been downloaded before, directly show full scale image.
I cannot find any method in Glide library, which tell me if a file exist in cache or not.
Any idea, how this can be done.
Glide.with(context.getApplicationContext())
.load(Your Path) //passing your url to load image.
.override(18, 18) //just set override like this
.error(R.drawable.placeholder)
.listener(glide_callback)
.animate(R.anim.rotate_backward)
.centerCrop()
.into(image.score);
with Glide v4:
Glide.with(context)
.load(URL)
.thumbnail(0.1f)
.into(image_view)
Better you can get idea from this Library or Use this library.
2 ways to do Blur and Original image in Android.
1) Initially load Blur Image Server URL path and once get success bitmap caching mechanism to load Original(Large) Image Server URL path.
Point 1 is possible, I got answer for you( Ask your server team to get Blur image or Low quality image to make blur and then load large image).
APK Link
Glide.with(mContext)
.load(image.getMedium())
.asBitmap()
.diskCacheStrategy(DiskCacheStrategy.ALL)
.into(new SimpleTarget<Bitmap>() {
#Override
public void onResourceReady(Bitmap bitmap, GlideAnimation anim) {
// Do something with bitmap here.
holder.thumbnail.setImageBitmap(bitmap);
Log.e("GalleryAdapter","Glide getMedium ");
Glide.with(mContext)
.load(image.getLarge())
.asBitmap()
.diskCacheStrategy(DiskCacheStrategy.ALL)
.into(new SimpleTarget<Bitmap>() {
#Override
public void onResourceReady(Bitmap bitmap, GlideAnimation anim) {
// Do something with bitmap here.
holder.thumbnail.setImageBitmap(bitmap);
Log.e("GalleryAdapter","Glide getLarge ");
}
});
}
});
2) Fresco by Facebook is a new image library for Android. Here’s the official blog post introducing the library. It supports the streaming of progressive JPEG images over the network which can be really helpful to display large images over slow connections. One can see the image gradually improve in quality.
Progressive JPEGs with Facebook Fresco
Use BitmapFactory.Options.inSampleSize to make a downsampled version of the image, and upload both versions. Load the sample image (which should take less time) and when the bigger version is downloaded, switch to that. You could also use a TransitionDrawable to make a fade transition.
this is not a perfect way but it will be easiest way to make it.
make placeHolder image as blur and set it into glide. then always it will show blur image and then after load the actual image it will appear.
you can refer this code to use glide.
//crete this method into your Utils class and call this method wherever you want to use.
//you can set these placeHolder() and error() image static as well. I made it as comment inside this method, then no need to use [placeHolderUrl and errorImageUrl] parameters. remove it from this method.
public static void loadImage(final Activity context, ImageView imageView, String url, int placeHolderUrl, int errorImageUrl) {
if (context == null || context.isDestroyed()) return;
//placeHolderUrl=R.drawable.ic_user;
//errorImageUrl=R.drawable.ic_error;
Glide.with(context) //passing context
.load(getFullUrl(url)) //passing your url to load image.
.placeholder(placeHolderUrl) //this would be your default image (like default profile or logo etc). it would be loaded at initial time and it will replace with your loaded image once glide successfully load image using url.
.error(errorImageUrl)//in case of any glide exception or not able to download then this image will be appear . if you won't mention this error() then nothing to worry placeHolder image would be remain as it is.
.diskCacheStrategy(DiskCacheStrategy.ALL) //using to load into cache then second time it will load fast.
.animate(R.anim.fade_in) // when image (url) will be loaded by glide then this face in animation help to replace url image in the place of placeHolder (default) image.
.fitCenter()//this method help to fit image into center of your ImageView
.into(imageView); //pass imageView reference to appear the image.
}
glide has a direct way of doing this :
val thumbnailRequest = Glide.with(this)
.load("https://picsum.photos/50/50?image=0")
Glide.with(this)
.load("https://picsum.photos/2000/2000?image=0")
.thumbnail(thumbnailRequest)
.into(imageThumbnail)
from the blog:
Thumbnails are a dynamic placeholders, that can be loaded from the Internet. Fetched thumbnail will be displayed until the actual request is loaded and processed. If the thumbnail for some reason arrives after the original image, it will be dismissed.
You must have a small-size and a full-size image on your server. You can use Firebase Resize Image Extension if you are using Firebase as your backend. Once you have a small-size image URL and a full-size image URL you can use Glide like this:
Glide.with(context)
.load(fullSizeImageUrl)
.thumbnail(
Glide.with(context)
.load(smallSizeImageUrl)
).into(imageView)
You'll get that blurry effect as the small-size image will be blurry
According to Glide Doc:
.thumbnail()
loads and displays the resource retrieved by the given thumbnail request if it finishes before this request. Best used for loading thumbnail resources that are smaller and will be loaded more quickly than the full size resource. There are no guarantees about the order in which the requests will actually finish. However, if the thumb request completes after the full request, the thumb resource will never replace the full resource.
use BitmapFactory.Options.inSamleSize to load a downsampled version of the image. Then load the bigger image and do a fade transition using a TransitionDrawable
Hope this will Helps you ! Cheers !

Glide not loading image from memory at the first time when rotating (orientation change), and after that it is loading from memory

Glide not loading image from memory at the first time when rotating (orientation change), and after that it is loading from memory.
I have tried to increase the memory size, the bitmap pool size, all kinds of caching strategies... nothing seemed to work...
I have attached a video.
https://youtu.be/szDnAGxrJLU
Thanks!
.dontAnimate() adding this to Glide solved my problem
Glide.with(view.getContext())
.load(url)
.placeholder(placeholder_image_crop))
.dontAnimate()
.into(view)
You may face this issue because of
CircleImageView/CircularImageView/RoundedImageView are known to have issues with TransitionDrawable (.crossFade() with .thumbnail() or .placeholder()) and animated GIFs, use a BitmapTransformation (.circleCrop() will be available in v4) or .dontAnimate() to fix the issue.
for more queries refer following links it may help you.
link 1 and link 2
Your ImageViews don't have the exact same size in portrait and in landscape and you are probably using fitCenter() or centerCrop() to resize the image to the ImageView size. When you change orientation, Glide loads the full-sized image from cache but it has to resize it on a background thread first before display, that's why you see a delay after the first orientation change. After resized images for both portrait and landscape are in the memory cache, there is no more delay.
Just to emphasize what is written above and add a solution.
It is possible to change the disk caching strategy to cache the source image but not the memory caching strategy, in that case it will not hit unless it is the same size.
What i did was use .override(width,height) in order to override this strategy and keep the source image in the memory cache.
Glide.with(context)
.load(imgUrl)
.crossFade()
.override(imageWidth,imageHeight)
.into(imgView);
To load image from cache you can pass DiskCacheStrategy.SOURCE to load images from cache.
You can use glide like below and keep don't animate method as it helps to load images in adapter without updating full list. For more check this
Glide.with(context)
.load(row_object.getImage())
.dontAnimate() // will load image
.diskCacheStrategy(DiskCacheStrategy.SOURCE)
.placeholder(ContextCompat.getDrawable(context,
R.mipmap.ic_user_placeholder_50dp))
.into(holder.rowIvPostUserIcon);
This code help me:
Glide.with(view.getContext())
.load(url)
.placeholder(AppCompatResources.getDrawable(view.getContext(), R.drawable.vector_placeholder_vendor_image_crop))
.dontAnimate()
.into(view);
//need add .dontAnimate()
For more information:
https://github.com/bumptech/glide/issues/1026#issuecomment-191709837
First Time glide is unable to load image on custom view like circular Imageview.you Can use error to load image on first time.
The following snippet should help you:
Glide.with(context)
.load(imgUrl)
.crossFade()
.override(imageWidth,imageHeight).error(R.drawable.yourdrawable)
.into(imgView);

Categories

Resources