J'essaie de définir la couleur du texte TextView
à l'aide de la bibliothèque de liaison de données
Android:textColor="@{holder.getTitleColor(context, item)}"
où la méthode dans la classe Holder
est définie comme ci-dessous
public int getTitleColor(Context context, Item item) {
...
}
Peu importe si je retourne color int (@ColorInt
) ou ressource de couleur (@ColorRes
), le texte est peint en blanc. Qu'est-ce que je fais mal?
Il semble que la int
que vous fournissez soit interprétée comme une couleur hexadécimale, même s'il semble intuitif que ce programme de paramétrage s'attende à un identifiant de ressource.
utilisez la référence Context
générée pour chaque vue pouvant être liée, et utilisez-la pour convertir l'ID de ressource en couleur vers laquelle vous pointez, comme décrit dans le Guide de développement DataBinding :
Une variable spéciale nommée context est générée pour être utilisée dans les expressions de liaison en fonction des besoins. La valeur de context est le contexte de getContext () de la vue racine.
utilisez-le pour définir la couleur comme ceci:
<TextView
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:text="@{data.text}"
Android:textColor="@{context.getColor(data.colorRes)}"
/>
créer une méthode en utilisant BindingAdapter
@BindingAdapter({"bind:color"})
public static void setFont(TextView textView, Item item) {
textView.setTextColor(<set color of your choice>);
}
et l'appeler depuis xml
app:color="@{item}"
Pour définir une couleur sur une partie de la chaîne - Cela fonctionne parfaitement avec Kotlin, les ressources de chaîne et la liaison de données
Ajoutez votre adaptateur de liaison (placez-le en dehors de toutes vos classes)
@BindingAdapter("app:full_text", "app:span_text", "app:span_color")
fun formatText(textView: TextView, full_text: String, span_text: String, span_color: Int) {
val firstMatchingIndex = full_text.indexOf(span_text)
val lastMatchingIndex = firstMatchingIndex + span_text.length
val spannable = SpannableString(full_text)
spannable.setSpan(ForegroundColorSpan(span_color), firstMatchingIndex, lastMatchingIndex, Spannable.SPAN_INCLUSIVE_EXCLUSIVE)
textView.text = spannable
}
Configuration des ressources de chaîne avec des variables
<string name="percentage">%1$d\%%</string>
<string name="booking_fee">Require card and collect %1$s at Booking</string>
Convertit la valeur en chaîne dans votre ViewHolder (si nécessaire)
fun bind(percentage: Int) {
binding.percentage = context.resources.getString(R.string.percentage, percentage)
binding.executePendingBindings()
}
Appliquer des liaisons via votre layout xml
<data>
<variable
name="percentage"
type="String" />
</data>
<TextView
...
app:full_text="@{@string/booking_fee(percentage)}"
app:span_color="@{@color/color_primary}"
app:span_text="@{percentage}" />
Résultat:
_ {N'utilisez pas Android:text="..."
dans votre fichier de mise en page} _
Créez l'adaptateur de liaison comme suit, je passe toutes les chaînes à colorier dans {}
. Remplacez la chaîne {blah}
par la chaîne blah
colorée dans la plage.
@BindingAdapter( "spanColor")
fun formatText(view:TextView, hexColorValue:Int) {
val text = view.text
val span = SpannableStringBuilder(text)
var i = 0
var diff = 0
while (i < text.length) {
val firstIndex = text.indexOf('{', i) - diff
val secondIndex = text.indexOf('}', i) - diff
if (firstIndex < 0 || secondIndex < 0) break
span.delete(firstIndex, firstIndex + 1)
span.delete(secondIndex - 1, secondIndex)
span.setSpan(ForegroundColorSpan(hexColorValue), firstIndex, secondIndex-1, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
i = secondIndex + diff + 1
diff += 2
}
view.text = span
}
Dans votre fichier XMl, utilisez l’attribut (app:spanColor="@{@color/colorAccent}"
) comme
<TextView
Android:layout_width="match_parent"
Android:layout_height="wrap_content"
Android:gravity="center"
Android:layout_marginTop="@dimen/space_xlarge"
style="@style/DefaultSmallText"
app:spanColor="@{@color/colorAccent}"
Android:text="@string/create_credential_message"/>
string.xml
<string name="create_credential_message"><![CDATA[{Username} must at least contain 8 alphanumeric characters or an email address. {Password} must be 8-20 characters long, contain uppercase, lowercase, number, & special characters.]]></string>