在导航中使用 TypeSafe 将多个参数传递给片段

Asg*_*med 3 android android-navigation android-architecture-components android-jetpack

我知道可以在源片段中使用 Action 传递单个参数

  override fun onClick(v: View) {
       val amountTv: EditText = view!!.findViewById(R.id.editTextAmount)
       val amount = amountTv.text.toString().toInt()
       val action = SpecifyAmountFragmentDirections.confirmationAction(amount)
       v.findNavController().navigate(action)

}
Run Code Online (Sandbox Code Playgroud)

并按照 android 文档中指定的方式在目标片段中获取它

    val args: ConfirmationFragmentArgs by navArgs()
        override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
            val tv: TextView = view.findViewById(R.id.textViewAmount)
            val amount = args.amount
            tv.text = amount.toString()
}
Run Code Online (Sandbox Code Playgroud)

请让我知道是否有任何方法可以以 TypeSafe 方式传递多个参数

Squ*_*uti 9

action是的,您可以通过在导航图中为片段定义多个参数,然后将它们传递到代码中来实现。这是一个例子:

导航.xml

<?xml version="1.0" encoding="utf-8"?>
<navigation 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"
    android:id="@+id/navigation"
    app:startDestination="@id/firstFragment">
    <fragment
        android:id="@+id/firstFragment"
        android:name="com.example.app.FirstFragment"
        android:label="FirstFragment"
        tools:layout="@layout/fragment_first">
        <action
            android:id="@+id/action_firstFragment_to_secondFragment"
            app:destination="@id/secondFragment"
            app:enterAnim="@anim/slide_in_right"
            app:popExitAnim="@anim/slide_out_left" />
    </fragment>
    <fragment
        android:id="@+id/secondFragment"
        android:name="com.example.app.SecondFragment"
        android:label="secondFragment"
        tools:layout="@layout/fragment_second">
        <argument
            android:name="firstDataList"
            app:argType="com.example.app.domain.FirstData[]" />
        <argument
            android:name="secondDataList"
            app:argType="com.example.app.domain.SecondData[]" />

        <argument
            android:name="isOkey"
            app:argType="boolean" />
        <argument
            android:name="myString"
            app:argType="string" />
    </fragment>


</navigation>
Run Code Online (Sandbox Code Playgroud)

然后在你的代码中:

您应该分别传递参数,因为它是 navigation.xml

第一个片段.kt

findNavController().navigate(
    FirstFragmentDirections.actionFirstFragmentToSecondFragment(
        firstDataList.toTypedArray(),
        secondDataList.toTypedArray(),
        isOkey,
        myString
    )
Run Code Online (Sandbox Code Playgroud)

然后在目的地检索它,如下所示bundle

第二个片段.kt

val args = arguments?.let {
    SecondFragmentArgs.fromBundle(
        it
    )
}
if (args != null) {
    firstDataList = args.firstDataList.toCollection(ArrayList())
    secondDataList = args.secondDataList.toCollection(ArrayList())
    isOkey = args.isOkey
    myString = args.myString

}
Run Code Online (Sandbox Code Playgroud)

要传递复杂的对象,您应该创建它们parcelable。在我的示例中,我传递了两个复杂模型列表,我将它们分割如下:

数据模型.kt

@Parcelize
data class FirstData(var id: Int, var color: Int = 0) : Parcelable

@Parcelize
data class SecondData(var name: String, var position: ArrayList<Int>) : Parcelable
Run Code Online (Sandbox Code Playgroud)