【FastDev4Android框架开发】Volley完全解析之进阶最佳实践与二次封装(二十七)

jerry Android 2015年11月26日 收藏

().前言:   

        上一讲我们已经对Volley使用基础阶段涉及到字符串,JSON,图片等等网络数据请求相关方法的使用。今天我们对于Volley框架来一个进阶使用扩展封装,以及对上一篇遗留的问题做一下具体修改使用。主要涉及新增GsonRequest,ImageLoader列表图片加载,ImageCache,Volley框架StringRequest二次封装以及post请求新增设置请求参数方法。

        FastDev4Android框架项目地址:https://github.com/jiangqqlmj/FastDev4Android

().post请求扩展请求参数方法

       还记得前面文章我们只是使用RequestGET请求方法,当然作为完善的网络框架POST请求必须支持,不过很可惜的是Volley框架没有给我们显示的提供设置POST请求参数的方法,不过我们有两种方法来进行设置。不过在做之前我们需要先从源码角度来分析一下。

        查看源码,我们发现Volley请求最终会被封装成HttpRequest子类对象HttpUrlRequest,该方法在HttpClientStack中的createHttpRequest()方法,代码和相关注释如下:


/**
     * 进行创建httprequest,这边获取httprequest的子类,httpurlrequest
     * Creates the appropriate subclass ofHttpUriRequest for passed in request.
     */
    @SuppressWarnings("deprecation")
    /* protected */ static HttpUriRequest createHttpRequest(Request<?> request,
            Map<String, String>additionalHeaders) throws AuthFailureError {
        switch (request.getMethod()) {
            case Method.DEPRECATED_GET_OR_POST:{
                // This is the deprecated waythat needs to be handled for backwards compatibility.
                // If the request's post bodyis null, then the assumption is that the request is
                // GET.  Otherwise, it is assumed that the request isa POST.
                byte[] postBody =request.getPostBody();
                if (postBody != null) {
                    HttpPost postRequest = new HttpPost(request.getUrl());
                    postRequest.addHeader(HEADER_CONTENT_TYPE,request.getPostBodyContentType());
                    HttpEntity entity;
                    entity = new ByteArrayEntity(postBody);
                   postRequest.setEntity(entity);
                    return postRequest;
                } else {
                    return newHttpGet(request.getUrl());
                }
            }
            case Method.GET:
                return newHttpGet(request.getUrl());
            case Method.DELETE:
                return newHttpDelete(request.getUrl());
            case Method.POST: {
                HttpPost postRequest = new HttpPost(request.getUrl());
               postRequest.addHeader(HEADER_CONTENT_TYPE,request.getBodyContentType());
                //设置请求体 body信息 -如果请求体不为空---[注意]
               setEntityIfNonEmptyBody(postRequest, request);
                return postRequest;
            }
            case Method.PUT: {
                HttpPut putRequest = new HttpPut(request.getUrl());
               putRequest.addHeader(HEADER_CONTENT_TYPE, request.getBodyContentType());
               setEntityIfNonEmptyBody(putRequest, request);
                return putRequest;
            }
            case Method.HEAD:
                return new HttpHead(request.getUrl());
            case Method.OPTIONS:
                return new HttpOptions(request.getUrl());
            case Method.TRACE:
                return new HttpTrace(request.getUrl());
            case Method.PATCH: {
                HttpPatch patchRequest = newHttpPatch(request.getUrl());
               patchRequest.addHeader(HEADER_CONTENT_TYPE,request.getBodyContentType());
               setEntityIfNonEmptyBody(patchRequest, request);
                return patchRequest;
            }
            default:
                throw newIllegalStateException("Unknown request method.");
        }
    }


注意查看以上caseMethod.POST部分中的setEntityIfNonEmptyBody();中进行设置请求体相关数据:

 /**
     * 如果request的请求体不为空,进行设置请求体信息
     * @param httpRequest
     * @param request
     * @throws AuthFailureError
     */
    private static void setEntityIfNonEmptyBody(HttpEntityEnclosingRequestBase httpRequest,
            Request<?> request) throws AuthFailureError {
        byte[] body = request.getBody();
        if (body != null) {
            HttpEntity entity = new ByteArrayEntity(body);
            httpRequest.setEntity(entity);
        }
    }

然后会执行RequestgetBody()方法来获取请求体。



/**
     * Returns the raw POST or PUT body to besent.
     * 如果请求是POST或者PUT方法,去获取请求参数信息,然后设置到请求中
     * <p>By default, the body consistsof the request parameters in
     * application/x-www-form-urlencodedformat. When overriding this method, consider overriding
     * {@link #getBodyContentType()} as well tomatch the new body format.
     *
     * @throws AuthFailureError in the event ofauth failure
     */
    public byte[] getBody() throws AuthFailureError {
        //获取请求参数信息
        Map<String, String> params =getParams();
        if (params != null &¶ms.size() > 0) {
            return encodeParameters(params,getParamsEncoding());
        }
        return null;
    }


最后会获取XxxRequest的基类Requst类中的getParams()来获取请求参数信息,然后设置进去。

OK这个设置POST请求参数信息的流程大家应该能清楚吧。但是Volley源代码这边就直接返回null,如下:


protected Map<String, String> getParams() throws AuthFailureError {
        return null;
    }


又因为Volley是开源的,那么下面我们开源对Request和XxxRequest类进行改造修改源代码,往外提供POST请求参数设置的方法,修改步骤如下:

        2.1.Request类一个Map对象mParams,然后添加set方法,然后在getParams()进行returnmParams。具体修改如下:


/**
     * 自定义修改 新增POST请求参数map
     */
    protected Map<String,String> mParams=null;
    public void setParams(Map<String,String> params) {
        this.mParams = params;
    }



/**
     * 进行获取post请求参数数据
     * Returns a Map of parameters to be usedfor a POST or PUT request.  Can throw
     * {@link AuthFailureError} asauthentication may be required to provide these values.
     *
     * <p>Note that you can directlyoverride {@link #getBody()} for custom data.</p>
     *
     * @throws AuthFailureError in the event ofauth failure
     */
    protected Map<String, String> getParams() throws AuthFailureError {
        //return null;
        //重新进行返回params
        return mParams;
    }

       2.2.间接着我们对StringRequest类进行扩展一个构造方法,加入请求参数Map对象,具体代码如下:


/**
     * 扩展POST请求构造函数
     * @param url 请求地址
     * @param listener   数据请求加载成功监听器
     * @param errorListener  数据请求加载失败监听器
     * @param params  POST请求参数
     */
    public StringRequest(String url,Listener<String> listener, ErrorListenererrorListener,Map<String,String> params) {
        this(Method.POST, url, listener,errorListener);
        //进行初始化Request中post 请求参数
        setParams(params);
    }


   OK这两步修改就完成了POST请求参数设置扩展,下面我们来一看一下具体使用方法:


RequestQueue requestQueue=Volley.newRequestQueue(this);
              //修改Volley源代码,扩展StringRequest支持post参数设置
                Map<String,String>params=new HashMap<String,String>();
               params.put("username","zhangsan");
               params.put("password","12345");
                StringRequest post_stringRequest=new StringRequest("http://10.18.3.123:8080/SalesWebTest/TestVolleyPost",new Response.Listener<String>() {
                    @Override
                    public void onResponse(String response) {
                       tv_result.setVisibility(View.VISIBLE);
                       img_result.setVisibility(View.GONE);
                       tv_result.setText(response.toString());
                    }
                }, new Response.ErrorListener(){
                    @Override
                    public void onErrorResponse(VolleyError error) {
 
                    }
                },params);
               requestQueue.add(post_stringRequest)


       这样就完成POST请求参数设置的扩展,另外的一种方案是创建StringRequest对象的时候实匿名类中重写getParams()方法,然后构造Map对象设置参数信息return该对象即可。不过个人觉的这种方案不推荐还是使用设置的方法比较好。

().ImageloaderImageCache

      在前面使用ImageLoder对象加载图片的时候,有一个优点我们没有深入讲解,因为ImageLoader是支持缓存功能,所以我们在创建ImageLoader需要传入一个缓存管理器,里面传入我们自定义的缓存策略,Fdv_ImageCache我们这边引入LruCache算法具体实现如下:


packagecom.chinaztt.fdv;
importandroid.graphics.Bitmap;
importandroid.util.LruCache;
importcom.android.volley.toolbox.ImageLoader;
/**
 * 当前类注释:图片缓存器,实现ImageLoder.ImageCache实现其中的方法,具体图片怎么样缓存让我们自己来实现
 * 这样可以考虑到将来的扩展性
 * 项目名:FastDev4Android
 * 包名:com.chinaztt.fdv
 * 作者:江清清 on 15/11/12 12:31
 * 邮箱:jiangqqlmj@163.com
 * QQ: 781931404
 * 公司:江苏中天科技软件技术有限公司
 */
public class Fdv_ImageCache  implements ImageLoader.ImageCache {
    private LruCache<String, Bitmap>mCache=null;
    private static final intCACHE_MAX_SIZE = 8 * 1024 * 1024;  //默认缓存大小为8M
    public Fdv_ImageCache(){
        if(mCache==null){
            mCache = new LruCache<String,Bitmap>(CACHE_MAX_SIZE) {
                @Override
                protected int sizeOf(Stringkey, Bitmap bitmap) {
                    return bitmap.getRowBytes()* bitmap.getHeight();
                }
            };
        }
    }
    /**
     * 从缓存中获取图片
     * @param url  获取图片key  当然该key可以根据实际情况 使用url进行变换修改
     * @return
     */
    @Override
    public Bitmap getBitmap(String url) {
        return mCache.get(url);
    }
    /**
     * 向缓存中添加图片
     * @param url  缓存图片key,当然该key可以根据实际情况 使用url进行变换修改 不过规格需要和上面方法的key保持一致
     * @param bitmap  需要缓存的图片
     */
    @Override
    public void putBitmap(String url, Bitmapbitmap) {
       mCache.put(url,bitmap);
    }
}


有了图片缓存机制,然后我们在配合ImageLoader来进行列表上面加载异步图片的实现,具体实现方式如下:


/**
 * 当前类注释:使用ImageLoader来进行测试列表图片异步加载以及缓存
 * 项目名:FastDev4Android
 * 包名:com.chinaztt.fda.test
 * 作者:江清清 on 15/11/12 15:19
 * 邮箱:jiangqqlmj@163.com
 * QQ: 781931404
 * 公司:江苏中天科技软件技术有限公司
 */
@EActivity(R.layout.base_adapter_test_layout)
public class VolleyLoaderActivity  extends BaseActivity {
    @ViewById
    ListView lv_base_adapter;
    @ViewById
    TextView tv_title;
    private QuickAdapter<ModuleBean>mAdapter;
    private List<ModuleBean> moduleBeans;
    private RequestQueue requestQueue;
    private ImageLoader imageLoader;
    private ImageLoader.ImageListener listener;
    @Override
    protected void onCreate(BundlesavedInstanceState) {
        super.onCreate(savedInstanceState);
        requestQueue=Volley.newRequestQueue(this);
        imageLoader=new ImageLoader(requestQueue,new Fdv_ImageCache());
    }
    @AfterViews
    public void setViews(){
       tv_title.setText("Loader 列表图片");
    }
    @AfterViews
    public void bindLvData(){
        moduleBeans=DataUtils.getAdapterData();
        if(mAdapter==null) {
            mAdapter = new QuickAdapter<ModuleBean>(this, R.layout.lv_item_base_layout,moduleBeans){
                @Override
                protected void convert(BaseAdapterHelper helper, ModuleBean item) {
                    //列表底下显示进度
                   mAdapter.showIndeterminateProgress(true);
                   helper.setText(R.id.text_lv_item_title, item.getModulename())
                           .setText(R.id.text_lv_item_description, item.getDescription());
                   //setImageUrl(R.id.img_lv_item, item.getImgurl());
                    //使用ImageLoader进行加载图片
                    ImageView loader_img=helper.getView(R.id.img_lv_item);
                   listener=ImageLoader.getImageListener(loader_img,R.drawable.ic_loading,R.drawable.ic_loading);
                   imageLoader.get(item.getImgurl(),listener);
                }
            };
           lv_base_adapter.setAdapter(mAdapter);
        }
    }
}


运行效果如下:


().GsonRequest封装

          前面我们已经使用过JsonObjectRequest,JsonArrayRequest两个工具类,这边是采用Android自身提供的JSONObject和JSONArray来进行实现解析JSON数据的,不过我们也知道如果我们已经有JSONObject和JSONArray对象然后一步步的解析还是挺麻烦的,所以我们这边可以使用JSON快速解析框架Gson来进行解决这个问题。现在我们自定义一个GsonRequest来专门处理请求GSON解析。在做之前我们先要看一下StringRequest的实现,首先StringRequest是继承Request类然后实现两个抽象方法,间接着提供若干个构造方法(进行数据初始化,请求类型GET/POST…,请求服务器地址,相应成功是否回调接口)。因为StringRequest的实现代码很少而且较简单,那么我们模仿StringRequest类的实现可以写出来一下GsonRequest代码如下:


/**
 * 当前类注释:进行扩展GSON数据解析json数据
 * 项目名:FastDev4Android
 * 包名:com.android.volley.toolbox
 * 作者:江清清 on 15/11/12 18:28
 * 邮箱:jiangqqlmj@163.com
 * QQ: 781931404
 * 公司:江苏中天科技软件技术有限公司
 */
public class GsonRequest<T> extends Request<T> {
    private final Response.Listener<T>listener;
    private Gson gson;
    private Class<T> mClass;
 
    /**
     * GsonRequest 构造函数
     * @param method  请求方法
     * @param url     请求地址
     * @param listener    数据请求成功回调接口
     * @param errorListener  数据请求失败回调接口
     * @param pClass     需要进行解析的类
     */
    public GsonRequest(int method,Stringurl,Response.Listener<T> listener,Response.ErrorListenererrorListener,Class<T> pClass){
         super(method,url,errorListener);
         this.listener=listener;
         gson=new Gson();
         mClass=pClass;
    }
 
    /**
     * GsonRequest 构造函数  默认使用GET请求方法
     * @param url
     * @param listener
     * @param errorListener
     * @param pClass
     */
    public GsonRequest(Stringurl,Response.Listener<T> listener,Response.ErrorListenererrorListener,Class<T> pClass){
        super(Method.GET,url,errorListener);
        this.listener=listener;
        gson=new Gson();
        mClass=pClass;
    }
 
    /**
     * 数据解析
     * @param response Response from thenetwork  网络请求返回数据
     * @return
     */
    @Override
    protected Response<T> parseNetworkResponse(NetworkResponse response) {
        try {
            String jsonStr=new String(response.data,HttpHeaderParser.parseCharset(response.headers));
            Tdata=gson.fromJson(jsonStr,mClass);
            returnResponse.success(data,HttpHeaderParser.parseCacheHeaders(response));
        } catch (UnsupportedEncodingExceptione) {
            return Response.error(newParseError(e));
        }
    }
 
    /**
     * 数据分发
     * @param response The parsed responsereturned by
     */
    @Override
    protected void deliverResponse(T response){
          listener.onResponse(response);
    }
}


          以上实现详解:GsonRequest继承Request,同样提供两个构造函数,然后在parseNetworkResponse()方法中进行解析数据,最后通过Gson组件来封装数据成Bean对象,最终数据回调即可。具体使用方法如下:


GsonRequest<UpdateBean> gsonRequest=new GsonRequest<UpdateBean>("http://interface.zttmall.com/update/mallUpdate",new Response.Listener<UpdateBean>() {
                    @Override
                    public void onResponse(UpdateBean response) {
                       tv_result.setVisibility(View.VISIBLE);
                       img_result.setVisibility(View.GONE);
                       tv_result.setText(response.toString());
                    }
                }, new Response.ErrorListener(){
                    @Override
                    public void onErrorResponse(VolleyError error) {
 
                    }
                }, UpdateBean.class);


运行效果如下:


().Volley二次封装(StringRequest为例)

        我们在使用Volley框架请求网络数据获取的时候,一般就是以下三步骤:

           1.创建RequestQueue对象

           2.创建XXRequest对象(XX代表String,JSON,Image等等)

           3.XXRequest对象添加到RequestQueue中即可

        虽然代码量不是不多,不过也还是需要做创建队列对象和请求对象加入到队列中的操作,而创建XxxRequest对象的构造函数中的参数又比较多,所以这边想了一种方案就是在进行网络请求的时候创建和add操作放在内部然后构造函数中的参数减少。所以这边只是以StringRequest为例,简单的封装了一个Get方法请求的方法,其他的功能还有待继续添加更新。

            我们已StringRequest为例二次封装了一个类Fdv_StringRequst,我们来看以下该类的使用方法代码:


newFdv_StringRequest<String>(VolleyTestActivity.this).get("http://www.baidu.com",new Fdv_CallBackListener<String>() {
                    @Override
                    public void onSuccessResponse(String response) {
                    }
                    @Override
                    public void onErrorResponse(VolleyError error) {
 
                    }
                });


这样即可,不在需要以前的RequestQueuerequestQueue=Volley.newRequestQueue(this);

requestQueue.add(object)这两句代码了,直接在内部已经做了。然后如果Get请求直接调用get()方法即可,不需要显示传入请求方法。下面我们来看一下具体实现:


      5.1.定义Fdv_Volley类,里边是一个单例方法,来获取RequestQueue请求队列对象.


/**
 * 当前类注释:全局Fdv_Volley封装类管理类
 * 项目名:FastDev4Android
 * 包名:com.chinaztt.fdv
 * 作者:江清清 on 15/11/11 23:02
 * 邮箱:jiangqqlmj@163.com
 * QQ: 781931404
 * 公司:江苏中天科技软件技术有限公司
 */
public class Fdv_Volley {
    private static RequestQueue instance;
    public static RequestQueue getInstace(Context pContext){
        if(instance==null){
            instance=Volley.newRequestQueue(pContext);
        }
        return instance;
    }
}


       5.2.定义XxxRequest的基类Fdv_BaseRequest,主要功能获取请求队列对象,然后定义一个addRequest()方法,让子类进行调用,添加当前请求对象到请求队列中。


/**
 * 当前类注释:
 * 项目名:FastDev4Android
 * 包名:com.chinaztt.fdv
 * 作者:江清清 on 15/11/11 22:59
 * 邮箱:jiangqqlmj@163.com
 * QQ: 781931404
 * 公司:江苏中天科技软件技术有限公司
 */
public class Fdv_BaseRequest{
    protected static RequestQueue requestQueue;
    private Context mContext;
    protected Fdv_BaseRequest(ContextpContext){
        this.mContext=pContext;
    }
    /**
     * 请求加入到Volley Request请求队列中
     * @param request
     */
    protected void addRequest(Request request){
       Fdv_Volley.getInstace(mContext).add(request);
    }


      5.3.请求结果回调接口Fdv_CallBackListener,这边暂时只加了两个很简单的方法,后期会进行扩展


/**
 * 当前类注释:
 * 项目名:FastDev4Android
 * 包名:com.chinaztt.fdv
 * 作者:江清清 on 15/11/11 23:18
 * 邮箱:jiangqqlmj@163.com
 * QQ: 781931404
 * 公司:江苏中天科技软件技术有限公司
 */
public interface Fdv_CallBackListener<T> {
    void onSuccessResponse(T response);
    void onErrorResponse(VolleyError error);
}


   5.4.最后是我们的核心类封装过后的StringRequest,Fdv_StringRequest该类继承Fdv_BaseRequest类,在该类中我们暂时只是提供一个get()方法来获取数据中,get()方法的实现还是使用原来的StringRequest进行获取数据,得到数据使用接口回调即可,实现代码如下:


/**
 * 当前类注释:Volley 字符串、文本数据请求封装类
 * 项目名:FastDev4Android
 * 包名:com.chinaztt.fdv
 * 作者:江清清 on 15/11/11 13:43
 * 邮箱:jiangqqlmj@163.com
 * QQ: 781931404
 * 公司:江苏中天科技软件技术有限公司
 */
public class Fdv_StringRequest<T> extends Fdv_BaseRequest{
    public Fdv_StringRequest(Context pContext){
        super(pContext);
    }
    public void get(String url, finalFdv_CallBackListener<T> listener){
        StringRequest stringRequest=new StringRequest(Request.Method.GET, url, new Response.Listener<String>() {
            @Override
            public void onResponse(Stringresponse) {
                if(listener!=null){
                   listener.onSuccessResponse((T) response);
                }
            }
        }, new Response.ErrorListener() {
            @Override
            public voidonErrorResponse(VolleyError error) {
                if(listener!=null){
                   listener.onErrorResponse(error);
                }
            }
        });
        addRequest(stringRequest);
    }
}


          OK有了以上的几步骤,我们的对于StringRequest的get方法请求简单封装就完成了,有了这样的封装我们的功能实现就会变得代码稍微少了一点,当然我们现在的封装的功能还非常的弱,后面我这边会继续更新封装功能以及重构,让整个工具类变得更加使用。具体更新代码都会FastDev4Android项目中。后期二次封装的Volley框架代码会在Github库中更新,敬请期待~

        以上所有的功能测试代码如下:


@EActivity(R.layout.volley_test_layout)
public class VolleyTestActivity  extends BaseActivity{
    private static final StringTAG=VolleyTestActivity.class.toString();
    @ViewById
    LinearLayout top_bar_linear_back;
    @ViewById
    TextView top_bar_title,tv_result;
    @ViewById
    ImageView img_result;
    @ViewById
    Buttonbtn_string,btn_json,btn_image_request,btn_image_loader,btn_image_network,btn_string_post,btn_loader_list,btn_gson;
    @ViewById
    NetworkImageView img_result_network;
    private RequestQueue requestQueue;
    @Override
    protected void onCreate(BundlesavedInstanceState) {
        super.onCreate(savedInstanceState);
       requestQueue=Volley.newRequestQueue(this);
    }
   @Click({R.id.top_bar_linear_back,R.id.btn_string,R.id.btn_json,R.id.btn_image_request,R.id.btn_image_loader,R.id.btn_image_network,R.id.btn_string_post,R.id.btn_loader_list,R.id.btn_gson})
    public void backLinearClick(View view){
        switch (view.getId()){
            case R.id.top_bar_linear_back:
                this.finish();
                break;
            case R.id.btn_string:
                //获取字符串
                Log.d(TAG,"点击获取字符串...");
                new Fdv_StringRequest<String>(VolleyTestActivity.this).get("http://www.baidu.com",new Fdv_CallBackListener<String>() {
                    @Override
                    public void onSuccessResponse(String response) {
                       tv_result.setVisibility(View.VISIBLE);
                       img_result.setVisibility(View.GONE);
                       tv_result.setText(response.toString());
                    }
                    @Override
                    public void onErrorResponse(VolleyError error) {
 
                    }
                });
//                StringRequest stringRequest=new StringRequest(Request.Method.GET, "http://www.baidu.com",new Response.Listener<String>() {
//                    @Override
//                    public void onResponse(String response) {
//                       tv_result.setVisibility(View.VISIBLE);
//                       img_result.setVisibility(View.GONE);
//                       tv_result.setText(response.toString());
//                    }
//                }, new Response.ErrorListener(){
//                    @Override
//                    public void onErrorResponse(VolleyError error) {
//
//                    }
//                });
//               requestQueue.add(stringRequest);
                break;
            case R.id.btn_json:
                //获取json
                Log.d(TAG,"点击获取json...");
                JsonObjectRequest jsonObjectRequest=new JsonObjectRequest(Request.Method.GET
                        , "http://interface.zttmall.com/update/mallUpdate",null,new Response.Listener<JSONObject>() {
                    @Override
                    public void onResponse(JSONObject response) {
                        Gson gson=new Gson();
                       tv_result.setVisibility(View.VISIBLE);
                       img_result.setVisibility(View.GONE);
                       tv_result.setText(gson.fromJson(response.toString(),UpdateBean.class).toString());
                    }
                }, new Response.ErrorListener(){
                    @Override
                    public void onErrorResponse(VolleyError error) {
 
                    }
                });
               requestQueue.add(jsonObjectRequest);
                break;
            case R.id.btn_image_request:
                //获取图片
               //http:\/\/interface.zttmall.com\/Images\/upload\/image\/20150325\/20150325083110_0898.jpg
                Log.d(TAG,"点击获取图片...");
                ImageRequest imageRequest=new ImageRequest("http://interface.zttmall.com/Images/upload/image/20150325/20150325083110_0898.jpg"
                        , newResponse.Listener<Bitmap>() {
                    @Override
                    public void onResponse(Bitmap response) {
                       tv_result.setVisibility(View.GONE);
                       img_result.setVisibility(View.VISIBLE);
                       img_result.setImageBitmap(response);
                    }
                }, 0, 0,ImageView.ScaleType.FIT_XY, Bitmap.Config.ARGB_8888, newResponse.ErrorListener() {
                    @Override
                    public void onErrorResponse(VolleyError error) {
 
                    }
                });
                requestQueue.add(imageRequest);
                break;
            case R.id.btn_image_loader:
                //使用imageloader进行获取图片
                ImageLoader imageLoader=new ImageLoader(requestQueue, new Fdv_ImageCache());
               tv_result.setVisibility(View.GONE);
               img_result.setVisibility(View.VISIBLE);
                ImageLoader.ImageListener listener=ImageLoader.getImageListener(img_result,R.drawable.ic_loading,R.drawable.ic_loading);
               imageLoader.get("http://interface.zttmall.com//Images//upload//image//20150328//20150328105404_2392.jpg",listener);
                break;
            case R.id.btn_image_network:
                //采用NetworkImageView imageview控件
                ImageLoader network_imageLoader=new ImageLoader(requestQueue, new Fdv_ImageCache());
               img_result_network.setVisibility(View.VISIBLE);
               img_result_network.setImageUrl("http://interface.zttmall.com//Images//upload//image//20150325//20150325083214_8280.jpg",network_imageLoader);
                break;
            case R.id.btn_string_post:
                //修改Volley源代码,扩展StringRequest支持post参数设置
                Map<String,String>params=new HashMap<String,String>();
               params.put("username","zhangsan");
               params.put("password","12345");
                StringRequestpost_stringRequest=new StringRequest("http://10.18.3.123:8080/SalesWebTest/TestVolleyPost",new Response.Listener<String>() {
                    @Override
                    public void onResponse(String response) {
                       tv_result.setVisibility(View.VISIBLE);
                       img_result.setVisibility(View.GONE);
                       tv_result.setText(response.toString());
                    }
                }, new Response.ErrorListener(){
                    @Override
                    public void onErrorResponse(VolleyError error) {
 
                    }
                },params);
               requestQueue.add(post_stringRequest);
                break;
            case R.id.btn_loader_list:
                //进行使用ImageLoader加载图片列表
               openActivity(VolleyLoaderActivity_.class);
                break;
            case R.id.btn_gson:
                //使用扩展工具 GsonRequest进行请求
                GsonRequest<UpdateBean> gsonRequest=new GsonRequest<UpdateBean>("http://interface.zttmall.com/update/mallUpdate",new Response.Listener<UpdateBean>() {
                    @Override
                    public void onResponse(UpdateBean response) {
                       tv_result.setVisibility(View.VISIBLE);
                       img_result.setVisibility(View.GONE);
                       tv_result.setText(response.toString());
                    }
                }, new Response.ErrorListener(){
                    @Override
                    public void onErrorResponse(VolleyError error) {
 
                    }
                }, UpdateBean.class);
                requestQueue.add(gsonRequest);
                break;
        }
    }
    @AfterViews
    public void setViews(){
       top_bar_title.setText("Volley网络框架测试实例");
    }
}


整个功能测试功能点如下图:


().结束语:

         到此为止我们已经讲完了Volley框架进阶部分:POST请求参数修改,图片缓存器,使用最佳实践,二次封装等相关高级进阶。具体实例和框架注释过的全部代码已经上传到FastDev4Android项目中了。同时欢迎大家去Github站点进行clone或者下载浏览:

https://github.com/jiangqqlmj/FastDev4Android 同时欢迎大家starfork整个开源快速开发框架项目~

       最后对于Volley框架二次封装的代码库,我这边会继续进行更新,后面会放入单独的Git库中,库地址后面会放出来的,敬请期待~