Sélecteur sur la couleur de fond de TextView


121

J'essaie de changer la couleur d'arrière-plan d'un TextViewwidget Android lorsque l'utilisateur le touche. J'ai créé un sélecteur à cet effet, qui est stocké dans res/color/selector.xmlet ressemble à peu près à ça:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:state_pressed="true"
        android:color="@color/semitransparent_white"
        />
    <item
        android:color="@color/transparent"
        />
</selector>

L' clickableattribut de TextViewest true, au cas où cela vous intéresse.

Lorsque j'attribue ce sélecteur à un TextViewas android:background="@color/selector", j'obtiens l'exception suivante au moment de l'exécution:

ERREUR / AndroidRuntime (13130): causée par: org.xmlpull.v1.XmlPullParserException: ligne de fichier XML binaire # 6: la balise nécessite un attribut 'drawable' ou une balise enfant définissant un dessinable

Quand je change l'attribut en drawable, cela fonctionne, mais le résultat est complètement faux car les ID semblent être interprétés comme des références d'image au lieu de références de couleur (comme le suggère le "drawable").

Ce qui me trouble, c'est que je peux définir une référence de couleur, par exemple "@ color / black", comme attribut d'arrière-plan directement. Cela fonctionne comme prévu. L'utilisation de sélecteurs ne fonctionne pas.

Je peux aussi utiliser le sélecteur comme le textColorsans problèmes.

Quelle est la bonne façon d'appliquer un sélecteur de couleur d'arrière-plan à un TextViewsous Android?


Une couleur peut être interprétée comme un dessin. En quoi le résultat est-il erroné exactement?
Romain Guy

Il ne montre pas la couleur mais une image de mes ressources dessinables comme arrière-plan.
digitalbreed

2
Ce qui précède devrait fonctionner, si vous utilisez android: drawable, pas android: color - au moins dans ce cas cela fonctionne pour moi: android: drawable = "@ color / my_custom_color". Mes couleurs sont définies dans values ​​/ colors.xml
AgentKnopf

Réponses:


226

Le problème ici est que vous ne pouvez pas définir la couleur d'arrière-plan à l'aide d'un sélecteur de couleur, vous avez besoin d'un sélecteur pouvant être dessiné . Ainsi, les changements nécessaires ressembleraient à ceci:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:state_pressed="true"
        android:drawable="@drawable/selected_state" />
</selector>

Vous devrez également déplacer cette ressource vers le drawablerépertoire où cela aurait plus de sens car ce n'est pas un sélecteur de couleur en soi.

Ensuite, vous devrez créer le res/drawable/selected_state.xmlfichier comme ceci:

<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" 
    android:shape="rectangle">
    <solid android:color="@color/semitransparent_white" />
</shape>

et enfin, vous l'utiliseriez comme ceci:

android:background="@drawable/selector"

Remarque : la raison pour laquelle l'OP obtenait une ressource image dessinée est probablement parce qu'il a essayé de simplement référencer sa ressource qui était toujours dans le répertoire des couleurs, mais en utilisant @drawableainsi il s'est retrouvé avec une collision d'ID, sélectionnant la mauvaise ressource.

J'espère que cela peut encore aider quelqu'un même si l'OP a probablement, j'espère, résolu son problème maintenant.


1
Merci, Benoit. Le problème a été résolu (je dois admettre que je ne me souviens plus comment exactement je l'ai fait à la fin) et le projet s'est terminé avec succès. J'apprécie que vous soyez revenu ici pour poster et aider les gens qui rencontrent le même problème à l'avenir, super esprit!
digitalbreed

Je ne peux pas faire fonctionner ça. J'essaie de l'appliquer à un bouton et cela définit l'arrière-plan sur la couleur par défaut du sélecteur, mais cela ne change pas pour la forme définie dans state_pressed. Que pourrais-je manquer? Je pourrais ouvrir une nouvelle question, juste au cas où vous pourriez m'indiquer la bonne direction.
Maragues le

@Maragues c'est difficile à dire sans voir de code. Je vous recommande d'ouvrir une nouvelle question et de publier le code correspondant afin que nous puissions déterminer ce qui pourrait ne pas être le bon. Vous pouvez également ajouter un commentaire à ce message avec un lien vers votre nouveau message.
Benoit Martin

9
Pourquoi ne pas simplement utiliser "drawable =" @ color / your_color "directement dans vos éléments de sélection à la place? Vous n'avez pas besoin de définir des formes ou tout autre fichier que ce soit, ayez simplement vos définitions de couleurs dans values ​​/ colors.xml (c'est toujours bon ne pas coder en dur les couleurs).
javaxian

Ca ne fonctionne pas. Il me montre la couleur différente des deux que j'ai déclarées en forme xml.
Er.Rohit Sharma

122

La solution de Benoit fonctionne, mais vous n'avez vraiment pas besoin d'engager des frais généraux pour dessiner une forme. Puisque les couleurs peuvent être dessinables, définissez simplement une couleur dans un fichier /res/values/colors.xml:

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <color name="semitransparent_white">#77ffffff</color>
</resources>

Et puis utilisez comme tel dans votre sélecteur:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:state_pressed="true"
        android:drawable="@color/semitransparent_white" />
</selector>

Pour une raison quelconque, votre solution n'affiche pas la couleur mais une image aléatoire de mon dossier de ressources dessinables. J'ai essayé de nettoyer le projet / corriger les propriétés / réenregistrer / rouvrir l'éclipse car cela semble vraiment étrange, mais en vain. Bizarre.
Yahel

@Yahel Vous avez peut-être nommé la ressource color drawable de la même manière qu'un fichier dessinable réel?
Jona

@Jona: Non, mais le dessinable s'appelait background_application et la couleur dessinable s'appelait background_white_transparent. Les deux avaient des antécédents en eux ... J'ai vu sur un autre fil la même chose arriver à d'autres, alors j'ai classé cela comme l'un des nombreux bogues Android et j'ai réorganisé toute ma mise en page pour le contourner.
Yahel

@Yahel Mmm ... Eh bien, je vois ce problème mais dans mon cas, pas les mêmes noms de fichiers ... Consultez mes questions ici stackoverflow.com/questions/9004744/...
Jona

n'a pas réussi à le faire fonctionner, la réponse de Benoit Martin a bien fonctionné.
Emmanuel Touzery

83

Une solution encore plus simple à ce qui précède:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed="true">
        <color android:color="@color/semitransparent_white" />
    </item>
    <item>
        <color android:color="@color/transparent" />
    </item>
</selector>

Enregistrez-le dans le dossier pouvant être dessiné et vous êtes prêt à partir.


1
Peut-être que cela fonctionne, mais n'est officiellement pas pris en charge (Android Studio le traite comme une erreur).
Blackhex

@Blackhex Strange. Fonctionne bien pour moi dans Eclipse. C'est probablement une erreur Lint, et si c'est le cas, vous devriez pouvoir la désactiver ou l'ignorer.
Jason Robinson

6
C'est ce que je considérerais comme la solution.
Lay González

<item android:state_pressed="true" android:color="@color/vantablack"/>ressemble sémantiquement identique à<item android:state_pressed="true"><color android:color="@color/vantablack"/></item>
samis

16

Même cela fonctionne.

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed="true" android:drawable="@color/dim_orange_btn_pressed" />
    <item android:state_focused="true" android:drawable="@color/dim_orange_btn_pressed" />
    <item android:drawable="@android:color/white" />
</selector>

J'ai ajouté l' android:drawableattribut à chaque élément et leurs valeurs sont des couleurs.

Au fait, pourquoi disent-ils que colorc'est l'un des attributs de selector? Ils n'écrivent pas ce qui android:drawableest obligatoire.

Ressource de liste d'état des couleurs

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android" >
    <item
        android:color="hex_color"
        android:state_pressed=["true" | "false"]
        android:state_focused=["true" | "false"]
        android:state_selected=["true" | "false"]
        android:state_checkable=["true" | "false"]
        android:state_checked=["true" | "false"]
        android:state_enabled=["true" | "false"]
        android:state_window_focused=["true" | "false"] />
</selector>

L'attribut de couleur fonctionne lorsque vous définissez les couleurs de la vue de texte, mais pas avec l'arrière-plan, car les couleurs du fond sont agies comme ColorDrawable
Akhil Dad

La meilleure et la plus simple solution à mettre en œuvre de tout ce qui précède.
4gus71n

6

Pour qui cherche à le faire sans créer de secteur d'arrière-plan, ajoutez simplement ces lignes à la TextView

android:background="?android:attr/selectableItemBackground"
android:clickable="true"

Aussi pour le rendre sélectionnable, utilisez:

android:textIsSelectable="true"
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.