我有一個Activity
與ListView
附加到custom adapter
。如何刷新listView(帶適配器)後androidnd回調
我有一個回調,表示一個可繪製項目完成下載。
它被調用多次(每個資源被下載)。
在我的回調中,我切換到UI線程,並將一個新陣列設置到同一個適配器。
然後我打電話adapter.notifyDataSetChanged()
但活動列表不會刷新到新的圖標。
我還需要做什麼?
1)致電mListView.requestLayout()
?但我怎麼知道什麼時候?
as notifyDataSetChanged
是異步的,我不知道它什麼時候完成。
2)覆蓋adapter's destroyView
?所以我不會創建一個新的listItem,但使用現有的?
我的適配器代碼:
公共類SettingValueAdapter延伸BaseAdapter {
private SettingsValue[] values;
private LayoutInflater inflater;
public SettingValueAdapter(Context context) {
inflater = LayoutInflater.from(context);
}
public SettingsValue[] getValues() {
return values;
}
@Override
public int getCount() {
if (values == null) {
return 0;
}
return values.length;
}
@Override
public Object getItem(int arg0) {
return values==null? null : values[arg0];
}
@Override
public long getItemId(int arg0) {
// TODO Auto-generated method stub
return 0;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
if (convertView == null) {
convertView = inflater.inflate(R.layout.settings_item, null);
}
SettingsValue item = values[position];
CheckedTextView name = (CheckedTextView) convertView.findViewById(R.id.itemText);
ImageView iconView = (ImageView) convertView.findViewById(R.id.itemIcon);
if (iconView != null && (item != null) && (item.icon != null)) {
iconView.setImageDrawable(item.icon);
iconView.setVisibility(View.VISIBLE);
} else {
iconView.setVisibility(View.GONE);
}
name.setText(item.display);
name.setChecked(item.isSelected);
View container = convertView.findViewById(R.id.itemContainer);
if (position == 0) {
if (position == values.length-1) {
container.setBackgroundResource(R.drawable.item_selector_single);
} else {
container.setBackgroundResource(R.drawable.item_selector_top);
}
} else {
if (position == values.length-1) {
container.setBackgroundResource(R.drawable.item_selector_bottom);
} else {
container.setBackgroundResource(R.drawable.item_selector_middle);
}
}
container.setPadding(0, 0, 0, 0);
return convertView;
}
public void setValues(SettingsValue[] values) {
this.values = values;
notifyDataSetChanged();
}
}
MyActivity代碼:
public class CategoriesActivity extends ActivityBase {
private Category[] categories;
SettingValueAdapter adapter;
ListView mListView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.settings_values);
((TitleBar) findViewById(R.id.theTitleBar)).init(this,
DisplayStrings.DS_CATEGORIES);
adapter = new SettingValueAdapter(this);
DriveToNativeManager nativeManager = DriveToNativeManager.getInstance();
nativeManager.getCategories(new CategoriesListener() {
@Override
public void onComplete(Category[] aCategories) {
categories = aCategories;
NativeManager nativeManager = AppService.getNativeManager();
SettingsValue[] values = new SettingsValue[categories.length];
for (int i = 0; i < categories.length; i++) {
values[i] = new SettingsValue(
categories[i].value,
nativeManager
.getLanguageString(categories[i].displayString),
false);
values[i].icon = ResManager
.GetSkinDrawable(categories[i].iconName + ".bin");
}
adapter.setValues(values);
}
});
mListView = (ListView) findViewById(R.id.settingsValueList);
mListView.setAdapter(adapter);
mListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> arg0, View arg1,
int position, long arg3) {
Intent intent = new Intent(CategoriesActivity.this,
SearchActivity.class);
intent.putExtra(PublicMacros.SEARCH_CATEGORY,
categories[position].value);
intent.putExtra(PublicMacros.SEARCH_MODE,
PublicMacros.FREE_SEARCH);
startActivityForResult(intent, 1);
}
});
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (resultCode == RESULT_OK) {
setResult(RESULT_OK);
finish();
}
super.onActivityResult(requestCode, resultCode, data);
}
public void refreshListIcons() {
// if (categories != null) {
// NativeManager nativeManager = AppService.getNativeManager();
// SettingsValue[] values = new SettingsValue[categories.length];
// for (int i = 0; i < categories.length; i++) {
// values[i] = new SettingsValue(
// categories[i].value,
// nativeManager
// .getLanguageString(categories[i].displayString),
// false);
// values[i].icon = ResManager
// .GetSkinDrawable(categories[i].iconName + ".bin");
// }
//
if (categories != null) {
SettingsValue[] values = adapter.getValues();
for (int i = 0; i < values.length; i++) {
values[i].icon = ResManager
.GetSkinDrawable(categories[i].iconName + ".bin");
}
adapter.setValues(values);
}
}
}
我打電話refreshIconsList
從回調。
但是,正如我所說 - 列表不刷新運行時,但只有在現有和重新進入活動。
我已經試過這一點,但沒有幫助:
public void refreshListIcons() {
// if (categories != null) {
// NativeManager nativeManager = AppService.getNativeManager();
// SettingsValue[] values = new SettingsValue[categories.length];
// for (int i = 0; i < categories.length; i++) {
// values[i] = new SettingsValue(
// categories[i].value,
// nativeManager
// .getLanguageString(categories[i].displayString),
// false);
// values[i].icon = ResManager
// .GetSkinDrawable(categories[i].iconName + ".bin");
// }
//
runOnUiThread(new Runnable() {
@Override
public void run() {
if (categories != null) {
SettingsValue[] values = adapter.getValues();
for (int i = 0; i < values.length; i++) {
values[i].icon = ResManager
.GetSkinDrawable(categories[i].iconName + ".bin");
}
adapter.setValues(values);
mListView.setAdapter(adapter);
adapter.notifyDataSetChanged();
}
}
});
}
'notifyDataSetChanged'應該足夠了。你可以顯示適配器代碼,是否有一個原因,你需要設置一個新的陣列,你不能只更新當前的? –
@PatrickEvans感謝您的幫助。我添加了代碼 –
請參閱http://stackoverflow.com/questions/7325437/how-to-add-item-to-listview-at-runtime,在那裏他除了'notifyAll'之外還添加了'setContentView'。爲什麼? –