如何使用 Android 数据绑定库制作粗体文本

How to make bold text with Android Data Binding Library

非常基本,我想根据是否阅读文本来使消息标题加粗。我似乎找不到解决方案。

这是我的 XML 代码:

            <TextView
                android:text="@{message.title}"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_alignParentLeft="true"
                android:layout_alignParentStart="true"
                android:layout_alignParentTop="true"
                android:layout_marginBottom="5dp"
                android:layout_marginTop="5dp"
                android:layout_toLeftOf="@+id/timestamp"
                android:textSize="18sp"
                android:textStyle='@{message.isRead() ? "bold" : "normal"}'
                android:textColor='@{message.isRead() ? 0xff313131 : 0xff0662ab}' />

颜色更改效果很好,只有粗体文本给我带来了一些问题。

错误:任务“:app:compileDebugJavaWithJavac”执行失败。

java.lang.RuntimeException: Found data binding errors. ****/ data binding error ****msg:Cannot find the setter for attribute 'android:textStyle' with parameter type java.lang.String on android.widget.TextView. file:D:......xml loc:39:41 - 39:79 ****\ data binding error ****

您需要在消息对象中创建 getMessageStyle

public String getMessageStyle() {
    return isRead() ? "bold" : "normal";
}

然后在您的代码中使用如下代码:

<TextView
    android:text="@{message.title}"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignParentLeft="true"
    android:layout_alignParentStart="true"
    android:layout_alignParentTop="true"
    android:layout_marginBottom="5dp"
    android:layout_marginTop="5dp"
    android:layout_toLeftOf="@+id/timestamp"
    android:textSize="18sp"
    android:textStyle="@{message.getMessageStyle()}"
    android:textColor="@{message.isRead() ? 0xff313131 : 0xff0662ab}" />

我最终使用了以下代码,它实现了 DataBinding。

public abstract class BindingAdapter {
    @android.databinding.BindingAdapter("android:typeface")
    public static void setTypeface(TextView v, String style) {
        switch (style) {
            case "bold":
                v.setTypeface(null, Typeface.BOLD);
                break;
            default:
                v.setTypeface(null, Typeface.NORMAL);
                break;
        }
    }
}

还有 XML

<TextView
    android:text="@{bericht.titel}"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignParentLeft="true"
    android:layout_alignParentStart="true"
    android:layout_alignParentTop="true"
    android:layout_marginBottom="5dp"
    android:layout_marginTop="5dp"
    android:layout_toLeftOf="@+id/timestamp"
    android:textSize="18sp"
    android:textColor='@{bericht.isGelezen() ? 0xff313131 : 0xff0662ab}'
    android:typeface='@{bericht.isGelezen() ? "normal" : "bold"}' />

Saif Bechan 的回答是正确的,我做了一些小改动以方便从视图模型进行数据绑定。

public abstract class BindingAdapter {
    @android.databinding.BindingAdapter("app:textStyle")
    public static void setTextStyle(TextView v, int style) {
        v.setTypeface(null, style);
    }
}

然后将 app 命名空间引入 XML

<layout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto">
...
</layout>

在视图模型中创建绑定

@Bindable
public int getValueFormat() {
    String message = getMyObject().getValue();
    if (message == MyObject.DEFAULT_VALUE)
        return Typeface.ITALIC;

    return Typeface.NORMAL;
}

现在可以直接绑定了

<TextView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    app:textStyle="@{viewModel.valueFormat}"
    android:text="@{viewModel.value}" />

一个简单的方法

public class TextViewBindingAdapter {
    @BindingAdapter("isBold")
    public static void setBold(TextView view, boolean isBold) {
        if (isBold) {
            view.setTypeface(null, Typeface.BOLD);
        } else {
            view.setTypeface(null, Typeface.NORMAL);
        }
    }
}

XML:

    <TextView
        android:id="@+id/text"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:isBold="@{item.bold}"/>

您只需将 Typeface 导入 xml 文件并像这样进行检查

    <variable
        name="vm"
        type="com.example.VM" />

    <import type="android.graphics.Typeface" />


        <TextView
            android:id="@+id/username"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textStyle="@{vm.isBold ? Typeface.BOLD : Typeface.NORMAL}"/>

您可以在不创建适配器的情况下执行此操作。

将字体导入您的 XML

<data>
    <import type="android.graphics.Typeface" />
...
</data>

将属性 android:typefaceTypeface.defaultFromStyle 一起使用:

android:typeface="@{Typeface.defaultFromStyle(message.isRead() ? Typeface.BOLD : Typeface.NORMAL)}"

所以,这周我遇到了同样的问题,我尝试使用 view.setTypeface() 方法,但我想保留我的字体样式。事实证明,当我在 setTypeFace 方法中传递 null 时,粗体样式有效,但是...传递 null 可以更改字体样式(看起来不一样)。当我尝试使用相同的字体样式并将视图设置为粗体时,它不起作用。

为了达到我想要的效果,因为我没有成功使用这种方法,所以我只是在需要粗体时更改字体样式,请参阅我的代码:

@BindingAdapter("boldOrRegular")
@JvmStatic
    fun TextView.boldOrRegular(isBold: Boolean) {
        typeface = if (isBold) {
            ResourcesCompat.getFont(context, R.font.myfont_bold)
        } else {
            ResourcesCompat.getFont(context, R.font.myfont_regular)
        }
    }

希望对大家有所帮助:)