นำทางไปยังจุดหมาย

คอมโพเนนต์การนำทางมีวิธีที่ตรงไปตรงมาและทั่วไปในการนำทางไปยังปลายทาง อินเทอร์เฟซนี้รองรับบริบทและเฟรมเวิร์ก UI ที่หลากหลาย เช่น คุณสามารถใช้คอมโพเนนต์การนำทางกับ Compose, View, Fragment, Activity และแม้แต่เฟรมเวิร์ก UI ที่กำหนดเอง

คู่มือนี้อธิบายวิธีใช้คอมโพเนนต์การนำทางเพื่อนำทางไปยังปลายทางในบริบทต่างๆ

ใช้ NavController

ประเภทคีย์ที่คุณใช้เพื่อย้ายไปมาระหว่างปลายทางคือ NavController ดูข้อมูลเพิ่มเติมเกี่ยวกับคลาสและวิธีสร้างอินสแตนซ์ของคลาสนี้ได้ที่ สร้างตัวควบคุมการนำทาง คู่มือนี้จะอธิบายรายละเอียดเกี่ยวกับวิธีใช้

ไม่ว่าคุณจะใช้เฟรมเวิร์ก UI ใดก็ตาม คุณสามารถใช้ฟังก์ชันเดียวเพื่อนำทางไปยังปลายทางได้ นั่นคือ NavController.navigate()

navigate() มีการโอเวอร์โหลดหลายรายการ การโอเวอร์โหลดที่คุณควรเลือกจะสอดคล้องกับบริบทที่แน่นอนของคุณ เช่น คุณควรใช้การโอเวอร์โหลดรายการหนึ่งเมื่อนำทางไปยัง Composable และอีกรายการหนึ่งเมื่อนำทางไปยัง View

ส่วนต่อไปนี้จะสรุปการโอเวอร์โหลด navigate() ที่สำคัญบางรายการที่คุณใช้ได้

นำทางไปยัง Composable

หากต้องการนำทางไปยัง Composable คุณควรใช้ NavController.navigate<T> การโอเวอร์โหลดนี้ navigate() จะรับอาร์กิวเมนต์ route รายการเดียวซึ่งคุณส่งประเภท โดยอาร์กิวเมนต์นี้จะทำหน้าที่เป็นคีย์ไปยังปลายทาง

@Serializable
object FriendsList

navController.navigate(route = FriendsList)

หากต้องการนำทางไปยัง Composable ในกราฟการนำทาง ให้กำหนด NavGraph ก่อนเพื่อให้ปลายทางแต่ละรายการสอดคล้องกับประเภท สำหรับ Composable คุณสามารถทำได้โดยใช้ฟังก์ชัน composable()

แสดงเหตุการณ์จาก Composable

เมื่อฟังก์ชันที่ประกอบกันได้ต้องนำทางไปยังหน้าจอใหม่ คุณไม่ควรส่งข้อมูลอ้างอิงไปยัง NavController เพื่อให้ฟังก์ชันดังกล่าวเรียก navigate() ได้โดยตรง ตามหลักการของ Unidirectional Data Flow (UDF) Composable ควรแสดงเหตุการณ์ที่ NavController จัดการแทน

กล่าวอีกนัยหนึ่งคือ Composable ควรมีพารามิเตอร์ประเภท () -> Unit เมื่อเพิ่มปลายทางลงใน NavHost ด้วยฟังก์ชัน composable() ให้ส่งการเรียก NavController.navigate() ไปยัง Composable

ดูตัวอย่างได้ในส่วนย่อยต่อไปนี้

ตัวอย่าง

เพื่อแสดงให้เห็นถึงส่วนก่อนหน้า โปรดสังเกตจุดต่อไปนี้ในข้อมูลโค้ดต่อไปนี้

  1. ระบบจะสร้างปลายทางแต่ละรายการในกราฟโดยใช้เส้นทาง ซึ่งเป็นออบเจ็กต์หรือคลาสที่ซีเรียลไลซ์ได้ซึ่งอธิบายข้อมูลที่ปลายทางนั้นๆ ต้องการ
  2. Composable MyAppNavHost มีอินสแตนซ์ NavController
  3. ดังนั้น การเรียก navigate() ควรเกิดขึ้นที่นั่น ไม่ใช่ใน Composable ระดับล่าง เช่น ProfileScreen
  4. ProfileScreen มีปุ่มที่นำทางผู้ใช้ไปยัง FriendsList เมื่อคลิก อย่างไรก็ตาม ปุ่มนี้ไม่ได้เรียก navigate() ด้วยตัวเอง
  5. แต่ปุ่มจะเรียกฟังก์ชันที่แสดงเป็นพารามิเตอร์ onNavigateToFriends
  6. เมื่อ MyAppNavHost เพิ่ม ProfileScreen ลงในกราฟการนำทาง สำหรับ onNavigateToFriends ระบบจะส่ง Lambda ที่เรียก navigate(route = FriendsList)
  7. ซึ่งจะช่วยให้มั่นใจได้ว่าเมื่อผู้ใช้กดปุ่ม ProfileScreen ระบบจะนำทางไปยัง FriendsListScreen อย่างถูกต้อง
@Serializable
object Profile
@Serializable
object FriendsList

@Composable
fun MyAppNavHost(
    modifier: Modifier = Modifier,
    navController: NavHostController = rememberNavController(),
) {
    NavHost(
        modifier = modifier,
        navController = navController,
        startDestination = Profile
    ) {
        composable<Profile> {
            ProfileScreen(
                onNavigateToFriends = { navController.navigate(route = FriendsList) },
                /*...*/
            )
        }
        composable<FriendsList> { FriendsListScreen(/*...*/) }
    }
}

@Composable
fun ProfileScreen(
    onNavigateToFriends: () -> Unit,
    /*...*/
) {
    /*...*/
    Button(onClick = onNavigateToFriends) {
        Text(text = "See friends list")
    }
}

นำทางโดยใช้รหัสจำนวนเต็ม

หากต้องการนำทางไปยังปลายทางโดยใช้รหัสจำนวนเต็ม ให้เรียกการ navigate(int) โอเวอร์โหลด โดยการโอเวอร์โหลดนี้จะใช้รหัสทรัพยากรของการดำเนินการหรือปลายทาง ข้อมูลโค้ดต่อไปนี้แสดงวิธีใช้การโอเวอร์โหลดนี้เพื่อนำทางไปยัง ViewTransactionsFragment

Kotlin

viewTransactionsButton.setOnClickListener { view ->
  view.findNavController().navigate(R.id.viewTransactionsAction)
}

Java

viewTransactionsButton.setOnClickListener(new View.OnClickListener() {
  @Override
  public void onClick(View view) {
      Navigation.findNavController(view).navigate(R.id.viewTransactionsAction);
  }
});

เมื่อนำทางโดยใช้รหัส คุณควรใช้ การดำเนินการ เมื่อเป็นไปได้ การดำเนินการจะให้ข้อมูลเพิ่มเติมในกราฟการนำทาง โดยแสดงให้เห็นภาพว่าปลายทางเชื่อมต่อกันอย่างไร

นำทางโดยใช้ NavDeepLinkRequest

หากต้องการนำทางไปยังปลายทาง Deep Link โดยนัย ให้ใช้การโอเวอร์โหลด navigate(NavDeepLinkRequest) ข้อมูลโค้ดต่อไปนี้แสดงการติดตั้งใช้งานเมธอดนี้

Kotlin

val request = NavDeepLinkRequest.Builder
  .fromUri("android-app://androidx.navigation.app/profile".toUri())
  .build()
findNavController().navigate(request)

Java

NavDeepLinkRequest request = NavDeepLinkRequest.Builder
  .fromUri(Uri.parse("android-app://androidx.navigation.app/profile"))
  .build()
NavHostFragment.findNavController(this).navigate(request)

การนำทางโดยใช้รหัสการดำเนินการหรือรหัสปลายทางจะแตกต่างจากการนำทางโดยใช้ Deep Link ตรงที่การนำทางโดยใช้ Deep Link จะนำทางไปยัง Deep Link ใดก็ได้ในกราฟ ไม่ว่าปลายทางจะมองเห็นได้หรือไม่ก็ตาม คุณสามารถนำทางไปยังปลายทางในกราฟปัจจุบันหรือปลายทางในกราฟอื่นโดยสิ้นเชิง

การดำเนินการและประเภท MIME

นอกจาก Uri แล้ว NavDeepLinkRequest ยังรองรับ Deep Link ที่มีการดำเนินการและประเภท MIME ด้วย หากต้องการเพิ่มการดำเนินการลงในคำขอ ให้ใช้ fromAction() หรือ setAction() หากต้องการเพิ่มประเภท MIME ลงในคำขอ ให้ใช้ fromMimeType() หรือ setMimeType()

สำหรับ NavDeepLinkRequest ที่จะตรงกับปลายทาง Implicit Deep Link อย่างถูกต้อง URI การดำเนินการ และประเภท MIME ทั้งหมดจะต้องตรงกับ NavDeepLink ใน ปลายทาง URI ต้องตรงกับรูปแบบ การดำเนินการต้องตรงกันทุกประการ และประเภท MIME ต้องมีความเกี่ยวข้อง เช่น image/jpg ตรงกับ image/\*

บริบทเพิ่มเติม

เอกสารนี้ครอบคลุมวิธีใช้ NavController.navigate() ในกรณีการใช้งานที่พบบ่อยที่สุด อย่างไรก็ตาม ฟังก์ชันนี้มีการโอเวอร์โหลดที่หลากหลายซึ่งคุณสามารถใช้ในบริบทต่างๆ และใช้ร่วมกับเฟรมเวิร์ก UI ใดก็ได้ ดูรายละเอียดเพิ่มเติมเกี่ยวกับการโอเวอร์โหลดเหล่านี้ได้ในเอกสารอ้างอิง

อ่านเพิ่มเติม

ดูข้อมูลเพิ่มเติมได้ที่หน้าต่อไปนี้