對Volley開源框架 進行封裝
Volley是Ficus Kirpatrick在Gooogle I/O 2013發布的一個處理和緩存網絡請求的庫,能使網絡通信更快,更簡單,更健壯。
Volley名稱的由來: a burst or emission of many things or a large amount at once。
該框架適用于大部分app應用,其特點在與方便頻繁與網絡交互,如:圖片加載,json解析等。
筆者對其進行封裝,使其在項目中能更加方便和實用,大大開發效率。使之能一句話加載網絡圖片,一句話解析json 。
我們來看一下源碼 volley.java
/* * Copyright (C) 2012 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.volley.toolbox; import android.content.Context; import android.content.pm.PackageInfo; import android.content.pm.PackageManager.NameNotFoundException; import android.net.http.AndroidHttpClient; import android.os.Build; import com.android.volley.Network; import com.android.volley.RequestQueue; import java.io.File; public class Volley { /** Default on-disk cache directory. */ private static final String DEFAULT_CACHE_DIR = "volley"; /** * Creates a default instance of the worker pool and calls {@link RequestQueue#start()} on it. * * @param context A {@link Context} to use for creating the cache dir. * @param stack An {@link HttpStack} to use for the network, or null for default. * @return A started {@link RequestQueue} instance. */ public static RequestQueue newRequestQueue(Context context, HttpStack stack) { File cacheDir = new File(context.getCacheDir(), DEFAULT_CACHE_DIR); String userAgent = "volley/0"; try { String packageName = context.getPackageName(); PackageInfo info = context.getPackageManager().getPackageInfo(packageName, 0); userAgent = packageName + "/" + info.versionCode; } catch (NameNotFoundException e) { } if (stack == null) { //用HttpUrlConnection 處理http請求 if (Build.VERSION.SDK_INT >= 9) { stack = new HurlStack(); } else { // Prior to Gingerbread, HttpUrlConnection was unreliable.用HttpClient處理網絡請求 // See: http://android-developers.blogspot.com/2011/09/androids-http-clients.html stack = new HttpClientStack(AndroidHttpClient.newInstance(userAgent)); } } //構建一個字節池 Network network = new BasicNetwork(stack); RequestQueue queue = new RequestQueue(new DiskBasedCache(cacheDir), network); queue.start(); return queue; } /** * Creates a default instance of the worker pool and calls {@link RequestQueue#start()} on it. * * @param context A {@link Context} to use for creating the cache dir. * @return A started {@link RequestQueue} instance. */ public static RequestQueue newRequestQueue(Context context) { return newRequestQueue(context, null); } }
package com.cn.framework.net; import android.content.Context; import android.widget.ImageView; import com.android.volley.RequestQueue; import com.android.volley.toolbox.ImageLoader; import com.android.volley.toolbox.ImageLoader.ImageCache; import com.android.volley.toolbox.ImageLoader.ImageContainer; import com.android.volley.toolbox.ImageLoader.ImageListener; import com.android.volley.toolbox.Volley; /** * 使用NetContext來訪問網絡,NetContext底部使用Volley作為通信框架 */ public class NetContext { /** 上下文 */ private Context context; /** 圖片請求隊列 */ private RequestQueue imageRequestQueue; /** json請求隊列 */ private RequestQueue jsonRequestQueue; /** 圖片ImageLoader */ private ImageLoader imageLoader; /** 圖片以及緩存LRU */ private ImageCache imageCache; /** LRU緩存的數量,為了防止內存溢出,一般不要超過60 */ private static final int LRU_CACHE_SIZE = 20; private static NetContext instance = null; /** * 構造函數 * * @param context android應用上下文 */ private NetContext(Context context){ this.context = context; this.jsonRequestQueue = Volley.newRequestQueue(context); this.imageRequestQueue = Volley.newRequestQueue(context); this.imageCache = new BitmapCache(LRU_CACHE_SIZE); this.imageLoader = new ImageLoader(imageRequestQueue, imageCache); } /** * 單例模式 * * @param context * @return NetUtil */ public static NetContext getInstance(Context context){ if (instance == null) { synchronized (NetContext.class) { if (instance == null) { instance = new NetContext(context); } } } return instance; } /** * 得到圖片加載器 * * @return ImageLoader */ public ImageLoader getImageLoader() { return imageLoader; } /** * 得到json的請求隊列 * @return RequestQueue */ public RequestQueue getJsonRequestQueue() { return jsonRequestQueue; } }
NetUtil.java 類 ,一句話解析Json,一句話加載網絡圖片
package com.cn.framework.util; import org.json.JSONArray; import org.json.JSONObject; import android.content.Context; import android.widget.ImageView; import com.android.volley.Response.ErrorListener; import com.android.volley.Response.Listener; import com.android.volley.toolbox.ImageLoader; import com.android.volley.toolbox.ImageLoader.ImageContainer; import com.android.volley.toolbox.ImageLoader.ImageListener; import com.android.volley.toolbox.JsonArrayRequest; import com.android.volley.toolbox.JsonObjectRequest; import com.kuaidian.framework.net.NetContext; public class NetUtil { /** * 防止工具類被實例化 */ private NetUtil(){ throw new AssertionError(); } /** * 加載圖片 * * @param context android應用上下文 * @param imageUrl 請求的圖片url * @param view 展示圖片的view * @param defaultImageResId 加載過程中的默認圖片資源Id,如果沒有則為0 * @param errorImageResId 加載過程中的錯誤圖片資源Id,如果沒有則為0 * @return ImageContainer 圖片請求和結果 */ public static ImageContainer loadImage(Context context, String imageUrl, ImageView view, int defaultImageResId, int errorImageResId){ NetContext netContext = NetContext.getInstance(context); ImageListener imgListener = ImageLoader.getImageListener(view, defaultImageResId, errorImageResId); return netContext.getImageLoader().get(imageUrl, imgListener); } /** * 以GET或者POST方式發送jsonObjectRequest * * @param context android應用上下文 * @param requestUrl 請求的Url * @param requestParameter 請求的參數,如果為null,則使用GET方法調用,否則使用POST方法調用 * @param listener 正確返回之后的lisenter * @param errorListener 錯誤返回的lisenter */ public static void sendJsonObjectRequest(Context context, String requestUrl, JSONObject requestParameter, Listener<JSONObject> listener, ErrorListener errorListener){ JsonObjectRequest request = new JsonObjectRequest(requestUrl, requestParameter, listener, errorListener); NetContext netContext = NetContext.getInstance(context); netContext.getJsonRequestQueue().add(request); } /** * 以GET方式發送jsonArrayRequest * * @param context android應用上下文 * @param requestUrl 請求的Url * @param listener 正確返回之后的lisenter * @param errorListener 錯誤返回的lisenter */ public static void sendJsonArrayRequest(Context context, String requestUrl, Listener<JSONArray> listener, ErrorListener errorListener){ JsonArrayRequest request = new JsonArrayRequest(requestUrl,listener, errorListener); NetContext netContext = NetContext.getInstance(context); netContext.getJsonRequestQueue().add(request); } }
Json解析接口 JsonParserInterface.java
package com.cn.framework.jsonparseinterface; import org.json.JSONObject; /** * jsonResonse的解析接口 */ public interface JsonParserInterface<T> { /** * @param result 返回的結果 * @param response 網絡傳遞進來的response */ void parseJson(T result,JSONObject response); }
package com.cn.framework.jsonparseimpl; import java.util.List; import org.json.JSONArray; import org.json.JSONObject; import com.kuaidian.framework.entity.Paper; import com.kuaidian.framework.jsonparseinterface.JsonParserInterface; public class PaperParser implements JsonParserInterface<List<Paper>> { private static PaperParser instance = null; private PaperParser(){} public synchronized static PaperParser getInstance(){ if (instance == null) { instance = new PaperParser(); } return instance; } @Override public void parseJson(List<Paper> list, JSONObject response) { try { JSONArray jsonArray = (JSONArray) response.get("data"); for (int i = 0; i < jsonArray.length(); i++) { JSONObject object = (JSONObject) jsonArray.get(i); int id = object.getInt("id"); String smallPic = object.getString("smallPic"); String title = object.getString("layoutpage"); String bigPic = object.getString("bigPic"); Paper newspaper = new Paper(); newspaper.setId(id); newspaper.setSmallPic(smallPic); newspaper.setLayoutpage(title); newspaper.setQi(periodId); newspaper.setBigPic(bigPic); list.add(newspaper); } } catch (Exception e) { e.printStackTrace(); } } }
解析Json時所需要用到的實體類 Paper.java
package com.cn.framework.entity; import java.util.Date; public class Paper { private int id; private Date date; private String bigPic; private String smallPic; private String bm; private String layoutpage; public Paper() { } public int getId() { return id; } public void setId(int id) { this.id = id; } public Date getDate() { return date; } public void setDate(Date date) { this.date = date; } public String getBigPic() { return bigPic; } public void setBigPic(String bigPic) { this.bigPic = bigPic; } public String getSmallPic() { return smallPic; } public void setSmallPic(String smallPic) { this.smallPic = smallPic; } public String getBm() { return bm; } public void setBm(String bm) { this.bm = bm; } public String getLayoutpage() { return layoutpage; } public void setLayoutpage(String layoutpage) { this.layoutpage = layoutpage; } @Override public String toString() { return "Newspaper [id=" + id + ", date=" + date + ", bigPic=" + bigPic + ", smallPic=" + smallPic + ", bm=" + bm + ", layoutpage=" + layoutpage + "]"; } }
在MainActivity.java中使用:
package com.cn.framework; import java.util.ArrayList; import java.util.List; import org.json.JSONObject; import android.app.Activity; import android.os.Bundle; import android.widget.ImageView; import com.android.volley.Response.ErrorListener; import com.android.volley.Response.Listener; import com.android.volley.VolleyError; import com.example.kuaidianframework.R; import com.kuaidian.framework.entity.Paper; import com.kuaidian.framework.jsonparseimpl.PaperParser; import com.kuaidian.framework.util.LogUtil; import com.kuaidian.framework.util.NetUtil; public class MainActivity extends Activity { private ImageView imageView; private List<Paper> papers = new ArrayList<Paper>(); @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); imageView = (ImageView) findViewById(R.id.imageView); testJsonRequest(); testImageRequset(); } //解析Json數據 private void testJsonRequest(){ String requestUrl = "http://42.51.16.158:8080/dsqy/action/phoneManager_getNewPaperByQi?type=1"; NetUtil.sendJsonObjectRequest(this, requestUrl, null, new Listener<JSONObject>(){ @Override public void onResponse(JSONObject response) { PaperParser newsPaperParser = PaperParser.getInstance(); //此處傳入papers對象,就將數據存在該對象中 newsPaperParser.parseJson(papers, response); for (int i = 0; i < papers.size(); i++) { LogUtil.info(MainActivity.class, papers.get(i).getBigPic()); } } }, new ErrorListener() { @Override public void onErrorResponse(VolleyError error) { //TODO } }); } //顯示網絡圖片 private void testImageRequset(){ //String imageUrl = "http://www.iqianyan.cc/simg/20140119/s_20140119195840.jpg"; String imageUrl = "http://b.hiphotos.baidu.com/pic/w%3D310/sign=9b24260fd53f8794d3ff4e2fe21a0ead/f636afc379310a55ba781b43b64543a98226102c.jpg"; NetUtil.loadImage(this, imageUrl, imageView, R.drawable.ic_launcher, 0); } }
不過在開發過程中也需要考慮到一些問題,比如:
1. 當圖片過多過大時,在ListView中滾動圖片錯位的問題。
2. 圖片過大,導致內存溢出等,需設置圖片一級、二級緩存問題。
來自:http://blog.csdn.net/gao_chun/article/details/34117083
本文由用戶 ygp8 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!