Jetpack Compose中Modifier搭配.apply使用时border修饰符不生效问题
为什么
border修饰符配合.apply { }使用时不会被应用? 核心原因
Jetpack Compose 中的 Modifier 是不可变类型,所有为 Modifier 添加样式/行为的扩展方法(比如border、padding、clickable)都会返回全新的 Modifier 实例,不会修改原有的实例。而你使用的apply函数特性是:始终返回调用它的原始对象本身,你在apply代码块中调用border生成的新 Modifier 实例没有被赋值、也没有被返回,直接被丢弃,自然不会生效。
其他附带错误
你的代码还有两处额外的问题会导致效果不更新:
apply代码块中直接写if (selected)判断的是MutableState实例本身是否非空,不会读取状态值selected.value,判断逻辑本身就是错误的。- 只有读取
selected.value时,Compose 才会将当前作用域标记为需要跟随这个状态重组,你没有读取value的情况下,selected状态变更时 Modifier 也不会重新计算。
错误代码等价逻辑
你写的代码实际效果和这段逻辑完全一致:
// 生成仅带padding的初始Modifier val modifierWithPadding = Modifier.padding(horizontal = 5.dp, vertical = 8.dp) modifierWithPadding.apply { if (selected) { // 生成了带border的新Modifier,但没有被任何变量接收,直接废弃 this.border(BorderStroke(1.dp, MaterialTheme.colors.primaryVariant), RoundedCornerShape(13.dp)) } } // 最终拿到的还是只有padding的旧Modifier val selectableModifier = modifierWithPadding
正确实现方案
方案1:用run替换apply,手动返回最终Modifier
run函数会返回代码块最后一行的结果,刚好符合Modifier链式拼接的要求:
val selected = remember { mutableStateOf(true) } val selectableModifier = Modifier .padding(horizontal = 5.dp, vertical = 8.dp) .run { // 读取selected.value订阅状态变化 if (selected.value) { // 满足条件时返回拼接了border的新Modifier border( BorderStroke(1.dp, MaterialTheme.colors.primaryVariant), RoundedCornerShape(13.dp) ) } else { // 不满足条件时返回原有Modifier this } }
方案2:用let做条件拼接(更常用的写法)
val selectableModifier = Modifier .padding(horizontal = 5.dp, vertical = 8.dp) .let { if (selected.value) it.border(1.dp, MaterialTheme.colors.primaryVariant, RoundedCornerShape(13.dp)) else it }
内容的提问来源于stack exchange,提问作者Sreekant Shenoy
相关产品推荐
相关产品推荐

