I'm developing an Android app but I'm a newbie and I got stuck...
My ListView single element has an ImageView and some TextViews, but sometimes (when I scroll the page and there are more than 7-8 elements) it doesn't display the right image in the right row.
I'm using a custom Image Loader to manage the downloaded images.
Here's my Adapter:
public class AddVideogameActivityAdapter extends BaseAdapter {
private ArrayList<Videogame> videogames;
private Typeface typefaceMedium;
private Typeface typefaceLight;
private ImageLoader loader;
private LayoutInflater mInflater;
public AddVideogameActivityAdapter(Context context, ArrayList<Videogame> results) {
videogames = results;
mInflater = LayoutInflater.from(context);
typefaceMedium = Typeface.createFromAsset(context.getAssets(), "Roboto-Medium.ttf");
typefaceLight = Typeface.createFromAsset(context.getAssets(), "Roboto-Light.ttf");
loader = new ImageLoader(context);
}
public int getCount() {
return videogames.size();
}
public Object getItem(int position) {
return videogames.get(position);
}
public long getItemId(int position) {
return position;
}
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder;
if (convertView == null) {
convertView = mInflater.inflate(R.layout.list_element,null);
holder = new ViewHolder();
holder.imgView = (ImageView) convertView.findViewById(R.id.thumbView);
holder.txtName = (TextView) convertView.findViewById(R.id.elementView);
holder.txtPlatform = (TextView) convertView.findViewById(R.id.elementView2);
convertView.setTag(holder);
}
else {
holder = (ViewHolder) convertView.getTag();
}
try {
Videogame vgame = (Videogame) videogames.get(position);
holder.txtName.setText(vgame.getTitle());
holder.txtName.setTypeface(typefaceMedium);
holder.txtPlatform.setText(videogames.get(position).getPlatform());
holder.txtPlatform.setTypeface(typefaceLight);
holder.imgUrl = videogames.get(position).getImage();
loader.display(holder.imgUrl, holder.imgView, R.drawable.youtube_icon);
}
catch (Exception e) {
e.printStackTrace();
Log.e(com.example.ludos2_0.MainActivity.TAG,
"Exception: " + e.getLocalizedMessage());
}
return convertView;
}
static class ViewHolder {
TextView txtName;
TextView txtPlatform;
public String imgUrl;
ImageView imgView;
}
}
Sorry for my english and thank you for your help!
EDIT:
Here's also the Loader:
public class ImageLoader implements ComponentCallbacks2 {
private TCLruCache cache;
public ImageLoader(Context context) {
ActivityManager am = (ActivityManager) context.getSystemService(
Context.ACTIVITY_SERVICE);
int memoryClass = am.getMemoryClass() * 1024 * 1024;
cache = new TCLruCache(memoryClass);
}
public void display(String url, ImageView imageview, int defaultresource) {
imageview.setImageResource(defaultresource);
Bitmap image = cache.get(url);
if (image != null) {
imageview.setImageBitmap(image);
}
else {
new SetImageTask(imageview).execute(url);
}
}
private class TCLruCache extends LruCache<String, Bitmap> {
public TCLruCache(int maxSize) {
super(maxSize);
}
}
private class SetImageTask extends AsyncTask<String, Void, Integer> {
private ImageView imageview;
private Bitmap bmp;
public SetImageTask(ImageView imageview) {
this.imageview = imageview;
}
#Override
protected Integer doInBackground(String... params) {
String url = params[0];
try {
bmp = getBitmapFromURL(url);
if (bmp != null) {
cache.put(url, bmp);
}
else {
return 0;
}
} catch (Exception e) {
e.printStackTrace();
return 0;
}
return 1;
}
#Override
protected void onPostExecute(Integer result) {
if (result == 1) {
imageview.setImageBitmap(bmp);
}
super.onPostExecute(result);
}
private Bitmap getBitmapFromURL(String src) {
try {
URL url = new URL(src);
HttpURLConnection connection
= (HttpURLConnection) url.openConnection();
connection.setDoInput(true);
connection.connect();
InputStream input = connection.getInputStream();
Bitmap myBitmap = BitmapFactory.decodeStream(input);
return myBitmap;
} catch (IOException e) {
e.printStackTrace();
return null;
}
}
}
}
RE-EDIT
Activity code:
public class AddVideogameActivity extends ListActivity {
private TextView searchField = null;
private final Handler handler = new Handler();
private ArrayList<Videogame> videogamesList = null;
private static AddVideogameActivity mContext = null;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_add_book);
mContext = this;
searchField = (TextView) findViewById(R.id.searchField);
searchField.setMaxLines(1);
searchField.setOnFocusChangeListener(new OnFocusChangeListener() {
#Override
public void onFocusChange(View v, boolean hasFocus) {
searchField.setHint("");
}
});
// Setup the list view and its listener
getListView().setOnItemClickListener(new OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
Log.d(MainActivity.TAG,
"AddBookActivity ---> AddButton:onClick()");
// Sets typefaces for TextView
String videogameId = videogamesList.get(position).getId();
String videogameName = videogamesList.get(position).getTitle();
String thumbnail = videogamesList.get(position).getThumbnail();
String description = videogamesList.get(position)
.getDescription();
String image = videogamesList.get(position).getImage();
String platform = videogamesList.get(position).getPlatform();
if (videogameName != null && videogameName.length() > 0
&& thumbnail != null && thumbnail.length() > 0
&& description != null && description.length() > 0
&& image != null && image.length() > 0
&& platform != null && platform.length() > 0) {
if (ListsManager.getInstance().addVideogame(
new Videogame(videogameId, videogameName,
thumbnail, image, description, platform)) == 0) {
Log.d(MainActivity.TAG,
"AddBookActivity --> Videogame:[" + videogameId
+ "#" + videogameName + "]");
Toast toast = Toast.makeText(mContext, "["
+ videogameName + "] Saved !",
Toast.LENGTH_LONG);
toast.show();
} else {
Log.e(MainActivity.TAG,
"AddBookActivity --> Error ! Videogame already in the list ! ");
Toast toast = Toast.makeText(mContext,
"Error! Videogame already in the list!",
Toast.LENGTH_LONG);
toast.show();
}
} else {
Log.e(MainActivity.TAG,
"AddBookActivity --> Error ! Invalid Videogame Name or Thumbnail or Id or Deck");
Toast toast = Toast
.makeText(
mContext,
"Error ! Invalid Videogame Name or Thumbnail or Id or Deck",
Toast.LENGTH_LONG);
toast.show();
}
Intent newIntent = new Intent(getApplicationContext(),
MainActivity.class);
startActivity(newIntent);
}
});
// Setup the search button and its listener
Button searchButton = (Button) findViewById(R.id.searchButton);
searchButton.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
Log.d(com.example.ludos2_0.MainActivity.TAG, "Search Game ...");
String searchInputString = searchField.getText().toString();
if (searchInputString != null && searchInputString.length() > 0) {
try {
String requestURL = ("http://www.giantbomb.com/api/search/?api_key=fcf60d6d67b98b0d17b3905d1a90b3fd31ed1e8e&format=json&query="
+ Uri.encode(searchInputString) + "&resources=game");
// String requestURL =
// String.format("https://gdata.youtube.com/feeds/api/videos?v=2&alt=jsonc&category=Music&orderby=relevance&q=%s",Uri.encode(searchInputString));
Log.d(com.example.ludos2_0.MainActivity.TAG, requestURL);
DownloadGiantBombJSONData giantbombAsyncTask = new DownloadGiantBombJSONData();
giantbombAsyncTask.execute(new String[] { requestURL });
} catch (Exception e) {
e.printStackTrace();
}
}
}
});
if (videogamesList == null)
videogamesList = new ArrayList<Videogame>();
else
updateVideogamesListView(videogamesList);
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.add_book, menu);
return true;
}
#Override
protected void onResume() {
super.onResume();
}
#Override
protected void onPause() {
super.onPause();
}
public void updateVideogamesListView(ArrayList<Videogame> values) {
AddVideogameActivityAdapter adapter = new AddVideogameActivityAdapter(this, values);
setListAdapter(adapter);
}
#Override
protected void onDestroy() {
super.onDestroy();
}
}
The other classes involved in building the ListView are the REST classes and the AsyncTask class that downloads and parses the JSon files.
What does your ListView look like, does it look like this:
<ListView android:id="#id/android:list"
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="0dip" ></ListView>
Especially the id of the ListView. Check your layout file, probably the bug exists there.
Related
I have a gridview inside my fragment that is populated by a BaseAdapter.
The problem is that in my adapter i have a favorite button, and when i click i want the button to change. But the logic in API is done, but my button just change when i reload page.
I tried using adapter.notifyDataSetChanged(); but didn't work.
My getView adapter code:
//Implementando os clicks
itemHolder.imgFavorito.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (!util.isLogado(context)) {
((MainActivity) context).selectDrawerItem(new LoginFragment());
}
try {
SharedPreferences pref = context.getSharedPreferences("MyPref", 0);
produtoFavorito(new favoritarProduto().execute(pref.getString("USID", "null"), item.getId() + "").get());
} catch (Exception e) {
e.printStackTrace();
}
fragment.notifyAdapterChanged();
}
});
In fragment.notifyAdapterChanged(); line a just call my Fragment that i recieve in constructor of adapter, and this is the function:
public void notifyAdapterChanged(){
adapter.notifyDataSetChanged();
}
EDIT1: How my layout looks like
http://i.imgur.com/SPr0HBS.png
EDIT2: My full Adapter
public class ProdutoAdapter extends BaseAdapter {
private LayoutInflater mInflater;
private List<ProdutoResumido> itens;
private HomeFragment fragment;
public ProdutoAdapter(Context context, List<ProdutoResumido> itens, HomeFragment fragment) {
//Itens do listview
this.itens = itens;
//Objeto responsável por pegar o Layout do item.
//mInflater = LayoutInflater.from(context);
mInflater = (LayoutInflater) context.
getSystemService(Context.LAYOUT_INFLATER_SERVICE);
this.fragment = fragment;
}
public int getCount() {
return itens.size();
}
public ProdutoResumido getItem(int position) {
return itens.get(position);
}
public long getItemId(int position) {
return position;
}
public View getView(int position, View view, ViewGroup parent) {
ItemSuporte itemHolder;
//se a view estiver nula (nunca criada), inflamos o layout nela.
if (view == null) {
//infla o layout para podermos pegar as views
view = mInflater.inflate(R.layout.lista_produtos_fg, null);
//cria um item de suporte para não precisarmos sempre
//inflar as mesmas informacoes
itemHolder = new ItemSuporte();
itemHolder.imgProduto = ((ImageView) view.findViewById(R.id.imgProduto));
itemHolder.txtPreco = ((TextView) view.findViewById(R.id.txtPreco));
itemHolder.imgFavorito = ((ImageView) view.findViewById(R.id.imgFavorito));
itemHolder.txtNomeProduto = ((TextView) view.findViewById(R.id.txtNomeProduto));
itemHolder.txtEstadoProduto = ((TextView) view.findViewById(R.id.txtEstadoProduto));
itemHolder.imgLoja = ((ImageView) view.findViewById(R.id.imgLoja));
itemHolder.txtNomeLoja = ((TextView) view.findViewById(R.id.txtNomeLoja));
//define os itens na view;
view.setTag(itemHolder);
} else {
//se a view já existe pega os itens.
itemHolder = (ItemSuporte) view.getTag();
}
final Context context = view.getContext();
//pega os dados da lista
//e define os valores nos itens.
final ProdutoResumido item = itens.get(position);
Loja loja = new Loja();
itemHolder.txtPreco.setText("R$ " + new DecimalFormat("#.00").format(item.getValor()));
itemHolder.imgFavorito.setImageResource(produtoFavorito(item.getFavorito()));
itemHolder.txtNomeProduto.setText(item.getNome());
itemHolder.txtEstadoProduto.setText("ESTADO: " + item.getTempoUso());
itemHolder.txtNomeLoja.setText(item.getLoja());
try {
if (item.getImagem() != null)
new DownloadImageTask(itemHolder.imgProduto).execute("http://200.98.202.23/JustForMoms/" + item.getImagem());
if (item.getLojaImg() != null)
new DownloadImageTask(itemHolder.imgLoja).execute("http://200.98.202.23/JustForMoms/" + item.getLojaImg());
} catch (Exception e) {
e.printStackTrace();
}
//Implementando os clicks
itemHolder.imgFavorito.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (!util.isLogado(context)) {
((MainActivity) context).selectDrawerItem(new LoginFragment());
}
try {
SharedPreferences pref = context.getSharedPreferences("MyPref", 0);
produtoFavorito(new favoritarProduto().execute(pref.getString("USID", "null"), item.getId() + "").get());
} catch (Exception e) {
e.printStackTrace();
}
fragment.notifyAdapterChanged();
}
});
//retorna a view com as informações
return view;
}
private int produtoFavorito(Boolean favorito) {
if (favorito)
return R.drawable.favorite;
else
return R.drawable.notfavorite;
}
/**
* Classe de suporte para os itens do layout.
*/
private class ItemSuporte {
ImageView imgProduto;
TextView txtPreco;
ImageView imgFavorito;
TextView txtNomeProduto;
TextView txtEstadoProduto;
ImageView imgLoja;
TextView txtNomeLoja;
}
private class DownloadImageTask extends AsyncTask<String, Void, Bitmap> {
ImageView bmImage;
public DownloadImageTask(ImageView bmImage) {
this.bmImage = bmImage;
}
protected Bitmap doInBackground(String... urls) {
String urldisplay = urls[0];
Bitmap mIcon11 = null;
try {
InputStream in = new java.net.URL(urldisplay).openStream();
mIcon11 = BitmapFactory.decodeStream(in);
} catch (Exception e) {
e.printStackTrace();
}
return mIcon11;
}
protected void onPostExecute(Bitmap result) {
bmImage.setImageBitmap(result);
}
}
public class favoritarProduto extends AsyncTask<String, Void, Boolean> {
private String retorno;
private String url;
#Override
protected Boolean doInBackground(String... params) {
String usID = params[0];
String prodID = params[1];
url = "http://200.98.202.23/JustForMoms/Produto/FavoritarProduto/" + usID + "/" + prodID;
webclient client = new webclient(url);
retorno = client.getmodel();
if (retorno != null) {
if (retorno.equals("\"incluido\"")) {
return true;
} else {
return false;
}
}
return false;
}
}
}
EDIT 3:
//Implementando os clicks
itemHolder.imgFavorito.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (!util.isLogado(context)) {
((MainActivity) context).selectDrawerItem(new LoginFragment());
}
try {
SharedPreferences pref = context.getSharedPreferences("MyPref", 0);
itemHolder.imgFavorito.setImageResource(produtoFavorito(new favoritarProduto().execute(pref.getString("USID", "null"), item.getId() + "").get()));
} catch (Exception e) {
e.printStackTrace();
}
ProdutoAdapter.this. notifyDataSetChanged();
}
});
Ok, You are calling favoritarProduto() which in turn makes a call to server to update the favorite status :)
But you missed one simple thing :) Dude its Async call :) That means it takes time to execute the code inside doInBackground:) How can you expect the status to be updated and ready immediately as if it is synchronous call??? :)
Modify the code as shown here
public class favoritarProduto extends AsyncTask<String, Void, Boolean> {
private String retorno;
private String url;
#Override
protected Boolean doInBackground(String... params) {
String usID = params[0];
String prodID = params[1];
url = "http://200.98.202.23/JustForMoms/Produto/FavoritarProduto/" + usID + "/" + prodID;
webclient client = new webclient(url);
retorno = client.getmodel();
if (retorno != null) {
if (retorno.equals("\"incluido\"")) {
return true;
} else {
return false;
}
}
return false;
}
#Override
protected void onPostExecute(Boolean response) {
//call your produtoFavorito fro the item holder based on prodID you have received :)
}
}
i wish to display my data and image which download from an URL but after i download the image from URL, the order of the image go wrong. I displayed my data and images using card view and recycle view, but the first image in first card go to second, while the second image at third card and the third one will missing and the first one will empty. Anyone can help me on this?
Below is my code. Tq
SimpleCardViewAdapter.java
public class SimpleCardViewAdapter extends RecyclerView.Adapter<SimpleCardViewAdapter.ViewHolder> {
private List<CardViewData> mDataset;
Bitmap downloadedBitmap;
ImageView row_image;
public SimpleCardViewAdapter(List<CardViewData> dataset) {
mDataset = dataset;
}
#Override
public ViewHolder onCreateViewHolder(final ViewGroup viewGroup, int i) {
View v = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.row_layout, viewGroup, false);
return new ViewHolder(v);
}
#Override
public void onBindViewHolder(final ViewHolder viewHolder, int i) {
final CardViewData cardViewData = mDataset.get(i);
viewHolder.mTitle.setText(cardViewData.getTitle());
viewHolder.mDescription.setText(cardViewData.getDescription());
String var = cardViewData.getImage();
new Thread(new getImageTask(var)).start();
viewHolder.mImage.setImageBitmap(downloadedBitmap);
viewHolder.itemView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Toast.makeText(v.getContext(), "Title: " + cardViewData.getTitle(), Toast.LENGTH_SHORT).show();
}
});
}
class getImageTask implements Runnable {
String imageUrl;
getImageTask(String imgUrl){
imageUrl = imgUrl;
}
#Override
public void run() {
try {
URL url = new URL(imageUrl);
downloadedBitmap = BitmapFactory.decodeStream(url.openConnection().getInputStream());
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
Message msg = new Message();
Bundle b = new Bundle();
b.putString("mfeApi", "1");
msg.setData(b);
handlerGroupedProductsImage.sendMessage(msg);
}
}
Handler handlerGroupedProductsImage = new Handler() {
public void handleMessage(Message msg) {
Bundle b = msg.getData();
String done = b.getString("mfeApi");
};
};
#Override
public int getItemCount() {
return mDataset == null ? 0 : mDataset.size();
}
public static class ViewHolder extends RecyclerView.ViewHolder {
public TextView mTitle;
public TextView mDescription;
public ImageView mImage;
public ViewHolder(View itemView) {
super(itemView);
mTitle = (TextView) itemView.findViewById(R.id.row_title);
mDescription = (TextView) itemView.findViewById(R.id.row_description);
mImage = (ImageView) itemView.findViewById(R.id.row_image);
}
}
Activity.java
private void getData() {
try {
final String toSend = "http://www.test.com.my/test/api/kipcard_helpAPI.php";
new Thread(new Runnable() {
#Override
public void run() {
URL url = null;
HttpURLConnection conn = null;
String receivedString = null;
try {
url = new URL(toSend);
conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("POST");
InputStream in = new BufferedInputStream(conn.getInputStream());
receivedString = IOUtils.toString(in, "UTF-8");
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
Message msg = new Message();
Bundle b = new Bundle();
b.putString("mfeApi", receivedString);
msg.setData(b);
hGet.sendMessage(msg);
}
}).start();
} catch (Exception e) {
e.printStackTrace();
}
}
Handler hGet = new Handler() {
public void handleMessage(Message msg) {
Bundle b = msg.getData();
String s = b.getString("mfeApi");
items = s.split("\\|\\|");
size = items.length;
List <CardViewData> list = new ArrayList<CardViewData>();
for(int i = 0 ; i <= size-3 ; i+=3){
Log.d("here",items[i] +"" );
//new Thread(new getImageTask(imahr)).start();
list.add(new CardViewData(items[i+2], items[i+3], items[i+1]));
}
mAdapter = new SimpleCardViewAdapter(list);
mRecyclerView.setAdapter(mAdapter);
};
};
The problem is here:
new Thread(new getImageTask(var)).start();
viewHolder.mImage.setImageBitmap(downloadedBitmap);
As the thread do it's job parallel not synchronously downloadedBitmap can hold another's thread "old" result.
Instead of
new Thread(new getImageTask(var)).start();
viewHolder.mImage.setImageBitmap(downloadedBitmap);
Try using
final int position = i;
viewHolder.position = i;
new AsyncTask<Object, Void, Bitmap>() {
private AlbumViewHolder v;
#Override
protected Bitmap doInBackground( Object[] params ) {
v = (AlbumViewHolder) params[ 0 ];
// download here your image
return b;
}
#Override
protected void onPostExecute( Bitmap result ) {
super.onPostExecute( result );
if ( v.position == position && result != null ) {
// If this item hasn't been recycled already, hide the
// progress and set and show the image
v.mImageView.setImageBitmap( result );
v.mImageView.setVisibility( View.VISIBLE );
v.mProgressBar.setVisibility( View.GONE );
}
}
}.execute( viewHolder );
and in ViewHolder :
public static class ViewHolder extends RecyclerView.ViewHolder {
public TextView mTitle;
public TextView mDescription;
public ImageView mImage;
public int position;
public ViewHolder(View itemView) {
super(itemView);
mTitle = (TextView) itemView.findViewById(R.id.row_title);
mDescription = (TextView) itemView.findViewById(R.id.row_description);
mImage = (ImageView) itemView.findViewById(R.id.row_image);
}
}
And one more thing - your ViewHolder should have position parameter. And think about caching.
Try this:
add Context to your constructor
public SimpleCardViewAdapter(List<CardViewData> dataset, Activity activity){
this.mActivity = activity;
}
change in onBindViewHolder method:
new Thread(new getImageTask(var, viewHolder.mImage)).start();
and change your task like this:
class getImageTask implements Runnable {
String imageUrl;
ImageView imageView
getImageTask(String imgUrl, ImageView imageView){
imageUrl = imgUrl;
this.imageView = imageView;
}
#Override
public void run() {
try {
URL url = new URL(imageUrl);
//change this line also
Bitmap bitmap = BitmapFactory.decodeStream(url.openConnection().getInputStream());
//set you downloaded image now...
//new change ....
mActivity.runOnUiThread(new Runnable() {
#Override
public void run() {
//Your code to run in GUI thread here
if(bitmap != null)
imageView.setImageBitmap(bitmap);
}
});
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
Message msg = new Message();
Bundle b = new Bundle();
b.putString("mfeApi", "1");
msg.setData(b);
handlerGroupedProductsImage.sendMessage(msg);
}
}
***but it will not cache bitmap, every time you scroll your recycler inside app it will download it again and again.
I have this exception on my APP... I don't know why happen it.
java.lang.IllegalStateException:
The content of the adapter has changed but ListView did not receive a notification. Make sure the content of your adapter is not modified from a background thread, but only from the UI thread.
In ListView(2131492879), class android.widget.ListView with Adapter class com.agencialanave.AdaptadorListaApps
I have tried many options but I have not managed to fix it.
Class: Apps.java
public class Apps
{
public Bitmap Colorbanda;
public Bitmap Logo;
public Bitmap LogoBasura;
public String NombreAPP;
public float MemoriaUsada;
public String NombrePaquete;
public File Apk;
public Apps(Bitmap colorbanda, Bitmap logo,String nombreAPP, float memoriaUsada, Bitmap logoBasura, String nombrePaquete, File apk)
{
super();
Colorbanda = colorbanda;
Logo = logo;
LogoBasura = logoBasura;
NombreAPP = nombreAPP;
MemoriaUsada = memoriaUsada;
NombrePaquete = nombrePaquete;
Apk = apk;
}
public Apps(Bitmap colorbanda, Bitmap logo,String nombreAPP, float memoriaUsada, Bitmap logoBasura, String nombrePaquete)
{
super();
Colorbanda = colorbanda;
Logo = logo;
LogoBasura = logoBasura;
NombreAPP = nombreAPP;
MemoriaUsada = memoriaUsada;
NombrePaquete = nombrePaquete;
}
public Bitmap getColorbanda() {
return Colorbanda;
}
public void setColorbanda(Bitmap colorbanda) {
Colorbanda = colorbanda;
}
public Bitmap getLogo() {
return Logo;
}
public void setLogo(Bitmap logo) {
Logo = logo;
}
public Bitmap getLogoBasura() {
return LogoBasura;
}
public void setLogoBasura(Bitmap logoBasura) {
LogoBasura = logoBasura;
}
public String getNombreAPP() {
return NombreAPP;
}
public void setNombreAPP(String nombreAPP) {
NombreAPP = nombreAPP;
}
public float getMemoriaUsada() {
return MemoriaUsada;
}
public void setMemoriaUsada(float memoriaUsada) {
MemoriaUsada = memoriaUsada;
}
public String getNombrePaquete() {
return NombrePaquete;
}
public void setNombrePaquete(String nombrePaquete) {
NombrePaquete = nombrePaquete;
}
public File getApk() {
return Apk;
}
public void setApk(File apk) {
Apk = apk;
}
}
Class: AdaptadorListaApps.java
public class AdaptadorListaApps extends ArrayAdapter<Apps>
{
private static Activity Context;
ArrayList<Apps> listaApps;
public AdaptadorListaApps(Activity context, ArrayList<Apps> lista)
{
super(context, R.layout.layout_list, lista);
Context = context;
listaApps = lista;
}
class ViewHolder
{
ImageView fotoBandaColor,fotoLogoApp,fotoDelete;
TextView nombreApp, memoriaUsada;
}
#Override
public View getView(int position, View convertView, ViewGroup parent)
{
View item =convertView;
ViewHolder holder;
if (item == null)
{
LayoutInflater inflater = Context.getLayoutInflater();
item = inflater.inflate(R.layout.layout_list, null);
holder = new ViewHolder();
holder.fotoBandaColor = (ImageView)item.findViewById(R.id.bandaColor);
holder.fotoLogoApp = (ImageView)item.findViewById(R.id.logoApp);
holder.fotoDelete = (ImageView)item.findViewById(R.id.borrarApp);
holder.nombreApp = (TextView)item.findViewById(R.id.nombreApp);
holder.memoriaUsada = (TextView)item.findViewById(R.id.memoriaUsada);
item.setTag(holder);
}
else
{
holder=(ViewHolder) item.getTag();
}
holder.fotoBandaColor.setImageBitmap(listaApps.get(position).getColorbanda());
holder.fotoLogoApp.setImageBitmap(listaApps.get(position).getLogo());
holder.fotoDelete.setImageBitmap(listaApps.get(position).getLogoBasura());
holder.memoriaUsada.setText(TamañoAppEnRam(listaApps.get(position).getMemoriaUsada()) + " MB ( " + PorcentageMemoria(listaApps.get(position).getMemoriaUsada())+"% )");
if(listaApps.get(position).getMemoriaUsada() < 4)
{
holder.memoriaUsada.setTextColor(Color.parseColor("#56E000"));
}
else if(listaApps.get(position).getMemoriaUsada() > 7)
{
holder.memoriaUsada.setTextColor(Color.RED);
}
else
{
holder.memoriaUsada.setTextColor(Color.parseColor("#FF8000"));
}
holder.nombreApp.setText(listaApps.get(position).getNombreAPP());
return item;
}
}
Code where update listview
private class GetRunningApps extends AsyncTask<String, ArrayList<Apps>, String>
{
#Override
protected String doInBackground(String... params) throws IllegalStateException
{
listaapps.clear();
listaapps = new ArrayList<Apps>();
cont = 0;
ActivityManager activityManager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
List<ActivityManager.RunningAppProcessInfo> runningTasks = activityManager.getRunningAppProcesses();
PackageManager pm = context.getPackageManager();
Drawable icon;
Bitmap logo;
float memoria = 0;
String nombrePaquete;
MB = 0;
int pids[] = new int[1];
adaptadorLista = new AdaptadorListaApps(activity,listaapps);
for (RunningAppProcessInfo appInfo : runningTasks)
{
try
{
if(appInfo.importance == RunningAppProcessInfo.IMPORTANCE_SERVICE || appInfo.importance == RunningAppProcessInfo.IMPORTANCE_BACKGROUND)
{
icon = pm.getApplicationIcon(appInfo.processName);
logo = ((BitmapDrawable) icon).getBitmap();
CharSequence c = pm.getApplicationLabel
(
pm.getApplicationInfo(appInfo.processName,PackageManager.GET_META_DATA)
);
pids[0] = appInfo.pid;
nombrePaquete = appInfo.processName;
android.os.Debug.MemoryInfo[] memoryInfoArray = activityManager.getProcessMemoryInfo(pids);
for(android.os.Debug.MemoryInfo pidMemoryInfo: memoryInfoArray)
{
memoria = (float)pidMemoryInfo.getTotalPss()/1024;
if(pidMemoryInfo.getTotalPss()/1024 <= 3)
{
listaapps.add(new Apps(bandaVerde, logo , c.toString() , memoria ,logoDelete, nombrePaquete, new File(getActivity().getPackageManager().getApplicationInfo(nombrePaquete, PackageManager.GET_META_DATA).publicSourceDir)));
}
else if((pidMemoryInfo.getTotalPss()/1024 >= 7))
{
listaapps.add(new Apps(bandaRoja, logo , c.toString() , memoria ,logoDelete,nombrePaquete, new File(getActivity().getPackageManager().getApplicationInfo(nombrePaquete, PackageManager.GET_META_DATA).publicSourceDir)));
}
else if((pidMemoryInfo.getTotalPss()/1024 > 3 && pidMemoryInfo.getTotalPss()/1024 < 7))
{
listaapps.add(new Apps(bandaNaranja, logo , c.toString() , memoria ,logoDelete,nombrePaquete, new File(getActivity().getPackageManager().getApplicationInfo(nombrePaquete, PackageManager.GET_META_DATA).publicSourceDir)));
}
}
cont++;
MB += memoria;
if(cont % 2 == 0)
{
try
{
publishProgress();
}
catch(IllegalStateException e){}
}
}
}
catch (Exception e) {}
}
cont = 0;
return null;
}
#Override
protected void onProgressUpdate(ArrayList<Apps>... values)
{
try
{
adaptadorLista = new AdaptadorListaApps(activity,listaapps);
listaAplicaciones.setAdapter(adaptadorLista);
adaptadorLista.notifyDataSetChanged();
}
catch(IllegalStateException e){}
}
#Override
protected void onPostExecute(String result)
{
adaptadorLista = new AdaptadorListaApps(activity,listaapps);
adaptadorLista.sort(new OrderList());
listaAplicaciones.setAdapter(adaptadorLista);
}
}
Please, help me... Thanks
You should never change the properties of a view or any of its underlying datasource on a background thread.
Do not manipulate the variable listaaps in your onBackground. Only change it in your onPostExecute or onProgressUpdate.
Do not manipulate the variable adaptorLista in your onBackground. Only change it in your onPostExecute or onProgressUpdate.
In the above image, there is a list view which contains list of items that the user can download. This is the image which tells user that he can download the file. On completion of download, the image will change to . My problem is when I download a file, the status image(which denotes that download has completed) gets changed for another row, instead, it should change for the row that I had selected. At present, if I download first file in the list, the image gets changed for 4th or 5th item in the list. Also, when I try to download any other file from the list. it opens up last downloaded file(This is functionality of the app that if file is already downloaded, then open it in pdf reader),i.e., if I download 1st file in the list and then go for second item,then instead of downloading 2nd file, it opens up last downloaded file. More over, if I scroll the listview, the status of download gets changed for other items in the list also. Below,is my adapter code:
public class DownloadListAdapter extends BaseAdapter {
Context ctx;
public ArrayList<DownloadListDao> mDownloadList;
String readMoreLink;
public static final String TAG = "DownloadListAdapter";
ProgressDialog mProgressDialog;
private boolean isSDCardPresent;
File tieDir;
int downloadState[];
public DownloadListAdapter(Context ctx,
ArrayList<DownloadListDao> mDownloadList) {
this.ctx = ctx;
this.mDownloadList = mDownloadList;
downloadState = new int [mDownloadList.size()];
for(int i = 0; i < mDownloadList.size(); i++) {
downloadState[i] = 0;
}
tieDir = new File(Environment.getExternalStorageDirectory().toString()
+ "/tie");
}// Constructor
public int getCount() {
return this.mDownloadList.size();
}// getCount
public Object getItem(int position) {
return this.mDownloadList.get(position);
}// getItem
public long getItemId(int position) {
return 0;
}// getItemId
static class ViewHolder {
TextView txtTitle, txtTheme, txtDate;
ImageView imgDownload;
}// ViewHolder
ViewHolder holder;
public View getView(final int position, View convertView, ViewGroup parent) {
final String url = mDownloadList.get(position).getUrl();
if (convertView == null) {
convertView = LayoutInflater.from(parent.getContext()).inflate(
R.layout.downlist_adapter, null);
holder = new ViewHolder();
holder.txtTitle = (TextView) convertView
.findViewById(R.id.txtTitle);
holder.txtTheme = (TextView) convertView
.findViewById(R.id.txtTheme);
holder.txtDate = (TextView) convertView.findViewById(R.id.txtDate);
holder.imgDownload = (ImageView) convertView
.findViewById(R.id.imgDload);
holder.imgDownload.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
File mediaFile = null;
if (url != null && !url.equals("null") && !url.equals("")) {
String fileName = url.toString().substring(
url.toString().lastIndexOf("/") + 1,
url.toString().length());
mediaFile = new File(tieDir, fileName);
}
processFile(mediaFile, url, position);
int pos = (Integer)v.getTag();
downloadState[pos] = 1;
}
});
convertView.setTag(holder);
} else {
holder = (ViewHolder) convertView.getTag();
}
if (mDownloadList != null && mDownloadList.size() > 0) {
if (mDownloadList.get(position).getTitle() != null
&& !mDownloadList.get(position).getTitle().equals("null")
&& !mDownloadList.get(position).getTitle().equals("")) {
holder.txtTitle.setText(mDownloadList.get(position).getTitle());
}
if (mDownloadList.get(position).getTheme() != null
&& !mDownloadList.get(position).getTheme().equals("null")
&& !mDownloadList.get(position).getTheme().equals("")) {
holder.txtTheme.setText(mDownloadList.get(position).getTheme());
}
if (mDownloadList.get(position).getDate() != null
&& !mDownloadList.get(position).getDate().equals("null")
&& !mDownloadList.get(position).getDate().equals("")) {
holder.txtDate.setText(mDownloadList.get(position).getDate());
}
if (downloadState[position] == 1) {
holder.imgDownload.setImageDrawable(ctx.getResources()
.getDrawable(R.drawable.ic_dloaded));
} else {
holder.imgDownload.setImageDrawable(ctx.getResources()
.getDrawable(R.drawable.ic_dload));
}
}
holder.imgDownload.setTag(position);
return convertView;
}// getView
protected void downloadFile(String url, int position, String fileName) {
Log.v(TAG, "Preparing to download");
mProgressDialog = new ProgressDialog(ctx);
mProgressDialog.setMessage("Dowloading...");
mProgressDialog.setIndeterminate(false);
mProgressDialog.setMax(100);
mProgressDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
isSDCardPresent = Environment.getExternalStorageState().equals(
Environment.MEDIA_MOUNTED);
if (!isSDCardPresent) {
noSDCardAlert(ctx);
} else {
if ((tieDir.exists()) && (tieDir != null)) {
if (NetworkConnection.isOnline(ctx)) {
if (tieDir.isDirectory()) {
Log.v(TAG, "if tie dir URL:::" + url);
new DownloadAudioAsync(ctx, position, fileName).execute(url);
}
} else {
((DownloadListActivity) ctx)
.OpenNetErrDialog("Please check your internet connection...");
}
} else {
boolean isDirectoryCreated = tieDir.mkdirs();
if (isDirectoryCreated) {
Log.v(TAG, "if tie not dir URL:::" + url);
if (NetworkConnection.isOnline(ctx)) {
new DownloadAudioAsync(ctx, position, fileName).execute(url);
} else {
((DownloadListActivity) ctx)
.OpenWiFiDialog("Please check your internet connection...");
}
}
}
}
}
private void noSDCardAlert(Context ctx) {
AlertDialog.Builder ad = new AlertDialog.Builder(ctx);
ad.setMessage("No sd card present..");
ad.setPositiveButton("OK", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
});
if (!((DownloadDetail) ctx).isFinishing()) {
ad.show();
}
}
public void OpenDialog(String messageID) {
final Dialog dialog = new Dialog(ctx,
android.R.style.Theme_Translucent_NoTitleBar);
dialog.setContentView(R.layout.dialog_base);
dialog.getWindow().getAttributes().windowAnimations = android.R.style.Animation_Dialog;
dialog.setCancelable(false);
TextView alertMessage = (TextView) dialog.findViewById(R.id.txtMessage);
Button btnOK = (Button) dialog.findViewById(R.id.btnOk);
btnOK.setText("Show");
alertMessage.setText(messageID);
dialog.show();
btnOK.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
dialog.dismiss();
}
});
}
protected void showPdf(File mediaFile) {
Intent intent = new Intent(Intent.ACTION_VIEW);
intent.setDataAndType(Uri.fromFile(mediaFile), "application/pdf");
intent.setFlags(Intent.FLAG_ACTIVITY_NO_HISTORY);
ctx.startActivity(intent);
}
public class DownloadAudioAsync extends AsyncTask<String, String, String> {
Context ctx;
int pos;
private ProgressDialog pd;
String fileName;
public DownloadAudioAsync(Context ctx, int pos, String fileName) {
this.ctx = ctx;
this.pos = pos;
this.fileName = fileName;
}
#Override
protected void onPreExecute() {
super.onPreExecute();
Log.v(TAG, "inside on pre execute");
pd = new ProgressDialog(ctx);
pd.setMessage("Downloading...\nPlease wait..");
pd.show();
}
#Override
protected String doInBackground(String... aurl) {
int count;
try {
Log.v(TAG,
"inside do in background with url::"
+ aurl[0].toString());
aurl[0] = aurl[0].replaceAll(" ", "%20");
URL url = new URL(aurl[0]);
URLConnection conexion = url.openConnection();
conexion.connect();
int lenghtOfFile = conexion.getContentLength();
fileName = URLDecoder.decode(fileName, "UTF-8");
InputStream input = new BufferedInputStream(url.openStream());
OutputStream output = new FileOutputStream(tieDir + "/"
+ fileName);
byte data[] = new byte[1024];
long total = 0;
while ((count = input.read(data)) != -1) {
total += count;
publishProgress("" + (int) ((total * 100) / lenghtOfFile));
output.write(data, 0, count);
}
output.flush();
output.close();
input.close();
} catch (Exception e) {
}
return null;
}
#Override
protected void onPostExecute(String unused) {
if (!((DownloadListActivity) ctx).isFinishing()) {
pd.dismiss();
updateView(pos);
}
}
private void updateView(int pos) {
View v = ((DownloadListActivity) ctx).menuListView.getChildAt(pos
- ((DownloadListActivity) ctx).menuListView
.getFirstVisiblePosition());
ImageView imgDloadBtn = (ImageView) v.findViewById(R.id.imgDload);
imgDloadBtn.setImageDrawable(ctx.getResources().getDrawable(
R.drawable.ic_dloaded));
notifyDataSetChanged();
}
}
private void processFile(File mediaFile, String url, int pos) {
if (url != null && !url.equals("null") && !url.equals("")) {
if (mediaFile != null) {
Log.v(TAG, "in processFile FileName " + mediaFile.getName());
Log.v(TAG, "in processFile Position " + pos);
if(!mediaFile.exists()) {
Log.v(TAG, "in processFile Media file doesn't exists");
downloadFile(url, pos, mediaFile.getName());
} else {
Log.v(TAG, "in processFile Media file exists");
try {
showPdf(mediaFile);
} catch (ActivityNotFoundException anfe) {
OpenDialog("PDF Reader is not installed on your device.");
}
}
}
}
}
}// DownloadAdapter
I had read this post for recycling the view(Thanks to Knickedi for in depth explaination). But, I can't figure out where is actual problem.
Issue with getview Method which keep recreating whenever you scroll your view, to handle exact position you have to play with setTag & getTag,check below few stackvoerflow answers to understand setTag & getTag:
Button in ListView using ArrayAdapter
Getting radio button value from custom list in android
and even store downloaded state into one booleanarray like below:
int boxState[];
within adapter constructor, set zero initially:
for (int i = 0; i < getData.size(); i++) {
boxState[i] = 0;
}
within adapter getview method:
holder.imgDownload.setTag(position);
Now you click on download button set value as 1 (Inside onclick of button):
pos = (Integer) v.getTag();
boxState[pos]=1;
At last when you scroll your view check condition into following way(put below code inside getview method):
if (boxState[position] == 0) {
holder.imgDownload.setImageDrawable(ctx.getResources()
.getDrawable(R.drawable.ic_dloaded)); //which aren't downloaded
} else {
holder.imgDownload.setImageDrawable(ctx.getResources()
.getDrawable(R.drawable.ic_dload)); // which are downloaded.
}
I am trying to parse the xml file and trying to load images and textviews and display it in a list view but whenever i try to load images in getView method in force closes the application even if try to scroll fast it also does the same. Iam tired of doing it in thread and asynctask for 5hours.please help if someone can solve it. Here are my two class files.
class NewsRowAdapter
public class NewsRowAdapter extends ArrayAdapter<Item>
{
LoadingImage loadingImage;
Bitmap bitmap = null;
private Activity activity;
private List<Item> items;
private Item objBean;
private int row;
public NewsRowAdapter(Activity act, int resource, List<Item> arrayList)
{
super(act, resource, arrayList);
this.activity = act;
this.row = resource;
this.items = arrayList;
}
#Override
public View getView(final int position, View convertView, ViewGroup parent)
{
View view = convertView;
final ViewHolder holder;
if (view == null)
{
LayoutInflater inflater = (LayoutInflater) activity.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(row, null);
holder = new ViewHolder();
view.setTag(holder);
} else
{
holder = (ViewHolder) view.getTag();
}
if ((items == null) || ((position + 1) > items.size()))
return view;
objBean = items.get(position);
holder.tvTitle = (TextView) view.findViewById(R.id.tvtitle);
holder.tvDesc = (TextView) view.findViewById(R.id.tvdesc);
holder.tvDate = (TextView) view.findViewById(R.id.tvdate);
holder.imgView = (ImageView) view.findViewById(R.id.image);
holder.pbar = (ProgressBar) view.findViewById(R.id.pbar);
if (holder.tvTitle != null && null != objBean.getTitle() && objBean.getTitle().trim().length() > 0)
{
holder.tvTitle.setText(Html.fromHtml(objBean.getTitle()));
}
if (holder.tvDesc != null && null != objBean.getDesc() && objBean.getDesc().trim().length() > 0)
{
holder.tvDesc.setText(Html.fromHtml(objBean.getDesc()));
}
if (holder.tvDate != null && null != objBean.getPubdate() && objBean.getPubdate().trim().length() > 0)
{
holder.tvDate.setText(Html.fromHtml(objBean.getPubdate()));
}
if (holder.imgView != null)
{
if (null != objBean.getLink() && objBean.getLink().trim().length() > 0)
{
final ProgressBar pbar = holder.pbar;
pbar.setVisibility(View.INVISIBLE);
//---------CHANGES MADE FOR LOADING IMAGE----------//
Log.d("IMAGE NULL----------", objBean.getLink());
//loadBitmap(objBean.getLink());
/*new Thread()
{
public void run()
{*/
try
{
URL linkurl = new URL(objBean.getLink());
bitmap = BitmapFactory.decodeStream(linkurl.openConnection().getInputStream());
holder.imgView.setImageBitmap(bitmap);
} catch (MalformedURLException e)
{
e.printStackTrace();
} catch (IOException e)
{
e.printStackTrace();
}
/*}
}.start();*/
} else
{
holder.imgView.setImageResource(R.drawable.ic_launcher);
}
}
return view;
}
//------LOADING IMAGE FROM URL------//
public static Bitmap loadBitmap(String url)
{
Bitmap bitmap = null;
final AndroidHttpClient client = AndroidHttpClient.newInstance("Android");
final HttpGet getRequest = new HttpGet(url);
try
{
HttpResponse response = client.execute(getRequest);
final int statusCode = response.getStatusLine().getStatusCode();
if (statusCode != HttpStatus.SC_OK)
{
Log.d("ImageDownloader", "Error " + statusCode + " while retrieving bitmap from " + url);
return null;
}
final HttpEntity entity = response.getEntity();
if (entity != null)
{
InputStream inputStream = null;
try
{
inputStream = entity.getContent();
bitmap = BitmapFactory.decodeStream(inputStream);
} finally
{
if (inputStream != null)
{
inputStream.close();
}
entity.consumeContent();
}
}
} catch (Exception e)
{
// Could provide a more explicit error message for IOException or IllegalStateException
getRequest.abort();
Log.d("Error while retrieving bitmap from " + url, e.toString());
} finally
{
if (client != null)
{
client.close();
}
}
return bitmap;
}
public class ViewHolder
{
public TextView tvTitle, tvDesc, tvDate;
private ImageView imgView;
private ProgressBar pbar;
}
}
and the main class is :
class MainActivity
public class MainActivity extends Activity implements OnItemClickListener
{
private static final String rssFeed = /*"https://www.dropbox.com/s/t4o5wo6gdcnhgj8/imagelistview.xml?dl=1"*/"http://78.46.34.27/kapapps/newparsedtransaction.xml";
List<Item> arrayOfList;
ListView listView;
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.mainnewtransaction);
listView = (ListView) findViewById(R.id.listview);
listView.setOnItemClickListener(this);
if (Utils.isNetworkAvailable(NewTransactionActivity.this))
{
new MyTask().execute(rssFeed);
} else
{
showToast("No Network Connection!!!");
}
}
// My AsyncTask start...
class MyTask extends AsyncTask<String, Void, Void>
{
ProgressDialog pDialog;
#Override
protected void onPreExecute()
{
super.onPreExecute();
pDialog = new ProgressDialog(NewTransactionActivity.this);
pDialog.setTitle("Latest Transaction");
pDialog.setMessage("Loading... Please wait");
pDialog.show();
}
#Override
protected Void doInBackground(String... params)
{
arrayOfList = new NamesParser().getData(params[0]);
return null;
}
#Override
protected void onPostExecute(Void result)
{
super.onPostExecute(result);
if (null == arrayOfList || arrayOfList.size() == 0)
{
showToast("No data found from web!!!");
NewTransactionActivity.this.finish();
} else
{
// check data...
/*
* for (int i = 0; i < arrayOfList.size(); i++)
* {
* Item item = arrayOfList.get(i); System.out.println(item.getId());
* System.out.println(item.getTitle());
* System.out.println(item.getDesc());
* System.out.println(item.getPubdate());
* System.out.println(item.getLink());
* }
*/
for(int i = 0 ; i < arrayOfList.size() ; i++)
{
Item item = arrayOfList.get(i);
Log.d("ID NEWTRANSACTION ACTIVITY ------>" , item.getId());
Log.d("TITLE NEWTRANSACTION ACTIVITY ------>" , item.getTitle());
Log.d("DESC NEWTRANSACTION ACTIVITY ------>", item.getDesc());
Log.d("LINK NEWTRANSACTION ACTIVITY ------>", item.getLink());
}
setAdapterToListview();
}
if (null != pDialog && pDialog.isShowing())
{
pDialog.dismiss();
}
}
}
#Override
public void onItemClick(AdapterView<?> parent , View view , int position , long id)
{
Item item = arrayOfList.get(position);
Intent intent = new Intent(NewTransactionActivity.this, DetailActivity.class);
intent.putExtra("url", item.getLink());
intent.putExtra("title", item.getTitle());
intent.putExtra("desc", item.getDesc());
Log.d("IMAGE_URL------>" , item.getLink());
startActivity(intent);
}
public void setAdapterToListview()
{
NewsRowAdapter objAdapter = new NewsRowAdapter(NewTransactionActivity.this , R.layout.row, arrayOfList);
listView.setAdapter(objAdapter);
}
public void showToast(String msg)
{
}
}
Do Image retrieving logic in another thread.It is taking too much time to load Images that's why you are getting ANR.
Use a single worker thread, and make it possible to stop in onPause() of activity.
Good way is to use a SingleThread Executor service to load images.
Here's an example https://stackoverflow.com/a/14579365/1366471
I recommend using the RemoteImageView from the Prime library. It reduces your work a lot.
In your layout, replace ImageView with com.handlerexploit.prime.widgets.RemoteImageView and in your code, change ImageView to RemoteImageView in your holder class.
In the getView method,
holder.imgView = (RemoteImageView) view.findViewById(R.id.image);
//...
holder.imgView.setImageURL(objBean.getLink());