每个ListView行中按钮按下状态的问题

时间:2012-09-19 21:31:58

标签: android listview button android-listview onclick

我在ListView行中按下按钮时遇到问题。每个Button的background属性引用XML选择器文件;为了在按下按钮时选择不同的图像。 我可以从OnClickListener获取新闻事件,但状态选择器会中断并且不会使用 android:state_pressed="true"android:state_focused="false"注册新闻。

如果我从按钮的父/根布局XML中删除android:descendantFocusability="blocksDescendants";然后按下状态将起作用,但无论你在ListView行上的哪个位置触摸都会触发,这很烦人。

我的问题:无法管理与内部按钮分开的行的默认/默认状态。他们互相干扰。

代码:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
   android:id="@+id/mainListLayout"
   android:layout_width="fill_parent"
   android:layout_height="wrap_content" 
   android:descendantFocusability="blocksDescendants">
..........

进一步向下行项目按钮:

<Button
        android:id="@+id/deleteButton"
        android:background="@drawable/del_button_selector"
        .....
        .....
        />
..........

drawable / del_button_selector:

<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:drawable="@drawable/deleteico" android:state_focused="true" android:state_pressed="false"/>
    <item android:drawable="@drawable/deletepressed" android:state_focused="true" android:state_pressed="true"/>
    <item android:drawable="@drawable/deleteico" android:state_focused="false" android:state_pressed="true" />

更改最后一个选择器行中的可绘制背景不起作用。它将显示按下的图像,但是在远离按钮的位置单击该行并不重要。

我可以更改按钮点击事件的背景但我需要在按钮释放时切换回默认背景,这很难捕获(?)。如果我可以在听众中捕获按下/释放事件,那么这对于按钮来说非常有用。

任何帮助表示赞赏!谢谢!

2 个答案:

答案 0 :(得分:3)

easy 解决方案是将android:clickable="true"设置为父视图。

这样它就会拦截触摸事件,并且不会突出显示子视图。

在你的具体案例中:

 <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
      android:id="@+id/mainListLayout"
      android:layout_width="match_parent"
      android:layout_height="wrap_content" 
      android:clickable="true">

答案 1 :(得分:1)

你找到了答案吗?

我也遇到过这个问题。我认为android框架中存在一个错误(和/或我们正面临 - 像往常一样 - 一个糟糕的框架设计)。然而,有一个名为android:duplicateParentState的xml字段在这种情况下是无用的(说实话我在另一个项目中使用它来复制父级的状态将其设置为true)。

所以我的解决方案就是这个(我知道它很丑陋,应该是一种更简单的方法):

  • 定义2个不同的drawable:一个用于按下,另一个用于未按下状态
  • 按钮的父级定义android:descendantFocusability="blocksDescendants"
  • 在按钮上设置onTouchListener

后者看起来像这样:

    button.setOnTouchListener(new View.OnTouchListener() {
        @Override
        public boolean onTouch(View v, MotionEvent event) {
            switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
                v.setBackgroundDrawable(mButtonDownDrawable); // this call is deprecated since Jelly Bean, use setBackground() instead
                break;
            case MotionEvent.ACTION_UP:
            case MotionEvent.ACTION_OUTSIDE: // just in case. this is never called
            case MotionEvent.ACTION_CANCEL:
                v.setBackgroundDrawable(mButtonUpDrawable);
                break;
            case MotionEvent.ACTION_MOVE:
                final Rect rect = new Rect(v.getLeft(), v.getTop(), v.getRight(), v.getBottom());
                if(!rect.contains((int)event.getX(), (int)event.getY())){
                    // User moved outside bounds
                    v.setBackgroundDrawable(mButtonUpDrawable);
                }
                break;
            }
            return false;
        }
    });