Question

I have a listView and an adapter,
I have scrolled to the middle of the list(say if we have 100 items I'm in item #50)
Once there, I get a couple of updates from the server.. say, like new stories from facebook..
A. I want to call notifyDataSetChanged() and maintain position- for that I used this code
B. I am using the lovely NetworkImageView from the volley library, I want, that when notifyDataSetChanged is called - the image won't get reloaded as it is right now, because,(and maybe that is the source of my problem), at the moment, reloading the image is causing some sort of flicker to the user(no photo- photo loaded)

EDIT:

    mQueue = Volley.newRequestQueue(getApplicationContext());// thread pool(4)
    mngr.setRequestQueue(mQueue);

    final int maxMemory = (int) (Runtime.getRuntime().maxMemory() / 1024);
    mImageLoader = new ImageLoader(mQueue, new ImageCache() {

        private final LruBitmapCache mCache = new LruBitmapCache(maxMemory);

        public void putBitmap(String url, Bitmap bitmap) {

            mCache.put(url, bitmap);
        }

        public Bitmap getBitmap(String url) {

            return mCache.get(url);

        }
    });

My solution:

//      final int maxMemory = (int) (Runtime.getRuntime().maxMemory() / 1024);
    mImageLoader = new ImageLoader(mQueue, new ImageCache() {

        private final BitmapLruCache mCache = new BitmapLruCache();

        public void putBitmap(String url, Bitmap bitmap) {

            mCache.put(url, bitmap);
        }

        public Bitmap getBitmap(String url) {

            return mCache.get(url);

        }
    });

I used the next bimtap lru cache implementation

public class BitmapLruCache extends LruCache<String, Bitmap> implements ImageCache {
public static int ONE_KILOBYTE = 1024;

public BitmapLruCache() {
    this(getDefaultLruCacheSize());
}

public BitmapLruCache(int maxSize) {
    super(maxSize);
}

public static int getDefaultLruCacheSize() {
    final int maxMemory = (int) (Runtime.getRuntime().maxMemory() / ONE_KILOBYTE);
    final int cacheSize = maxMemory / 8;

    return cacheSize;
}

@Override
protected int sizeOf(String key, Bitmap value) {
    return value.getRowBytes() * value.getHeight() / ONE_KILOBYTE;
}

@Override
public Bitmap getBitmap(String url) {
    return get(url);
}

@Override
public void putBitmap(String url, Bitmap bitmap) {
    put(url, bitmap);
}
}

What do you guys think?

10x

Était-ce utile?

La solution

I am using the lovely NetworkImageView from the volley library, I want, that when notifyDataSetChanged is called - the image won't get reloaded as it is right now, because,(and maybe that is the source of my problem), at the moment, reloading the image is causing some sort of flicker to the user(no photo- photo loaded)

Did you supply your ImageLoader with an in-Memory Cache? When calling .setImageUrl, Volley first tries to grab the Image from the Cache you supplied when instantiating your ImageLoader, then goes to the Disk-Cache (built in to Volley), then goes to the network. If you properly used a Memory-Cache, .setImageUrl should return instantly without flickering. My guess is you used a disk-cache (which unfortunately is recommended in some tutorials out there).

An example for a memory-cache can be found for example here: https://github.com/ogrebgr/android_volley_examples/blob/master/src/com/github/volley_examples/toolbox/BitmapLruCache.java then instantiate ImageLoader like this:

int cacheSize = 1024 * 1024 * 10; // 10MB Cache
mImageLoader = new ImageLoader(mRequestQueue, new BitmapLruCache(cacheSize));
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top