Compose Text简单使用


theme: channing-cyan

Text控件的相关API说明

Compose中的Text就等价于Android原生中的TextView,API也比较简单: fun Text( text: String, // 文字内容,可以直接传递字符串,也可以使用stringResource(id = R.string.hello)来指定 modifier: Modifier = Modifier, // 修饰符,可以指定宽高,背景,点击事件等。 color: Color = Color.Unspecified, // 文字颜色 fontSize: TextUnit = TextUnit.Unspecified, // 文字大小 fontStyle: FontStyle? = null, // 文字样式,比如斜体 fontWeight: FontWeight? = null, // 字体宽度,比如粗体 fontFamily: FontFamily? = null, // 字体样式,比如SansSerif,Serif等 letterSpacing: TextUnit = TextUnit.Unspecified, // 字符间距 textDecoration: TextDecoration? = null, // 装饰物,比如添加下划线 textAlign: TextAlign? = null, // 文字对齐方式,比如居中对齐,但是不能垂直居中 lineHeight: TextUnit = TextUnit.Unspecified, // 行高 overflow: TextOverflow = TextOverflow.Clip, // 文字溢出的展示方式,比如裁剪,或末尾显示...等 softWrap: Boolean = true, // 文字过长是否换行 maxLines: Int = Int.MAX_VALUE, // 最大行数 onTextLayout: (TextLayoutResult) -> Unit = {}, // 布局变化的回调 style: TextStyle = LocalTextStyle.current // 设置Style,类似TextView的style ) TextStyle的API,内容跟Text里面的大部分相同,具体可以查看相关API,这里有个点需要提一下: Text不能垂直居中,要想垂直居中,可以在外面包一层父View,比如Box

基础示例

我们来个小Demo @Composable fun TextDemo() { val text = "this is compose text demo, which likes TextView in android native xml layout" Text( text = text, // 文字 color = Color.Green, // 字体颜色 fontSize = 16.sp, // 字体大小 fontStyle = FontStyle.Italic, // 斜体 fontWeight = FontWeight.Bold, // 粗体 textAlign = TextAlign.Center, // 对齐方式: 居中对齐 modifier = Modifier.width(300.dp), // 指定宽度为300dp maxLines = 2, // 最大行数 overflow = TextOverflow.Ellipsis, // 文字溢出后就裁剪 softWrap = true, // 文字过长时是否换行 textDecoration = TextDecoration.Underline, // 文字装饰,这里添加下划线 ) } 效果如下:

示例

然后我们加上字体样式: fontFamily = FontFamily.Cursive, // 字体样式 效果如下:

示例

我们再加上行高和字符间距: lineHeight = 40.sp, // 行高40sp letterSpacing = 5.sp // 字符间距5sp 效果如下:

示例

富文本

使用原生的TextView如果想要实现富文本,需要使用Spanable,而且需要计算文字的下标,非常麻烦,Compose的就相当好用了。

1 使用SpanStyle来实现富文本

API如下: class SpanStyle( val color: Color = Color.Unspecified, // 文字颜色 val fontSize: TextUnit = TextUnit.Unspecified, // 文字大小 val fontWeight: FontWeight? = null, // 字体粗细,比如粗体 val fontStyle: FontStyle? = null, // 文字样式,比如斜体 val fontSynthesis: FontSynthesis? = null, // 指定的字体找不到时,所采用的策略 val fontFamily: FontFamily? = null, // 字体样式,比如Serif val fontFeatureSettings: String? = null, // 字体的排印设置,可以取CSS中font-feature-settings的值 val letterSpacing: TextUnit = TextUnit.Unspecified, // 字符间距 val baselineShift: BaselineShift? = null, // 文字举例baseline的向上偏移量 val textGeometricTransform: TextGeometricTransform? = null, // 用于几何变换,比如缩放、倾斜等 val localeList: LocaleList? = null, // 国际化相关符号列表 val background: Color = Color.Unspecified, // 背景色 val textDecoration: TextDecoration? = null, // 装饰,比如下划线 val shadow: Shadow? = null // 阴影 )

直接看Demo: ``` @Composable fun TextDemo2() { Text(buildAnnotatedString { // 使用白色背景,红色字体,18sp,Monospace字体来绘制"Hello " (注意后面有个空格) withStyle(style = SpanStyle(color = Color.Red, background = Color.White, fontSize = 18.sp, fontFamily = FontFamily.Monospace)) { append("Hello ") } // 正常绘制"World" append("World ") // 使用黄色背景,绿色字体,18sp,Serif字体,W900粗体来绘制"Click" withStyle(style = SpanStyle(color = Color.Green, background = Color.Yellow, fontSize = 30.sp, fontFamily = FontFamily.Serif, fontWeight = FontWeight.W900)) { append("Click") } // 正常绘制" Me" (注意前面有个空格) append(" Me")

// 添加阴影及几何处理
    withStyle(
        style = SpanStyle(
            color = Color.Yellow,
            background = Color.White,
            baselineShift = BaselineShift(1.0f), // 向BaseLine上偏移10
            textGeometricTransform = TextGeometricTransform(scaleX = 2.0F, skewX = 0.5F), // 水平缩放2.0,并且倾斜0.5
            shadow = Shadow(color = Color.Blue, offset = Offset(x = 1.0f, y = 1.0f), blurRadius = 10.0f) // 添加音阴影和模糊处理
        )
    ) {
        append(" Effect")
    }
})

} ``` 其中buildAnnotatedString()可以理解为构建了一个作用域,在该作用域内可以使用withStyle(style)来指定文字格式,效果如下:

示例

2 使用ParagraphStyle来实现段落

API如下: class ParagraphStyle constructor( val textAlign: TextAlign? = null, // 对齐方式 val textDirection: TextDirection? = null, // 文字方向 val lineHeight: TextUnit = TextUnit.Unspecified, //行高 val textIndent: TextIndent? = null // 缩进方式 )

直接看Demo: ``` @Composable fun TextDemo3() { Text(buildAnnotatedString { // 指定对齐方式为Start,通过textIndent指定第一行每段第一行缩进32sp,其余行缩进8sp withStyle(style = ParagraphStyle(textAlign = TextAlign.Start, textIndent = TextIndent(firstLine = 32.sp, restLine = 8.sp))) {

// 第一段,因为只有一行,所以直接缩进32sp
        withStyle(style = SpanStyle(color = Color.Red)) {
            append("Hello, this is first paragraph\n")
        }
        // 第二段(第一行会缩进32sp,后续每行会缩进8sp)
        withStyle(style = SpanStyle(color = Color.Green, fontWeight = FontWeight.Bold)) {
            append("Hello, this is second paragraph,very long very long very long very long very long very long very long very long very long very long\n")
        }
        // 第三段,因为只有一行,所以直接缩进32sp
        append("Hello, this is third paragraph\n")
    }
})

} ``` 效果如下:

示例

交互

传统的Android的TextView可以实现选中/不可选中,但是却很难实现部分可选中,部分不可选中;传统的TextView可以设置点击事件,但是很难实现获取点击文字的位置,这些在Compose中都不是事。

1 可选中和不可选中

我们可以直接使用SelectionContainer来包括可以选中的文本,使用DisableSelection来包括不可选中的文本,eg:

``` @Composable fun TextDemo4() { // 设置可选区域 SelectionContainer { // Column等价于竖直的LinearLayout Column { Text(text = "可以选中我,可以选中我,可以选中我")

// 设置不可选区域
        DisableSelection {
            Text(text = "选不中我,选不中我,选不中")
        }

        // 位于可选区域内,可选
        Text(text = "可以选中我,可以选中我,可以选中我")
    }
}

} ``` 效果如下:

示例

2 单个文字响应点击事件

我们可以直接使用ClickableText来实现点个文字的点击效果,API如下: fun ClickableText( text: AnnotatedString, // 传入的文字,这里必须传入AnnotatedString modifier: Modifier = Modifier, // 修饰符 style: TextStyle = TextStyle.Default, // 文本Style softWrap: Boolean = true, // 文本长度过长时,是否换行 overflow: TextOverflow = TextOverflow.Clip, // 文字超出显示范围的处理方式,默认Clip,就是不显示 maxLines: Int = Int.MAX_VALUE, // 最大行数 onTextLayout: (TextLayoutResult) -> Unit = {}, // 布局发生变化的回调 onClick: (Int) -> Unit // 点击事件,参数为点击文字的下标 )

Demo如下: @Composable fun TextDemo5(context: Context) { ClickableText(text = AnnotatedString("请点击我"), onClick = { index -> Toast.makeText(context, "点击位置:$index", Toast.LENGTH_SHORT).show() }) } 效果如下:

示例

如果要给整个Text()设置点击事件,直接使用Modifier.clickable{}即可。

3 给指定文字添加注解(超链接)

我们可以使用pushStringAnnotation()和pop()函数对来给指定文字添加注解,如下:

``` @Composable fun TextDemo6(context: Context) {

// 构建注解文本
val url_tag = "article_url";
val articleText = buildAnnotatedString {
    append("点击")

    // pushStringAnnotation()表示开始添加注解,可以理解为构造了一个<tag,annotation>的映射
    pushStringAnnotation(tag = url_tag, annotation = "https://devloper.android.com")
    // 要添加注解的文本为"展示Android官网"
    withStyle(style = SpanStyle(color = Color.Blue, fontWeight = FontWeight.Bold)) {
        append("展示Android官网")
    }
    // pop()表示注解结束
    pop()
}

// 构造可点击文本
ClickableText(text = articleText, onClick = { index ->
    // 根据tag取出annotation并打印
    articleText.getStringAnnotations(tag = url_tag, start = index, end = index).firstOrNull()?.let { annotation ->
        Toast.makeText(context, "点击了:${annotation.item}", Toast.LENGTH_SHORT).show()
    }
})

} ``` 效果如下:

示例

Demo可在这里下载: https://gitee.com/lloydfinch/compose-text-demo

当然,Text的用法远不止此,更多的用法可以查看官方API即可。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值