룬아님의 취중코딩

Android Navigation component 안전하게 데이터 넘기기 본문

개발/안드로이드 개발

Android Navigation component 안전하게 데이터 넘기기

룬아님 2019. 11. 11. 15:47

2019/11/08 - [개발/안드로이드 개발] - Android Navigation component 사용해보기

 

Android Navigation component 사용해보기

https://youtu.be/Y0Cs2MQxyIs #안드로이드 스튜디오에서 Navigation을 활용하기 위해서는 안드로이드 스튜디오 버전이 3.3혹은 그 이상이여야 합니다. 1. build.gradle 추가 dependencies { def nav_version = "2..

myung6024.tistory.com

 

1. 프로젝트 build.gradle에 classpath 추가

classpath "androidx.navigation:navigation-safe-args-gradle-plugin:$navigationVersion"

 

2. app build.gradle에 plugin 추가

apply plugin: "androidx.navigation.safeargs.kotlin"

 

3. nav_graph에 argument 선언

<fragment
    android:id="@+id/detail_screen"
    android:name="com.runeanim.mytoyproject.ui.detail.DetailFragment"
    android:label="Detail screen"
    tools:layout="@layout/detail_fragment">
    <argument
        android:name="repoUrl"
        app:argType="string" />
    <argument
        android:name="userName"
        app:argType="string" />
</fragment>

argument는 보내는 곳이 아닌 받는 쪽에 선언을 합니다.
argument는 nullable을 통해 null이 가능한지 아닌지를 명확하게 해주어야 하며 default는 false입니다.

 

4. 화면 이동하기

위의 plugin을 사용하면 databinding을 쓸 때 처럼 Generated classes가 만들어 집니다.
그렇기 때문에 기존에 사용하던 방법을 그대로 사용할 수 없고 새롭게 구현해주어야합니다.

fun moveScreenToSearchFragment() {
	//Navigation.findNavController(viewDataBinding.root)
	//    .navigate(R.id.action_main_screen_to_search_screen)

    MainFragmentDirections.actionMainScreenToSearchScreen()
        .also { findNavController().navigate(it) }
        
    //같은 코드
    val action = MainFragmentDirections.actionMainScreenToSearchScreen()
    findNavController().navigate(action)
}

각 fragment 별로 (Fragment 명)Directions class가 만들어 지고 거기에 (action id)로 함수가 만들어 집니다 (global action 같은 경우에는 모든 class에 만들어집니다).

findNavController는 plugin 적용 이후 만들어진 extension입니다.

fun Fragment.findNavController(): NavController =
        NavHostFragment.findNavController(this)

 

5. 데이터 넣고 화면 이동하기

private fun moveScreenToDetailFragment(repositoryEntity: RepositoryEntity) {
    with(repositoryEntity) {
        MainFragmentDirections.actionGlobalDetailScreen(
            fullName,
            ownerName
        ).also { findNavController().navigate(it) }
    }
}

만약 해당 스크린에 argument가 선언되어 있다면 action에 argument를 넣도록 구현해야합니다.
타입과 갯수는 nav_graph에서 선언한 것을 따라야 하기 때문에 타입 오류나 예외 상황을 고려하지 않고 안전하게 데이터를 보낼 수 있습니다.

 

6. 데이터 받기

private val args: DetailFragmentArgs by navArgs()

override fun onActivityCreated(savedInstanceState: Bundle?) {
    super.onActivityCreated(savedInstanceState)
    getUserAndRepositoryInfo(
        args.repoUrl,
        args.userName
    )
}

데이터를 받은 쪽에서는 (Fragment 명)Args 타입으로 받아올 수 있으며 nav_fragment에서 정해둔 name으로 사용할 수 있습니다.
nullable을 false로 하였기 때문에 nullCheck도 필요없이 바로 사용할 수 있습니다.

 

 

반응형
Comments