0

I am working on an app where the list item are complex, TextView and two ImageButtons. I have looked at the around for a solution, and tried all that I have seen, still nothing.

The list is part of the ListFragment on I have Override onListItemClick.

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#FFF" >

    <TextView
        android:id="@+id/medcine_info_txt"
        android:layout_width="fill_parent"
        android:layout_height="200dp"
        android:layout_alignParentLeft="true"
        android:layout_alignParentTop="true"
        android:clickable="false"
        android:focusable="false"
        android:focusableInTouchMode="false"
        android:padding="3dp"
        android:textColor="@color/black" />

    <ImageButton
        android:id="@+id/item_edit"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignBottom="@+id/medcine_info_txt"
        android:layout_alignParentLeft="true"
        android:contentDescription="@string/item_edit"
        android:focusable="false"
        android:focusableInTouchMode="false"
        android:src="@android:drawable/ic_menu_edit" />

    <ImageButton
        android:id="@+id/item_history"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignBottom="@+id/medcine_info_txt"
        android:layout_centerHorizontal="true"
        android:contentDescription="@string/item_history"
        android:focusable="false"
        android:focusableInTouchMode="false"
        android:src="@android:drawable/btn_star" />

</RelativeLayout>

This my adapter getView where I have on handle the buttons click, and it implements OnClickListener

public View getView(int position, View convertView, ViewGroup parent) {
    LayoutInflater inflator = (LayoutInflater) getContext()
            .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    View listItem = inflator.inflate(R.layout.medcince_list_item, null);

    ImageButton mEdit = (ImageButton)listItem.findViewById(R.id.item_edit);
    mEdit.setOnClickListener(this);
    mEdit.setTag(getItem(position));

    ImageButton mHistory = (ImageButton)listItem.findViewById(R.id.item_history);
    mHistory.setOnClickListener(this);
    mHistory.setTag(getItem(position));

    return listItem;
}

Any thoughts on why the onListItemClick is not handling the click?

Robi Kumar Tomar
  • 3,418
  • 3
  • 20
  • 27
Mustafa ALMulla
  • 870
  • 2
  • 10
  • 23

4 Answers4

2

I think your ImageButton is stealing away the onItemClickLister event. Add this attribute to your layout

android:descendantFocusability="blocksDescendants"

<TextView
    android:id="@+id/medcine_info_txt"
    android:layout_width="fill_parent"
    android:layout_height="200dp"
    android:layout_alignParentLeft="true"
    android:layout_alignParentTop="true"
    android:clickable="false"
    android:focusable="false"
    android:focusableInTouchMode="false"
    android:padding="3dp"
    android:textColor="@color/black" />

<ImageButton
    android:id="@+id/item_edit"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    .......

Thanks

Md. Monsur Hossain Tonmoy
  • 11,045
  • 2
  • 22
  • 19
  • 1
    similar better answer [here](http://stackoverflow.com/a/17502381/1264893). You need to add android:descendantFocusability="blocksDescendants" in layout and android:focusable="false" and android:focusableInTouchMode="false" on imagebutton – iluvatar_GR Jun 06 '14 at 16:51
1

This is common question for ListView. I read source code about this.
Question: why onListItemClick not be called?
Answer:

  • AbsListView class override onTouchEvent method.
  • Snip code come from onTouchEvent method.
     
    if (inList && !child.hasFocusable()) {
                        if (mPerformClick == null) {
                            mPerformClick = new PerformClick();
                        }
    .....
    }
    

    PerformClick will be call if child.hasFocusable() return false which child is you ListView item view;
  • Snip code come from hasFocusable method.
 
@Override
    public boolean hasFocusable() {
        if ((mViewFlags & VISIBILITY_MASK) != VISIBLE) {return false; }
        if (isFocusable()) {return true;}
        final int descendantFocusability = getDescendantFocusability();
        if (descendantFocusability != FOCUS_BLOCK_DESCENDANTS) {
            final int count = mChildrenCount;
            final View[] children = mChildren;
            for (int i = 0; i 


So solution:
Solution A,set ListView item descendantFocusability property, let its getDescendantFocusability() is not equal FOCUS_BLOCK_DESCENDANTS.
Solution B, ListView item all child views is not hasFocusable( hasFocusable() return false).

boiledwater
  • 10,372
  • 4
  • 37
  • 38
  • Excellent analysis. But..For solution A, you mean `descendantFocusability` attribute should be set to`blocksDescendants` right? Your line - "let its getDescendantFocusability() is not equal FOCUS_BLOCK_DESCENDANTS" implies the exact opposite. Anyway does'nt work either way for me. – faizal Sep 12 '14 at 14:00
  • @faizal all you set is make sure hasFocusable() return false; you can pass FOCUS_BEFORE_DESCENDANTS or FOCUS_AFTER_DESCENDANTS to setDescendantFocusability method. – boiledwater Sep 15 '14 at 10:05
  • thanks. the problem in my case was that i had `android:LongClickable="true"' in one of the elements of the item layout. The click listener started working after i removed this attribute. – faizal Sep 15 '14 at 13:07
  • @faizal you mean is 'remove android:LongClickable="true" attribute, listview click listener can work' or 'remove android:descendantFocusability attribute, elements which android:LongClickable="true" click listener can work'. Can you supply full detail about this? – boiledwater Sep 16 '14 at 01:53
  • i mean - remove android:LongClickable="true" attribute, listview click listener can work' – faizal Sep 16 '14 at 14:33
  • @faizal ,if you set android:LongClickable="true",ListView.hasFocusable() method return ture; So listview click listener not work. By the way you can have a test by set android:LongClickable="true",and pass FOCUS_BEFORE_DESCENDANTS or FOCUS_AFTER_DESCENDANTS to setDescendantFocusability method. I guess listview click listener will be work. – boiledwater Sep 17 '14 at 04:41
0

Make the ListFragment implement the View.OnClickListener interface, and implement the code you want to be called when the button are pressed in the method OnClick(View view), which is @Override

Hitman
  • 588
  • 4
  • 10
0

you can create View.OnClickListner object which can listen your imagebutton click in getView. onListItemClick generally used to handle row click event not items in rows.

public View getView(int position, View convertView, ViewGroup parent) {
    LayoutInflater inflator = (LayoutInflater) getContext()
            .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    View listItem = inflator.inflate(R.layout.medcince_list_item, null);

    ImageButton mEdit = (ImageButton)listItem.findViewById(R.id.item_edit);
    mEdit.setOnClickListener(new View.OnClickListener(){

    @Override
    public void onClick(View v) {
        // HERE YOU CAN HANDLE BUTTON CLICK. POSITION YOU CAN HAVE FROM getView already.
    }

    });
    mEdit.setTag(getItem(position));

    ImageButton mHistory = (ImageButton)listItem.findViewById(R.id.item_history);
    mHistory.setOnClickListener(new View.OnClickListener(){

    @Override
    public void onClick(View v) {
        // HERE YOU CAN HANDLE BUTTON CLICK. POSITION YOU CAN HAVE FROM getView already.
    }

    });
    mHistory.setTag(getItem(position));

    return listItem;
}
Bharat Sharma
  • 3,926
  • 2
  • 17
  • 29