[Android] Jetpack Compose - 1. Compose 기본사항 (1)

문승연·2023년 8월 28일
0

이 포스트는 Android 공식 홈페이지의 Jetpack Compose 튜토리얼 을 기반으로 작성되었습니다.

이번 포스트에서는 Jetpack Compose를 공부한 기록을 남겨보기로 했다.

튜토리얼이 꽤 길고 그만큼 Compose에 대한 내용도 많기 때문에 시리즈로 포스트가 구성될 것 같다.

Jetpack Compose란?

Jetpack Compose네이티브 Android UI를 빌드하기 위한 최신 도구 키트이다.

기존의 xml 기반 레이아웃 작성 방식과 다르게 Jetpack Compose를 사용하면 더 적은 코드, 강력한 도구, 직관적인 Kotlin API로 안드로이드에서 UI 개발을 간소화하고 가속화할 수 있습니다.

이번 포스트에서는 선언형 함수를 사용하여 간단한 UI 구성요소를 빌드해보도록 한다.

1. Composable Functions

Jetpack ComposeComposable 함수를 중심으로 빌드되어있다. Composable 함수를 사용하여 Programmatic 하게 앱의 UI를 정의할 수 있다.

Composable 함수를 만들기 위해서는 함수 이름에 @Composable 주석을 추가하기만 하면 된다.

Text 요소 추가 (기존 Composable 함수 활용)

Android 스튜디오 최신버전에서 새 프로젝트를 생성하면 아래처럼 처음 MainActivity 가 생성된다.

해당 프로젝트를 빌드 후 실행하면 빈 화면에 "Hello world!" 라는 텍스트가 표시된다.

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            Text("Hello world!")
        }
    }
}

setContent 블록은 Composable 함수가 호출되는 활동의 레이아웃을 정의한다.

이 때 Composable 함수는 다른 Composable 함수에서만 호출할 수 있다.

위 화면처럼 텍스트를 표시하려면 Composable 함수인 Text 함수를 호출하면 된다.

Composable 함수 정의

Text 함수처럼 기존에 구성되어 있는 Composable 함수가 아닌 새로 구현한 함수를 Composable로 정의하려면 @Composable 주석을 추가하면 된다.

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            MessageCard("Android")
        }
    }
}

@Composable
fun MessageCard(name: String) {
    Text(text = "Hello $name!")
}

MessageCard 함수를 정의하고 @Composable 주석을 추가한다. 이러면 MessageCard 함수가 Composable 함수가 된다.

추가로 @Preview 주석을 사용하면 앱을 빌드해서 실행해보지 않아도 안드로이드 스튜디오 내에서 미리볼 수 있다. 단, @Preview 주석은 매개변수를 사용하지 않는 함수에 사용해야한다.

@Composable
fun MessageCard(name: String) {
    Text(text = "Hello $name!")
}

@Preview
@Composable
fun PreviewMessageCard() {
    MessageCard("Android")
}

2. 레이아웃

Message 객체에 작성자 이름, 메시지 내용을 표시하여 일반 String 보다 더욱 복잡하게 만든다.

MessageCard 함수에 매개변수로 Message 객체를 허용하도록 하고 MessageCard Composable 함수 내에 Text 함수들을 추가한다.

여러 텍스트 추가

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            MessageCard(Message("Android", "Jetpack Compose"))
        }
    }
}

data class Message(val author: String, val body: String)

@Composable
fun MessageCard(msg: Message) {
    Text(text = msg.author)
    Text(text = msg.body)
}

@Preview
@Composable
fun PreviewMessageCard() {
    MessageCard(
        msg = Message("Colleague", "Hey, take a look at Jetpack Compose, it's great!")
    )
}

그러나 위치 정렬 방식에 대한 지정을 해주지 않았기 때문에 동일한 위치에 2개의 텍스트가 표시된다.

열(Column) 사용

Column 함수를 사용하면 요소를 수직으로 정렬할 수 있다.

@Composable
fun MessageCard(msg: Message) {
    Column {
        Text(text = msg.author)
        Text(text = msg.body)
    }
}

반대로 Row 함수를 사용하면 요소들을 수평으로 정렬할 수 있고 Box 를 사용하면 요소를 쌓을 수 있다.

이미지 추가

발신자의 프로필 사진을 추가하여 MessageCard 를 보한다.

이미지를 추가할때는 Image 함수를 추가하면 된다.

@Composable
fun MessageCard(msg: Message) {
    Row {
        Image(
            painter = painterResource(R.drawable.profile_picture),
            contentDescription = "Contact profile picture",
        )
    
       Column {
            Text(text = msg.author)
            Text(text = msg.body)
        }
  
    }
  
}

레이아웃 구성 및 수정

모든 구성 요소가 레이아웃에 배치되었지만 각 요소별 크기가 적절하지 않고 간격이 균등하지 않은 등 문제가 많다.

이런 부분을 해결하기 위해 Compose는 modifier 를 사용한다.

modifier를 이용해 컴포저블 요소의 크기, 레이아웃, 모양 등을 변경하거나 클릭 가능하게 만드는 등 상호작용을 추가할 수 있다.

@Composable
fun MessageCard(msg: Message) {
    // Add padding around our message
    Row(modifier = Modifier.padding(all = 8.dp)) {
        Image(
            painter = painterResource(R.drawable.profile_picture),
            contentDescription = "Contact profile picture",
            modifier = Modifier
                // Set image size to 40 dp
                .size(40.dp)
                // Clip image to be shaped as a circle
                .clip(CircleShape)
        )

        // Add a horizontal space between the image and the column
        Spacer(modifier = Modifier.width(8.dp))

        Column {
            Text(text = msg.author)
            // Add a vertical space between the author and message texts
            Spacer(modifier = Modifier.height(4.dp))
            Text(text = msg.body)
        }
    }
}

profile
"비몽(Bemong)"이라는 앱을 개발 및 운영 중인 안드로이드 개발자입니다.

0개의 댓글