Volley is an HTTP library that makes networking for Android apps easier and most importantly, faster. Volley is available through the open AOSP repository.
Volley offers the following benefits:
- Automatic scheduling of network requests.
- Multiple concurrent network connections.
- Transparent disk and memory response caching with standard HTTP cache coherence.
- Support for request prioritization.
- Cancellation request API. You can cancel a single request, or you can set blocks or scopes of requests to cancel.
- Ease of customization, for example, for retry and backoff.
- Strong ordering that makes it easy to correctly populate your UI with data fetched asynchronously from the network.
- Debugging and tracing tools.
First we need to download Volley framework as a library and add it to our project.
Clone the below url
git clone https: //android.googlesource.com/platform/frameworks/volley |
Now you will get a volley project downloaded.
I assume that you have created a Android Studio Project and opened it.
Now from that Window, Click File Menu -> New -> Import Module and Select Volley project we just downloaded.
We can see a Module Name while importing. You need to use this name in the gradle file to add the Volley library to your project.
My gradle file is looking like this.
dependencies { compile fileTree(dir: 'libs' , include: [ '*.jar' ]) testCompile 'junit:junit:4.12' compile 'com.android.support:appcompat-v7:23.2.1' compile 'com.android.support:design:23.2.1' compile 'com.google.code.gson:gson:1.7.2' compile project( ':volley' ) } |
OR
Add Dependency
Add this dependency in build.gradle.
compile 'com.android.volley:volley:1.0.0' |
Create a Singleton class for handling Volley requests.
package com.coderzheaven.volleydemo; import android.content.Context; import android.graphics.Bitmap; import android.support.v4.util.LruCache; import com.android.volley.Request; import com.android.volley.RequestQueue; import com.android.volley.toolbox.ImageLoader; import com.android.volley.toolbox.Volley; public class MySingleton { private static MySingleton mInstance; private RequestQueue mRequestQueue; private ImageLoader mImageLoader; private static Context mCtx; private MySingleton(Context context) { mCtx = context; mRequestQueue = getRequestQueue(); mImageLoader = new ImageLoader(mRequestQueue, new ImageLoader.ImageCache() { private final LruCache<String, Bitmap> cache = new LruCache<String, Bitmap>( 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 MySingleton getInstance(Context context) { if (mInstance == null ) { mInstance = new MySingleton(context); } return mInstance; } public RequestQueue getRequestQueue() { if (mRequestQueue == null ) { // getApplicationContext() is key, it keeps you from leaking the // Activity or BroadcastReceiver if someone passes one in. mRequestQueue = Volley.newRequestQueue(mCtx.getApplicationContext()); } return mRequestQueue; } public <T> void addToRequestQueue(Request<T> req) { getRequestQueue().add(req); } public ImageLoader getImageLoader() { return mImageLoader; } } |
Send a simple String request
Volley provides a convenience method Volley.newRequestQueue that sets up a RequestQueue for you, using default values, and starts the queue.
// Request a string response from the provided URL. StringRequest stringRequest = new StringRequest(Request.Method.GET, url, new Response.Listener<String>() { @Override public void onResponse(String response) { Log.i(TAG, response.substring( 0 , 500 )); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { Log.e(TAG, "Error :" + error.getLocalizedMessage()); } }); stringRequest.setTag(queueTAG); // Add the request to the RequestQueue. mRequestQueue.add(stringRequest); |
Simple Request With Cache
A RequestQueue needs two things to do its job: a network to perform transport of the requests, and a cache to handle caching.
// Instantiate the cache Cache cache = new DiskBasedCache(getCacheDir(), 1024 * 1024 ); // 1MB cap // Set up the network to use HttpURLConnection as the HTTP client. Network network = new BasicNetwork( new HurlStack()); // Instantiate the RequestQueue with the cache and network. mRequestQueue = new RequestQueue(cache, network); // Start the queue mRequestQueue.start(); // Formulate the request and handle the response. StringRequest stringRequest = new StringRequest(Request.Method.GET, url, new Response.Listener<String>() { @Override public void onResponse(String response) { Log.i(TAG, "simpleRequestWithNetworkCache : " + response.substring( 0 , 500 )); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { Log.e(TAG, "(simpleRequestWithNetworkCache) Error :" + error.getLocalizedMessage()); } }); // Add the request to the RequestQueue. mRequestQueue.add(stringRequest); |
Download an Image
Method 1
// Retrieves an image specified by the URL, displays it in the UI. ImageRequest request = new ImageRequest(IMAGE_URL, new Response.Listener<Bitmap>() { @Override public void onResponse(Bitmap bitmap) { mImageView.setImageBitmap(bitmap); } }, 0 , 0 , null , new Response.ErrorListener() { public void onErrorResponse(VolleyError error) { mImageView.setImageResource(R.drawable.no_image); } }); // Access the RequestQueue through your singleton class. MySingleton.getInstance( this ).addToRequestQueue(request); |
Method 2
// Get the ImageLoader through your singleton class. mImageLoader = MySingleton.getInstance( this ).getImageLoader(); // Set the URL of the image that should be loaded into this view, and // specify the ImageLoader that will be used to make the request. mNetworkImageView.setImageUrl(IMAGE_URL, mImageLoader); |
Method 3 – Load Image with DiskCache
ImageLoader mImageLoader = new ImageLoader(mRequestQueue, new LruBitmapCache( LruBitmapCache.getCacheSize(getApplicationContext()))); mImgCont = mImageLoader.get(IMAGE_URL, ImageLoader.getImageListener(mImageView, R.drawable.android, R.drawable.no_image)); mImageView.setImageBitmap(mImgCont.getBitmap()); |
Load Local Image Without Listener
// Get the ImageLoader through your singleton class. mImageLoader = MySingleton.getInstance( this ).getImageLoader(); mImgCont = mImageLoader.get(IMAGE_URL, ImageLoader.getImageListener(mImageView, R.drawable.android, R.drawable.no_image)); mImageView.setImageBitmap(mImgCont.getBitmap()); |
Load Local Image With Listener
// Get the ImageLoader through your singleton class. mImageLoader = MySingleton.getInstance( this ).getImageLoader(); mImgCont = mImageLoader.get(IMAGE_URL, ImageLoader.getImageListener(mImageView, R.drawable.android, R.drawable.no_image)); mImageLoader.get(IMAGE_URL, new ImageLoader.ImageListener() { @Override public void onResponse(ImageLoader.ImageContainer response, boolean isImmediate) { mImageView.setImageBitmap(response.getBitmap()); } @Override public void onErrorResponse(VolleyError error) { mImageView.setImageResource(R.drawable.no_image); } }); |
Send GET Request
Volley provides the following classes for JSON requests:
- JsonArrayRequest—A request for retrieving a JSONArray response body at a given URL.
- JsonObjectRequest—A request for retrieving a JSONObject response body at a given URL, allowing for an optional JSONObject to be passed in as part of the request body.
Both classes are based on the common base class JsonRequest.
JsonObjectRequest jsObjRequest = new JsonObjectRequest (Request.Method.GET, jsonUrl, null , new Response.Listener<JSONObject>() { @Override public void onResponse(JSONObject response) { try { Log.i(TAG, "Site : " + response.getString( "Site" )); } catch (JSONException e) { } } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { Log.i(TAG, "requestJSON :" + error.getLocalizedMessage());; } }); // Access the RequestQueue through your singleton class. MySingleton.getInstance( this ).addToRequestQueue(jsObjRequest); |
Sending POST Requests
// Sending POST Request void sendPOSTRequest(){ // Post params to be sent to the server HashMap<String, String> params = new HashMap<String, String>(); params.put( "key" , "value" ); JsonObjectRequest req = new JsonObjectRequest(postJsonUrl, new JSONObject(params), new Response.Listener<JSONObject>() { @Override public void onResponse(JSONObject response) { try { VolleyLog.v( "Response:%n %s" , response.toString( 4 )); } catch (JSONException e) { e.printStackTrace(); } } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { VolleyLog.e( "Error: " , error.getMessage()); } }); // Access the RequestQueue through your singleton class. MySingleton.getInstance( this ).addToRequestQueue(req); } |
Custom GSON request
You can check this post on How to Create Custom GSON request with Volley.
Here is the complete MainActivity Class.
package com.coderzheaven.volleydemo; import android.graphics.Bitmap; import android.os.Bundle; import android.support.v7.app.AppCompatActivity; import android.support.v7.widget.Toolbar; import android.util.Log; import android.view.View; import android.widget.AdapterView; import android.widget.ArrayAdapter; import android.widget.ImageView; import android.widget.ListView; import android.widget.ProgressBar; import android.widget.TextView; import com.android.volley.Cache; import com.android.volley.Network; import com.android.volley.Request; import com.android.volley.RequestQueue; import com.android.volley.Response; import com.android.volley.VolleyError; import com.android.volley.toolbox.BasicNetwork; import com.android.volley.toolbox.DiskBasedCache; import com.android.volley.toolbox.HurlStack; import com.android.volley.toolbox.ImageLoader; import com.android.volley.toolbox.ImageRequest; import com.android.volley.toolbox.JsonObjectRequest; import com.android.volley.toolbox.NetworkImageView; import com.android.volley.toolbox.StringRequest; import org.json.JSONException; import org.json.JSONObject; public class MainActivity extends AppCompatActivity implements AdapterView.OnItemClickListener, View.OnClickListener { public static final String TAG = "VolleyDemo" ; public static final String queueTAG = "Req1" ; ProgressBar mPb; TextView mTextView; ListView mListView; ImageView mImageView; ImageLoader mImageLoader; NetworkImageView mNetworkImageView; ImageLoader.ImageContainer mImgCont; RequestQueue mRequestQueue = null ; private static final String IMAGE_URL = "http://cdn3.pcadvisor.co.uk/cmsdata/features/3420161/Android_800_thumb800.jpg" ; private static final String url = "http://www.coderzheaven.com" ; private static final String jsonUrl = "http://echo.jsontest.com/Site/coderzheven.com/demo/Volley" ; String[] listValues = new String[]{ "Simple Request" , "Simple Request With Network Cache" , "Download Image" , "Loading Local Image without Listener" , "Loading Local Image with Listener" , "Loading Image with Custom LRU Disk Cache" , "Request JSON" , "Custom GSON Request" }; @Override protected void onCreate(Bundle savedInstanceState) { super .onCreate(savedInstanceState); setContentView(R.layout.activity_main); Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); setSupportActionBar(toolbar); mPb = (ProgressBar) findViewById(R.id.toolbar_progress_bar); mTextView = (TextView) findViewById(R.id.tv); mListView = (ListView) findViewById(R.id.list1); mImageView = (ImageView) findViewById(R.id.image1); mNetworkImageView = (NetworkImageView) findViewById(R.id.networkImageView); mNetworkImageView.setOnClickListener( this ); mImageView.setOnClickListener( this ); // Get a RequestQueue mRequestQueue = MySingleton.getInstance( this .getApplicationContext()). getRequestQueue(); ArrayAdapter<String> adapter = new ArrayAdapter<String>( this , android.R.layout.simple_list_item_1, android.R.id.text1, listValues); // Assign adapter to ListView mListView.setAdapter(adapter); mListView.setOnItemClickListener( this ); //hide the progreebar initially hidePb(); } void showPb() { mPb.setVisibility(View.VISIBLE); } void hidePb() { mPb.setVisibility(View.GONE); } void simpleRequest() { showPb(); // Request a string response from the provided URL. StringRequest stringRequest = new StringRequest(Request.Method.GET, url, new Response.Listener<String>() { @Override public void onResponse(String response) { mTextView.setVisibility(View.VISIBLE); Log.i(TAG, response.substring( 0 , 500 )); mTextView.setText( "SimpleRequest : Response Received" ); hidePb(); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { mTextView.setVisibility(View.VISIBLE); Log.e(TAG, "Error :" + error.getLocalizedMessage()); mTextView.setText( "SimpleRequest : Response Error" ); hidePb(); } }); stringRequest.setTag(queueTAG); // Add the request to the RequestQueue. mRequestQueue.add(stringRequest); } void simpleRequestWithNetworkCache() { showPb(); // Instantiate the cache Cache cache = new DiskBasedCache(getCacheDir(), 1024 * 1024 ); // 1MB cap // Set up the network to use HttpURLConnection as the HTTP client. Network network = new BasicNetwork( new HurlStack()); // Instantiate the RequestQueue with the cache and network. mRequestQueue = new RequestQueue(cache, network); // Start the queue mRequestQueue.start(); // Formulate the request and handle the response. StringRequest stringRequest = new StringRequest(Request.Method.GET, url, new Response.Listener<String>() { @Override public void onResponse(String response) { mTextView.setVisibility(View.VISIBLE); Log.i(TAG, "simpleRequestWithNetworkCache : " + response.substring( 0 , 500 )); mTextView.setText( "SimpleRequestWithNetworkCache : Response Received" ); hidePb(); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { mTextView.setVisibility(View.VISIBLE); mTextView.setText( "SimpleRequestWithNetworkCache : Response Error" ); Log.e(TAG, "(simpleRequestWithNetworkCache) Error :" + error.getLocalizedMessage()); hidePb(); } }); // Add the request to the RequestQueue. mRequestQueue.add(stringRequest); } void downloadImage() { showPb(); mNetworkImageView.setVisibility(View.GONE); mImageView.setVisibility(View.VISIBLE); // Retrieves an image specified by the URL, displays it in the UI. ImageRequest request = new ImageRequest(IMAGE_URL, new Response.Listener<Bitmap>() { @Override public void onResponse(Bitmap bitmap) { mImageView.setImageBitmap(bitmap); hidePb(); } }, 0 , 0 , null , new Response.ErrorListener() { public void onErrorResponse(VolleyError error) { mImageView.setImageResource(R.drawable.no_image); hidePb(); } }); // Access the RequestQueue through your singleton class. MySingleton.getInstance( this ).addToRequestQueue(request); } // You can use ImageLoader by itself to display an Image. void loadLocalImageWithoutListener() { showPb(); mNetworkImageView.setVisibility(View.GONE); mImageView.setVisibility(View.VISIBLE); // Get the ImageLoader through your singleton class. mImageLoader = MySingleton.getInstance( this ).getImageLoader(); mImgCont = mImageLoader.get(IMAGE_URL, ImageLoader.getImageListener(mImageView, R.drawable.android, R.drawable.no_image)); mImageView.setImageBitmap(mImgCont.getBitmap()); hidePb(); } // You can use ImageLoader by itself to display an Image. void loadLocalImageWithListener() { showPb(); mNetworkImageView.setVisibility(View.GONE); mImageView.setVisibility(View.VISIBLE); // Get the ImageLoader through your singleton class. mImageLoader = MySingleton.getInstance( this ).getImageLoader(); mImgCont = mImageLoader.get(IMAGE_URL, ImageLoader.getImageListener(mImageView, R.drawable.android, R.drawable.no_image)); mImageLoader.get(IMAGE_URL, new ImageLoader.ImageListener() { @Override public void onResponse(ImageLoader.ImageContainer response, boolean isImmediate) { mImageView.setImageBitmap(response.getBitmap()); hidePb(); } @Override public void onErrorResponse(VolleyError error) { mImageView.setImageResource(R.drawable.no_image); hidePb(); } }); } void downloadImage2() { showPb(); mImageView.setVisibility(View.GONE); mNetworkImageView.setVisibility(View.VISIBLE); // Get the ImageLoader through your singleton class. mImageLoader = MySingleton.getInstance( this ).getImageLoader(); // Set the URL of the image that should be loaded into this view, and // specify the ImageLoader that will be used to make the request. mNetworkImageView.setImageUrl(IMAGE_URL, mImageLoader); hidePb(); } void loadImageWithDiskCache() { showPb(); mNetworkImageView.setVisibility(View.GONE); mImageView.setVisibility(View.VISIBLE); ImageLoader mImageLoader = new ImageLoader(mRequestQueue, new LruBitmapCache( LruBitmapCache.getCacheSize(getApplicationContext()))); mImgCont = mImageLoader.get(IMAGE_URL, ImageLoader.getImageListener(mImageView, R.drawable.android, R.drawable.no_image)); mImageView.setImageBitmap(mImgCont.getBitmap()); hidePb(); } void requestJSON() { showPb(); JsonObjectRequest jsObjRequest = new JsonObjectRequest (Request.Method.GET, jsonUrl, null , new Response.Listener<JSONObject>() { @Override public void onResponse(JSONObject response) { mTextView.setVisibility(View.VISIBLE); try { Log.i(TAG, "Site : " + response.getString( "Site" )); mTextView.setText( "Site : " + response.getString( "Site" ) + "\n" + "Demo : " + response.getString( "demo" )); } catch (JSONException e) { } hidePb(); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { mTextView.setVisibility(View.VISIBLE); Log.i(TAG, "requestJSON :" + error.getLocalizedMessage()); mTextView.setText( "RequestJSON :JSON Error" ); hidePb(); } }); // Access the RequestQueue through your singleton class. MySingleton.getInstance( this ).addToRequestQueue(jsObjRequest); } private Response.Listener<MyGson> createSuccessListener() { return new Response.Listener<MyGson>() { @Override public void onResponse(MyGson response) { Log.i(TAG, "Response : " + response.getSite()); mTextView.setVisibility(View.VISIBLE); mTextView.setText( "Site : " + response.getSite()); hidePb(); } }; } private Response.ErrorListener createErrorListener() { return new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { Log.i(TAG, "Error : " + error.getLocalizedMessage()); mTextView.setVisibility(View.VISIBLE); mTextView.setText( "Error : " + error.getLocalizedMessage()); hidePb(); } }; } public void customGSONRequest() { showPb(); GsonRequest<MyGson> myReq = new GsonRequest<MyGson>(jsonUrl, MyGson. class , null , createSuccessListener(), createErrorListener()); mRequestQueue.add(myReq); } @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { switch (position) { case 0 : simpleRequest(); break ; case 1 : simpleRequestWithNetworkCache(); break ; case 2 : downloadImage(); break ; case 3 : loadLocalImageWithoutListener(); break ; case 4 : downloadImage2(); break ; case 5 : loadImageWithDiskCache(); break ; case 6 : requestJSON(); break ; default : customGSONRequest(); break ; } } @Override protected void onStop() { super .onStop(); if (mRequestQueue != null ) { mRequestQueue.cancelAll(queueTAG); Log.i(TAG, "Cancelled : " + queueTAG); } } @Override public void onClick(View v) { v.setVisibility(View.GONE); } } |
Layouts
Layout – activity_main.xml
<? xml version = "1.0" encoding = "utf-8" ?> < android.support.design.widget.CoordinatorLayout xmlns:android = "http://schemas.android.com/apk/res/android" xmlns:app = "http://schemas.android.com/apk/res-auto" xmlns:tools = "http://schemas.android.com/tools" android:layout_width = "match_parent" android:layout_height = "match_parent" android:fitsSystemWindows = "true" tools:context = "com.coderzheaven.volleydemo.MainActivity" > < android.support.design.widget.AppBarLayout android:layout_width = "match_parent" android:layout_height = "wrap_content" android:theme = "@style/AppTheme.AppBarOverlay" > < android.support.v7.widget.Toolbar android:id = "@+id/toolbar" android:layout_width = "match_parent" android:layout_height = "?attr/actionBarSize" android:background = "?attr/colorPrimary" app:popupTheme = "@style/AppTheme.PopupOverlay" > < ProgressBar android:id = "@+id/toolbar_progress_bar" android:layout_width = "30dp" android:layout_height = "30dp" android:layout_gravity = "right" android:layout_marginRight = "10dp" android:indeterminateTint = "#FFFFFF" android:indeterminateTintMode = "src_in" /> </ android.support.v7.widget.Toolbar > </ android.support.design.widget.AppBarLayout > < include layout = "@layout/content_main" /> </ android.support.design.widget.CoordinatorLayout > |
The Layout – content_main.xml
<? xml version = "1.0" encoding = "utf-8" ?> < RelativeLayout xmlns:android = "http://schemas.android.com/apk/res/android" xmlns:app = "http://schemas.android.com/apk/res-auto" xmlns:tools = "http://schemas.android.com/tools" android:layout_width = "match_parent" android:layout_height = "match_parent" android:paddingBottom = "@dimen/activity_vertical_margin" android:paddingLeft = "@dimen/activity_horizontal_margin" android:paddingRight = "@dimen/activity_horizontal_margin" android:paddingTop = "@dimen/activity_vertical_margin" app:layout_behavior = "@string/appbar_scrolling_view_behavior" tools:context = "com.coderzheaven.volleydemo.MainActivity" tools:showIn = "@layout/activity_main" > < android.support.v7.widget.ListViewCompat android:id = "@+id/list1" android:layout_width = "match_parent" android:layout_height = "wrap_content" android:layout_alignParentTop = "true" android:layout_marginBottom = "10dp" android:scrollIndicators = "right" android:scrollbars = "vertical" /> < TextView android:id = "@+id/tv" android:layout_width = "match_parent" android:layout_height = "wrap_content" android:layout_alignParentBottom = "true" android:layout_marginTop = "5dp" android:visibility = "gone" android:background = "@android:color/holo_green_light" android:padding = "5dp" android:textColor = "@android:color/white" /> < android.support.v7.widget.AppCompatImageView android:id = "@+id/image1" android:layout_width = "match_parent" android:layout_height = "wrap_content" android:layout_centerInParent = "true" /> < com.android.volley.toolbox.NetworkImageView android:id = "@+id/networkImageView" android:layout_width = "match_parent" android:layout_height = "wrap_content" android:layout_centerInParent = "true" /> </ RelativeLayout > |
All Done.
You can download the complete Android Studio Source Code from here.
Pingback: Uploading audio, video or image files from Android to server – CoderzHeaven