Compose基础控件

Text 文本显示控件

kotlin 复制代码
@Composable
fun Text(
    text: String?,
    modifier: Modifier? = Modifier,
    color: Color? = Color.Unspecified,
    fontSize: TextUnit? = TextUnit.Unspecified,
    fontStyle: FontStyle? = null,
    fontWeight: FontWeight? = null,
    fontFamily: FontFamily? = null,
    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
): Unit

用法

直接显示

kotlin 复制代码
@Composable
fun TextSample() {
    Text(text = "Hello World!")
}

从 res 中读取文字显示

kotlin 复制代码
@Composable
fun TextSample() {
    Text(text = stringResource(R.string.content))
}
xml 复制代码
<resources>
    <string name="content">你好,世界!</string>
</resources>

参数

color 设置字体颜色

kotlin 复制代码
@Composable
fun TextSample() {
    Text(text = "Hello World!", color = Color.Red)
}

fontSize 设置文字大小

fontSize 默认是跟随父级文字大小。

接收的是一个 TextUnit,可以设置 SP(像素值) 和 EM(字体值) 单位的值

以下示例是直接使用 TextUnit 创建对象进行赋值,因为这个构造函数还是实验性的,随时都可能有改动或删除,因此需要在函数前增加@OptIn(ExperimentalUnitApi::class)注解

kotlin 复制代码
@OptIn(ExperimentalUnitApi::class)
@Composable
fun TextSample() {
    Text(text = "Hello World!", fontSize = TextUnit(16f, TextUnitType.Sp))
}

当然,系统对 IntDoubleFloat 三种类型进行了扩展,可以直接按照下面的方式进行使用

kotlin 复制代码
import androidx.compose.ui.unit.sp
import androidx.compose.ui.unit.em

@Composable
fun TextSample1() {
    Text(text = "Hello World!", fontSize = 16.0.sp))
}

@OptIn(ExperimentalUnitApi::class)
@Composable
fun TextSample2() {
    Text(text = "Hello World!", fontSize = 16.em))
}

使用 em 的效果

fontStyle 设置文字样式

  • FontStyle.Italic 设置为斜体
  • FontStyle.Normal 设置为正常体(默认状态)
kotlin 复制代码
@Composable
fun TextSample() {
    Text(text = "Hello World!", fontStyle = FontStyle.Italic))
}

fontWeight 设置文字比重

系统预设了很多比重值可以直接使用,例如 FontWeight.Bold ,也可以使用 FontWeight(100)

fontFamily 设置文字字体

同样系统也预设了几个字体供选择使用,例如 FontFamily.SansSerif。也可以加载 res 下的字体文件

kotlin 复制代码
@Composable
fun TextSample() {

    val firaSansFamily = FontFamily(
        Font(R.font.firasans_light, FontWeight.Light),
        Font(R.font.firasans_regular, FontWeight.Normal),
        Font(R.font.firasans_italic, FontWeight.Normal, FontStyle.Italic),
        Font(R.font.firasans_medium, FontWeight.Medium),
        Font(R.font.firasans_bold, FontWeight.Bold)
    )

    Text(text = "Hello World!", fontFamily = firaSansFamily))
}

letterSpacing 设置字符间距

kotlin 复制代码
@Composable
fun TextSample() {
    Text(text = "Hello World!", letterSpacing = 15.sp))
}

textDecoration 设置文字装饰

  • TextDecoration.None 无装饰(默认)
  • TextDecoration.Underline 下划线
  • TextDecoration.LineThrough 删除线

还可以通过TextDecoration.combine()合并使用多种装饰

kotlin 复制代码
@Composable
fun TextSample() {
    Text(
        text = "Hello World!",
        textDecoration = TextDecoration.combine(
            listOf(
                TextDecoration.LineThrough,
                TextDecoration.Underline
            )
        )
    )
}

textAlign 设置文本对齐方式

需要固定宽度,才有效果

  • TextAlign.Center
  • TextAlign.End
  • TextAlign.Justify

效果如图

lineHeight 设置文本行高

kotlin 复制代码
@Composable
fun TextSample() {
    Text(text = "Hello World!", lineHeight = 15.sp))
}

overflow 设置文本超出时如何显示

  • TextOverflow.Ellipsis 以省略号显示
  • TextOverflow.Clip 裁剪
  • TextOverflow.Visible 尽可能显示

目前省略号只能在末尾,无法自定义省略号位置

maxLines 文本显示行数

kotlin 复制代码
@Composable
fun TextSample() {
    Text(text = "Hello World!", maxLines = 1))
}

style 样式

上面讲到的大部分文字修饰,都可以直接通过 TextStyle 进行修饰,除此之外还多出几个样式

  • fontFeatureSettings字体的高级设置,类似 CSS 的font-feature-settings,可以参考www.w3.org/TR/css-font...
  • background 设置背景颜色
  • shadow 设置阴影
  • textIndent 设置首先缩进
kotlin 复制代码
@Composable
fun TextSample() {
    Text(
        text = "锄禾日当午,汗滴禾下土。谁知盘中餐,粒粒皆辛苦",
        modifier = Modifier.width(110.dp),
        style = TextStyle(
            background = Color.White,
            shadow = Shadow(
                color = Color.Red,
                offset = Offset(5f, 5f),
                blurRadius = 10f
            ),
            textIndent = TextIndent(20.sp)
        )
    )
}

SelectionContainer 文字复制

默认情况下 Text 并不能进行复制等操作,我们需要设置 SelectionContainer 来包装 Text

kotlin 复制代码
@Composable
fun TextSample() {
    SelectionContainer(
        Text(
            text = "锄禾日当午,汗滴禾下土。谁知盘中餐,粒粒皆辛苦"
        )
    )
}

Text 语句中设置不同样式

如果想让一个 Text 语句中有不同的样式,需要使用到 AnnotaedString

AnnotaedString 是一个数据类,包含文本,以及多种样式

kotlin 复制代码
@Composable
fun TextSample() {
    Text(
        buildAnnotatedString {
            withStyle(style = SpanStyle(Color.Red)) {
                append("锄禾日当午,")
            }
            withStyle(style = SpanStyle(Color.Green)) {
                append("汗滴禾下土。")
            }
            withStyle(style = SpanStyle(Color.Blue)) {
                append("谁知盘中餐,")
            }
            withStyle(style = SpanStyle(Color.Yellow)) {
                append("粒粒皆辛苦")
            }
        }
    )
}

ClickableText文本点击控件

想要让文本可以接收到点击事件,可以使用 ClickableText,控件带有一个 onClick 参数,参数回调中还可以知道当前点击字条的 offset 是多少

简单用法

kotlin 复制代码
@Composable
fun TextSample() {
    ClickableText(
        buildAnnotatedString {
            withStyle(style = SpanStyle(Color.Red)) {
                append("锄禾日当午,")
            }
            withStyle(style = SpanStyle(Color.Green)) {
                append("汗滴禾下土。")
            }
            withStyle(style = SpanStyle(Color.Blue)) {
                append("谁知盘中餐,")
            }
            withStyle(style = SpanStyle(Color.Yellow)) {
                append("粒粒皆辛苦")
            }
        }, onClick = { offset ->
            Log.d("TextSample", "offset:$offset")
        }
    )
}

高级用法

从上面 设置不同样式文本点击 我们知道了如何在 Text 语句内设置不同的样式,也知道了如何获得点击的文字,那我们是不是可以实现在文本内设置部分文字可以点击呢!

比如『点击登录代表您知悉和同意用户协议隐私政策

kotlin 复制代码
@Composable
fun TextSample() {
    val annotatedString = buildAnnotatedString {
        append("点击登录代表您知悉和同意")

        //往字符串中添加一个注解,直到遇到 pop() 。tag 为注解标识,annotation 为传递内容
        pushStringAnnotation("protocol", annotation = "https://docs.bughub.icu/compose")
        withStyle(style = SpanStyle(Color.Blue)) {
            append("用户协议")
        }
        pop()

        append("和")

        pushStringAnnotation("privacy", annotation = "https://randywei.gitee.com")
        withStyle(style = SpanStyle(Color.Blue)) {
            append("隐私政策")
        }
        pop()
    }

    ClickableText(
        annotatedString, onClick = { offset ->
            //从字符串中查找注解
            annotatedString.getStringAnnotations("protocol", start = offset, end = offset)
                .firstOrNull()?.let { annotation ->
                    Log.d("TextSample", "点击了用户协议:${annotation.item}")
                }

            annotatedString.getStringAnnotations("privacy", start = offset, end = offset)
                .firstOrNull()?.let { annotation ->
                    Log.d("TextSample", "点击了隐私政策:${annotation.item}")
                }
        }
    )
}

Button

属性

kotlin 复制代码
@Composable
fun Button(
    onClick: () -> Unit,
    modifier: Modifier = Modifier,
    enabled: Boolean = true,
    interactionSource: MutableInteractionSource = remember { MutableInteractionSource() },
    elevation: ButtonElevation? = ButtonDefaults.elevation(),
    shape: Shape = MaterialTheme.shapes.small,
    border: BorderStroke? = null,
    colors: ButtonColors = ButtonDefaults.buttonColors(),
    contentPadding: PaddingValues = ButtonDefaults.ContentPadding,
    content: @Composable RowScope.() -> Unit
): Unit

基本用法

kotlin 复制代码
@Composable
fun ButtonSample() {
    Button(
        onClick = {
            Log.d("ButtonSample", "click the button")
        },
    ) {
        Text(text = "这里有一个按钮")
    }
}

参数

  • enabled 是否启用或禁用
  • elevation 投影
  • border 边框线
kotlin 复制代码
@Composable
fun ButtonSample() {
    Button(
        onClick = {
            Log.d("ButtonSample", "click the button")
        },
        border = BorderStroke(1.dp,Color.Red)
    ) {
        Text(text = "这里有一个按钮")
    }
}
  • colors设置颜色,可以设置背景颜色、前景颜色、禁用状态和启动状态下的颜色
kotlin 复制代码
@Composable
fun ButtonSample() {
    Button(
        onClick = {
            Log.d("ButtonSample", "click the button")
        },
        colors = ButtonDefaults.buttonColors(
            backgroundColor = Color.Yellow,
            contentColor = Color.Green
        )
    ) {
        Text(text = "这里有一个按钮")
    }
}
  • contentPadding 内容内间距

TextButton

TextButton一般是用来显示文字按钮的

kotlin 复制代码
@Composable
fun ButtonSample() {
    TextButton(
        onClick = {
            Log.d("ButtonSample", "click the button")
        },
    ) {
        Text(text = "TextButton")
    }
}

OutlinedButton

用于实现带有边框的按钮

kotlin 复制代码
@Composable
fun OutlinedButtonDemo(){
    OutlinedButton(onClick = {
        println("点击1")
        Log.d("OutlinedButtonDemo", "click the button")
    },
    border = BorderStroke(2.0.dp, Color.Green),
    colors = ButtonDefaults.buttonColors(Color.Red)
    ) {
        Text("Outlined Button")
    }
}

IconButton

用来显示图标按钮

kotlin 复制代码
@Composable
fun ButtonSample() {
    IconButton(
        onClick = {
            Log.d("ButtonSample", "click the button")
        },
    ) {
        Icon(imageVector = Icons.Default.Stairs, contentDescription = null)
    }
}
相关推荐
QING6182 小时前
Jetpack Compose 中的 ViewModel 作用域管理 —— 新手指南
android·kotlin·android jetpack
惟恋惜13 小时前
Jetpack Compose 的状态使用之“界面状态”
android·android jetpack
喜熊的Btm17 小时前
探索 Kotlin 的不可变集合库
kotlin·android jetpack
惟恋惜20 小时前
Jetpack Compose 界面元素状态(UI Element State)详解
android·ui·android jetpack
惟恋惜1 天前
Jetpack Compose 多页面架构实战:从 Splash 到底部导航,每个 Tab 拥有独立 ViewModel
android·ui·架构·android jetpack
alexhilton3 天前
Jetpack Compose 2025年12月版本新增功能
android·kotlin·android jetpack
モンキー・D・小菜鸡儿4 天前
Android Jetpack Compose 基础控件介绍
android·kotlin·android jetpack·compose
darryrzhong6 天前
FluxImageLoader : 基于Coil3封装的 Android 图片加载库,旨在提供简单、高效且功能丰富的图片加载解决方案
android·github·android jetpack
我命由我123456 天前
Android 开发问题:在无法直接获取或者通过传递获取 Context 的地方如何获取 Context
android·java·java-ee·android studio·android jetpack·android-studio·android runtime
儿歌八万首6 天前
Jetpack Compose 实战:实现手势缩放图片 (Zoomable Image) 组件
kotlin·android jetpack