web-dev-qa-db-ja.com

RecyclerViewアイテムの背景セレクター

私は以下のようなRecyclerViewを使用しています:

<Android.support.v7.widget.RecyclerView
    Android:id="@+id/list"
    Android:layout_width="320dp"
    Android:layout_height="match_parent"/>

そして私のリストアイテム:

<LinearLayout  Android:layout_width="match_parent"
    Android:layout_height="wrap_content"
    Android:background="@drawable/selector_medium_high">
    <com.basf.suvinil.crie.ui.common.widget.CircleView
        Android:id="@+id/circle"
        Android:layout_width="22dp"
        Android:layout_height="22dp"/>
    <TextView
        Android:id="@+id/label"
        Android:layout_width="match_parent"
        Android:layout_height="wrap_content"
        Android:minHeight="57.5dp"/>
</LinearLayout>

この部分の詳細を見るAndroid:background="@drawable/selector_medium_high"これは通常のセレクターです。

<selector xmlns:Android="http://schemas.Android.com/apk/res/Android">
    <item Android:drawable="@color/background_high" Android:state_activated="true"/>
    <item Android:drawable="@color/background_high" Android:state_pressed="true"/>
    <item Android:drawable="@color/background_high" Android:state_checked="true"/>
    <item Android:drawable="@color/background_high" Android:state_focused="true"/>
    <item Android:drawable="@color/background_medium"/>
</selector>

しかし、このコードを実行すると、行をタッチしても背景色に変化はありません。

38
ademar111190

clickable "list"のすべての要素で、focusablefocusableInTouchModetrueRecyclerViewに設定します。

52
Ahmed Ghonim

追加 :

Android:background="?android:attr/selectableItemBackground"

item.xml

31
100rbh

私にとってはうまくいかなかったように、これがうまくいかない場合は、次のコードを使用します。

Android:foreground="?android:attr/selectableItemBackground"

トリックはAndroid:foreground属性...

15
NixSam

Android:background="?android:attr/selectableItemBackground"my_list_item.xmlの-​​ルートレイアウトに追加すると、うまくいくようです(デフォルトの選択色が必要な場合)。

また、行全体を選択できるように、ルートレイアウトのAndroid:layout_widthmatch_parentではなくwrap_contentであることを確認してください。

13
Lawrr

残念ながら、フォーカス可能なビューを使用してアイテム選択をシミュレートすることは、良い解決策ではありません

  • notifyDataSetChangedが呼び出されるとフォーカスが失われます
  • 子ビューがフォーカス可能である場合、フォーカスは問題があります

私は、RecyclerViewでアイテムの選択を自動的に処理する基本アダプタークラスを作成しました。アダプターをアダプターから派生させ、リストビューで行うように、state_selectedで描画可能な状態リストを使用するだけです。

Blog Post Here がありますが、コードは次のとおりです。

public abstract class TrackSelectionAdapter<VH extends TrackSelectionAdapter.ViewHolder> extends RecyclerView.Adapter<VH> {
    // Start with first item selected
    private int focusedItem = 0;

    @Override
    public void onAttachedToRecyclerView(final RecyclerView recyclerView) {
        super.onAttachedToRecyclerView(recyclerView);

        // Handle key up and key down and attempt to move selection
        recyclerView.setOnKeyListener(new View.OnKeyListener() {
            @Override
            public boolean onKey(View v, int keyCode, KeyEvent event) {
                RecyclerView.LayoutManager lm = recyclerView.getLayoutManager();

                // Return false if scrolled to the bounds and allow focus to move off the list
                if (event.getAction() == KeyEvent.ACTION_DOWN) {
                    if (keyCode == KeyEvent.KEYCODE_DPAD_DOWN) {
                        return tryMoveSelection(lm, 1);
                    } else if (keyCode == KeyEvent.KEYCODE_DPAD_UP) {
                        return tryMoveSelection(lm, -1);
                    }
                }

                return false;
            }
        });
    }

    private boolean tryMoveSelection(RecyclerView.LayoutManager lm, int direction) {
        int tryFocusItem = focusedItem + direction;

        // If still within valid bounds, move the selection, notify to redraw, and scroll
        if (tryFocusItem >= 0 && tryFocusItem < getItemCount()) {
            notifyItemChanged(focusedItem);
            focusedItem = tryFocusItem;
            notifyItemChanged(focusedItem);
            lm.scrollToPosition(focusedItem);
            return true;
        }

        return false;
    }

    @Override
    public void onBindViewHolder(VH viewHolder, int i) {
        // Set selected state; use a state list drawable to style the view
        viewHolder.itemView.setSelected(focusedItem == i);
    }

    public class ViewHolder extends RecyclerView.ViewHolder {
        public ViewHolder(View itemView) {
            super(itemView);

            // Handle item click and set the selection
            itemView.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    // Redraw the old selection and the new
                    notifyItemChanged(focusedItem);
                    focusedItem = mRecyclerView.getChildPosition(v);
                    notifyItemChanged(focusedItem);
                }
            });
        }
    }
} 
6
Greg Ennis
    viewHolder.mRlPrince.setOnTouchListener(new View.OnTouchListener() {
        @Override public boolean onTouch(View v, MotionEvent event) {

            if (event.getAction()==MotionEvent.ACTION_DOWN){
                viewHolder.mRlPrince.setBackgroundColor(Color.parseColor("#f8f8f8"));
            }if (event.getAction()==MotionEvent.ACTION_UP){
                viewHolder.mRlPrince.setBackgroundColor(Color.WHITE);
            }

            return false;
        }
    });
4
jingyuan iu

アイテム「my_list_item.xml」に以下の属性を追加します
Android:descendantFocusability="blocksDescendants"これは私のために働く!

3

要素xmlでAndroid:clickable="true"を設定する必要があります。また、ビュー内のいくつかのビューにさらにセレクターがある場合は、そこにもAndroid:duplicateParentState="true"を設定する必要があります。 Thatsは、事前ハニカムAPIで機能します。

1
Bruno Pinto

デザインファイルまたはxmlファイルに次の行を配置するだけです。

Android:clickable="true"
Android:focusable="true"
Android:background="?android:attr/activatedBackgroundIndicator"
0
Juboraj Sarker

他の多くの人が答えたように、唯一の方法はセレクタと新しいクラスを組み合わせて選択を追跡することですが、この計算をアダプタに委任することをお勧めします。ライブラリFlexibleAdapterは選択を追跡します。構成の変更にも互換性があります。

さざ波のある背景色は、XML部分なしで実行できますが、動的データを管理するコードで実行できます。

最後に、同じライブラリで多くの機能を使用できます。選択できるのはごく小さな基本機能です。

説明、Wikiページ、完全な動作例をご覧ください。 https://github.com/davideas/FlexibleAdapter

0
Davideas