1

ListView の行でボタンを押すと問題が発生します。各 Button の background 属性は、XML セレクター ファイルを参照します。ボタンを押して別の画像を選択するため。OnClickListener からプレス イベントを取得できますが、ステート セレクターが壊れて、 と でプレスを登録しませ android:state_pressed="true"android:state_focused="false"

android:descendantFocusability="blocksDescendants"ボタンの親/ルート レイアウト XML から削除すると、次に、プレス状態は機能しますが、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" />

最後のセレクター行で描画可能な背景を変更しても機能しません。押された画像が表示されますが、ボタンから離れた行のどこをクリックしてもかまいません。

ボタン クリック イベントの背景を変更できますが、ボタンを離したときにデフォルトの背景に戻す必要があり、これをキャプチャするのは困難です (?)。リスナーでプレス/リリース イベントをキャプチャできれば、ボタンのみに最適です。

どんな助けでも大歓迎です!ありがとう!

4

2 に答える 2

1

答えは見つかりましたか?

私もこの問題を抱えていました。Androidフレームワークにバグがあると思います(そして/または、いつものように、フレームワークの設計が不十分です)。android:duplicateParentStateただし、この場合は役に立たないというxmlフィールドがあります(実を言うと、別のプロジェクトでそれを使用して、親の状態をtrueに設定して 複製しました)。

だから私の解決策はこれでした(私はそれが醜いことを知っており、これを行うためのより簡単な方法であるべきです):

  • 2 つの異なるドローアブルを定義します。1 つは押された状態用、もう 1 つは押されていない状態用です。
  • ボタンの親が定義する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;
        }
    });
于 2013-03-01T15:55:09.243 に答える