Hello Am facing a particular problem in which I need to download images and display them onto a ListView
corresponding to their particular TextView's
. The code I have is successfully displaying the The TextView's
I need to display but I don't know how to display all these different images next to my text views in my ListView
.
After going through many threads in SO. The top answers are to solve this by 1. Lazy List 2. Universal Image Loader
I have gone through both the solutions. I downloaded Lazy List codes in which the URL's are hardcoded strings stored in an Array. What I would like to do is create my own Strings dynamically. Store them onto cache and display all the corresponding images.
Here is my code:
public class Tools_ListItemActivity extends ListActivity
{
private Context context;
String s;
private static final String TAG_POSTS = "posts";
private static final String TAG_MDNAME = "mdname";
private static final String TAG_UTCOST = "utcost";
private static final String TAG_IIMG= "iimg";
JSONArray posts = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
s=getIntent().getExtras().getString("url");
new ProgressTask(Tools_ListItemActivity.this).execute();
}
@Override
protected void onListItemClick(ListView l, View v, int position, long id) {
// TODO Auto-generated method stub
super.onListItemClick(l, v, position, id);
}
ArrayList<HashMap<String, String>> jsonlist = new ArrayList<HashMap<String, String>>();
ListView lv ;
private class ProgressTask extends AsyncTask<String, Void, Boolean> {
private ProgressDialog dialog;
public ProgressTask(ListActivity activity) {
Log.i("1", "Called");
context = activity;
dialog = new ProgressDialog(context);
}
/** progress dialog to show user that the backup is processing. */
/** application context. */
private Context context;
protected void onPreExecute() {
this.dialog.setMessage("Progress start");
this.dialog.show();
}
@Override
protected void onPostExecute(final Boolean success) {
if (dialog.isShowing()) {
dialog.dismiss();
}
ListAdapter adapter = new SimpleAdapter(context, jsonlist,
R.layout.activity_toolsitem, new String[] { TAG_IIMG, TAG_MDNAME, TAG_UTCOST }, new int[] {
R.id.imageViewUrl, R.id.mdname, R.id.utcost });
setListAdapter(adapter);
// selecting single ListView item
lv = getListView();
}
protected Boolean doInBackground(final String... args) {
JSONParser jParser = new JSONParser();
// getting JSON string from URL
JSONObject json = jParser.getJSONFromUrl(s);
try {
posts = json.getJSONArray(TAG_POSTS);
} catch (JSONException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
try
{
// looping through All Contacts
for(int i = 0; i < posts.length(); i++){
JSONObject c = posts.getJSONObject(i);
// Storing each json item in variable
String mdname = c.getString(TAG_MDNAME);
String utcost= c.getString(TAG_UTCOST);
String iimg=c.getString(TAG_IIMG);
//Forming the Url of the image to be shown in the list view
String imageUrl="My_App_URL"+iimg;
/* try {
String imageUrl="My_App_URL"+iimg;
ImageView imageView = (ImageView)findViewById(R.id.imageViewUrl);
Bitmap bitmap = BitmapFactory.decodeStream((InputStream)new URL(imageUrl).getContent());
imageView.setImageBitmap(bitmap);
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} */
// creating new HashMap
HashMap<String, String> map = new HashMap<String, String>();
// adding each child node to HashMap key => value
map.put(TAG_MDNAME, mdname);
map.put(TAG_UTCOST, utcost);
map.put(TAG_IIMG, iimg);
jsonlist.add(map);
} }catch (JSONException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
}
}
Here i have debugged and found out that imageUrl
gets formed correctly. Json
only returns the name of the jpg
so i append that to the URL and Store it in imageUrl
. The other two textviews are getting properly parsed and displayed. If any one can help me out in displaying the images in the image view too then it would be great. Thanks.
Update: I was able to solve my particular problem with the help of the link shared by Pankaj(https://github.com/AndroidBegin/Android-JSON-Parse-Images-and-Texts-Tutorial) and the concept knowledge shared by Raghunandan down below. Please go through these answers for a detailed explanation as well as implementation of Lazy loading. My apologies for not being able to reward an answer with bounty as i was away for two days.
I dont know about storing the images, as my app uses images from the APK. However I believe for displaying those images you want a custom Arrayadapter.
This inflates a layout for each item and places it in a list. This layout is defined by and XML layout you create and specify in its construction. You should try extending whatever adapter you currently use for your list view with a custom one that sets the image view according to the item.
I do this with ImageView.setImageResource(resource ID); But your mileage may vary. I have my images in the APK not sure how to display them from an external source
Here's how I load and cache images in a
ListView
that creates a contact list for the user. So imagine profile picture on the left, some text views on the right (which sounds close to the problem you're dealing with. Ignore the ugly debug tags and probably poor formatting (sorry). I guess this is kind of like LazyList but here's a detailed explanation in case anyone was confused.Step 1: Set Up Your Cache
In my approach I use an
LruCache
and aHashMap
to track which user's images I've downloaded. You'll see how its implemented later but the idea is to avoid downloading stuff from the server unless you have to. Then in youronCreate()
or some related method, initialize your cache.My next step is to add the default "empty image" bitmap to the cache in case I reach an entry that does not have a picture associated with it. That way I only have to process and add this bitmap once
Then its time to get the data you need for the list!
Step 2: Get The Data
Here's a borring
AsyncTask
that takes aJSONArray
of user data as an argument. I left out that part because it's pretty much just a basic HTTP download that doesn't need explanation. The getUsers method is where I start to put together what will be added to myListView
. What I do next is process the JSON downloaded from the server to create user objects that will be added it to a list of users that will be displayed.I associate the picture with the user object that will eventually be displayed. I figure this isn't a total waste of time since the image is pulled from the bitmap cache
If a picture exists in the cache it is returned, if not it is downloaded. For me, displaying users, each picture is cached according to userid so even if someone were to appear more than once in the list, there would only be one picture stored in the cache for that user.
The only thing left to do is find the
ImageView
in your adapter and set that view to the picture you associated with the object in your list.Do you want something easy to use? With take care of caching files, deleting the cache, release when the memory is at border line?
Try LazyList, check it out:
https://github.com/nicolasjafelle/LazyList
As it is explained, you only need to create the Singleton in your Application class or any other Activity or Fragment:
Then in your view that has the ImageView to display de Image you need to implement ImageProcessingCallback interface:
Finally you need to add this permission in your androidManifest.xml
And that's it. Then you have methods to clear the cache for ram cache or disk cache or both.
Lazy loading using Universal Imageloader. Replace the hardcoded urls with url of images.
Modify the below according to your requirements
What's LazyList?. Check this link for details.
MainActivity.java
activity_main.xml
LazyAdapter.java
row.xml
Add permission in manifest
Please try this with universal image loader