목록-세부정보는 한 창은 항목 목록을 표시하고 다른 창은 목록에서 선택한 항목의 세부정보를 표시하는 이중 창 레이아웃으로 구성된 UI 패턴입니다.
이 패턴은 이메일 목록과 각 이메일 메시지의 세부 내용이 있는 이메일 클라이언트와 같이 대규모 컬렉션의 요소에 대한 심층적인 정보를 제공하는 애플리케이션에 특히 유용합니다. 목록-세부정보는 앱 환경설정을 카테고리 목록으로 분할하고 세부정보 창에 각 카테고리의 환경설정이 있는 것과 같이 덜 중요한 경로에도 사용할 수 있습니다.
ListDetailPaneScaffold
로 UI 패턴 구현
ListDetailPaneScaffold
는 앱에서 목록-세부정보 패턴의 구현을 간소화하는 컴포저블입니다. 목록-세부정보 Scaffold는 목록 창, 세부정보 창, 선택적 추가 창 등 최대 세 개의 창으로 구성할 수 있습니다. 스캐폴드는 화면 공간 계산을 처리합니다. 충분한 화면 크기를 사용할 수 있으면 세부정보 창이 목록 창 옆에 표시됩니다. 작은 화면 크기에서 Scaffold는 목록 창 또는 세부정보 창을 전체 화면으로 표시하도록 자동으로 전환됩니다.
종속 항목 선언
ListDetailPaneScaffold
는 Material 3 적응형 레이아웃 라이브러리의 일부입니다.
앱에는 다음과 같은 세 가지 관련 Material 3 라이브러리의 종속 항목이 포함되어야 합니다.
- 적응형 —
HingeInfo
및Posture
와 같은 하위 수준 빌딩 블록 - adaptive-layout —
ListDetailPaneScaffold
및SupportingPaneScaffold
와 같은 적응형 레이아웃입니다.- adaptive-navigation - 창 내부 및 창 간 탐색을 위한 컴포저블
앱 또는 모듈의 build.gradle
파일에 종속 항목을 추가합니다.
Kotlin
implementation("androidx.compose.material3.adaptive:adaptive:1.0.0-alpha12") implementation("androidx.compose.material3.adaptive:adaptive-layout:1.0.0-alpha12") implementation("androidx.compose.material3.adaptive:adaptive-navigation:1.0.0-alpha12")
Groovy
implementation 'androidx.compose.material3.adaptive:adaptive:1.0.0-alpha12' implementation 'androidx.compose.material3.adaptive:adaptive-layout:1.0.0-alpha12' implementation 'androidx.compose.material3.adaptive:adaptive-navigation:1.0.0-alpha12'
기본 사용법
다음과 같이 ListDetailPaneScaffold
를 구현합니다.
선택할 콘텐츠를 나타내는 클래스를 사용합니다. 선택된 목록 항목의 저장 및 복원을 지원하려면 이 클래스가
Parcelable
이어야 합니다. kotlin-parcelize 플러그인을 사용하여 코드를 생성하세요.@Parcelize class MyItem(val id: Int) : Parcelable
rememberListDetailPaneScaffoldNavigator
로ThreePaneScaffoldNavigator
를 만들고BackHandler
를 추가합니다. 이 탐색기는 목록 창, 세부정보 창, 추가 창 간에 이동하는 데 사용됩니다. 일반 유형을 선언하면 탐색기가 Scaffold의 상태 (즉,MyItem
가 표시되는 상태)도 추적합니다. 이 유형은 parcelable이므로 탐색기에서 상태를 저장하고 복원하여 구성 변경을 자동으로 처리할 수 있습니다.BackHandler
는 시스템 뒤로 동작 또는 버튼을 사용하여 뒤로 이동하는 기능을 지원합니다.ListDetailPaneScaffold
의 뒤로 버튼의 예상 동작은 창 크기와 현재 Scaffold 값에 따라 다릅니다.ListDetailPaneScaffold
가 현재 상태로 되돌리기를 지원할 수 있다면canNavigateBack()
는true
이며BackHandler
를 사용 설정합니다.val navigator = rememberListDetailPaneScaffoldNavigator<MyItem>() BackHandler(navigator.canNavigateBack()) { navigator.navigateBack() }
scaffoldState
를navigator
에서ListDetailPaneScaffold
컴포저블로 전달합니다.ListDetailPaneScaffold( directive = navigator.scaffoldDirective, value = navigator.scaffoldValue, // ... )
목록 창 구현을
ListDetailPaneScaffold
에 제공합니다. 탐색 중에 기본 창 애니메이션을 적용하려면AnimatedPane
를 사용합니다. 그런 다음ThreePaneScaffoldNavigator
를 사용하여 세부정보 창ListDetailPaneScaffoldRole.Detail
로 이동하고 전달된 항목을 표시합니다.ListDetailPaneScaffold( directive = navigator.scaffoldDirective, value = navigator.scaffoldValue, listPane = { AnimatedPane { MyList( onItemClick = { item -> // Navigate to the detail pane with the passed item navigator.navigateTo(ListDetailPaneScaffoldRole.Detail, item) } ) } }, // ... )
ListDetailPaneScaffold
에 세부정보 창 구현을 포함합니다. 탐색이 완료되면currentDestination
에는 창에 표시된 콘텐츠를 비롯하여 앱이 이동한 창이 포함됩니다.content
속성은 원래 remember 호출(이 예에서는MyItem
)에 지정된 유형이므로 표시해야 하는 모든 데이터의 속성에 액세스할 수도 있습니다.ListDetailPaneScaffold( directive = navigator.scaffoldDirective, value = navigator.scaffoldValue, listPane = // ... detailPane = { AnimatedPane { navigator.currentDestination?.content?.let { MyDetails(it) } } }, )
위 단계를 구현하면 코드가 다음과 비슷하게 표시됩니다.
val navigator = rememberListDetailPaneScaffoldNavigator<MyItem>() BackHandler(navigator.canNavigateBack()) { navigator.navigateBack() } ListDetailPaneScaffold( directive = navigator.scaffoldDirective, value = navigator.scaffoldValue, listPane = { AnimatedPane { MyList( onItemClick = { item -> // Navigate to the detail pane with the passed item navigator.navigateTo(ListDetailPaneScaffoldRole.Detail, item) }, ) } }, detailPane = { AnimatedPane { // Show the detail pane content if selected item is available navigator.currentDestination?.content?.let { MyDetails(it) } } }, )