前言
Jetpack Compose虽然已经逐渐完善,但是其实还是有很多地方未满足需求。比如播放视频、相机预览等等依然需要原来的View。所以目前阶段Jetpack Compose与xml的混合开发非常重要。
在compose中添加TextView
View与Jetpack Compose进行混合时,主要依靠的是AndroidView
效果图
代码
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
APage()
}
}
@Composable
fun APage() {
val timeData = remember {
mutableStateOf(0L)
}
Column(
Modifier.fillMaxSize(),
horizontalAlignment = Alignment.CenterHorizontally,
verticalArrangement = Arrangement.Center
) {
//这里在AndroidView的factory构建TextView
AndroidView(factory = {
TextView(it).apply {
text = System.currentTimeMillis().toString()
textSize = 40f
setTextColor(android.graphics.Color.WHITE)
}
}, modifier = Modifier.background(color = Color.Gray)//这边依然可以使用compose的modifier对View进行配置
, update = { //update是用来更新AndroidView里的数据的
it.text = timeData.value.toString()
})
//这里举例通过Button更新AndroidView里的数据
Button(onClick = {
timeData.value = System.currentTimeMillis()
}) {
Text(text = "更新时间")
}
}
}
通过ViewBinding导入xml布局
效果图
所需依赖
这个版本是跟随compose的大版本,需要参考你的androidx.compose.ui:ui: 、androidx.compose.ui:ui-tooling: 版本
//androidView binding
implementation("androidx.compose.ui:ui-viewbinding:1.4.3")
此外还需要在build文件中启用viewBinding
android {
//略...
defaultConfig {
//略...
}
buildFeatures{
viewBinding = true
}
//略...
}
xml布局
item_user_layout.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content"
xmlns:app="http://schemas.android.com/apk/res-auto">
<ImageView
android:id="@+id/image"
android:layout_width="200dp"
android:layout_height="200dp"
android:src="@mipmap/ic_fruit_apple"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="20dp"
android:textSize="40sp"
android:text="名称"
android:textColor="@color/black"
app:layout_constraintEnd_toEndOf="@+id/image"
app:layout_constraintStart_toStartOf="@+id/image"
app:layout_constraintTop_toBottomOf="@+id/image" />
</androidx.constraintlayout.widget.ConstraintLayout>
代码
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
APage()
}
}
@Composable
fun APage() {
val imageRes = remember {
mutableListOf(R.mipmap.ic_fruit_apple, R.mipmap.ic_fruit_banana,R.mipmap.ic_fruit_coconut)
}
val nameData = remember {
mutableListOf("苹果", "香蕉","椰子")
}
val count = remember {
mutableStateOf(0)
}
Column(
Modifier.fillMaxSize(),
horizontalAlignment = Alignment.CenterHorizontally,
verticalArrangement = Arrangement.Center
) {
AndroidViewBinding(factory = ItemUserLayoutBinding::inflate) {
//这里已经是AndroidViewBinding的update参数lambda
image.setImageResource(imageRes[count.value])
name.text = nameData[count.value]
//这里也举例一下,可以在AndroidViewBinding里更新remember的数据
image.setOnClickListener {
image.setImageResource(imageRes[count.value])
name.text = nameData[count.value]
count.value++
if (count.value > 2){
count.value = 0
}
}
}
//这是compose的Button,这里举例通过Button更新AndroidViewBinding里的数据
Button(onClick = {
count.value++
if (count.value > 2){
count.value = 0
}
}) {
Text(text = "更新数据")
}
}
}
从Compose调用Android框架
下面的代码通过附带效应DisposableEffect实现了监听音量变化的例子,如果你对附带效应不甚了解可以参考我的博客:Android开发 Jetpack_Compose_6 附带效应
效果图
代码
@Composable
fun APage() {
val volumeData = remember {
mutableStateOf(0)
}
Column(
Modifier.fillMaxSize(),
horizontalAlignment = Alignment.CenterHorizontally,
verticalArrangement = Arrangement.Center
) {
AndroidView(factory = {
TextView(it).apply {
setTextColor(android.graphics.Color.BLACK)
textSize = 50f
}
}, update = {
it.text = volumeData.value.toString()
})
}
val context = LocalContext.current
DisposableEffect(context){
val volumeReceiver = object : BroadcastReceiver() {
override fun onReceive(context: Context, intent: Intent) {
if (intent.action.equals("android.media.VOLUME_CHANGED_ACTION")) {
val audioManager = context.getSystemService(Context.AUDIO_SERVICE) as AudioManager
val currVolume: Int = audioManager.getStreamVolume(AudioManager.STREAM_MUSIC) // 当前的媒体音量
volumeData.value = currVolume
}
}
}
val filter = IntentFilter()
filter.addAction("android.media.VOLUME_CHANGED_ACTION")
context.registerReceiver(volumeReceiver, filter)
onDispose {
//注销广播
context.unregisterReceiver(volumeReceiver)
}
}
}
end
本文来自博客园,作者:观心静 ,转载请注明原文链接:https://www.cnblogs.com/guanxinjing/p/17607554.html
本文版权归作者和博客园共有,欢迎转载,但必须给出原文链接,并保留此段声明,否则保留追究法律责任的权利。