When I pass in my Image URI to imageLoader.displayImage, it is automatically getting appended with _[W]x[H] at the end of each url. Is there a way to override that string, or prevent it from getting appended at all?
The API i am calling already has querystring parameters setup for height and width. It would be great if I could override this value.
Thank you.
This appendix is used only for memory cache. So different sizes of the same image can be cached in memory. This appendix isn't used for HTTP requests.
Related
I am using an ArrayAdapter along with ListView to display some images (I use Picasso to help with image handling). The images are initially loaded from the state on the local device. The adapter has ids for the images, which the getView() method of the adapter uses to get the path. If the image is not available locally, the local state returns an URL for the image. If the URL has expired, I need to fetch this from the backend.
If the URL is not expired, I have no issues, as I can either directly provide the path to Picasso or the URL and Picasso will handle everything for me. However, when I need to fetch the URL from the backend, I need to do this asynchronously. After fetching the URL, I tried doing the following but it doesn't seem to work (my getView() will in this case use Picasso with the URL):
adapter.remove(id);
adapter.add(id);
notifyDataSetChanged() doesn't seem to do much as well.
What is the best way to handle this situation? Is there any other way than what I am trying to do with the adapters? I want to delay the URL fetch from the backend as much as possible, basically until the user needs to see the image.
UPDATE: for now, I am replacing the id with a temp_id when the URL is expired and then add the correct id again, when I have the valid URL so that the view gets refreshed.
Have you tried clearing your ArrayList of image urls with myArray.clear()? Not so sure if I get your question or how your code looks like.
But I have issues like this before. What worked for me was to repopulating the adapter completely.
This link should help.
I'm using Picasso to download images in my app. My understanding is that it uses a http client (HttpResponseCache or OkHttpClient) to cache these images on disk.
Without knowing much about either of these libraries, is it possible to mark certain images as permanent? In other words, I would like to download an image and guarantee that it will be available offline.
Thinking about it, I couldn't really have the disk cache go over a certain size, so I guess what I really need is to remove the TTL on the image url and allow the cache to remove images in a first in first out scenario.
In that case, can I control which image will be deleted first (by using a timestamp based on accessed, rather than downloaded)?
Update
Based on the answer from this SO question:
Android + Picasso: changing URL cache expiration
So this answers the first part of the question - we can control the TTL through the server.
After talking to a colleague, he pointed out that the http client should take into account how frequently an image is accessed (in addition to the TTL). So hopefully I don't have to worry about this either.
That leaves me with one question. I know which images I don't need anymore, can I remove an image from the disk cache?
You can iterate the elements in OkHttp's disk cache, and call Iterator.remove() to get rid of the ones you don't want.
http://square.github.io/okhttp/javadoc/com/squareup/okhttp/Cache.html#urls--
You'd have to extend Picasso's default cache and create a custom Picasso instance to use it:
Extend LruCache
Override the void set(String key, Bitmap bitmap) method to do what you describe (adding timestamp, etc.). Check out the original source code here.
Make sure that the original trimToSize method is never called by set (and clearKeyUri for that matter), and write your own to check for the timestamp etc to get the behavior you describe
Create a custom Picasso instance with your custom cache like this:
Picasso picasso = new Picasso.Builder(context).memoryCache(cache).build(); Picasso.setSingletonInstance(picasso);
Where cache is an instance of your custom LruCache class
when you want to store the images on the disk you should use the okhttpdownloader
OkHttpClient client = new OkHttpClient.Builder()
.cache(new Cache(getCacheDir(), Integer.MAX_VALUE))
.build();
Picasso build = new Picasso.Builder(this)
.downloader(new OkHttp3Downloader(client))
.build();
Picasso.setSingletonInstance(build);
I'm trying to load an static map using this url:
http://maps.googleapis.com/maps/api/staticmap?center=43.137022,13.067162&zoom=16&size=600x400&maptype=roadmap&sensor=true&markers=color:blue|43.137022,13.067162
I'm doing it with Square's Picasso, but it fails to load.
With some tests I've to the conclusion that the char | is the one messing up Picasso. Any idea on how to overcome this issue?
Picasso appears to expect a URL-encoded URL. This means that the values of form variables need to be URL-encoded, the way they would if this were a submitted HTML form.
Alphanumeric characters do not need escaping, which is why most of your URL is fine. However, the markers parameter contains special characters, particularly that |, which need to be converted into URL-encoded values.
If you were programmatically generating the URL by pieces, you might use URLEncoder and encode() to handle this conversion for you.
I have a fairly large list of image URL's that I'm using to load up a ViewPager using Picasso. I need to be able to provide sharing capabilities for these images via an intent (ultimately sharing via ShareActionProvider). From what I've read, Picasso isn't really built to handle this sort of thing out of the box, though it provides all the necessary tools to do so.
My plan before research was to create a simple LruCache which uses the url as the key and bitmap value. This caching would occur in onBitmapLoaded via Picasso's Target interface. Whenever I want to share an image, I'll check the cache for the bitmap. If it's not there, I'll fetch with Picasso. Now that I have a cached bitmap regardless, I'll write to a file (...this part doesn't seem right, though I have to write to a file to get a uri, right?) and add the file uri to the intent.
However I see that with the Picasso.Builder I can set (and retain a reference to) my own cache - https://stackoverflow.com/a/18552559/413254. This means I could do away with the custom Target and confusion with properly implementing hashCode and equals methods to ensure accurate recycling, retrieval, etc.
My question is, how does Picasso use this cache? What are the keys? Is there a way to get a bitmap Uri without writing it to disk?
If you want to use ShareActionProvider to share the image on the current page you don't have to keep your own cache of images. But to be able to share it to others, the image should be in the shared file system on the device.
It would be better if you use image loading libraries with custom disk cache support like Universal Image Loader
If you want to use Picasso (which is a good decision).
You either have to save a copy of the image on every page change which is nor a good option.
Or you can give a custom network handler to Picasso and set a custom cache implementation to it. I would suggest using OkHttp with custom caching which stores files in the format you desire. When you do that, you have to have a function that converts image URLs to file path on a device.
In every page change, if you have a Fragment inside your ViewPager, put the ShareActionProvider into your Fragments.
Get the reference of the ShareActionProvider inside onCreateOptionsMenu. And then set the Intent with the file path you get.
Intent shareIntent = new Intent(Intent.ACTION_SEND);
Uri phototUri = Uri.parse(Utils.getFilePath(imageUrl));
shareIntent.setData(phototUri);
shareIntent.setType("image/png");
shareIntent.putExtra(Intent.EXTRA_STREAM, phototUri);
mShareActionProvider.setShareIntent(intent);
Edit:
The other option I would prefer is to ditch ShareActionProvider and use a normal menu item for this. The problem with ShareActionProvideris that you have to make the share Intent ready for user to share before hand. You have to make it ready even the user won't share it.
But when you have a normal button, it is much easier because you only make the operation when the user clicks the share button. In that case you can simply request the image one more time from Picasso with a Target object and write the Bitmap you got to a file in the shared external file system and share it.
I'm using NOSTRA's Universal Image Loader library and I have caching in memory enabled. It seems that the bitmaps are cached using the URI set in the displayImage() method as the key. As a workaround I created another HashMap that contains the URIs for the images, with a unique id associated with it as the key. The reason for that is the id value is also used to load data in other places, so that value is unique for each image.
So is there a way to change the key for the cached bitmap to something other than the URI?
Bitmap are cached in memory cache by key pattern [imageUrl]_[width]x[height]. There is no way to change this pattern in current lib version (1.7.0).
# NOSTRA :
Can we do like this.
instead of passing [imageUrl]_[width]x[height] while generating cachekey we can just pass our unique ID for cache key.