问题描述
|
我正在使用自定义可扩展列表适配器。当用户单击它时,我突出显示一个孩子。在用户打开/折叠组之前,此方法工作正常。假设用户触摸第2组项目1。这将突出显示第2组项目1。然后,用户打开第1组。现在,第3组项目2被突出显示。我已经进行了一些测试,选择了不同的项目,但是找不到突出显示的行将跳转到的模式。有时它在列表中上升,有时它在下降中。我在弄清楚放入活动的
onGroupExpandListener
和onGroupCollapseListener
以突出显示正确视图的逻辑时遇到了麻烦。有任何想法吗?
编辑:我的onChildClickListener内部的当前代码
if (groupPosition == 0){
switch(childPosition) {
case 0:
prevIoUslySelectedView.setBackgroundResource(R.color.transparent);
currentlySelectedView.setBackgroundResource(R.color.blue);
break;
所有组/儿童使用相同的代码
解决方法
ExpandableListView中的项目选择是通过平面列表(绝对位置)进行的。因此,如果新打开的组在选择curnet之前,并且子节点较少,则选择将向上移动,反之亦然。我建议将选择模式设置为无,并实现onclick / expand逻辑来处理您自己的焦点-例如,为视图实现标签,并通过该标签设置当前突出显示的项目。
以下是一些建议:
首先,在ExpandableListView.OnChildClickListener中,执行ExpandableListView.findViewWithTag(theTag)以检查带有此类标记的视图并将其取消标记(也为setTag(null))并恢复背景。然后为该项目单击setTag(theTag),并将背景更改为选定。当然,您可以具有其他逻辑并标记多个项目。请注意,一旦视图被破坏,您将丢失选择(例如,在展开期间)。
有一些自定义地图或将拥有视图的唯一ID和(未标记)状态的内容。这是最好的解决方案,它将允许在滚动和扩展之间保持持久选择。
在后备适配器中,引入“已标记”状态。因此,即使在应用程序启动/停止之间,标记也将保持不变。但是,这不是一个好方法,因为选择更多是一种UI行为。
我目前正在使用列表的“选择模式倍数”进行ExpandableListView选择。但是,正如我所说的那样,选择是在功能方面我必须牺牲的每个位置,也就是说,每当进行操作时,我都会清除选择。以前的实现是使用自定义Map来保存选定的ID,老实说,这是更好的方法。
这是我获取选定ID的方式(请记住我多次使用选择模式):
final SparseBooleanArray checkedPositions = expList.getCheckedItemPositions();
final ExpandableListAdapter adapter = expList.getExpandableListAdapter();
List<Long> checkedIds = new ArrayList<Long>();
if (packedPositionType == ExpandableListView.PACKED_POSITION_TYPE_GROUP) {
for (int i = checkedPositions.size() - 1; i >= 0; i--) {
if (checkedPositions.valueAt(i)) {
checkedIds.add(adapter.getGroupId(checkedPositions.keyAt(i)));
}
}
}
但是,就您而言,您将需要检查是否有儿童打包的职位。另请注意,我的适配器具有稳定的(唯一)ID。如果您没有稳定的ID,则可以依靠ExpandableListView的getPackedPositionForChild()方法并按标记存储打包位置。
,正确的方法(解决组崩溃时跳出突出显示的问题)
在ExpandableListView上执行以下操作:
步骤1.将选择模式设置为单一(可以在xml中以android:choiceMode = \“ singleChoice \”的形式完成)
步骤2.使用选择器xml作为背景(android:listSelector = \“ @ drawable / selector_list_item \”)
<?xml version=\"1.0\" encoding=\"utf-8\"?>
<selector xmlns:android=\"http://schemas.android.com/apk/res/android\"
android:exitFadeDuration=\"@android:integer/config_mediumAnimTime\">
<item android:drawable=\"@android:color/holo_blue_bright\" android:state_pressed=\"true\"/>
<item android:drawable=\"@android:color/holo_blue_light\" android:state_selected=\"true\"/>
<item android:drawable=\"@android:color/holo_blue_dark\" android:state_activated=\"true\"/>
</selector>
步骤3.在onChildClick()回调中调用expandableListView.setItemChecked(index,true)。
index是子项的基于0的索引,计算如下
第1组[索引= 0]
子项1
子项2
子项3 [索引= 3]
第2组[索引= 4]
子项1
子项2
子项3 [索引= 7]
第3组[索引= 8]
子项1
子项2
子项目3 [索引= 11]
如果我们也有列表头,那么它们还将考虑索引值。
这是一个工作示例:
@Override
public boolean onChildClick(ExpandableListView parent,View v,int groupPosition,int childPosition,long id) {
...
int index = parent.getFlatListPosition(ExpandableListView.getPackedPositionForChild(groupPosition,childPosition));
parent.setItemChecked(index,true);
return true;
}
,我对崩溃问题的解决方案:
mDrawerExpandableList.setOnGroupCollapseListener(new OnGroupCollapseListener() {
@Override
public void onGroupCollapse(int groupPosition) {
if(ExpandableListView.getPackedPositionGroup(selectedFragmentId) == groupPosition) {
mDrawerExpandableList.setItemChecked(mDrawerExpandableList.getFlatListPosition(ExpandableListView.getPackedPositionForGroup(groupPosition)),true);
}
}
});
mDrawerExpandableList.setOnGroupExpandListener(new OnGroupExpandListener() {
@Override
public void onGroupExpand(int groupPosition) {
if(ExpandableListView.getPackedPositionGroup(selectedFragmentId) == groupPosition) {
mDrawerExpandableList.setItemChecked(((ExpandableListView)drawerListView).getFlatListPosition(selectedFragmentId),true);
}
}
});
,//MY LIST A FOLLOWS
(0)SALES
(0)SALES
(1)SALES VIEW
(2)SALES RETURN
(3)SALES RETURN VIEW
(1)STOCK
(0)ADD STOCK
(1)VIEW STOCK
(2)SETTINGS
(3)NOTIFICATION
//declare tow integer variable globali as follows
private int lastCheckedGroupPosition=-1;
private int lastCheckedChildPosition=-1;
mDrawerList.setOnGroupClickListener(new OnGroupClickListener() {
@Override
public boolean onGroupClick(ExpandableListView parent,long id) {
if(groupPosition==2){
lastCheckedGroupPosition=groupPosition;
lastCheckedChildPosition=-1;
int index = parent.getFlatListPosition(ExpandableListView.getPackedPositionForGroup(groupPosition));
parent.setItemChecked(index,true);
//TODO Write here the code for opening settings page
...............
...............
...............
return true;
}
else if(groupPosition==3){
lastCheckedGroupPosition=groupPosition;
lastCheckedChildPosition=-1;
int index = parent.getFlatListPosition(ExpandableListView.getPackedPositionForGroup(groupPosition));
parent.setItemChecked(index,true);
//TODO Write here the code for opening settings page
...............
...............
...............
return true;
}
return false;
}
});
mDrawerList.setOnChildClickListener(new OnChildClickListener() {
@Override
public boolean onChildClick(ExpandableListView parent,long id) {
if(groupPosition==0){
if(childPosition==0){
//TODO Write here the code for opening SALES page
...............
...............
...............
}
else if(childPosition==1){
//TODO Write here the code for opening SALES VIEW page
...............
...............
...............
}
else if(childPosition==2){
//TODO Write here the code for opening SALES RETURN page
...............
...............
...............
}
else if(childPosition==3){
//TODO Write here the code for opening SALES RETURN VIEW page
...............
...............
...............
}
}
else if(groupPosition==1){
if(childPosition==0){
//TODO Write here the code for opening ADD STOCK page
...............
...............
...............
}
else if(childPosition==1){
//TODO Write here the code for opening VIEW STOCK page
...............
...............
...............
}
}
int index = parent.getFlatListPosition(ExpandableListView.getPackedPositionForChild(groupPosition,childPosition));
parent.setItemChecked(index,true);
lastCheckedGroupPosition=groupPosition;
lastCheckedChildPosition=childPosition;
return false;
}
});
mDrawerList.setOnGroupExpandListener(new OnGroupExpandListener() {
@Override
public void onGroupExpand(int groupPosition) {
if(groupPosition==lastCheckedGroupPosition){
if(lastCheckedChildPosition!=-1){
int index = mDrawerList.getFlatListPosition(ExpandableListView.getPackedPositionForChild(lastCheckedGroupPosition,lastCheckedChildPosition));
mDrawerList.setItemChecked(index,true);
}
else{
int index = mDrawerList.getFlatListPosition(ExpandableListView.getPackedPositionForGroup(lastCheckedGroupPosition));
mDrawerList.setItemChecked(index,true);
}
}
else{
if(mDrawerList.isGroupExpanded(lastCheckedGroupPosition)){
if(lastCheckedChildPosition!=-1){
int index = mDrawerList.getFlatListPosition(ExpandableListView.getPackedPositionForChild(lastCheckedGroupPosition,lastCheckedChildPosition));
mDrawerList.setItemChecked(index,true);
}
else{
int index = mDrawerList.getFlatListPosition(ExpandableListView.getPackedPositionForGroup(lastCheckedGroupPosition));
mDrawerList.setItemChecked(index,true);
}
}
else{
mDrawerList.setItemChecked(-1,true);
}
}
}
});
mDrawerList.setOnGroupCollapseListener(new OnGroupCollapseListener() {
@Override
public void onGroupCollapse(int groupPosition) {
if(groupPosition==lastCheckedGroupPosition){
if(lastCheckedGroupPosition!=-1){
int index = mDrawerList.getFlatListPosition(ExpandableListView.getPackedPositionForGroup(lastCheckedGroupPosition));
mDrawerList.setItemChecked(index,true);
}
else{
mDrawerList.setItemChecked(-1,true);
}
}
if(mDrawerList.isGroupExpanded(lastCheckedGroupPosition)){
if(lastCheckedChildPosition!=-1){
int index = mDrawerList.getFlatListPosition(ExpandableListView.getPackedPositionForChild(lastCheckedGroupPosition,true);
}
}
else{
mDrawerList.setItemChecked(-1,true);
}
}
});