如何在ListView中从网络下载图像而不会延迟?

时间:2011-04-23 04:55:27

标签: java android imageview android-arrayadapter listadapter

我有一个ListAdapter,其中包含从Internet上下载的一堆图像。当我向上和向下滚动时,似乎有性能损失,事情变得不稳定。我该如何解决这个问题?

@Override
        public View getView(int position, View convertView, ViewGroup parent) {
            View v = convertView;
            if (v == null) {
                LayoutInflater vi = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE);
                v = vi.inflate(R.layout.message_row, null);
            }

            STMessage aMessage = messages.get(position);

            if (aMessage != null) {
                TextView usernameTextView = (TextView) v.findViewById(R.id.usernameTextView);
                TextView bodyTextView = (TextView) v.findViewById(R.id.bodyTextView);
                TextView dateTextView = (TextView) v.findViewById(R.id.dateTextView);
                ImageView avatarImageView = (ImageView)v.findViewById(R.id.avatarImageView);

                if (usernameTextView != null) {
                    usernameTextView.setText(Html.fromHtml(aMessage.getUser_login()));
                }
                if (bodyTextView != null) {
                    bodyTextView.setText(aMessage.getBody());

                    //linkify urls
                    Linkify.addLinks(bodyTextView, Linkify.WEB_URLS);


                    //linkify symbols
                    Pattern symbolMatcher = Pattern.compile("/(?:^|\\s|[\\.(\\+\\-\\,])(?:\\$?)\\$((?:[0-9]+(?=[a-z])|(?![0-9\\.\\:\\_\\-]))(?:[a-z0-9]|[\\_\\.\\-\\:](?![\\.\\_\\.\\-\\:]))*[a-z0-9]+)/i");
                    String symbolURL =    "content://com.stocktwits.activity/symbol/";
                    Linkify.addLinks(bodyTextView, symbolMatcher, symbolURL);
                }
                if (dateTextView != null) {
                    dateTextView.setText(aMessage.getUpdated_at());
                }

                if (avatarImageView != null) {
                    imageDownloader.download(aMessage.getAvatar_url(), avatarImageView);
                }
            }

            return v;
        }

3 个答案:

答案 0 :(得分:4)

使用延迟加载图片 - Lazy load of images in ListView

答案 1 :(得分:0)

也许通过使用线程池(队列)并在此期间放置时间图像?

答案 2 :(得分:0)

这是一个很好的方法。

至少我认为它很好。我做到了:)

这是我用来在后台加载ImageView的类。

public class DownloadImageTask extends AsyncTask<String, Void, Bitmap> {
    private ImageView destination;
    private String cachedFile;
    private Date startTime; 
    private DownloadCompletedListener completedListener; 

    public DownloadImageTask(ImageView destination, String cachedFile, DownloadCompletedListener completedListener)
    {
        this.destination = destination;
        this.cachedFile = cachedFile;
        this.startTime = new Date();
        this.completedListener = completedListener;
    }

    protected Bitmap doInBackground(String... urls) 
    {
        Bitmap result = getBitmapFromURL(urls[0]);
        if (result != null)
        {
            try {
            FileOutputStream out = new FileOutputStream(HSAppUtil.getFilePath(getFilenameFromUrl(urls[0])));
                result.compress(Bitmap.CompressFormat.PNG, 90, out);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
        else
        {
            result = Bitmap.createBitmap(1,1,Config.ARGB_8888);
        }
        return result;
    }

    public String getHost() {
        return "http://MyMainHost";
    }

    public Bitmap getBitmapFromURL(String fileUrl) {
        String newFileUrl = null;
        if (!fileUrl.contains("://"))
        {
            newFileUrl = getHost() + fileUrl;
        }
        else
        {
            newFileUrl = fileUrl;
        }
        URL myFileUrl = null;
        try {
            myFileUrl = new URL(newFileUrl);
        } catch (MalformedURLException e) {
            e.printStackTrace();
        }

        try {
            HttpURLConnection conn = (HttpURLConnection) myFileUrl.openConnection();
            conn.setDoInput(true);
            conn.connect();
            int length = conn.getContentLength();
            InputStream is = conn.getInputStream();
            length++;
            return BitmapFactory.decodeStream(is);
        } catch (IOException e) {
            e.printStackTrace();
        }
        return null;
    }
    protected void onPostExecute(Bitmap result) 
    {
        synchronized (destination) 
        {
            Date lastUpdated = (Date)destination.getTag();

            if (lastUpdated == null || lastUpdated.before(startTime))
            {
                boolean handled = false;

                if (completedListener != null)
                {
                    handled = completedListener.handleDownloadCompleted(destination, result);
                }   
                if (!handled && destination != null)
                {
                    destination.setTag(startTime);
                    destination.setImageBitmap(result);
                }
            }   
            result = null;
        }
    }

    public interface DownloadCompletedListener {
        boolean handleDownloadCompleted(ImageView i, Bitmap b);
    }
}

然后当你想使用它时,你会这样称呼它。

new DownloadImageTask(imView, fileUrl, completedListener).execute(fileUrl);

并将imView发送到UI。它将在下载时加载图像。

请给我你诚实的反馈。