将图像加载到自定义列表视图 - 如何逐步加载?

时间:2014-04-07 09:43:40

标签: android android-listview

我有一个自定义Listview - 其中包含imageView,文本和复选框。

我正在从dropbox加载图片(使用thumnails或者将共享URL添加到图片中),然后使用ImageAdapter将它们加载到自定义Listview中。

将图像加载到给定文件夹中的速度非常慢。加载一些图像只需要几秒钟,如果有几十张图片需要几分钟,而我的应用程序崩溃了,如果有大量图像,我会假设内存不足异常。

从Dropbox获取URL似乎需要大约2秒钟(如果您对流进行解码,则需要获取位图)。因此,需要60秒才能检索30个图像网址。这是非常过分的(不确定为什么这么长时间?)

我希望我能更快地改进我的代码。我想逐步加载图像,即保持UI响应并分批加载图像。

我已经在使用Async任务,所以希望有人可以提供建议。

请注意,我已尝试使用通用图像加载程序,但仍需要很长时间才能加载图像。

我应该注意到,我认为问题在于从dropbox检索图像数据。下面的代码检索缩略图文件,速度非常慢。我已经尝试更改代码而不是检索到图像的URL链接,但再次执行和循环非常慢。

在循环完成之前,循环中是否有任何方法可以获取图像开始在ListView中显示数据?那就是 - 不要#39; t等到OnTaskCompleted - 而是开始在doInBackground内显示图片?

以下是异步任务的doInBackground

 @Override
    protected Boolean doInBackground(DbxFileSystem... params) {
        //Opens thumbnails for each image contained in the dropbox folder
        try {
            DbxFileSystem fileSystem = params[0];


            for (DbxFileInfo fileInfo: fileSystem.listFolder(currentPath)) {
                DbxFile file;

//this code below is very slow to execute
                try{
                    if(fileInfo.thumbExists) // if it has a thumbnail then retrieve it
                    {
                        file = fileSystem.openThumbnail(fileInfo.path, ThumbSize.XS, ThumbFormat.PNG);
                        Bitmap image = BitmapFactory.decodeStream(file.getReadStream());
                        pix.add(image);  // image to display in the custom listview
                        paths.add(fileInfo.path); // path to display in the custom listview

                        file.close();                     
                    }
                    else
                    {
                        //must be a folder if it has no thumb, so add local drawable folder icon
                        Bitmap image = BitmapFactory.decodeResource(getResources(), R.drawable.dbfolder);
                        pix.add(image);
                        paths.add(fileInfo.path);                   

                    }
                }catch (DbxException e1) {
                    e1.printStackTrace();
                } catch (IOException e) {
                    e.printStackTrace();
                }
                System.gc();
            }
        }
        catch (Exception e) {
            e.printStackTrace();

            return false;
        } finally {
            loadingDialog.dismiss();
        }
        return true;
    }

然后在onTaskCompleted中我们设置了Image Adapter:

       public void onTaskCompleted(int requestID, ArrayList<Bitmap> urls, ArrayList<DbxPath> path) {

            lstView = (ListView) findViewById(R.id.lstView);
            this.paths = path;

            ImageAdapter adapter = new ImageAdapter(this, urls, paths);
            lstView.setAdapter(adapter);
}

这是ImageAdapter.java

的getView
    public View getView(int position, View arg1, ViewGroup arg2) {
        LayoutInflater inflater = (LayoutInflater) context
                .getSystemService(Context.LAYOUT_INFLATER_SERVICE);

        View gridView;


        gridView = new View(context);

        // inflate image_helper layout
        gridView = inflater.inflate(R.layout.list_row, null);

        // set images
        ImageView imageView = (ImageView) gridView
                .findViewById(R.id.list_image);

        imageView.setImageBitmap(images.get(position));

        TextView textView = (TextView) gridView
                .findViewById(R.id.filename);

           textView.setText(folderName.get(position).toString());

        return gridView;
    }

1 个答案:

答案 0 :(得分:1)

为此,您可以使用通用图像加载器jar universal-image-loader-1.9.2-SNAPSHOT-with-sources.jar

然后适配器就像这样

public class LinkAdapter extends ArrayAdapter<MediaModel>{

    ArrayList<MediaModel> medias;
    Activity context;
    ImageLoader imageLoader;
    DisplayImageOptions options;

    public LinkAdapter(Activity context, int textViewResourceId,
            ArrayList<MediaModel> objects) {
        super(context, textViewResourceId, objects);
        this.medias = objects;
        this.context = context;
        imageLoader = ImageLoader.getInstance();
        imageLoader.init(ImageLoaderConfiguration.createDefault(context));
        options = new DisplayImageOptions.Builder()
        .showImageOnLoading(R.drawable.ic_launcher)
        .showImageForEmptyUri(R.drawable.ic_launcher)
        .showImageOnFail(R.drawable.ic_launcher).cacheInMemory(true)
        .cacheOnDisc(true).considerExifParams(true)
        .bitmapConfig(Bitmap.Config.RGB_565).build();
    }

    static class ViewHolder {
        TextView title;
        TextView description;
        ImageView iconImage;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        View v = convertView;
        ViewHolder holder;

        if (convertView == null) {
            LayoutInflater vi = (LayoutInflater) getContext()
                    .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            v = vi.inflate(R.layout.link_row, null);

            holder = new ViewHolder();
            holder.title = (TextView) v.findViewById(R.id.txt_row_title);
            holder.description = (TextView) v.findViewById(R.id.txt_row_description);
            holder.iconImage = (ImageView) v.findViewById(R.id.img_row_icon);
            v.setTag(holder);
        } else {
            holder = (ViewHolder) v.getTag();
        }

        holder.title.setText(medias.get(position).mediaTitle);
        holder.description.setText(medias.get(position).mediaInfo);
        imageLoader.displayImage(medias.get(position).mediaThumbImgUrl, holder.iconImage,options);

        return v;
    }

}