无法在 xml 中直接使用方法
Can't use method direct in xml
Android Studio 3.6
在build.gradle中:
apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
apply plugin: 'kotlin-android-extensions'
apply plugin: 'kotlin-kapt'
android {
viewBinding {
enabled = true
}
dataBinding {
enabled = true
}
主要活动:
import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import com.myproject.android.androidtestproject.BuildConfig
import com.myproject.android.androidtestproject.R
import com.myproject.android.androidtestproject.databinding.MainActivityBinding
import com.myproject.android.androidtestproject.util.Debug
class MainActivity : AppCompatActivity() {
private lateinit var binding: MainActivityBinding
private val TAG = MainActivity::class.java.name
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.main_activity)
binding = MainActivityBinding.inflate(layoutInflater)
val view = binding.root
setContentView(view)
init()
}
我想在xml中直接使用DateUtil.getCurrrentDateAsString()
。
所以我在布局中使用了这个main_activity.xml
android:text='@{DateUtil.getCurrrentDateAsString()}'
此处布局:
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools">
<data>
<import type="com.myproject.android.androidtestproject.util.DateUtil" />
</data>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="@+id/appNameTextView"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_margin="@dimen/default_margin"
android:gravity="center"
android:textSize="18sp"
app:layout_constraintBottom_toTopOf="@+id/loadListButton"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/currentDateTextView"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:gravity="center"
android:text='@{DateUtil.getCurrrentDateAsString()}'
app:layout_constraintBottom_toTopOf="@+id/loadListButton"
app:layout_constraintEnd_toEndOf="@+id/appNameTextView"
app:layout_constraintStart_toStartOf="@+id/appNameTextView"
app:layout_constraintTop_toBottomOf="@+id/appNameTextView" />
<Button
android:id="@+id/loadListButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/default_margin"
android:layout_marginBottom="@dimen/default_margin"
android:text="@string/load_list"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="@+id/appNameTextView"
app:layout_constraintStart_toStartOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>
这里 DateUtil.kt :
import java.text.SimpleDateFormat
import java.util.*
class DateUtil {
companion object {
const val DEFAULT_DATE_FORMAT = "dd.MM.yyyy"
const val ISO_DATE_FORMAT = "yyyy-MM-dd"
@JvmStatic
fun getCurrrentDateAsString(pattern: String = DEFAULT_DATE_FORMAT): String {
val currentDate = getCurrentDate()
val currentDateAsString = getDateAsString(currentDate, pattern)
return currentDateAsString
}
fun getCurrentDate(): Date {
return Date()
}
// if pattern is null then will be use defaultDTCDateFormat
fun getDateAsString(date: Date?, pattern: String = DEFAULT_DATE_FORMAT): String {
if (date == null) {
return ""
}
var sdf: SimpleDateFormat? = null
return try {
sdf = SimpleDateFormat(pattern)
sdf.format(date)
} catch (ex: IllegalArgumentException) {
sdf = SimpleDateFormat(pattern)
sdf.format(date)
}
}
}
}
但是当我尝试构建时出现错误:
> Task :app:validateSigningDebug UP-TO-DATE
> Task :app:kaptDebugKotlin FAILED
AndroidTestProject/android/AndroidTestProject/app/build/generated/source/kapt/debug/com/myproject/android/androidtestproject/DataBinderMapperImpl.java:9: error: cannot find symbol
import com.gmail.alexei28.android.androidtestproject.databinding.MainActivityBindingImpl;
^
symbol: class MainActivityBindingImpl
location: package com.gmail.alexei28.android.androidtestproject.databinding
FAILURE: Build failed with an exception.
* What went wrong:
Execution failed for task ':app:kaptDebugKotlin'.
> A failure occurred while executing org.jetbrains.kotlin.gradle.internal.KaptExecution
> java.lang.reflect.InvocationTargetException (no error message)
* Try:
Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output. Run with --scan to get full insights.
* Get more help at https://help.gradle.org
BUILD FAILED in 10s
我想,你的问题出现是因为你调用的方法有参数("pattern"),你没有把它放在你的xml.
中
尽管它有默认值,但 DataBinding 无法解决这个问题。
也许有更优雅的决定,但你可以试试这些:
将您的 xml 代码更改为:
android:text=@{DateUtil.getCurrrentDateAsString(DateUtil. DEFAULT_DATE_FORMAT)}'
添加一些 DataBinding adapter 以从代码中调用您的方法
Android Studio 3.6
在build.gradle中:
apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
apply plugin: 'kotlin-android-extensions'
apply plugin: 'kotlin-kapt'
android {
viewBinding {
enabled = true
}
dataBinding {
enabled = true
}
主要活动:
import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import com.myproject.android.androidtestproject.BuildConfig
import com.myproject.android.androidtestproject.R
import com.myproject.android.androidtestproject.databinding.MainActivityBinding
import com.myproject.android.androidtestproject.util.Debug
class MainActivity : AppCompatActivity() {
private lateinit var binding: MainActivityBinding
private val TAG = MainActivity::class.java.name
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.main_activity)
binding = MainActivityBinding.inflate(layoutInflater)
val view = binding.root
setContentView(view)
init()
}
我想在xml中直接使用DateUtil.getCurrrentDateAsString()
。
所以我在布局中使用了这个main_activity.xml
android:text='@{DateUtil.getCurrrentDateAsString()}'
此处布局:
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools">
<data>
<import type="com.myproject.android.androidtestproject.util.DateUtil" />
</data>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="@+id/appNameTextView"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_margin="@dimen/default_margin"
android:gravity="center"
android:textSize="18sp"
app:layout_constraintBottom_toTopOf="@+id/loadListButton"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/currentDateTextView"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:gravity="center"
android:text='@{DateUtil.getCurrrentDateAsString()}'
app:layout_constraintBottom_toTopOf="@+id/loadListButton"
app:layout_constraintEnd_toEndOf="@+id/appNameTextView"
app:layout_constraintStart_toStartOf="@+id/appNameTextView"
app:layout_constraintTop_toBottomOf="@+id/appNameTextView" />
<Button
android:id="@+id/loadListButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/default_margin"
android:layout_marginBottom="@dimen/default_margin"
android:text="@string/load_list"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="@+id/appNameTextView"
app:layout_constraintStart_toStartOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>
这里 DateUtil.kt :
import java.text.SimpleDateFormat
import java.util.*
class DateUtil {
companion object {
const val DEFAULT_DATE_FORMAT = "dd.MM.yyyy"
const val ISO_DATE_FORMAT = "yyyy-MM-dd"
@JvmStatic
fun getCurrrentDateAsString(pattern: String = DEFAULT_DATE_FORMAT): String {
val currentDate = getCurrentDate()
val currentDateAsString = getDateAsString(currentDate, pattern)
return currentDateAsString
}
fun getCurrentDate(): Date {
return Date()
}
// if pattern is null then will be use defaultDTCDateFormat
fun getDateAsString(date: Date?, pattern: String = DEFAULT_DATE_FORMAT): String {
if (date == null) {
return ""
}
var sdf: SimpleDateFormat? = null
return try {
sdf = SimpleDateFormat(pattern)
sdf.format(date)
} catch (ex: IllegalArgumentException) {
sdf = SimpleDateFormat(pattern)
sdf.format(date)
}
}
}
}
但是当我尝试构建时出现错误:
> Task :app:validateSigningDebug UP-TO-DATE
> Task :app:kaptDebugKotlin FAILED
AndroidTestProject/android/AndroidTestProject/app/build/generated/source/kapt/debug/com/myproject/android/androidtestproject/DataBinderMapperImpl.java:9: error: cannot find symbol
import com.gmail.alexei28.android.androidtestproject.databinding.MainActivityBindingImpl;
^
symbol: class MainActivityBindingImpl
location: package com.gmail.alexei28.android.androidtestproject.databinding
FAILURE: Build failed with an exception.
* What went wrong:
Execution failed for task ':app:kaptDebugKotlin'.
> A failure occurred while executing org.jetbrains.kotlin.gradle.internal.KaptExecution
> java.lang.reflect.InvocationTargetException (no error message)
* Try:
Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output. Run with --scan to get full insights.
* Get more help at https://help.gradle.org
BUILD FAILED in 10s
我想,你的问题出现是因为你调用的方法有参数("pattern"),你没有把它放在你的xml.
中尽管它有默认值,但 DataBinding 无法解决这个问题。
也许有更优雅的决定,但你可以试试这些:
将您的 xml 代码更改为:
android:text=@{DateUtil.getCurrrentDateAsString(DateUtil. DEFAULT_DATE_FORMAT)}'
添加一些 DataBinding adapter 以从代码中调用您的方法