在同步中加载GridView中的图像 - Android

时间:2013-05-21 20:18:59

标签: android multithreading gridview imageview

我有一个问题,我有一个GridView,我在其中使用ImageView加载图像,这些图像存储在SD中,为此我使用Runnable类进行加载。 当它滚动浏览GridView时,图像被加载到对应的框中(ImageView),在其他表中也是如此,我正在制作类似音乐专辑的列表,图像被加载到专辑中,但也加载到另一个,等等,你怎么做同步?,即如果一次充电,不加载到另一个

我希望我理解

感谢

PD:抱歉我的英文

public View getView(int position, View convertView, ViewGroup parent) {
    View v = convertView;
    if (v == null) {
        LayoutInflater vi = (LayoutInflater) getContext().getSystemService("layout_inflater");
        v = vi.inflate(R.layout.listitemalbum, null);
    }

    bnSong = songs.get(position);
    if (bnSong != null) {
        coverAlbum = (ImageView) v.findViewById(R.id.imgCover);
        coverAlbum.setScaleType(ImageView.ScaleType.CENTER_CROP);

        if (bnSong.getAlbum() == null){
            coverAlbum.setBackgroundResource(R.drawable.mksong);
        }else{
            try {
                Runnable r = new Runnable() {
                    @Override
                    public void run() {
                        try{
                            Thread.sleep(1000);                                 
                            Storage storage = new Storage();                                
                            cover = storage.getOpenImagen(bnSong.getAlbum(), "ALBUM");
                        }catch (Exception e){
                            e.printStackTrace();
                        }
                        coverAlbum.post(new Runnable() {
                            @Override
                            public void run() {
                                coverAlbum.invalidate();
                                coverAlbum.setImageBitmap(null);
                                if (cover != null){
                                    coverAlbum.setImageBitmap(cover);
                                }else {
                                    coverAlbum.setBackgroundResource(R.drawable.mksong);
                                }
                            }
                        });
                    }
                };
                new Thread(r).start();
            } catch (Exception e) {
                coverAlbum.setBackgroundResource(R.drawable.mksong);
            }
        }
    }
    return v;
}

2 个答案:

答案 0 :(得分:1)

我正在使用Android Universal Loader,这是我用来制作此https://github.com/nostra13/Android-Universal-Image-Loader

的最佳库

答案 1 :(得分:1)

有一个专门针对您的问题的库,由Google团队发布,名为“volley”。虽然它很新鲜。此处的信息:https://developers.google.com/live/shows/474338138/

为了解决没有图书馆的问题: 首先,您应该在runnable和线程上使用android AsyncTask和executeOnExecutor(THREAD_POOL_EXECUTOR)方法。你正在为屏幕上的每个视图创建一个新线程,以及每次滚动时。如果你真的想用runnables做这个,可以使用ExecutorService创建一个线程池,并在那里发布你的runnables。

现在,您遇到的问题是在重复使用视图时图像被覆盖。您需要做的是在下载图像后检查查看位置的项目是否具有相同的相册。通常最好使用视图上的标记来完成。

public View getView(int position, View convertView, ViewGroup parent) {
View v = convertView;
if (v == null) {
    LayoutInflater vi = (LayoutInflater) getContext().getSystemService("layout_inflater");
    v = vi.inflate(R.layout.listitemalbum, null);
}

final Song song = songs.get(position);
if (song != null) {
    final ImageView coverAlbum = (ImageView) v.findViewById(R.id.imgCover);
    coverAlbum.setScaleType(ImageView.ScaleType.CENTER_CROP); // Why not do this once, at inflation?

    final Album album = song.getAlbum();
    coverAlbum.setTag(album);        

    if (album == null){
        coverAlbum.setBackgroundResource(R.drawable.mksong);
    }else{
        // This should really be in a full class which extends AsyncTask
        AsyncTask<Album, Void, Bitmap> task = new AsyncTask<Album, Void, Bitmap>() {
            @Override
            public Bitmap doInBackground(Album... albums) {
                final Album album = albums[0];
                try{
                    Storage storage = new Storage();                                
                    return storage.getOpenImagen(album, "ALBUM");
                }catch (Exception e){
                    e.printStackTrace();
                    return null;
                }
            }

            @Override
            protected void onPostExecute(Bitmap cover) {
                final Album currentAlbum = (Album) coverAlbum.getTag();
                if(!album.equals(currentAlbum))
                    return;

                coverAlbum.invalidate();
                coverAlbum.setImageBitmap(null);
                if (cover != null){
                    coverAlbum.setImageBitmap(cover);
                }else {
                    coverAlbum.setBackgroundResource(R.drawable.mksong);
                }
            }
        }

        task.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR, album)
    }
}
return v;