【问题标题】:How to cache a NetworkImage to use in Another Activity using Volley如何使用 Volley 缓存 NetworkImage 以在另一个 Activity 中使用
【发布时间】:2017-06-03 16:01:52
【问题描述】:

我有两种观点,一种是主要的,另一种是细节的。我从服务器获取所有 url 并在 gridview 上相应地显示位图。一旦用户单击网格项目,我想使用主视图中的缓存图像。但是,我的以下实现不起作用。

我的测试方式如下:首先,我在gridview上显示所有图像并断开互联网,并希望在细节上查看缓存的图像。但是,在详细活动中,图像未显示。

我正在使用以下 Volley Singleton 类,如下所示:

public class CustomVolleyRequest {

    private static CustomVolleyRequest customVolleyRequest;
    private static Context context;
    private RequestQueue requestQueue;
    private ImageLoader imageLoader;

    private CustomVolleyRequest(Context context) {
        CustomVolleyRequest.context = context;
        this.requestQueue = getRequestQueue();

        imageLoader = new ImageLoader(requestQueue,
                new ImageLoader.ImageCache() {
                    private final LruCache<String, Bitmap>
                            cache = new LruCache<>(20);

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

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

    public static synchronized CustomVolleyRequest getInstance(Context context) {
        if (customVolleyRequest == null) {
            customVolleyRequest = new CustomVolleyRequest(context);
        }
        return customVolleyRequest;
    }

    public RequestQueue getRequestQueue() {
        if (requestQueue == null) {
            requestQueue = Volley.newRequestQueue(context.getApplicationContext(), 10 * 1024 * 1024);
        }
        return requestQueue;
    }

    ImageLoader getImageLoader() {
        return imageLoader;
    }
}

主活动适配器

public View getView(final int position, View convertView, @NonNull ViewGroup parent) {
    final ViewHolder holder;
    if(convertView == null) {
        holder = new ViewHolder();
        convertView = LayoutInflater.from(getContext()).inflate(R.layout.grid_item, parent, false);
    }
  holder.imageView.setImageUrl(imageRecord.getUrl(), mImageLoader);
}

详细活动

String url = getArguments().getString("image_url");
ImageLoader imageLoader = CustomVolleyRequest.getInstance(getContext()).getImageLoader();
mImageView.setImageUrl(url, imageLoader);

【问题讨论】:

    标签: android caching gridview android-volley


    【解决方案1】:

    如果 ImageView 的大小不同,则图像缓存的默认实现将不起作用,因为 ImageLoader 传递的缓存的键包括视图的大小:

    private static String getCacheKey(String url, int maxWidth, int maxHeight, ScaleType scaleType) {
        return "#W" + maxWidth + "#H" + maxHeight + "#S" + scaleType.ordinal() + url;
    }
    

    您有两个主要选择:

    1) 重新设计 ImageLoader 和可能的 NetworkImageView,因为它放置了实际转换的位图,可能大小不同,您可能需要调用 createScaledBitmap() 将其调整为视图。

    2) 确保从网络接收的原始图像数据被缓存。

    所以 1) 相对复杂,因为您必须更改几个类来更改 ImageRequest 中完成的解析,而不是缩放原始图像数据,而是在接收和缓存图像后执行缩放,基本上在 NetworkImageView 或 ImageLoader 后期

    如果您选择 2,如果您的服务器不发送缓存标头或 etag,您可能需要调整 Volley 的默认网络缓存实现。 在这种情况下,您需要对 ImageLoader 进行一些更改,您可以查看https://stackoverflow.com/a/36549815/2267924

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-11-01
      • 2023-03-29
      • 1970-01-01
      • 1970-01-01
      • 2015-02-21
      • 1970-01-01
      • 2014-05-15
      • 1970-01-01
      相关资源
      最近更新 更多