【问题标题】:How to force a cache clearing using Universal Image Loader Android?如何使用 Universal Image Loader Android 强制清除缓存?
【发布时间】:2012-12-08 21:02:31
【问题描述】:

我正在使用 UIL 在列表视图中加载图像。

当我在列表视图中长按一张图片时,我会显示一个对话框来修改该图片,并使用相机将其替换为新图片。

如果我拍了一张新照片,当对话框关闭时,我的列表视图仍会显示旧图像(因为它已被缓存)。如果我在转到列表视图时关闭并重新启动我的应用程序,则新图像正确存在。

这就是我设置 UIL 的方式:

// Get singletone instance of ImageLoader
    imageLoader = ImageLoader.getInstance();

    //set display options for image loader
    DisplayImageOptions displayOptions = new DisplayImageOptions.Builder()
    .cacheInMemory()
    .displayer(new FadeInBitmapDisplayer(500)) //fade in images
    .resetViewBeforeLoading()
    .build();

    //set image loader options
    ImageLoaderConfiguration config = new ImageLoaderConfiguration.Builder(this).defaultDisplayImageOptions(displayOptions).build();

    // Initialize ImageLoader with configuration.
    imageLoader.init(config);

如果我删除 .cacheInMemory() 一切正常。我只是想知道仅在打开对话框时是否可以清除缓存。我试图抓住所选的 ImageView 并在没有成功打开对话框时调用myImageView.invalidate()

图片是从文件中加载的:

// Load and display image asynchronously
imageLoader.displayImage(file_prefix + image_path, image);

有什么建议吗?

编辑:长按图像时创建上下文菜单的代码,我试图清除那里的缓存:

@Override
public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
    super.onCreateContextMenu(menu, v, menuInfo);

    //get info about item selected
    AdapterView.AdapterContextMenuInfo info;
    try {
        // Casts the incoming data object into the type for AdapterView objects.
        info = (AdapterView.AdapterContextMenuInfo) menuInfo;
    } catch (ClassCastException e) {
        // If the menu object can't be cast, logs an error.
        Log.e("no info", "bad menuInfo", e);
        return;
    }
    Cursor cursor = (Cursor) getListAdapter().getItem(info.position);
    if (cursor == null) {
        // For some reason the requested item isn't available, do nothing
        return;
    }

    //remove selected image from cache (if it is an image)
    imageUrl = cursor.getString(cursor.getColumnIndex("image_path"));
    if (!imageUrl.equalsIgnoreCase("")) {
        MemoryCacheUtil.removeFromCache(imageUrl, imageLoader.getMemoryCache());
    }

    Log.i("imageUrl", imageUrl);

    //get defect row ID and text content to pass it to defect activity
    defect_row_id = cursor.getLong(cursor.getColumnIndex("_id"));
    defect_txt = cursor.getString(cursor.getColumnIndex("defect"));

    MenuInflater inflater = getMenuInflater();

    Log.i("cursor", DatabaseUtils.dumpCursorToString(cursor));

    //set project identifier in context menu header, mapping cursor sequence of values
    menu.setHeaderTitle(getString(R.string.select_an_option));
    inflater.inflate(R.menu.menu_defect_row, menu);

}

选择菜单项(编辑或删除)时

@Override
public boolean onContextItemSelected(MenuItem item) {
    //AdapterContextMenuInfo info = (AdapterContextMenuInfo) item.getMenuInfo();
    switch (item.getItemId()) {

    case R.id.edit:

        //open defect activity with the specified image and defect pre-loaded
        Intent editDefectIntent = new Intent(this, DefectActivity.class);

        editDefectIntent.putExtra("defect_row_id", defect_row_id);
        editDefectIntent.putExtra("imageUrl", imageUrl);

        startActivity(editDefectIntent);

        return true;
    case R.id.delete:

        askDeleteConfirm();

        return true;

    default:
        return false;
    }

}//onContextItemSelected

编辑:显示图像列表的代码

@Override
public void onResume() {
    super.onResume();

    //open connection to db
    db = new DBAdapter(this);
    db.open();

    Log.i("DefectListActivity -> onResume", "called");

    // get all defects for this unit
    defectList = db.getAllDefectsByUnit(unit_id);
    // create an array adapter and let it to display our row
    defects = new SimpleCursorAdapter(this, R.layout.defect_row, defectList, new String[] { "defect", "image_path" }, new int[] { R.id.defect, R.id.image }, 0);

    //set custom view using ViewBinder
    SimpleCursorAdapter.ViewBinder binder = new SimpleCursorAdapter.ViewBinder() {
        @Override
        public boolean setViewValue(View view, Cursor cursor, int columnIndex) {

            int placeholder_id = getResources().getIdentifier("placeholder", "drawable", getPackageName());

            //get column name
            String name = cursor.getColumnName(columnIndex);

            //for the thumbnail column,if we have an image replace the placeholder
            if ("image_path".equals(name)) {

                ImageView image = (ImageView) view.findViewById(R.id.image);
                //Bitmap thumbnail;
                String image_path = cursor.getString(columnIndex);

                Log.i("image_path ->", image_path);

                if (!image_path.equalsIgnoreCase("")) {

                // Load and display image asynchronously
                imageLoader.displayImage(file_prefix + image_path, image);

                } else {

                    image.setImageResource(placeholder_id);


                    }

                return true;

            }

            //for the defect column, just add the text to the view
            if ("defect".equals(name)) {

                String defect_text = cursor.getString(columnIndex);

                TextView defect_holder = (TextView) view.findViewById(R.id.defect);
                defect_holder.setText(defect_text);

                return true;
            }

            return false;
        }
    };

    defects.setViewBinder(binder);

    setListAdapter(defects);

}//onResume

【问题讨论】:

    标签: android universal-image-loader


    【解决方案1】:

    如果你同时缓存在内存和磁盘中,例如:

    ImageLoaderConfiguration config = new ImageLoaderConfiguration.Builder(getApplicationContext())         
            .memoryCache(new UsingFreqLimitedMemoryCache(2 * 1024 * 1024)) 
            .discCache(new UnlimitedDiscCache(cacheDir)) 
    .........
    

    确保将其从两者中删除,然后重新加载图像视图。

    MemoryCacheUtils.removeFromCache(url, ImageLoader.getInstance().getMemoryCache());
    DiscCacheUtils.removeFromCache(url, ImageLoader.getInstance().getDiscCache());
    

    【讨论】:

    • 你刚刚救了我的命。
    • 我没有找到DiscCacheUtils 也没有找到getDiscCache。我想你想说DiskCacheUtilsgetDiskCache
    • 我在旧版本的库中,我目前正在使用 ImageLoader.getInstance().getDiscCache() ImageLoader.getInstance().getMemoryCache()DiscCacheUtil 仍然在 1.9 版中。+ 我相信。
    【解决方案2】:

    这应该可行:

    imageLoader.clearMemoryCache();
    

    【讨论】:

    • 清除内存缓存:imageLoader.clearMemoryCache(); 并清除磁盘缓存:imageLoader.clearDiscCache();
    【解决方案3】:

    我认为您应该在打开对话框时删除内存缓存中的缓存图像。为此使用MemoryCacheUtil

    MemoryCacheUtils.removeFromCache(imageUrl, imageLoader.getMemoryCache());
    

    【讨论】:

    • 我试过了,还是不行。我正在打开一个上下文菜单,然后是一个对话框。我将这些行添加到我的onCreateContextMenu,但它没有做任何事情。我还尝试将图像 url 传递给对话框并从那里清除缓存以获取 imageLoader 单例,仍然相同。
    • 用相机换了一张新照片后,你会打电话给imageLoader.displayImage(file_prefix + image_path, image);吗?
    • 其实之前,打开对话框时
    • 我应该在刷新列表视图之前调用它吗?
    • 我不明白你的逻辑。在问题中添加一些代码。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-12-13
    • 1970-01-01
    相关资源
    最近更新 更多