0

我正在构建一种 Pulse 类型的 UI。为此,我使用Galleryinside ListView。但是,我遇到了一个奇怪的问题,当我滚动浏览列表视图时,我的应用程序中的内存分配逐渐从 9 MB 增加到 64 MB,直到它最终崩溃。

什么不起作用:

  • 我怀疑这是否是因为我使用的位图。因此,我在画廊内没有图像的情况下对其进行了测试。我还使用了 Universal Image Loader库。然而,一切都没有改变。

  • 我在 SO 中阅读了类似的问题,禁用scrollingCachelistView 可能会有所帮助。但是,仍然没有效果。

什么有效:

  • ViewHolder使用,设计高效的适配器getTag()setTag()解决了内存问题。但是,它带来了一个奇怪的问题,listView 有时会显示空行或重复行,从而在 UI 中显示错误的数据。我该如何解决这个问题?有没有更好的方法来解决这个问题?

ListViewAdapter.java

public class ListViewAdapter extends BaseAdapter {
    String user_locale;
    Context context;
    LayoutInflater inflater;
    AssetsAdapter assestsAdapter;
    List<Category> categoryList;
    List<BaseAssets> baseAssetList;
    AssetsTable assetTable;
    ViewHolder viewHolder;

public ListViewAdapter(Context context, List<Category> categoryList) {
    this.context = context;
    user_locale = Universal.getCurrentLanguage(context);
    inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    this.categoryList = categoryList;
    assetTable = new AssetsTable(context);
    viewHolder = new ViewHolder();
}

public int getCount() {
    return categoryList.size();
}

public Object getItem(int position) {
    return position;
}

public long getItemId(int position) {
    return position;
}

public View getView(final int position, View convertView, ViewGroup parent) {
    String catID = categoryList.get(position).catID;

    if (convertView == null)
    {
        convertView = inflater.inflate(R.layout.category_list_item, parent, false);
        viewHolder.categoryTitle = (TextView) convertView.findViewById(R.id.category_title);
        viewHolder.gallery = (Gallery) convertView.findViewById(R.id.gallery);
        convertView.setTag(viewHolder);
    } else
        viewHolder = (ViewHolder) convertView.getTag();

    assetTable = new AssetsTable(context);
    int count = assetTable.getCountOfParticularCategory(catID);

    initializeGallery(catID);

    String text = categoryList.get(position).catName + "  (" + count + ")  ";
    viewHolder.categoryTitle.setText(text);
    return convertView;

}

public void initializeGallery(String catID) {
    assetTable = new AssetsTable(context);
    baseAssetList = assetTable.getAllBaseAssets(catID);
    assestsAdapter = new AssetsAdapter(context, baseAssetList);
    adjustGalleryHeight();
    viewHolder.gallery.setAdapter(assestsAdapter);
}

public void adjustGalleryHeight() {
    boolean isPortrait = false;
    final String TAG_PORTRAIT = "portrait";

    for (BaseAssets b : baseAssetList)
    {
        if (b.thumbOrientation.equals(TAG_PORTRAIT))
            isPortrait = true;
    }

    final float scale = context.getResources().getDisplayMetrics().density;
    if (isPortrait)
    {
        RelativeLayout.LayoutParams params1 = (RelativeLayout.LayoutParams) viewHolder.gallery.getLayoutParams();
        params1.height = (int) (350 * scale);
        viewHolder.gallery.setLayoutParams(params1);
    } else
    {
        RelativeLayout.LayoutParams params1 = (RelativeLayout.LayoutParams) viewHolder.gallery.getLayoutParams();
        params1.height = (int) (280 * scale);
        viewHolder.gallery.setLayoutParams(params1);
    }
}

class ViewHolder {
    TextView categoryTitle;
    Gallery gallery;

}

}

GalleryAdapter.java:

public class GalleryAdapter extends BaseAdapter {

final String TAG_PORTRAIT = "portrait";
LayoutInflater inflater;
ImageLoader imageLoader;
DisplayImageOptions options;
Context context;
List<BaseAssets> baseAssetsList;

Gallery.LayoutParams params;

public GalleryAdapter(Context context, List<BaseAssets> baseAssetsList) {
    imageLoader = ImageLoader.getInstance();
    options = new DisplayImageOptions.Builder().cacheOnDisc().imageScaleType(ImageScaleType.EXACTLY).bitmapConfig(Bitmap.Config.RGB_565).cacheInMemory().showStubImage(
            R.drawable.no_preview).build();
    this.context = context;
    this.baseAssetsList = baseAssetsList;
    inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);

}

public int getCount() {
    return baseAssetsList.size();
}

public Object getItem(int position) {
    return position;
}

public long getItemId(int position) {
    return position;
}

public View getView(final int position, View convertView, ViewGroup parent) {

    ViewHolder viewHolder;
    if (convertView == null)
    {
        viewHolder = new ViewHolder();
        convertView = inflater.inflate(R.layout.gallery_list_item, parent, false);
        viewHolder.galleryWrapper = (RelativeLayout) convertView.findViewById(R.id.gallery_wrapper);
        viewHolder.downloadThumbnail = (ImageView) convertView.findViewById(R.id.thumbnailDownloadStatus);
        viewHolder.assetImage = (ImageView) convertView.findViewById(R.id.thumbnail_image);
        viewHolder.assetName = (TextView) convertView.findViewById(R.id.thumbnail_name);
        convertView.setTag(viewHolder);
    } else
        viewHolder = (ViewHolder) convertView.getTag();

    final float scale = context.getResources().getDisplayMetrics().density;

    if (baseAssetsList.get(position).thumbOrientation.equals(TAG_PORTRAIT))
    {

        params = new Gallery.LayoutParams((int) (166 * scale), (int) (245 * scale));
        viewHolder.galleryWrapper.setLayoutParams(params);

    } else
    {
        params = new Gallery.LayoutParams((int) (238 * scale), (int) (191 * scale));
        viewHolder.galleryWrapper.setLayoutParams(params);
    }

    viewHolder.assetName.setText(baseAssetsList.get(position).contentTitle);
    String raw_url = baseAssetsList.get(position).thumbnail;
    String correctUrl = correctUrl(raw_url);
    imageLoader.displayImage(correctUrl, viewHolder.assetImage, options);

    convertView.setOnClickListener(new View.OnClickListener() {

        public void onClick(View v) {
            Intent intent = new Intent(context, DownloadActivity.class);
            intent.putExtra(Universal.ASSET_TYPE, baseAssetsList.get(position).contentType);
            intent.putExtra(Universal.ASSET_TITLE, baseAssetsList.get(position).contentTitle);
            intent.putExtra(Universal.ASSET_URL, baseAssetsList.get(position).path);
            intent.putExtra(Universal.ASSET_LARGE_THUMBNAIL, baseAssetsList.get(position).thumbnail);

            intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

            context.startActivity(intent);

        }
    });

    return convertView;
}

public String correctUrl(String raw_url) {
    String corrected_url = raw_url;
    if (!raw_url.contains("http:/"))
        corrected_url = ("http:/" + raw_url);
    return corrected_url;
}

class ViewHolder {
    RelativeLayout galleryWrapper;
    ImageView assetImage;
    ImageView downloadThumbnail;
    TextView assetName;

}

}

4

2 回答 2

2

在你的ListViewAdapter你没有打电话

viewHolder = new ViewHolder();

在什么getView()时候。convertViewnull

核实!这可能是问题所在。

于 2013-04-16T05:51:33.907 回答
1

尝试更改“viewHolder = new ViewHolder();” 如果 convertview 为空,则在 Adapter 的 getview 内;

喜欢 :

public View getView(final int position, View convertView, ViewGroup parent) {
String catID = categoryList.get(position).catID;

if (convertView == null)
{
    viewHolder = new ViewHolder(); //Add this line. Otherwise u are sharing the same instance for other views.
    convertView = inflater.inflate(R.layout.category_list_item, parent, false);
    viewHolder.categoryTitle = (TextView) convertView.findViewById(R.id.category_title);
    viewHolder.gallery = (Gallery) convertView.findViewById(R.id.gallery);
    convertView.setTag(viewHolder);
} else
    viewHolder = (ViewHolder) convertView.getTag();

assetTable = new AssetsTable(context);
int count = assetTable.getCountOfParticularCategory(catID);

initializeGallery(catID);

String text = categoryList.get(position).catName + "  (" + count + ")  ";
viewHolder.categoryTitle.setText(text);
return convertView;

}

于 2013-04-16T05:46:35.990 回答