Android/Jetpack Compose

[Jetpack Compose] LaunchedEffect란?

chattymin 2023. 9. 8. 16:45
728x90
반응형

LaunchedEffect가 뭘까?

코루틴을 사용하기 위한 suspend function을 호출하기 위해 필요하다.

좀 더 쉽게 말하자면 중간에 멈추고자 하는 함수를 넣기 위해서 존재한다.

 

이게 무슨소린가 싶을거다.

이전에 내가 작성한 Delay함수 관련 글이 있다. 이것처럼 도중에 멈추고 싶을때 LaunchedEffect를 사용한다.

https://naemamdaelo.tistory.com/entry/Jetpack-Compose-%08Delay-%EC%A3%BC%EB%8A%94-%EB%B0%A9%EB%B2%95

 

[Jetpack Compose] Delay 주는 방법

개발을 하다보면 특정 초 지난 후 에 기능이 작동하면 좋겠다는 생각을 할 때가 있다. 그러면 Delay를 줘야하는데 어떻게 줄 수 있을까? 두가지 방법이 있다. 1. Handler Handler(Looper.getMainLooper()).postDel

naemamdaelo.tistory.com

@Composable
@NonRestartableComposable
fun LaunchedEffect(key1: Any?, block: suspend CoroutineScope.() -> Unit): Unit

@Composable
@NonRestartableComposable
fun LaunchedEffect(key1: Any?, key2: Any?, block: suspend CoroutineScope.() -> Unit): Unit

@Composable
@NonRestartableComposable
fun LaunchedEffect(key1: Any?, key2: Any?, key3: Any?, block: suspend CoroutineScope.() -> Unit): Unit

@Composable
@NonRestartableComposable
fun LaunchedEffect(vararg keys: Any?, block: suspend CoroutineScope.() -> Unit): Unit

 

 

 

어떻게 쓸까?

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            BlogContentTheme {
                // A surface container using the 'background' color from the theme
                Surface(
                    modifier = Modifier.fillMaxSize(),
                    color = MaterialTheme.colors.background
                ) {
                    LaunchedEffectExample()
                }
            }
        }
    }
}

@Composable
fun LaunchedEffectExample(){
    var text by remember { mutableStateOf("Loading...") }
    var loadData by remember { mutableStateOf(false) }
    var isLaunch by remember { mutableStateOf(false) }
    var cnt by remember { mutableStateOf(0) }


    if (loadData){
        LaunchedEffect(isLaunch) {
            cnt++
            text = loadText(cnt)
        }
    }


    Surface {
        Column(modifier = Modifier.padding(16.dp)) {
            Button(onClick = {
                loadData = true
                text = "Loading..."
                isLaunch = !isLaunch
            }) {
                Text(text = "Load")
            }
            Text(text = text)
        }
    }
}

suspend fun loadText(cnt: Int): String{
    delay(2.seconds)
    return "Load End $cnt"
}

// 좋은코드는 아니니까 참고만 하자. 대충 짰다...

간단한 예시다.

 

LaunchEffect를 통해서 버튼을 클릭하면 서버로부터 정보를 받아오는 과정을 약식으로 표현했다.

 

이 코드를 통해서 LaunchEffect의 특징에 대해서 알 수 있다.

 

 

key값이 변화하면 호출된다.

버튼을 클릭하면 isLaunch변수를 이전 값과 달라지게 설정해뒀다.

그렇기 때문에 버튼을 클릭하면 LaunchEffect의 key값이 변경되고, 실행된다.

 

당연히 boolean값이 아니라 int, string, char 뭐든지 가능하다.

 

 

중복 호출시 이전 호출을 종료시킨다

이 부분은 아래 영상을 보자

버튼을 누를때 마다 아래에 있는 숫자가 하나씩 올라간다.

한번 누르면 2초 후 1이 올라가는 모습을 볼 수 있을 것이다

 

그 후 여러번 동시에 누르니 한번에 숫자가 올라간다.

이것을 보면 알 수 있듯이 LaunchEffect가 호출되면 이전에 호출된 LaunchEffect는 즉시 종료된다.

 

 

만약 코드가 실행되자마자 별도의 트리거 없이 실행되면 좋겠다면?

LaunchedEffect(Unit) {
            // do Something
        }

key를 Unit으로 설정하면 된다.

 

 

만약 key가 여러개라면?

LaunchedEffect(keySt, keyNd, keyRd) {
        // do Something
    }

key가 3개일 경우에는 어떤 상황일때 LaunchEffect가 실행될까?

 

셋다 바뀌어야 실행된다고 생각할 수도 있지만, 셋 중 하나라도 바뀐다면 실행된다.

728x90
반응형