最新下载
热门教程
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
XML Shape/Selector 转 Kotlin 动态创建
时间:2026-06-03 10:10:01 编辑:袖梨 来源:一聚教程网
传统安卓开发依赖XML定义Shape和Selector,但存在颜色硬编码、重复代码与文件冗余问题。以下展示如何用Kotlin动态创建可配置的圆角按钮背景,替代XML写法。
XML Shape/Selector → Kotlin 动态创建
老写法(XML drawable)
res/drawable/bg_rounded_button.xml:

<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="#4CAF50"/>
<corners android:radius="8dp"/>
<stroke android:width="1dp" android:color="#388E3C"/>
shape>
res/drawable/selector_button.xml:
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true">
<shape>
<solid android:color="#388E3C"/>
<corners android:radius="8dp"/>
shape>
item>
<item>
<shape>
<solid android:color="#4CAF50"/>
<corners android:radius="8dp"/>
shape>
item>
selector>
Java 中使用:
view.setBackgroundResource(R.drawable.selector_button);
问题在哪里
XML drawable 有三个局限:颜色写死不能动态改、不同状态下要写多份 shape 重复代码、需要在 res/drawable 里维护一堆小文件。
新写法(Kotlin 动态创建)
fun roundedButtonBg(
context: Context,
normalColor: Int,
pressedColor: Int,
cornerRadiusDp: Int,
strokeColor: Int,
strokeWidthDp: Int = 1
): StateListDrawable {
val density = context.resources.displayMetrics.density
val radius = cornerRadiusDp * density
val strokeWidth = strokeWidthDp * density val normal = GradientDrawable().apply {
shape = GradientDrawable.RECTANGLE
setColor(normalColor)
cornerRadius = radius
setStroke(strokeWidth.toInt(), strokeColor)
} val pressed = GradientDrawable().apply {
shape = GradientDrawable.RECTANGLE
setColor(pressedColor)
cornerRadius = radius
setStroke(strokeWidth.toInt(), strokeColor)
} return StateListDrawable().apply {
addState(intArrayOf(android.R.attr.state_pressed), pressed)
addState(intArrayOf(), normal)
}
}
使用:
view.background = roundedButtonBg(
context = context,
normalColor = Color.parseColor("#4CAF50"),
pressedColor = Color.parseColor("#388E3C"),
cornerRadiusDp = 8,
strokeColor = Color.parseColor("#388E3C")
)
一句话注意
GradientDrawable.cornerRadius 和 setStroke 的参数单位是像素,不是 dp。传 dp 值必须乘以 density,否则不同分辨率手机上圆角大小不一致。StateListDrawable.addState 的状态数组顺序很重要,越具体的状态(如 state_pressed)要放在前面,默认状态(空数组)放最后。
通过Kotlin动态创建StateListDrawable与GradientDrawable,彻底摆脱XML硬编码与重复文件,实现颜色、圆角、描边等参数的灵活配置。本系列将持续探索Java旧项目迁移中的高效替代方案。
相关文章
- 实测Gemini 3.0使用教程:5个常见避坑与全流程实操 06-04
- Gemini下载怎么用?3个步骤搞定 06-04
- Gemini API密钥怎么申请?2026实测4种渠道对比 06-04
- 壹深圳app如何查看回放 06-04
- 我亲测了Gemini学生认证,全流程+踩坑记录 06-04
- Gemini 3.0使用教程 vs 4.0:3大区别与选择建议 06-04