android - GridView 内的项目在上下滚动时再次加载

标签 android android-layout android-gridview baseadapter universal-image-loader

我正在使用 GridView 来显示许多图像的缩略图,因此用户可以选择其中任何一个,我将全屏显示该图像。 网格的每个项目仅由一个 ImageView 组成,图像是从远程服务器检索的。

当触摸某个项目时,将启动另一个 Activity 以全屏显示图像。

这里我用了Universal Image Loader 。在这里,我对 Gridview 使用相同的方式,如 this类是通用图像加载器的一部分。

我以为一切都很顺利,直到我注意到当我滚动屏幕时,某些项目正在重复并再次加载。

所以我将显示图像逻辑放在 convertview== null 部分中,所以现在每当我在网格中向下滚动然后返回时,项目都会更改其位置并被复制。项目 ImageView (缩略图)在很多项目中重复,但其实际内容不同,当我单击该项目时,我可以看到这一点。现在滚动速度比第一个代码太慢。

所以我的主要问题是

如果我使用第一个代码:

1)如果我使用第一个代码,那么当我向下或向上滚动时,图像(项目)会一次又一次地加载。

如果我使用第二个代码:

2)如果我使用第二个代码,则项目(图像缩略图)将显示重复并显示为其他图像的缩略图。 3)Gridview滚动太慢。

代码:1

public class ImageAdapter extends BaseAdapter {
    ArrayList<GallaryImage> imageList = null;
    private Context context;

    private class ViewHolder {
        public ImageView image;
        public ProgressBar pb;
    }

    public ImageAdapter(final Context context,
            final ArrayList<GallaryImage> imageAttributesList) {
        this.imageList = imageAttributesList;
        this.context = context;

    }

    @Override
    public int getCount() {
        return imageList.size();
    }

    @Override
    public GallaryImage getItem(final int position) {
        return imageList.get(position);
    }

    @Override
    public long getItemId(final int position) {
        return position;
    }

    @Override
    public View getView(final int position, final View convertView,
            final ViewGroup parent) {
        View view = convertView;
        ViewHolder holder = null;
        if (convertView == null) {

            LayoutInflater inflater = (LayoutInflater) context
                    .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            view = inflater
                    .inflate(R.layout.item_grid_image, parent, false);
            holder = new ViewHolder();
            holder.pb = (ProgressBar) view.findViewById(R.id.pb_grid_image);
            holder.image = (ImageView) view.findViewById(R.id.grid_image);
            view.setTag(holder);
        } else {
            holder = (ViewHolder) view.getTag();
        }
        display(holder.image, imageList.get(position).mImageUrl, holder.pb);
        return view;
    }

    /**
     * @param img
     * @param url
     * @param spinner
     */
    public void display(ImageView img, String url, final ProgressBar spinner) {
        imageLoader.displayImage(url, img, options,
                new ImageLoadingListener() {
                    @Override
                    public void onLoadingStarted(String imageUri, View view) {
                        spinner.setVisibility(View.VISIBLE);
                    }

                    @Override
                    public void onLoadingFailed(String imageUri, View view,
                            FailReason failReason) {
                        spinner.setVisibility(View.GONE);

                    }

                    @Override
                    public void onLoadingComplete(String imageUri,
                            View view, Bitmap loadedImage) {
                        spinner.setVisibility(View.GONE);
                    }

                    @Override
                    public void onLoadingCancelled(String imageUri,
                            View view) {

                    }

                });
    }

    /**
     * @param updateData
     */
    public void updatedData(ArrayList<GallaryImage> imgList) {
        this.imageList = imgList;
        notifyDataSetChanged();
    }
}

代码:2

private static final String TAG = "[Photography: ImageGridActivity]";
private DisplayImageOptions options;
private GridView mGridView = null;
ArrayList<GallaryImage> mGridViewImagesList;
private ImageAdapter mImageAdapter = null;
private String mImageUrl = null;
private String mGallaryTitle = null;

@Override
public void onCreate(final Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_image_grid);
    options = new DisplayImageOptions.Builder()
            .showImageOnFail(R.drawable.ic_error)
            .showStubImage(R.drawable.photo_default).cacheOnDisc()
            .bitmapConfig(Bitmap.Config.RGB_565).build();

    final Bundle bundle = getIntent().getExtras();
    if (bundle != null) {
        mImageUrl = bundle.getString(Constants.GALLARY_FETCH_URL);

        mGallaryTitle = bundle.getString(Constants.GALLARY_TYPE);
        if (mGallaryTitle != null) {

            Locale loc = Locale.getDefault();
            TextView tvTitleText = (TextView) findViewById(R.id.tv_title_bar_text);
            tvTitleText.setText(mGallaryTitle.toUpperCase(loc));
        }
        mGridView = (GridView) findViewById(R.id.gridview);

        mGridViewImagesList = Utility.getImagesList(mImageUrl,
                ImageGridActivity.this);

        if (mGridViewImagesList != null && !mGridViewImagesList.isEmpty()) {
            mImageAdapter = new ImageAdapter(ImageGridActivity.this,
                    mGridViewImagesList);
            ((GridView) mGridView).setAdapter(mImageAdapter);
        } else {
            // did refresh after the previous images are loaded in the
            // gridview.
            if (Utility.checkConnection(ImageGridActivity.this)) {
                Log.i(TAG,
                        "Wifi/Internet Connection found , have to parse the xml");

                final FetchImagesAsyncTaskFeed asyncTask = new FetchImagesAsyncTaskFeed(
                        true);
                asyncTask.execute(mImageUrl);

            }

        }

        mGridView.setOnItemClickListener(new OnItemClickListener() {
            @Override
            public void onItemClick(final AdapterView<?> parent,
                    final View view, final int position, final long id) {

                if (mGridViewImagesList != null
                        && !mGridViewImagesList.isEmpty()) {
                    startImagePagerActivity(mGridViewImagesList, position);
                } else {
                    Log.d(TAG, "There is no image about this grid image");
                }
            }
        });

    }

}

/**
 * back button key event
 */
private void goBack() {
    finish();
    // overridePendingTransition(R.anim.slide_in_right,
    // R.anim.slide_out_right);
}

@Override
public boolean onKeyUp(int keyCode, KeyEvent event) {
    if (keyCode == KeyEvent.KEYCODE_BACK) {
        goBack();
        return true;
    }
    return super.onKeyUp(keyCode, event);
}

/**
 * @param position
 */
private void startImagePagerActivity(
        final ArrayList<GallaryImage> mImageAttributesList,
        final int position) {
    String[] urls = new String[mImageAttributesList.size()];
    final Intent intent = new Intent(this, ImagePagerActivity.class);
    intent.putExtra(Constants.GALLARY_IMAGE_POSITION_BUNDLE_KEY, position);
    for (int i = 0; i < mImageAttributesList.size(); i++) {
        urls[i] = mImageAttributesList.get(i).mImageUrl;
    }
    intent.putExtra(Constants.GALLARY_IMAGES_IMAGE_BUNDLE_KEY, urls);
    startActivity(intent);
}

public class ImageAdapter extends BaseAdapter {
    ArrayList<GallaryImage> imageList = null;

    private class ViewHolder {
        public ImageView image;
        public ProgressBar pb;
    }

    public ImageAdapter(final Context context,
            final ArrayList<GallaryImage> imageAttributesList) {
        this.imageList = imageAttributesList;

    }

    @Override
    public int getCount() {
        return imageList.size();
    }

    @Override
    public GallaryImage getItem(final int position) {
        return imageList.get(position);
    }

    @Override
    public long getItemId(final int position) {
        return position;
    }

    @Override
    public View getView(final int position, final View convertView,
            final ViewGroup parent) {
        View view = convertView;
        final ViewHolder holder;
        if (convertView == null) {
            view = getLayoutInflater().inflate(R.layout.item_grid_image,
                    parent, false);
            holder = new ViewHolder();
            holder.pb = (ProgressBar) view.findViewById(R.id.pb_grid_image);
            holder.image = (ImageView) view.findViewById(R.id.grid_image);
            view.setTag(holder);
            display(holder.image, imageList.get(position).mImageUrl, holder.pb);
        } else {
            holder = (ViewHolder) view.getTag();
        }
        return view;
    }

    /**
     * @param img
     * @param url
     * @param spinner
     */
    public void display(ImageView img, String url, final ProgressBar spinner) {
        imageLoader.displayImage(url, img, options,
                new ImageLoadingListener() {
                    @Override
                    public void onLoadingStarted(String imageUri, View view) {
                        spinner.setVisibility(View.VISIBLE);
                    }

                    @Override
                    public void onLoadingFailed(String imageUri, View view,
                            FailReason failReason) {
                        spinner.setVisibility(View.GONE);

                    }

                    @Override
                    public void onLoadingComplete(String imageUri,
                            View view, Bitmap loadedImage) {
                        spinner.setVisibility(View.GONE);
                    }

                    @Override
                    public void onLoadingCancelled(String imageUri,
                            View view) {

                    }

                });
    }

    /**
     * @param updateData
     */
    public void updatedData(ArrayList<GallaryImage> imgList) {
        this.imageList = imgList;
        notifyDataSetChanged();
    }
}

/**
 * @author
 * 
 */
private class FetchImagesAsyncTaskFeed extends
        AsyncTask<String, Void, String> {
    ProgressBar progressbar = null;
    boolean showProgress = false;

    public FetchImagesAsyncTaskFeed(boolean showProgress) {
        this.showProgress = showProgress;
    }

    @Override
    protected void onPreExecute() {
        if (showProgress) {

            progressbar = (ProgressBar) ImageGridActivity.this
                    .findViewById(R.id.gv_progressBar);
            progressbar.setVisibility(View.VISIBLE);

        }
    }

    @Override
    protected String doInBackground(final String... urls) {
        try {
            final String imageUrl = urls[0];
            final GridViewImagesXMLHandler mGallaryXMLHandler = new GridViewImagesXMLHandler();
            mGridViewImagesList = mGallaryXMLHandler.getImages(imageUrl);
            if (mGridViewImagesList != null
                    && !mGridViewImagesList.isEmpty()) {
                Utility.setImagesInfromation(imageUrl, mGridViewImagesList,
                        ImageGridActivity.this);
            }
        } catch (final Exception e) {
            Log.e(TAG, "Exception in fetch images from the url", e);
        }
        return null;
    }

    @Override
    protected void onPostExecute(final String result) {
        if (mGridViewImagesList != null && !mGridViewImagesList.isEmpty()) {
            if (mImageAdapter != null) {
                mImageAdapter.updatedData(mGridViewImagesList);
                // mPullRefreshGridView.onRefreshComplete();
            } else {
                mImageAdapter = new ImageAdapter(ImageGridActivity.this,
                        mGridViewImagesList);
                ((GridView) mGridView).setAdapter(mImageAdapter);
            }
        }
        // mPullRefreshGridView.onRefreshComplete();
        if (progressbar != null) {
            progressbar.setVisibility(View.GONE);
        }
    }
}

GridView XML 文件

<GridView
    android:id="@+id/gridview"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:layout_below="@id/title_bar"
    android:alwaysDrawnWithCache="true"
    android:gravity="center"
    android:horizontalSpacing="4dip"
    android:numColumns="4"
    android:scrollingCache="true"
    android:smoothScrollbar="true"
    android:stretchMode="columnWidth"
    android:verticalSpacing="4dip" />

请帮我解决这个问题。感谢您的帮助。

谢谢

最佳答案

因为我们每次进入getView()时都会设置ImageView的背景。每次当一个项目对用户可见时(当您滚动时发生),getView() 都会调用。 由于 BaseAdapter 回收 View ,因此我们被迫在 if 和 else 条件之后设置数据。将所有图像保存在一个 DiskLruCache 更快地加载它们并检查它是否存在,然后从那里显示,否则下载它并将其添加到 DiskLruCache

关于android - GridView 内的项目在上下滚动时再次加载,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16556242/

相关文章:

php - 接收 JSON 列表时出错

android - 在多个 Activity 中使用抽屉导航

java - 如何将框架布局的 y 值设置为屏幕高度的 3/4?

java - 如何正确使用 setOnItemClickListener?

java - Java 代码在单个线程中的执行是否保证是顺序的?

java - 如何在 Android 单元测试中用模拟数据填充适配器?

android - 复选框未显示在 android 布局上

android - 以编程方式在后台有 GL View 的软键盘上使用 EditText

Android:响应项目点击的多个gridView行

安卓 : GridView was Not Marked insit of that it load to empty Activity