如何引用Anko DSL中的其他视图?
我在我的Android项目中使用Anko,但我不知道如何引用我在DSL中创建的子视图,当引用的视图不在我参考它的同一级别。
以下代码工作:
alert { customView { val input = textInputLayout { editText { hint = "Name" textColor =resources.getColor(R.color.highlight) } } positiveButton("OK") { "${input.editText.text}" } } }.show()
但下面的代码不起作用:
alert { customView { val vertical = verticalLayout { textView { text = "Edit device name" textColor = resources.getColor(R.color.highlight) textSize = 24F } val input = textInputLayout { editText { hint = "Name" textColor = resources.getColor(R.color.highlight) } } } positiveButton("OK") { "${vertical.input.editText.text}" } // Cannot resolve "input" } }.show()
正如我所看到的,有两种方法。 super hacky的方法是在textInputLayout
块中声明正的按钮。 这是可能的,因为您可以从任何嵌套范围内访问所有外部范围,并且在alert
范围内声明positiveButton
方法:
alert { customView { verticalLayout { textInputLayout { val editText = editText { hint = "Name" } positiveButton("OK") { toast("${editText.text}") } } } } }.show()
更简单的方法是声明一个可以从两个范围访问的变量。 但是,由于无法立即初始化,因此需要将其设置为空。
alert { var editText: EditText? = null customView { verticalLayout { textInputLayout { editText = editText { hint = "Name" } } } } positiveButton("OK") { toast("${editText!!.text}") } }.show()
我建议使用findViewById()
alert { customView { val vertical = verticalLayout { textView { text = "Edit device name" textSize = 24F } val input = textInputLayout { editText { id = R.id.my_id_resource // put your id here hint = "Name" } } } positiveButton("OK") { "${(vertical.findViewById(R.id.my_id_resource) as? EditText)?.text}" } } }.show()
您始终可以提升视图,手动传递vertical
上下文:
customView { val vertical = verticalLayout { textView { text = "Edit device name" textColor = resources.getColor(R.color.highlight) textSize = 24F } } val input = /*here:*/ vertical.textInputLayout { editText { hint = "Name" textColor = resources.getColor(R.color.highlight) } } positiveButton("OK") { "${input.editText.text}" } }
我通常在一个带有lateinit
修饰符的类中声明一个属性。 这种方式不是可以空的,大部分视图都在一个地方声明,提高了可读性:
lateinit var toolbar: Toolbar ... appBarLayout { toolbar = toolbar {}.lparams(width = matchParent, height = matchParent) }.lparams(width = matchParent) ... setSupportActionBar(toolbar)
可能最好的方法是使用Android ID作为您以后需要引用的元素,以及find<T : View>(Int) : T
函数。 这允许您从任何地方引用它们,只要视图仍然存在,并且您可以访问应用程序/活动范围。
有关详细信息,请参阅Anko文档
示例:将按钮动态添加到现有视图
verticalLayout { id = R.id.button_container } //note that the code below here may be executed anywhere after the above in your onCreate function //verticalLayout is a Anko subclass of LinearLayout, so using the android class is valid. val buttonContainer = find<LinearLayout>(R.id.button_container) val containerContext = AnkoContext.Companion.create(ctx, buttonContainer) val button = ctx.button { text = "click me" onClick = { toast("created with IDs!") } } buttonContainer.addView(button.createView(containerContext, buttonContainer))
- 如何在Anko上使用selectableButtonBackground?
- kotlin android – Xposed IllegalArgumentException'android.content.res.CoollifeUITpedArray'
- 在处理kotlin中的getter和setter时出错
- Android工作室突然未能解决其他模块的依赖关系
- 定义null局部变量时需要没有错误,稍后在方法中进行设置
- 与RxKotlin获取NetworkOnMainThreadException
- Android Kotlin将列表添加到另一个活动的列表中
- 协议缓冲gradle支持Kotlin Android不工作?
- Activity的onCreate方法中,Kotlin视图变量意外地为null