[요약] What's new in Jetpack Compose (Google I/O '21)

[요약] What's new in Jetpack Compose (Google I/O '21)

May 29, 2021. | By: pluulove


Compose는 Android의 최신 네이티브 UI 도구 키트이다

  • 현재 베타버전이며 곧 1.0이 출시된다

  • 처음부터 개발을 빠르게 하도록 설계되었다
  • 훨씬 적은 코드로 UI를 구현할 수 있다

  • View 기반의 기존 Toolkit은 10년 넘게 사용했다
  • 기기 성능도 향상되었고 앱에 대한 기대감도 커졌다
  • UI는 훨씬 동적이고 다양하게 표현한다
  • 기존 Views로도 개발할 수 있지만, 최신 아키텍처를 기반으로 하며 Kotlin을 활용하는 최신 도구 키트 요청이 많았다

  • 구글 또한 기능 및 개선 사항을 빠르게 적용하길 원한다
  • 선언적 독립형 도쿠 키트인 Jetpack Compose를 3년 전부터 개발하기 시작했다

Declarative UI Toolkit

Compose의 2가지 개념

Declarative

  • 요즘 앱은 데이터가 동적이며 실시간으로 업데이트된다

  • 기존 Android Views를 사용하면 XML에 UI를 선언해야 한다
  • 데이터 변경 시 UI도 업데이트를 위해 속성을 설정해야 한다
    • 앱의 상태(DB, 네트워크 호출이 로드)가 바뀔 때마다 새로운 정보로 UI를 업데이트해서 데이터를 동기화해야 한다
    • View마다 상태가 다르며 각각 업데이트해야 하므로 과정이 복잡해진다

  • Compose와 같은 선언적 UI는 상태를 UI로 변환하는 방식이다
  • UI는 변경 불가능하며 한번 생성하면 업데이트가 불가능하다. 앱 상태가 바뀌면 새로운 상태를 새로운 표현으로 변환한다.
  • 새로운 표현 적용 시 UI 전체를 다시 생성하지만, Compose는 변경되지 않은 요소에 대한 작업은 건너뛴다
    • 개념적으로 특정 상태에 맞춰 UI를 다시 생성하는 것과 같다

  • Compose에서 UI 구성요소는 Composable 주석이 달린 함수일 뿐이다
  • UI 구성요소를 빠르고 쉽게 만들 수 있다
  • 재사용 가능한 요소로 구성된 라이브러리로 UI를 나누는 것이 좋다
  • Composable 함수는 값 반환 대신 UI를 전달한다
  • 예제는 텍스트를 수직으로 배열하고 텍스트 레이블을 표시하며, 메시지가 없는 경우에 “No message” 레이블을 표시할 수도 있다
  • Composable은 데이터를 매개변수로 받아서 UI를 전달하는 방식이다.
  • 상태가 바뀌거나 메시지 목록이 바뀌었을 때 이 함수를 실행하면 새 UI가 생성된다. 이를 Recomposing이라고 한다

  • 메시지 목록은 ViewModel이 message의 LiveData를 노출한다
  • 관찰한 messages 필드를 읽는 Composable은 새 데이터가 입력될 때마다 recomposable 된다
  • Compose Compiler가 어느 Composable이 상태를 읽는지 추적하고 상태 변경 시 자동으로 재실행한다
    • 상태가 변경된 Composable만 다시 실행하고 나머지는 건너뛴다

  • 각 Composable은 Immutable 하므로 Composable을 참조하거나 나중에 쿼리 혹은 내용을 업데이트할 수 없다
  • 정보를 입력할 때는 모두 매개변수로 Composable에 전달해야 한다

모든 메시지를 선택하는 CheckBox를 추가한 예제

  • CheckBox는 미선택된 상태가 기본이다
  • 기존 View와는 달리 CheckBox를 클릭하더라도 시각적인 변화는 없다. 그 이유는 상태를 상수(false)로 전달했기 때문이다

  • CheckBox 선택 여부를 결정하는 로컬 변수를 추가했다
  • CheckBox 클릭 시 onCheckChange의 콜백에서 로컬 상태를 업데이트할 수 있다
  • 코드 작성을 해야만 CheckBox 클릭 시 선택된다는 것이 직관적이지 못하다고 생각할 수 있지만, 그것이 선언적 UI의 핵심 개념이다
  • 요소는 전달되는 매개변수가 완전히 통제한다. 이렇게 단일 진실 공급원(Single source of truth) 을 생성한다 → 동기화해야 할 상태를 없앤다

  • 재실행하거나 Recomposition을 호출하더라도 유지하고 싶은 변수가 있을 경우 remember 함수를 사용하면 이전 실행에서 얻은 값을 기억할 수 있다
  • 값을 재사용함으로써 재할당을 방지하거나 상태를 고정할 수 있다
  • 위 예제는 이벤트 핸들링을 인라인으로 구현

  • state와 업데이트 람다를 Composable의 매개변수로 전달하고 단일 진실 공급원으로 로직을 올릴 수 있다

선언적 UI의 핵심은

  • 특정 상태에서 UI의 형태를 완전히 설명한다
  • 상태가 바뀌면 프레임워크에서 UI 업데이트를 처리한다

  • Compose는 단방향 데이터 흐름을 따르는 아키텍처와 잘 맞는다
  • ViewModel이 화면 상태의 단일 스트림을 노출하면 Compose UI에서 관찰하고 각 구성요소의 매개변수로 전달한다
  • 각 구성요소는 필요한 상태만 수신하므로 데이터를 바꿀 때만 업데이트하면 된다
  • 상태 변경을 ViewModel 한곳에서 처리하는 데 도움이 된다

Declarative UI Toolkit

Jetpack Compose는 Material Design Component와 Theme 시스템을 구현한다

  • 앱을 만드는데 필요한 컴포넌트도 제공한다
  • 모든 컴포넌트는 기본적으로 Material Styling을 따른다

  • Material Theme를 구현하므로 모든 컴포넌트를 커스텀 설정할 수 있다 (Color, Typography, Shapes)

  • 새로운 레이아웃을 제공한다 (가로/세로 LinearLayout과 유사)
  • Views와는 달리 Compose Layout 모델은 여러 개의 measure를 전달할 수 없어서 중첩된 레이아웃에 적합하다

  • Compose DSL을 적용한 ConstraintLayout을 사용하면 복잡한 레이아웃을 표현 가능하다

  • 또한 커스텀 레이아웃도 훨씬 간단하게 구현된다
  • measure / layout을 직접 설정하고 싶으면 함수를 구현하기만 하면 된다

  • 새로운 애니메이션 시스템은 기존보다 효과적이고 간단하게 UI에 모션을 적용할 수 있다
  • Compose에 MotionLayout을 가져오는 작업도 진행하고 있다

  • Compose에서는 테스트와 접근성이 1급 객체이다

  • 테스트 기능을 극대화하는 전용 Test Artifact를 제공하며 Composable을 테스트하는 간단한 API를 제공한다
  • Test Rule에서 clock이 노출된 후, UI가 업데이트되고 이를 제어하기 위한 API가 제공된다
  • 애니메이션 코드를 테스트할 때도 테스트를 완전히 통제할 수 있다

  • Compose는 Kotlin으로만 개발되었다

  • Coroutine을 사용하면 간단하게 비동기 API를 작성할 수 있다
  • 예를 들어 제스처를 애니메이션으로 핸드오프 하는 것처럼 비동기식 이벤트를 결합한 코드를 간단하게 작성할 수 있다

우측 이미지와 같이 Composable을 구현하는 방법

  1. topic Model 객체로 매개변수를 받는 Composable 함수 생성
  2. 이미지와 텍스트가 있는 행으로 구성된 구성 요소를 생성
  3. 배경에 Card Composable로 행을 감싼다
  4. 텍스트 주변 간격을 위해서 padding moodifier 매개변수로 Composable을 정의한다
  5. 이미지 위에 체크 아이콘을 노출하기 위해 Boolean 매개변수를 추가한다

  • 이미지를 Box로 감싼 후 선택한 매개변수에 따라서 아이콘을 추가할 수 있다

  • 선택한 항목의 모서리 또한 선택한 매개변수에 따라서 모서리 Radius를 설정한다

  • 애니메이션으로 바꾸려면 animateAsState 함수로 조건을 사용합니다. 모서리 Radius가 자동으로 애니메이션으로 변환된다

Layout

  • Compose LazyColumn Composable을 제공한다. RecyclerView처럼 뷰포트를 채우는 형태와 비슷하다
  • 객체 목록을 items block으로 전달하고 각 항목을 렌더링에 전달할 수 있다

  • Compose에서 Custom Layout을 사용하면 Topic을 수평으로 한 순차 노출도 가능하다

Theme

  • 우측 이미지 예제 Owl은 Theme에서 배경색을 가져온다
  • 앱이 다크 모드를 지원하도록 쉽게 테마를 설정할 수 있다

  • 시스템이 다크 모드인지 판단한 후 Coloe Scheme를 전달한다
  • Compsoe에서 모든 테마는 런타임에서 실행되므로 기본 테마 외의 동적 테마도 쉽게 지원한다

Compose Sample Repository : goo.gle/compose-sample

Built for interop

Jetpack Compose는 기본 View 시스템과 호환된다

  • Compose를 필요에 따라 점진적으로 도입할 수 있다
  • 필요한 단계별로 진행할 수 있다

  • 또한 Compose에 기존 Views를 호스팅 할 수 있다
  • MapView의 광고처럼 아직 Compose로 대응하지 않은 콘텐츠를 표시할 때 유용하다

  • 다른 주요 라이브러리와의 통합을 제공한다
  • Compose는 기존 애플리케이션 아키텍처와도 호환된다

  • Component와 함께 Preview를 정의할 수 있다

  • 다양한 폼팩터를 지원한다

Compose 학습 자료

  • goo.gle/compose-pathway
  • goo.gle/compose-samples
  • goo.gle/compose-docs
  • goo.gle/compose-slack
  • goo.gle/compose-feedback

comments powered by Disqus

Currnte Pages Tags

Android

About

Pluu, Android Developer Blog Site

이전 블로그 링크 :네이버 블로그

Using Theme : SOLID SOLID Github

Social Links