1

我知道标题有点乱,但问题出在这里……我的目标是检索标题,并使用缩略图 URL 将我的 youtube 频道视频的缩略图绘制到 listView……到目前为止,我有textView 可以正确显示视频标题,但无论如何都无法绘制缩略图.....顺便说一下,我已经正确完成了 json / sqlite 东西类,它们可以正确检索数据,所以我不必担心。 ..唯一困扰我的是缩略图不会显示,imageView在应用程序中显示为空白空间......

这是我的代码,请帮帮我。谢谢

这是活动的创建方法...

public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);


    String[] uiBindFrom = { TutListDatabase.COL_TITLE, TutListDatabase.COL_THUMBNAIL };
    int[] uiBindTo = { R.id.title, R.id.thumbnail };

    getLoaderManager().initLoader(TUTORIAL_LIST_LOADER, null, this);

    adapter = new SimpleCursorAdapter(
            getActivity().getApplicationContext(), R.layout.list_item,
            null, uiBindFrom, uiBindTo,
            CursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER);
    adapter.setViewBinder(new MyViewBinder());
    setListAdapter(adapter);
}

而这个是把东西放到listView上的私有类...

private class MyViewBinder implements SimpleCursorAdapter.ViewBinder{

    @Override
    public boolean setViewValue(View view, Cursor cursor, int columnIndex) {
        int viewId = view.getId();
        switch(viewId){
        case R.id.title:
            TextView titleTV = (TextView)view;
            titleTV.setText(cursor.getString(columnIndex));
            break;

                    // it is not displaying any thumbnail in app....
        case R.id.thumbnail:
            ImageView thumb = (ImageView) view;
            thumb.setImageURI(Uri.parse(cursor.getString(columnIndex)));

        break;
        }
        return false;
    }

}

这是xml布局文件...

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:gravity="center_vertical"
android:orientation="horizontal" >

<ImageView
    android:id="@+id/thumbnail"
    android:layout_width="101dp"
    android:layout_height="101dp"
    android:src="@drawable/icon" />

<TextView
    android:id="@+id/title"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:padding="6dp"
    android:textSize="24dp" />


</LinearLayout>
4

1 回答 1

2

我可以向您展示我使用过的一种方法,并且效果很好,首先我们需要一种缓存图像的方法,而我迄今为止看到的最好的方法是使用 LruCache,如出色的 Google IO 演示文稿中所述事半功倍:http ://www.youtube.com/watch?v=gbQb1PVjfqM

这是我对该演示文稿中描述的方法的实现。

public class BitmapCache extends LruCache<String, Bitmap> { 

    public BitmapCache(int sizeInBytes) {
        super(sizeInBytes);
    }   

    public BitmapCache(Context context) {
        super(getOptimalCacheSizeInBytes(context));
    }   

    public static int getOptimalCacheSizeInBytes(Context context) {
        ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);

        int memoryClassBytes = am.getMemoryClass() * 1024 * 1024;

        return memoryClassBytes / 8;
    }

    @Override
    protected int sizeOf(String key, Bitmap value) {
        return value.getRowBytes() * value.getHeight();
    }
}

接下来我们需要使用 AsyncTask 异步加载图像,以下实现负责将图像加载到给定的 ImageView 并处理缓存:

public class LoadImageAsyncTask extends AsyncTask<Void, Void, Pair<Bitmap, Exception>> {
    private ImageView mImageView;
    private String mUrl;
    private BitmapCache mCache;

    public LoadImageAsyncTask(BitmapCache cache, ImageView imageView, String url) {
        mCache = cache;
        mImageView = imageView;
        mUrl = url;

        mImageView.setTag(mUrl);
    }

    @Override
    protected void onPreExecute() {
        Bitmap bm = mCache.get(mUrl);

        if(bm != null) {
            cancel(false);

            mImageView.setImageBitmap(bm);
        }
    }

    @Override
    protected Pair<Bitmap, Exception> doInBackground(Void... arg0) {
        if(isCancelled()) {
            return null;
        }

        URL url;
        InputStream inStream = null;
        try {
            url = new URL(mUrl);
            URLConnection conn = url.openConnection();

            inStream = conn.getInputStream();

            Bitmap bitmap = BitmapFactory.decodeStream(inStream);

            return new Pair<Bitmap, Exception>(bitmap, null);

        } catch (Exception e) {
            return new Pair<Bitmap, Exception>(null, e);
        }
        finally {
            closeSilenty(inStream);
        }
    }

    @Override
    protected void onPostExecute(Pair<Bitmap, Exception> result) {
        if(result == null) {
            return;
        }

        if(result.first != null && mUrl.equals(mImageView.getTag())) {
            mCache.put(mUrl, result.first);
            mImageView.setImageBitmap(result.first);
        }
    }

    public void closeSilenty(Closeable closeable) {
        if(closeable != null) {
        try {
            closeable.close();
        } catch (Exception e) {
            // TODO: Log this
        }
        }
    }
}

接下来,您需要在托管 ListView 的 Activity 或 Fragment 中的 onCreate(...) 或 onActivityCreated(...) 中创建 BitmapCache 的实例:

mBitmapCache = new BitmapCache(this); // or getActivity() if your using a Fragment

现在我们需要更新显示图像的 SimpleCursorAdapter,我已经省略了大部分代码,因为它特定于我的项目,但想法是你覆盖 setViewImage,其中值应该是绑定到光标的值,我将imageview 为 null 以确保它没有来自与项目关联的缓存中的奇数图像。

    @Override
    public void setViewImage(ImageView iv, String value) {
        final String url = value;
        iv.setImageBitmap(null);
        new LoadImageAsyncTask(mBitmapCache, iv, url).execute();

    }

更新

为了清楚起见,您的适配器应该看起来像这样

    adapter = new SimpleCursorAdapter(
            context, R.layout.list_item,
            null, uiBindFrom, uiBindTo,
            CursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER) {
        @Override
        public void setViewImage(ImageView iv, String value) {
                final String url = value;
                iv.setImageBitmap(null);
                new LoadImageAsyncTask(mBitmapCache, iv, url).execute();
        }
    };

希望有帮助!

于 2012-09-20T13:40:11.483 回答