使用volley+universal image loader实现数据缓存和读取

什么是volley

volley是谷歌于2013推出的一款网络访问框架。具体怎样使用可以参考csdn其他博客教程,这里不重复造轮子

volley隐藏特性

1.默认自带缓存,缓存路径在-----'根目录/data/data/你的程序包名/cache/volley/'中
2.volley获取数据的途径是:检测内存,没有数据就访问硬盘缓存,再没有就访问网络重新获取数据
3.通过 queue.getCache().get(url)得到缓存对象,
4.通过queue.getCache().get(url).data得到缓存对象数据(url为你有网情况下访问数据的地址,volley会记录该值并在没网情况下通过该值得到缓存数据)

什么是universal image loader

universal image loader是一款热门的图片下载缓存框架
github下载地址:https://github.com/nostra13/Android-Universal-Image-Loader.git

你可以自定义image loader配置,也可以使用默认配置
注意点:编写一个类继承Application,需要在androidManifest.xml中配置application
<application
    android:name="Application"
    android:allowBackup="true"
    android:icon="@drawable/icon"
    android:label="@string/app_name"
    android:supportsRtl="true"
    android:theme="@style/AppTheme">

这里我使用自定义配置,配置文件如下,根据实际情况,你可以修改
public class Application extends android.app.Application {
    @Override
    public void onCreate() {

        super.onCreate();

        //创建默认的ImageLoader配置参数

        ImageLoaderConfiguration config = new ImageLoaderConfiguration.Builder(
                this)

                // 内存缓存文件最大质量
                .memoryCacheExtraOptions(480, 800)
             //   .discCacheExtraOptions(480,800,null)

                // 线程池内加载的数量

                .threadPoolSize(3)

                .threadPriority(Thread.NORM_PRIORITY - 2)

                .denyCacheImageMultipleSizesInMemory()

                .memoryCache(new UsingFreqLimitedMemoryCache(3 * 1024 * 1024))

                .memoryCacheSize(3 * 1024 * 1024)//内存缓存大小,这里为3M

                .discCacheSize(50 * 1024 * 1024)//硬盘缓存库大小,这里为50M

                .discCacheFileNameGenerator(new Md5FileNameGenerator())


                .tasksProcessingOrder(QueueProcessingType.FIFO)


                .discCacheFileCount(100)

                .discCache(
                        new UnlimitedDiscCache(new File(Environment
                                .getExternalStorageDirectory() + "myApp/ImgCache"))
                )

                .defaultDisplayImageOptions(getDisplayOptions())


                .imageDownloader(
                        new BaseImageDownloader(this, 5 * 1000, 30 * 1000)
                )  //下载

                .writeDebugLogs()  //写错误日志

                .build();//开始构建
        ImageLoader.getInstance().init(config);//使用自定义配置
    }

    private DisplayImageOptions getDisplayOptions(){

        DisplayImageOptions options;
        options=new DisplayImageOptions.Builder()
                .showImageOnLoading(R.mipmap.ic_launcher)
                .showImageForEmptyUri(R.mipmap.ic_launcher)
                .showImageOnFail(R.mipmap.ic_launcher)
                .cacheInMemory(true)
                .cacheOnDisc(true)
                .imageScaleType(ImageScaleType.EXACTLY)
                .bitmapConfig(Bitmap.Config.RGB_565)
                .resetViewBeforeLoading(true)
                .displayer(new RoundedBitmapDisplayer(20))
                .displayer(new FadeInBitmapDisplayer(0))
                .build();

        return options;

    }


}
 
 
在你的adapter或activity总实例化imageloader
ImageLoader imageLoader = ImageLoader.getInstance();//实例化
使用loader.displayImage(url,view)实现显示图片//url为你的图片地址,view为你的imageview
 
 
好了,下面上volley网络请求源码,这里我把它封装在一个我项目的一个方法里面了
/**
 * @param url 请求数据的url
 */
private void requestData(final String url) {
    //网络请求不管怎么封装, 里面多数情况都使用子线程去执行。
    final RequestQueue queue = Volley.newRequestQueue(context);
    StringRequest request = new StringRequest(
            url,
            new Response.Listener<String>() {
                //从发出请求,到成功返回数据, 需要经过3s钟,也就是3s了之后,才能执行onResponse
                @Override
                public void onResponse(String response) {

                    try {
                        response = new String(response.getBytes("ISO-8859-1"), "utf-8");

                        //关闭下拉刷洗头
                        swipeRefreshLayout.setRefreshing(false);
                        Log.d("response-----", response);


                        //1. 解析json数据
                        Gson gson = new Gson();
                        newlistBean = gson.fromJson(response, NewListBean.class);
                        Log.d("title------", newlistBean.getData().getTopnews().get(0).getTitle());

                        //动态添加imageview
                        setView();

                        //初始化圆点
                        initDot();

                        //进入轮播自动任务
                        autoLoader();


                        //5.表明是加载更多
                        if (isLoadMore) {
                            adapter.addData(newlistBean.getData().getNews());
                        } else {
                            adapter.setData(newlistBean.getData().getNews());
                        }

                        //通知界面刷新
                        adapter.notifyDataSetChanged();

                        //6 关闭下拉刷新
                        closeRefresh();

                        //7. 关闭加载更多
                        closeLoadMore();

                        //swipeRefreshLayout.setRefreshing(false);//关闭刷新

                    } catch (UnsupportedEncodingException e) {
                        e.printStackTrace();
                    }
                }
            },

            //没网络是就从缓存中读取
            new Response.ErrorListener() {
                @Override
                public void onErrorResponse(VolleyError error) {
                    //--------------------------这里是核心


                    if(queue.getCache().get(url)!=null){
                        String cachedResponse = new String(queue.getCache().get(url).data);

                    
                    //--------------------------这里是核心
                        Log.d("cachejsons",cachedResponse);
                        //1. 解析json数据
                        Gson gson = new Gson();
                        newlistBean = gson.fromJson(cachedResponse, NewListBean.class);
                        Log.d("title------", newlistBean.getData().getTopnews().get(0).getTitle());

                        //动态添加imageview
                        setView();

                        //初始化圆点
                        initDot();

                        //进入轮播自动任务
                        autoLoader();

                        //5.表明是加载更多
                        if (isLoadMore) {
                            adapter.addData(newlistBean.getData().getNews());
                        } else {
                            adapter.setData(newlistBean.getData().getNews());
                        }

                        //通知界面刷新
                        adapter.notifyDataSetChanged();

                    }

                    //6 关闭刷新
                    closeRefresh();

                    //7. 关闭加载更多
                    closeLoadMore();
                    Log.d("error----", error.toString());
                }
            }

    );
    queue.add(request);
}
下面是我adapter类中getview方法,核心代码在最后一段
@Override
public View getView(int i, View view, ViewGroup viewGroup) {

    ViewHodler hodler=null;
    //可以使用viwGroup.getContext()获得上下文
    if(view==null) {
        view = View.inflate(viewGroup.getContext(), R.layout.item_newslist, null);

        //使用viewhodler方式找到view
        hodler=new ViewHodler();
        hodler.tvtitle=(TextView) view.findViewById(R.id.tv_title);
        hodler.tvtime=(TextView) view.findViewById(R.id.tv_time);
        hodler.ivicon=(ImageView) view.findViewById(R.id.iv_icon);
        view.setTag(hodler);
    }else {
        hodler= (ViewHodler) view.getTag();
    }

    NewListBean.DataBean.NewsBean newsBean=mNews.get(i);
    hodler.tvtitle.setText(newsBean.getTitle());
    hodler.tvtime.setText(newsBean.getPubdate());
   // Picasso.with(viewGroup.getContext()).load(newsBean.getListimage()).into(hodler.ivicon);

    //使用三级缓存对图片数据进行缓存
    mImageLoader.displayImage(newsBean.getListimage(),hodler.ivicon);
    return view;
}

总结:


利用框架能够轻松完成数据缓存和读取,总体实现逻辑就是从缓存中读出数据,把数据设置到适配器中,然后
显示数据,这里volley就是缓存数据的,imageloader就是根据传过来的url从硬盘或内存中读取照片并
显示,附项目图





评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值