Состояние цвета фона CardView не соблюдается
вкратце:
Как мы можем определить цветовые состояния свойства CardView cardBackgroundColor (в макете ListView, в данном случае)?
(Я использую RC1 из Android L developer preview, на телефоне с установленным 4.4 и " com.андроид.поддержка: cardview-v7: 21.0.0-rc1 " в сборке.gradle)
больше:
в макете CardView мы устанавливаем радиус угла и цвет фона CardView через cardCornerRadius и cardBackgroundColor.
однако цвет фона не отражает выбранные состояния,например, если элемент списка нажат.
Если во внутреннем виде CardView вы задаете цвет фона и связанные состояния, которые соблюдаются, однако, он будет отображаться по углам, определенным в CardView.
Итак, как мы можем гарантировать, что государства в CardView cardBackgroundColor уважаются?
вот цвет, используемый для cardBackgroundColor, colour_with_states.XML-код:
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_focused="true" android:state_enabled="false" android:state_pressed="true" android:color="@android:color/holo_green_dark" />
<item android:state_focused="true" android:state_enabled="false" android:color="@android:color/holo_green_dark" />
<item android:state_focused="true" android:state_pressed="true" android:color="@android:color/holo_green_dark" />
<item android:state_focused="false" android:state_pressed="true" android:color="@android:color/holo_green_dark" />
<item android:state_focused="true" android:color="@android:color/holo_green_dark" />
<!-- Only this below is seen in the cardview dispaly -->
<item android:color="@android:color/holo_blue_bright" />
</selector>
и макет, который использует CardView:
<android.support.v7.widget.CardView
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:cardview="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content"
cardview:cardCornerRadius="10dp"
cardview:cardBackgroundColor="@color/colour_with_states"
>
<!-- If we set a background color below, it will overwrite our radius defined above -->
<TextView
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
tools:text="Lorem ipsum"
android:id="@android:id/text1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceListItem"
android:background="@null"
android:gravity="center_vertical"
android:paddingTop="8dip"
android:paddingBottom="8dip"
android:paddingStart="8dip"
android:paddingEnd="8dip"
/>
</android.support.v7.widget.CardView>
8 ответов:
хотя это не идеально, так как края не закруглены, вы можете добавить сенсорную обратную связь к
CardViewтакой :<android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" android:layout_width="match_parent" android:layout_height="wrap_content" app:cardCornerRadius="4dp" android:clickable="true" android:foreground="?android:attr/selectableItemBackground"> //Nested View ... </android.support.v7.widget.CardView>добавлять
android:foregroundиandroid:clickableатрибутыCardView.кроме этого имеет отрицательный побочный эффект в том, что
android:clickableатрибут переопределяет любой clickListener, и поэтому эти clickListeners не срабатывают.обновление
у меня есть несколько примеров реализации CardView
петли (https://github.com/lawloretienne/Loop) - https://github.com/lawloretienne/Loop/blob/master/app/src/main/res/layout/category_card.xml
QuickReturn (https://github.com/lawloretienne/QuickReturn) - https://github.com/lawloretienne/QuickReturn/blob/master/sample/src/main/res/layout/activity_quick_return.xml
обновление 2
после дополнительных исследований я придумал хорошее решение для CardViews на всех версиях API, включая pre-Lollipop.
https://medium.com/@etiennelawlor/layout-tips-for-pre-and-post-lollipop-bcb2e4cdd6b2#.9h0v1gmaw
иногда, вы можете хотеть
CardViewдля визуальной обратной связи. Элементandroid:foreground="?android:attr/selectableItemBackground"решение идеально подходит для этого.тем не менее, вы можете рассмотреть возможность использования
drawSelectorOnTop(true)С вашим ListView. Это не потребует никаких изменений на вашемCardViewна всех.Дайте мне знать, если необходимы дополнительные разъяснения.
вот мой способ решить вашу проблему.
во-первых, создайте пользовательский класс с именем
CustomCardViewextendsCardViewзатем переопределить
drawableStateChanged()метод, изменить цвет фона карты по вызовуsetCardBackgroundColor()метод при изменении состояния печати карты.наконец, замените CardView этим CustomCardView в файле макета.
единственным недостатком этого решения является то, что cardview не может отображать эффект пульсации на Android 5.0 и выше.
вот мой код:
public class CustomCardView extends CardView { public CustomCardView(Context context) { super(context); // TODO Auto-generated constructor stub } public CustomCardView(Context context, AttributeSet attrs) { super(context, attrs); // TODO Auto-generated constructor stub } public CustomCardView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); // TODO Auto-generated constructor stub } @Override protected void drawableStateChanged() { super.drawableStateChanged(); if (isPressed()) { this.setCardBackgroundColor(getContext().getResources().getColor(R.color.card_view_pressed)); } else { this.setCardBackgroundColor(getContext().getResources().getColor(R.color.card_view_normal)); } }}
один обходной путь, который я использовал, состоял в том, чтобы сделать изменения пользовательского интерфейса программно, переопределив представление.OnTouchListener OnTouch() обработчик событий в моей пользовательской ViewHolder.
@Override public boolean onTouch (View v, MotionEvent event) { int action = event.getActionMasked(); if (action == MotionEvent.ACTION_DOWN) { mCardView.setCardBackgroundColor(STATE_PRESSED_COLOR); } else if (action == MotionEvent.ACTION_UP || action == MotionEvent.ACTION_CANCEL) { mCardView.setCardBackgroundColor(DEFAULT_COLOR); } return false; }
* * просто добавьте туда строки внутри вида карты**
android:clickable="true" android:focusableInTouchMode="true" android:foreground="?android:attr/selectableItemBackground"
Если вы посмотрите на определение свойства carBackgroundColor, по крайней мере, в библиотеке поддержки android это:
<resources> <declare-styleable name="CardView"> <!-- Background color for CardView. --> <attr name="cardBackgroundColor" format="color" /> </declare-styleable> </resource>здесь он говорит, что он принимает только цвет для cardBackgroundValue. Я думаю, это означает, что селектор не соблюдается, но падает до значения по умолчанию ie. цвет в нижней части селектора.
использовать
android:foregroundвместоandroid:backgroundв своем<CardView/>. ниже приведен пример кода CardView .<android.support.v7.widget.CardView android:layout_width="match_parent" android:layout_height="wrap_content" android:clickable="true" android:foreground="?android:attr/selectableItemBackground" app:cardCornerRadius="2dp" app:cardElevation="2dp"> // others view component </android.support.v7.widget.CardView>

Comments