ExpandableListView有一个setOnChildClickListener方法,但缺少 setOnChild 长 ClickListener 方法。
当我在setOnLongClickListener()
的子视图中添加getChildView()
时,整个子列表变得完全无法点击(尽管parentView.setOnChildClickListener()
存在并且之前正在工作)。
如何在子视图上启用长按?
答案 0 :(得分:85)
我设法使用以下内容对ExpandableListView
子项进行长时间点击:
getExpandableListView().setOnItemLongClickListener(new OnItemLongClickListener() {
@Override
public boolean onItemLongClick(AdapterView<?> parent, View view, int position, long id) {
if (ExpandableListView.getPackedPositionType(id) == ExpandableListView.PACKED_POSITION_TYPE_CHILD) {
int groupPosition = ExpandableListView.getPackedPositionGroup(id);
int childPosition = ExpandableListView.getPackedPositionChild(id);
// You now have everything that you would as if this was an OnChildClickListener()
// Add your logic here.
// Return true as we are handling the event.
return true;
}
return false;
}
});
花了很长时间才发现onItemLongClick中的id参数是packedPosition
*方法所需的getPackedPosition
参数,当然也不清楚文档。
注意:要使此解决方案正常工作,您需要覆盖适配器中的getGroupId
和getChildId()
方法
@Override
public long getGroupId(int groupPosition) {
return groupPosition;
}
@Override
public long getChildId(int groupPosition, int childPosition) {
return childPosition;
}
答案 1 :(得分:40)
我在Steve Oliver的博客上找到了答案:http://steveoliverc.wordpress.com/2009/10/16/context-menus-for-expandable-lists/
您应该使用onCreateContextMenu()
而不是寻找setOnChildLongClickListener()
。这是史蒂夫的信息:
可扩展列表支持上下文菜单,其方式与标准列表完全相同:为上下文菜单添加侦听器(当用户长按列表项时)。但是,与标准列表视图不同,您可能想知道用户是选择了组(可扩展项)还是子项(子项)列表项。
此外,如果用户尝试在组项上显示上下文菜单,您可能不想做任何事情。在某些情况下,您可能希望对组内的所有子项执行某些操作,但在我的Librarium应用程序中,我想忽略组项目并仅为子项显示上下文菜单。
首先,您需要知道何时创建上下文菜单,以便您可以识别用户是按下了一个组还是一个孩子。如果他们按下组,则取消上下文菜单。这也让我们有机会获取子项的文本,以便我们可以将它放入上下文菜单的标题中。
public void onCreateContextMenu(ContextMenu menu, View v,
ContextMenuInfo menuInfo)
{
super.onCreateContextMenu(menu, v, menuInfo);
ExpandableListView.ExpandableListContextMenuInfo info =
(ExpandableListView.ExpandableListContextMenuInfo) menuInfo;
int type =
ExpandableListView.getPackedPositionType(info.packedPosition);
int group =
ExpandableListView.getPackedPositionGroup(info.packedPosition);
int child =
ExpandableListView.getPackedPositionChild(info.packedPosition);
// Only create a context menu for child items
if (type == ExpandableListView.PACKED_POSITION_TYPE_CHILD)
{
// Array created earlier when we built the expandable list
String page =mListStringArray[group][child];
menu.setHeaderTitle(page);
menu.add(0, MENU_READ, 0, “Read page”);
menu.add(0, MENU_EDIT, 0, “Edit page”);
menu.add(0, MENU_FAVORITE, 0, “Add page to favorites”);
menu.add(0, MENU_EXPORT, 0, “Export page to file”);
menu.add(0, MENU_DELETE, 1, “Delete page”);
}
}
其次,创建上下文菜单:
public boolean onContextItemSelected(MenuItem menuItem)
{
ExpandableListContextMenuInfo info =
(ExpandableListContextMenuInfo) menuItem.getMenuInfo();
int groupPos = 0, childPos = 0;
int type = ExpandableListView.getPackedPositionType(info.packedPosition);
if (type == ExpandableListView.PACKED_POSITION_TYPE_CHILD)
{
groupPos = ExpandableListView.getPackedPositionGroup(info.packedPosition);
childPos = ExpandableListView.getPackedPositionChild(info.packedPosition);
}
// Pull values from the array we built when we created the list
String author = mListStringArray[groupPos][0];
String page = mListStringArray[groupPos][childPos * 3 + 1];
rowId = Integer.parseInt(mListStringArray[groupPos][childPos * 3 + 3]);
switch (menuItem.getItemId())
{
case MENU_READ:
readNote(rowId);
return true;
case MENU_EDIT:
editNote(rowId);
return true;
// etc..
default:
return super.onContextItemSelected(menuItem);
}
}
就是这样。现在,用户可以长按可扩展列表中的项目,并获取上下文菜单(如果它是子项目。)
答案 2 :(得分:32)
我知道这个答案可能没有必要,但我有类似的情况,这些答案没有解决我的问题。 所以我发布我的,以防有人可能需要它。 希望你们所有人都不介意。
@Override
public boolean onItemLongClick(AdapterView<?> parent, View childView, int flatPos, long id) {
if (ExpandableListView.getPackedPositionType(id) == ExpandableListView.PACKED_POSITION_TYPE_CHILD) {
final ExpandableListAdapter adapter = ((ExpandableListView) parent).getExpandableListAdapter();
long packedPos = ((ExpandableListView) parent).getExpandableListPosition(flatPos);
int groupPosition = ExpandableListView.getPackedPositionGroup(packedPos);
int childPosition = ExpandableListView.getPackedPositionChild(packedPos);
// do whatever you want with groupPos and childPos here - I used these to get my object from list adapter.
return false;
}
修改强> Listview的这个解决方案很久以前了。我强烈建议立即转到 RecyclerView 。
答案 3 :(得分:12)
我正在寻找这个答案,但是这里没有给出正确的结果。
来自tomash的明确回答表明完全不同的方式。来自Nicholas的答案部分正确,但使用'id'不正确。
正确,有效,回答是:将position
参数转换为packedPosition
,然后即可!使用此新packedPosition
值来获取组和子ID。检查以下代码
getExpandableListView().setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() {
@Override
public boolean onItemLongClick(AdapterView<?> parent, View view, int position, long id) {
long packedPosition = getExpandableListView().getExpandableListPosition(position);
if (ExpandableListView.getPackedPositionType(packedPosition) ==
ExpandableListView.PACKED_POSITION_TYPE_CHILD) {
// get item ID's
int groupPosition = ExpandableListView.getPackedPositionGroup(packedPosition);
int childPosition = ExpandableListView.getPackedPositionChild(packedPosition);
// handle data
...
// return true as we are handling the event.
return true;
}
return false;
}
});
编辑:我现在看到autobot几乎没有正确的解决方案,除了getPackedPositionType
上的id
而不是packetPosition
上的{{1}}
答案 4 :(得分:1)
我处理你的问题。只需设置一个标签ur项并使用它,如下所示:
adapter = new ExpandableListAdapter() {
private String[] groups = { "Biceps", "Deltoids", "Hamstrings", "Lower Back","Quadriceps","Triceps","Wrist" };
private String[][] children = {
{ "Konsantra Dumbell curl", "Hammer curl", "Barbell Biceps Curl", "Prone Curl" },
{ "Arnold Press", "Lateral Raise", "Dumbell Upright row", "Bar Military Press" },
{ "Dead Lift", "Hack Squat","Zercher Squat","Seated Leg Flexion" },
{ "Back Raise", "Superman" },
{ "Back Squat", "Bulgarian Split Squat","Dumbell Lunge" },
{ "Bench Dip", "French Press","Triceps Extension" },
{ "Dumbell Wrist Curl "," Reverse Writst Curl"}
};
public void unregisterDataSetObserver(DataSetObserver observer) {
// TODO Auto-generated method stub
}
public void registerDataSetObserver(DataSetObserver observer) {
// TODO Auto-generated method stub
}
public void onGroupExpanded(int groupPosition) {
// TODO Auto-generated method stub
}
public void onGroupCollapsed(int groupPosition) {
// TODO Auto-generated method stub
}
public boolean isEmpty() {
// TODO Auto-generated method stub
return false;
}
public boolean isChildSelectable(int groupPosition, int childPosition) {
// TODO Auto-generated method stub
return true;
}
public boolean hasStableIds() {
// TODO Auto-generated method stub
return true;
}
public View getGroupView(int groupPosition, boolean isExpanded,
View convertView, ViewGroup parent) {
TextView textView = getGenericView();
textView.setText(getGroup(groupPosition).toString());
textView.setTag((Object)getGroup(groupPosition).toString()+"G");
return textView;
}
public long getGroupId(int groupPosition) {
// TODO Auto-generated method stub
return groupPosition;
}
public int getGroupCount() {
// TODO Auto-generated method stub
return groups.length;
}
public Object getGroup(int groupPosition) {
// TODO Auto-generated method stub
return groups[groupPosition];
}
public long getCombinedGroupId(long groupId) {
// TODO Auto-generated method stub
return 0;
}
public long getCombinedChildId(long groupId, long childId) {
// TODO Auto-generated method stub
return 0;
}
public int getChildrenCount(int groupPosition) {
// TODO Auto-generated method stub
return children[groupPosition].length;
}
public View getChildView(int groupPosition, int childPosition,
boolean isLastChild, View convertView, ViewGroup parent) {
TextView textView = getGenericView();
textView.setText(getChild(groupPosition, childPosition).toString());
textView.setTag((Object)getChild(groupPosition, childPosition).toString()+"C");
return textView;
}
public long getChildId(int groupPosition, int childPosition) {
// TODO Auto-generated method stub
return childPosition;
}
public Object getChild(int groupPosition, int childPosition) {
// TODO Auto-generated method stub
return children[groupPosition][childPosition];
}
public boolean areAllItemsEnabled() {
// TODO Auto-generated method stub
return false;
}
public TextView getGenericView() {
// Layout parameters for the ExpandableListView
AbsListView.LayoutParams lp = new AbsListView.LayoutParams(
ViewGroup.LayoutParams.FILL_PARENT, 64);
TextView textView = new TextView(expandXml.this);
textView.setLayoutParams(lp);
// Center the text vertically
textView.setGravity(Gravity.CENTER_VERTICAL | Gravity.LEFT);
// Set the text starting position
textView.setPadding(36, 0, 0, 0);
return textView;
}
};
然后为可扩展ListView设置setOnItemLongClickListener。
listView.setOnItemLongClickListener(new OnItemLongClickListener() {
public boolean onItemLongClick(AdapterView<?> arg0, View arg1,
int arg2, long arg3) {
// TODO Auto-generated method stub
String s=null;
int childPosition =ExpandableListView.getPackedPositionChild(arg3);
if(arg1.getTag()!=null){
Object o= arg1.getTag();
s = o.toString();
}
Toast.makeText(expandXml.this ,s , Toast.LENGTH_SHORT).show();
return false;
}
});
我们走了。