是的,从 iOS 开发人员的角度来看,我发现很难应用诸如“启动时设置默认选择”和“用户点击行后记住选择状态等功能强>”到 ListView。
所以让我们先从“记住选择”开始。问题是即使你知道
您可以使用选择器 xml 来定义突出显示/按下/聚焦样式。但该样式不会
在用户单击该行后保留。例如,我有一个像这样的突出显示选择器 xml(res/drawable 文件夹下的 list_selector.xml)(但您可能有其他字段需要突出显示,例如行中 textview 的文本颜色):
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="@drawable/list_selector_pressed" android:state_pressed="true" />
<item android:drawable="@drawable/list_selector_pressed" android:state_selected="true" />
</selector>
和 list_selector_pressed.xml 定义了高亮样式——设置背景颜色
变成灰色:
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="@color/dark_gray" />
</shape>
</item>
</layer-list>
正如@David Hedlund 建议的那样:
相反,分配一个 OnItemClickListener,并让它将所选项目的 id 存储到某个变量中。
你需要在你的类之上创建一个实例变量:
private View currentSelectedView;
然后去
@Override
public void onListItemClick(ListView l, View v, int position, long id) {
if (currentSelectedView != null && currentSelectedView != v) {
unhighlightCurrentRow(currentSelectedView);
}
currentSelectedView = v;
highlightCurrentRow(currentSelectedView);
//other codes
}
非常简单:我们检查 currentSelectedView 是否为 null 或当前单击的视图。我们首先通过调用方法 unhighlightCurrentRow(currentSelectedView) 来取消突出显示任何样式---你可能想知道为什么我们将即时变量 currentSelectedView 作为参数传递,我稍后会解释。然后我们将视图分配给 currentSelectedView 并突出显示当前行;这样样式在用户单击完成后将保持不变。
private void unhighlightCurrentRow(View rowView) {
rowView.setBackgroundColor(Color.TRANSPARENT);
TextView textView = (TextView) rowView.findViewById(R.id.menuTitle);
textView.setTextColor(getResources().getColor(R.color.white));
}
private void highlightCurrentRow(View rowView) {
rowView.setBackgroundColor(getResources().getColor(
R.color.dark_gray));
TextView textView = (TextView) rowView.findViewById(R.id.menuTitle);
textView.setTextColor(getResources().getColor(R.color.yellow));
}
啊哈,就是这样。这就是我们为列表视图实现“记住选择”的方式。如你所见,
我们必须在 xml 和 java 代码中复制样式代码——非常愚蠢:(
接下来关于“设置默认选择”。你可能认为你可以做到这一点
listView.setAdapter(adatper)
listView.setSelection(0);
currentSelectedView = listView.getChildAt(0);
highlightCurrentRow(currentSelectedView);
在活动中的 onCreate() 或片段中的 onActivityCreated() 中。
但是如果你运行它,你会得到 NullPointer 异常,为什么?
因为此时列表视图尚未呈现,Android 不喜欢具有 viewWillAppear 的 iOS。所以你必须创建一个即时变量来记住它是否是第一次呈现列表视图单元格并在 onListItemClick 中取消设置该变量:
所以在currentSelectedView声明下:
private Boolean firstTimeStartup = true;
然后添加方法:假设我们要突出显示列表视图中的第一行:
public class HomeAdapter extends ArrayAdapter<String> {
int layoutResourceId;
public HomeAdapter(Context context, int textViewResourceId,
ArrayList<String> objects) {
super(context, textViewResourceId, objects);
layoutResourceId = textViewResourceId;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
if (convertView == null) {
convertView = LayoutInflater.from(getContext()).inflate(
layoutResourceId, null);
}
if (firstTimeStartup && postion == 0) {
highlightCurrentRow(convertView);
} else {
unhighlightCurrentRow(convertView);
}
TextView title = (TextView) convertView
.findViewById(R.id.menuTitle);
title.setText(getItem(position));
return convertView;
}
}
很简单。
但是你需要对 onListItemClick 方法做一些改变:
@Override
public void onListItemClick(ListView l, View v, int position, long id) {
if (firstTimeStartup) {// first time highlight first row
currentSelectedView = l.getChildAt(0);
}
firstTimeStartup = false;
if (currentSelectedView != null && currentSelectedView != v) {
unhighlightCurrentRow(currentSelectedView);
}
currentSelectedView = v;
highlightCurrentRow(currentSelectedView);
//other codes
}
给你!享受 Android :)