-1

I am developing an app similar to what 9gag is doing. https://play.google.com/store/apps/details?id=com.ninegag.android.app&hl=en

I have already implemented most of it but when I run the app the images that get loaded from the internet are not loaded in the ImageView until it comes on screen. I know that this is how ListView works with recycling but it doesnt seem smooth since i have to wait for each list item to load its image every time its shown on screen.

What do you suggest I could do to improve this issue?

My CustomAdapter class:

public class CustomAdapter extends BaseAdapter implements ResultsListener{
Context context;
Holder holder;
int postItemsLength=0;
ArrayList<PostItem> postItems;
PlaceholderFragment activity;

private static LayoutInflater inflater=null;
public CustomAdapter(PlaceholderFragment activity, ArrayList<PostItem> postItems) {
    // TODO Auto-generated constructor stub
    this.activity=activity;
    this.context=activity.getContext();
    this.postItems = postItems;
    inflater = ( LayoutInflater )context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    Log.d("FOUND","entered constructor");


}

@Override
public int getCount() {
    // TODO Auto-generated method stub
    return postItems.size();
}

@Override
public Object getItem(int position) {
    // TODO Auto-generated method stub
    return position;
}

@Override
public long getItemId(int position) {
    // TODO Auto-generated method stub
    return position;
}

@Override
public void onResultsSucceeded(Bitmap image, int position) {
    holder.img.setImageBitmap(image);
    CustomAdapter.this.notifyDataSetChanged();
    holder.progressBar.setVisibility(View.GONE);
}

public class Holder
{
    TextView tv;
    TextView imgName;
    ImageView img;
    WebView wView;
    TextView likes;
    TextView comments;
    TextView op;
    ProgressBar progressBar;
    FrameLayout webViewLayout;
}



@Override
public View getView(final int position, View convertView, ViewGroup parent) {
    final Holder holder;
    Log.d("FOUND","entered GetView");
    // Check if the item's view is recycled
    if(convertView == null)
    {
        Log.d("FOUND","convertView is not null");
        // The item's view doesn't exist
        // Create the item's view
        LayoutInflater inflater = ((Activity) context).getLayoutInflater();
        convertView = inflater.inflate(R.layout.list_item, parent, false);

        holder = new Holder(); // Create the holder

        holder.tv=(TextView) convertView.findViewById(R.id.titleTextView);
        holder.img=(ImageView) convertView.findViewById(R.id.imageView);
        holder.likes=(TextView) convertView.findViewById(R.id.likeNumTextView);
        holder.comments=(TextView) convertView.findViewById(R.id.commentNumTextView);
        holder.imgName = (TextView) convertView.findViewById(R.id.imageNameTextView);
        holder.op=(TextView) convertView.findViewById(R.id.opTextView);
        holder.webViewLayout = (FrameLayout) convertView.findViewById(R.id.webViewLayout);
        holder.progressBar = (ProgressBar) convertView.findViewById(R.id.progressBar);

        // Store the holder with the view.
        convertView.setTag(holder);
    }
    else
    {
        // The item's view already exist
        // Retrieve the older
        holder = (Holder) convertView.getTag();
        Log.d("FOUND","alreay exists");
    }

    holder.img.setImageResource(R.drawable.empty_img);
    holder.tv.setText(postItems.get(position).getTitle());
    holder.imgName.setText(postItems.get(position).getImageName());
    holder.op.setText(postItems.get(position).getUploader());
    holder.likes.setText(postItems.get(position).getLikeNum()+"");
    holder.comments.setText(postItems.get(position).getCommentNum()+"");

    LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(getDpWidth(), adjustHeight(postItems.get(position).getWidth(), postItems.get(position).getHeight()));
    holder.webViewLayout.setLayoutParams(lp);


    DownloadImageTask dTask = new DownloadImageTask(holder.img);
    dTask.setOnResultsListener(CustomAdapter.this);
    dTask.execute("http://torifi.net/images/" + postItems.get(position).getImageName());

    Log.d("FOUND","entered");
    //holder.likes.setText(likeNum.get(position));
     //    holder.comments.setText(commentNum.get(position));

    /*
    convertView.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View v) {
            // TODO impl

        }
    });
*/
    return convertView;
}

public int getDpWidth()
{
    DisplayMetrics displayMetrics = context.getResources().getDisplayMetrics();
    return Math.round(displayMetrics.widthPixels);// / displayMetrics.density);
}

public int adjustHeight (float imageWidth, float imageHeight)
{
    DisplayMetrics displayMetrics = context.getResources().getDisplayMetrics();
    float dpHeight = displayMetrics.heightPixels;// / displayMetrics.density;
    float dpWidth = displayMetrics.widthPixels;// / displayMetrics.density;

    return Math.round((imageHeight/imageWidth)*dpWidth);
}

}
Andreas Ch.
  • 203
  • 1
  • 8

2 Answers2

0

Use Glide to load your images, which cache your images until their uri changes, and gives very fast and smooth loading experience.

you can load images as simple as following example.

ImageView imageView = (ImageView) findViewById(R.id.my_image_view);

Glide.with(this).load("image url").into(imageView);
Nikhil
  • 3,711
  • 8
  • 32
  • 43
0

I think the best solution is to seperate download and view creation.

You know the data to display in your ListView, so download the images onto the device (for example into the apps cache-dir like shown in this answer). You don't have to eagerly download the images of all the ListViews entries. Just keep track of the users scrolling status and start downloading the next few images.

When initializing the ImageView set the Image-Source to your local file like shown in this answer.

Community
  • 1
  • 1
DaniEll
  • 1,022
  • 4
  • 22
  • 31
  • Hi. i dont think dowbloading all the images would be very efficient since my listview is "infinite". Maybe i can download like 10 of them each time save them at the cache and load them from there. Because i dont think i can load 500+ images in the cache. – Andreas Ch. Sep 10 '16 at 16:08