最初我从服务器获取数据列表并将其设置为listview。
当向下滚动列表视图时,我从服务器收集数据并调用我的自定义适配器的notifydatasetchanged。
在自定义适配器的getView()方法中,我通过asyntask从服务器下载图像。成功下载并在本地存储后。然后只是尝试刷新该asyntask的onPostExecute列表视图。但它没有得到更新。
onPostExecute上的日志正在打印,但listview没有得到刷新。
public void loadBitmap(MainActivity mainActivity,String imageKey,ImageView imageView,boolean isScrolling) { final Bitmap bitmap = getBitmapFromCache(imageKey);
if (bitmap != null) {
imageView.setImageBitmap(bitmap);
} else {
imageView.setImageResource(R.drawable.ic_launcher);
if (!isScrolling && !mCurrentTasks.contains(imageKey)
&& mainActivity.internetIsAvailable()) {
BitmapLoaderTask task = new BitmapLoaderTask(imageKey,
mainActivity.getAdapter());
task.execute();
}
}
}
private class BitmapLoaderTask extends AsyncTask<Void, Void, Bitmap> {
private ListAdapter mListAdapter;
private String mImageKey;
public BitmapLoaderTask(String imageKey, ListAdapter adapter) {
mListAdapter = adapter;
mImageKey = imageKey;
}
@Override
protected void onPreExecute() {
mCurrentTasks.add(mImageKey);
}
@Override
protected Bitmap doInBackground(Void... params) {
Bitmap b = null;
try {
URL url = new URL(mImageKey);
HttpURLConnection connection = (HttpURLConnection) url
.openConnection();
connection.connect();
b = BitmapFactory.decodeStream(connection.getInputStream());
if (b != null) {
int width = b.getWidth();
int height = b.getHeight();
if (width >= mMaxWidth || height >= mMaxHeight) {
while (true) {
if (width <= mMaxWidth || height <= mMaxHeight) {
break;
}
width /= 2;
height /= 2;
}
b = Bitmap.createScaledBitmap(b, width, height, false);
}
connection.disconnect();
addBitmapToCache(mImageKey, b);
return b;
}
return null;
} catch (IOException e) {
if (e != null) {
e.printStackTrace();
}
return null;
}
}
@Override
protected void onPostExecute(Bitmap param) {
mCurrentTasks.remove(mImageKey);
if (param != null) {
mListAdapter.notifyDataSetChanged();
}
}
}
答案 0 :(得分:0)
你的代码看起来正确..但我认为问题可能是mainActivity.getAdapter()
我认为你应该在全局范围内声明适配器。
private AdapterYourCustomAdapter adapter;
然后在onCreate()
adapter = new AdapterYourCustomAdapter(context,arraylist(whatever constructor is));
然后将调用传递给它:
if (bitmap != null) {
imageView.setImageBitmap(bitmap);
} else {
imageView.setImageResource(R.drawable.ic_launcher);
if (!isScrolling && !mCurrentTasks.contains(imageKey)
&& mainActivity.internetIsAvailable()) {
new BitmapLoaderTask( imageKey, adapter ).execute();
}
}
答案 1 :(得分:0)
尝试将每个位图的ImageView
传递给构造中的BitmapLoaderTask
,并将ImageView
作为成员变量保留在其中。加载完位图后,使用onPostExecute
方法将该位图指定为ImageView
drawable。
private class BitmapLoaderTask extends AsyncTask<Void, Void, Bitmap> {
private String mImageKey;
private ImageView mImageView;
public BitmapLoaderTask(ImageView imageView, String imageKey) {
mImageView = imageView;
mImageKey = imageKey;
}
protected void onPreExecute() {
/* Pre execute stuff */
}
protected Bitmap doInBackground(Void... params) {
/* Your bitmap processing */
return bitmap;
}
protected void onPostExecute(Bitmap param) {
if(param != null) {
mImageView.setImageBitmap(param);
}
}
}
这是构建AsyncTask
的完美示例。 doInBackground()
方法在后台线程上运行,因此不会干扰UI处理,但是android权限要求不允许此类后台线程触及UI元素。这就是onProgressUpdate()
和onPostExecute()
的用途,只要doInBackground
达到了更新的里程碑,它们就会在主UI线程上运行快速UI更新。在这种情况下,您可以使用它们在相应的位图准备就绪时通知您的ImageView对象。