Volley与XUtils网络请求使用对比,心得,两者基本使用

         之前一直使用的Volley作为网络请求框架,它是Google 在2013年的I/O大会 上,发布的。Volley是Android平台上的网络通信库,能使网络通信更快,更简单,更健壮,同时扩展性很强。在用它之前我进行了简单的封装,因为Volley默认的请求线程生命周期伴随着Activity的周期,这有时并不能满足项目需要,so上代码:

  1     <span style="font-size:14px;"><span style="font-size:14px;">public class VolleyController extends Application  
  2     {  
  3         /* 
  4          * 网络请求TAG标签 
  5          */  
  6         public static final String TAG = "VolleyPatterns";  
  7           
  8         /* 
  9          * 创建请求队列 
 10          */  
 11         private RequestQueue requestQueue;  
 12           
 13         /* 
 14          * 创建单例模式对象 
 15          */  
 16         private static VolleyController volleyController;  
 17           
 18         private Context context;  
 19           
 20         @Override  
 21         public void onCreate()  
 22         {  
 23             super.onCreate();  
 24             volleyController = this;  
 25         }  
 26           
 27         /** 
 28          * 获得VolleyConroller的单例对象 
 29          */  
 30         public static synchronized VolleyController getInstance()  
 31         {  
 32             if (volleyController != null)  
 33             {  
 34                   
 35                 return volleyController;  
 36             }  
 37             else  
 38             {  
 39                 return volleyController = new VolleyController();  
 40             }  
 41         }  
 42           
 43         /** 
 44          * 获得消息队列对象 
 45          *  
 46          * @return 
 47          */  
 48         public RequestQueue getRequestQueue(Context context)  
 49         {  
 50             this.context = context;  
 51             if (requestQueue == null)  
 52             {  
 53                 synchronized (VolleyController.class)  
 54                 {  
 55                     if (requestQueue == null)  
 56                     {  
 57                         // LogUtils.i(TAG, "------getApplicationContext------" + getApplicationContext());  
 58                         requestQueue = Volley.newRequestQueue(context);  
 59                     }  
 60                 }  
 61                   
 62             }  
 63             return requestQueue;  
 64               
 65         }  
 66           
 67         /** 
 68          * 将请求放入消息队列中,tag是每个请求在消息队列的标签,方便对其经行控制 
 69          *  
 70          * @param request 
 71          * @param tag 
 72          */  
 73         public <T> void addToRequestQuere(Request<T> request, String tag)  
 74         {  
 75             request.setTag(TextUtils.isEmpty(tag) ? TAG : tag);  
 76             VolleyLog.d("Adding request to queue: %s", request.getUrl());  
 77             getRequestQueue(context).add(request);  
 78         }  
 79           
 80         /** 
 81          * 将请求放入消息队列中,tag是使用的是默认标签 
 82          *  
 83          * @param request 
 84          * @param tag 
 85          */  
 86         public <T> void addToRequestQuere(Request<T> request)  
 87         {  
 88             request.setTag(TAG);  
 89             getRequestQueue(context).add(request);  
 90             LogUtils.i(TAG, "网络请求已发出");  
 91               
 92         }  
 93           
 94         /** 
 95          * 通过tag取消网络请求对像 
 96          *  
 97          * @param tag 
 98          */  
 99           
100         public void canclePendingRequest(Object tag)  
101         {  
102             if (requestQueue != null)  
103             {  
104                 requestQueue.cancelAll(tag);  
105                 LogUtils.i(TAG, "网络请求已取消");  
106             }  
107         }</span>  
108     }</span>  

      里面的注释比较清楚,就不一一赘述了。在第一次进行网络请求时构建线程池,以后请求只是将Request对象放入线程池即可。不过这样是有风险的,如 果程序在运行中崩溃,后面就会连续崩溃,一直闪退到创建线程池的那个界面。不过也可以在每次网络请求时都创建一个消息队列,但是想想每进行网络请求都创建 一个线程池是多么奢侈,而且也会浪费不必要的资源。Volley中StringRequest其实是在项目中是用的比较多的,下面就是我使用 StringRequest示例:

 1     <span style="font-size:14px;"> /** 
 2          * 意见反馈接口 
 3          */  
 4         private void userFeedbackTask()  
 5         {  
 6             StringRequest stringRequest = new StringRequest(Request.Method.POST(请求类型), feedback(网络请求地址), new Listener<String>()  
 7             {  
 8                   
 9                 @Override  
10                 public void onResponse(String response)  
11                 {  
12                     Gson gson = new Gson();  
13                     OutJsonArrayJson outJsonArrayJson = gson.fromJson(response, new TypeToken<OutJsonArrayJson>()  
14                     {  
15                     }.getType());  
16                     if (outJsonArrayJson.getCode() == 200)  
17                     {  
18                         // 退出该页面  
19                         AppManager.getAppManager().finishActivity(getCurActivity());  
20                         ToastManagerUtils.show("反馈成功", getCurActivity());  
21                     }  
22                     ToastManagerUtils.show(outJsonArrayJson.getMsg(), getCurActivity());  
23                     dialog.dismiss();  
24                 }  
25             }, new ErrorListenerCallBack())  
26             {  
27                 @Override  
28                 protected Map<String, String> getParams()  
29                     throws AuthFailureError  
30                 {  
31                     Map<String, String> map = new HashMap<String, String>();  
32                     map.put("uid",  
33                         SharedPreferencesUtils.GetUserLoginDatailsValue(getCurActivity(), "GatherLuckUserDetails", "uid"));  
34                       
35                     map.put("pwd",  
36                         SharedPreferencesUtils.GetUserLoginDatailsValue(getCurActivity(), "GatherLuckUserDetails", "pwd"));  
37                       
38                     map.put("content", edActivityFeedbackInput.getText().toString().trim());  
39                     LogUtils.i(TAG,"意见反馈接口参数---->"+map.toString());  
40                     return map;  
41                 }  
42             };  
43             VolleyController.getInstance().addToRequestQuere(stringRequest);  
44         }</span>  

这是我项目中的一个"意见反馈接口"例子,写的一般希望大家多提意见。下来再看看请求图片示例:

 1     <span style="font-size:14px;">/** 
 2          * 获得用户头像 
 3          */  
 4         private void getNetWorkImage(final String url)  
 5         {  
 6             /** 
 7              * 使用ImageRequest加载网络图片 
 8              */  
 9             ImageRequest imageRequest = new ImageRequest(url, new Listener<Bitmap>()  
10             {  
11                   
12                 @Override  
13                 public void onResponse(Bitmap response)  
14                 {  
15                     rimgActivityDetailsOfMineHeadImage.setImageBitmap(response);  
16                 }  
17             }, 60, 100, Config.ARGB_8888, new ErrorListenerCallBack());  
18             VolleyController.getInstance().addToRequestQuere(imageRequest);  
19         }</span>  

这是我项目中获取用户头像的例子,将网络图片地址传入,返回Bitmap对象,这里 Bitmap默认32位ARGB位图,位图数越高,图片越逼真。60为Bitmap最大宽度,100为最大高度。以上就是Volley在项目中经常使用的 地方。不过比较悲催的一点是:Volley没有直接的文件上传请求,不过可以扩展的,网上有封装好的。

       下来我就说一下xUtils的基本使用,其实说起Xutils它很不错,但我不太习惯,用起来总感觉碍手碍脚的。各种封装的都很好,包含DbUtils模块,ViewUtils模块,HttpUtils模块,BitmapUtils模块。

        因为它封装的比较完善,我用的时候只是封装了BitmapUtils。上代码:

 1     <span style="font-size:14px;"> private void submitFeedbackTask()  
 2         {  
 3            try{  
 4       
 5             RequestParams requestParams = new RequestParams();  
 6             requestParams.addBodyParameter("act", "feedback");  
 7             requestParams.addBodyParameter("content", edActivityFeedbackInput.getText().toString().trim());  
 8             HttpUtils httpUtils = new HttpUtils();  
 9             httpUtils.send(HttpMethod.POST, QueryAddress.Feed_Back, requestParams, new RequestCallBack<String>()  
10             {  
11                   
12                 @Override  
13                 public void onFailure(HttpException arg0, String arg1)  
14                 {  
15                     // TODO Auto-generated method stub  
16                     ToastManagerUtils.show("提交失败", getCurActivity());  
17                     dialog.cancel();  
18                 }  
19                   
20                 @Override  
21                 public void onSuccess(ResponseInfo<String> arg0)  
22                 {  
23                     OutJsonArrayJson<String> outJsonArrayJson =  
24                         gson.fromJson(arg0.result, new TypeToken<OutJsonArrayJson<String>>()  
25                         {  
26                         }.getType());  
27                     if (outJsonArrayJson.getCode() == 200)  
28                     {  
29                         ToastManagerUtils.show("提交成功", getCurActivity());  
30                         AppManager.getAppManager().finishActivity(getCurActivity());  
31                     }  
32                     dialog.cancel();  
33                 }  
34                   
35                 @Override  
36                 public void onLoading(long total, long current, boolean isUploading)  
37                 {  
38                     dialog.show();  
39                 }  
40             });</span>  
41     <span style="font-size:14px;">}catch(Ex e){  
42     }  
43      }</span>  

这是我另一个项目的"意见反馈"网络请求,可以看出它已经将访问失败和成功封装。但是我一般在onFailure()里面做是否链接网络判断的。 下来再看看BitmapUtils的使用。

      这里我简单封装了一下,其实也就是借鉴的网上的;

  1 public class xUtilsImageLoader  
  2 {  
  3     private BitmapUtils bitmapUtils;  
  4       
  5     private Context mContext;  
  6       
  7     private View view;  
  8       
  9     // otherOrImage为true是设置view背景  
 10     private boolean otherOrImage;  
 11       
 12     @SuppressWarnings("unused")  
 13     public xUtilsImageLoader(Context context)  
 14     {  
 15         // TODO Auto-generated constructor stub  
 16         this.mContext = context;  
 17           
 18         bitmapUtils = new BitmapUtils(mContext);  
 19         bitmapUtils.configDefaultLoadingImage(R.drawable.bg_default_truth_words);// 正在加载时显示图片  
 20         bitmapUtils.configDefaultLoadFailedImage(R.drawable.bg_default_truth_words);// 加载失败时显示图片  
 21         bitmapUtils.configDefaultBitmapConfig(Bitmap.Config.RGB_565);// Bitmap的位图格式  
 22           
 23     }  
 24       
 25     /** 
 26      *  
 27      * @author sunglasses 
 28      * @category 鍥剧墖鍥炶皟鍑芥暟 
 29      */  
 30     public class CustomBitmapLoadCallBack extends DefaultBitmapLoadCallBack<ImageView>  
 31     {  
 32           
 33         @Override  
 34         public void onLoading(ImageView container, String uri, BitmapDisplayConfig config, long total, long current)  
 35         {  
 36         }  
 37           
 38         @Override  
 39         public void onLoadCompleted(ImageView container, String uri, Bitmap bitmap, BitmapDisplayConfig config,  
 40             BitmapLoadFrom from)  
 41         {  
 42             fadeInDisplayNormal(container, view, bitmap, otherOrImage);  
 43         }  
 44           
 45         @Override  
 46         public void onLoadFailed(ImageView container, String uri, Drawable drawable)  
 47         {  
 48             // TODO Auto-generated method stub  
 49               
 50         }  
 51     }  
 52       
 53     private static final ColorDrawable TRANSPARENT_DRAWABLE = new ColorDrawable(android.R.color.transparent);  
 54       
 55     /** 
 56      * @author sunglasses 
 57      * @category 鍥剧墖鍔犺浇鏁堟灉 
 58      * @param imageView 
 59      * @param bitmap 
 60      */  
 61       
 62     @SuppressLint("NewApi")  
 63     private void fadeInDisplayNormal(ImageView imageView, View view, Bitmap bitmap, boolean otherOrImage)  
 64     {  
 65         // 设置图片加载动画  
 66         final TransitionDrawable transitionDrawable =  
 67             new TransitionDrawable(new Drawable[] {TRANSPARENT_DRAWABLE,  
 68                 new BitmapDrawable(imageView.getResources(), bitmap)});  
 69         if (otherOrImage)  
 70         {  
 71             view.setBackground(transitionDrawable);  
 72         }  
 73         else  
 74         {  
 75             imageView.setImageDrawable(transitionDrawable);  
 76         }  
 77         transitionDrawable.startTransition(300);  
 78           
 79     }  
 80       
 81     public void display(View view, String url, boolean otherOrImage)  
 82     {  
 83         bitmapUtils.display(new ImageView(mContext), url, new CustomBitmapLoadCallBack());  
 84         this.view = view;  
 85         this.otherOrImage = otherOrImage;  
 86     }  
 87       
 88     public void clearCache()  
 89     {  
 90         bitmapUtils.clearMemoryCache();  
 91     }  
 92       
 93     public void clearCache(String url)  
 94     {  
 95         bitmapUtils.clearCache(url);  
 96     }  
 97       
 98     public void setFailedImage(int id)  
 99     {  
100         bitmapUtils.configDefaultLoadFailedImage(id);  
101     }  
102 }  

我发现有时候加载网络图片,有图片出不来的问题。而且它是有图片缓存的。让人真的很不爽。原生的BitmapUtils不能传入自定义View,比如常见 的RoundImageView等。我看同事的是写回调来获得Bitmap对象,我是直接将自定义View传入,通过otherOrImage这个 boolean判断的,有点偷奸耍滑的感觉。其实大家也可以看看Glide这个图片请求框架,很不错的。好了就到这吧,该下班了。其实都是些比较基础的, 这也是受到了工作年龄的限制。希望以后可以给大家带来些有用的。反正努力就是了。

原文地址:https://www.cnblogs.com/huolongluo/p/5808295.html