Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
Jetpack Composeで 様々な画面サイズに対応する/With Jetpack Com...
Search
Sponsored
·
SiteGround - Reliable hosting with speed, security, and support you can count on.
→
t_takahiro
January 23, 2024
Programming
0
1.8k
Jetpack Composeで 様々な画面サイズに対応する/With Jetpack Compose Adapt to various screen sizes
2024/1/23開催 ZOZO Tech Meetup Androidの発表資料です。
t_takahiro
January 23, 2024
Tweet
Share
Other Decks in Programming
See All in Programming
Amazon Bedrockを活用したRAGの品質管理パイプライン構築
tosuri13
5
790
AI & Enginnering
codelynx
0
120
ぼくの開発環境2026
yuzneri
0
240
MUSUBIXとは
nahisaho
0
140
AI時代の認知負荷との向き合い方
optfit
0
160
AI によるインシデント初動調査の自動化を行う AI インシデントコマンダーを作った話
azukiazusa1
1
750
AI巻き込み型コードレビューのススメ
nealle
2
1.2k
AIエージェント、”どう作るか”で差は出るか? / AI Agents: Does the "How" Make a Difference?
rkaga
4
2k
Unicodeどうしてる? PHPから見たUnicode対応と他言語での対応についてのお伺い
youkidearitai
PRO
1
2.6k
フロントエンド開発の勘所 -複数事業を経験して見えた判断軸の違い-
heimusu
7
2.8k
CSC307 Lecture 09
javiergs
PRO
1
840
React Native × React Router v7 API通信の共通化で考えるべきこと
suguruooki
0
100
Featured
See All Featured
KATA
mclloyd
PRO
34
15k
Designing for humans not robots
tammielis
254
26k
個人開発の失敗を避けるイケてる考え方 / tips for indie hackers
panda_program
122
21k
We Are The Robots
honzajavorek
0
170
Organizational Design Perspectives: An Ontology of Organizational Design Elements
kimpetersen
PRO
1
470
Navigating the moral maze — ethical principles for Al-driven product design
skipperchong
2
250
How to Create Impact in a Changing Tech Landscape [PerfNow 2023]
tammyeverts
55
3.2k
Prompt Engineering for Job Search
mfonobong
0
160
Raft: Consensus for Rubyists
vanstee
141
7.3k
So, you think you're a good person
axbom
PRO
2
1.9k
Become a Pro
speakerdeck
PRO
31
5.8k
The Art of Delivering Value - GDevCon NA Keynote
reverentgeek
16
1.8k
Transcript
Jetpack Composeで 様々な画面サイズに対応する 株式会社ZOZO ブランドソリューション開発本部 FAANS部 フロントエンドブロック 田中 崇裕
Copyright © ZOZO, Inc. 1
© ZOZO, Inc. 株式会社ZOZO ブランドソリューション開発本部 FAANS部 フロントエンドブロック 田中 崇裕 •
2023年10月中途入社 • 3年日記をもう少しで書き終えます 2
© ZOZO, Inc. 3 目次 1. 様々な画面サイズに対応することについて 2. WindowSizeClassを用いた実装 3.
その他の手法 4. まとめ
© ZOZO, Inc. 4 1 様々な画面サイズに対応することについて 実情 • なかなか優先度が高くない •
色々な形や大きさの端末があって気にしていたらキリがない
© ZOZO, Inc. 5 1 様々な画面サイズに対応することについて 実情 • なかなか優先度が高くない •
色々な形や大きさの端末があって気にしていたらキリがない しかし • Androidプラットフォームは様々な端末にアプローチしやすい • 市場にモバイル以外の端末が増えてきている
© ZOZO, Inc. 6 1 様々な画面サイズに対応することについて 実情 • なかなか優先度が高くない •
色々な形や大きさの端末があって気にしていたらキリがない しかし • Androidプラットフォームは様々な端末にアプローチしやすい • 市場にモバイル以外の端末が増えてきている 対応することについて • UX向上に少なからず繋がるはず • いま対応するかはさておき、いずれ対応が必要になった時に心理的ハードルが低く なっていることが大事
© ZOZO, Inc. 7 2 WindowSizeClassを用いた実装 2-1 対応する画面サイズの定義 2-2 事前準備
2-3 実装例 (ナビゲーション、ペイン)
© ZOZO, Inc. 8 2-1 対応する画面サイズの定義 マテリアルデザインで分類されている3つのサイズに対して対応する (heightにも同じ定義があるが今回はwidthを使用) https://codelabs.developers.google.com/jetpack-compose-adaptability?hl=en#2
© ZOZO, Inc. 9 2-1 対応する画面サイズの定義 マテリアルデザインで分類されている3つのサイズに対して対応する (heightにも同じ定義があるが今回はwidthを使用) →WindowSizeClassを用いれば簡単に分岐が可能 https://codelabs.developers.google.com/jetpack-compose-adaptability?hl=en#2
© ZOZO, Inc. 10 2-2 事前準備 依存関係を追加 dependencies { implementation
"androidx.compose.material3:material3-window-size-class:1.1.0" }
© ZOZO, Inc. 11 2-2 事前準備 端末の横幅を取得する @OptIn(ExperimentalMaterial3WindowSizeClassApi::class) override fun
onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContent { ReplyTheme { val windowSize = calculateWindowSizeClass(this) ReplyApp(windowSize.widthSizeClass) } } }
© ZOZO, Inc. 12 2-2 事前準備(補足) @Previewで別々の端末サイズを指定可能 @Preview(showBackground = true,
widthDp = 700) @Composable fun ReplyAppPreviewTablet() { ReplyTheme { ReplyApp( replyHomeUIState = ReplyHomeUIState(,,,), windowSize = WindowWidthSizeClass.Medium ) } }
© ZOZO, Inc. 13 2-2 事前準備(補足) AndroidStudio>Tools>DeviceManager>CreateDvices>Resizable(Experimental)をAPI33で作成
© ZOZO, Inc. 14 2-3 実装例 端末サイズによって以下の出し分けを実施する • ナビゲーション •
ペイン
© ZOZO, Inc. 15 2-3 実装例(ナビゲーション) ナビゲーションの種類 • Bottom Navigation
• Navigation Rail • NavigationDrawer ◦ Modal Navigation Drawer ◦ Permanent Navigation Drawer
© ZOZO, Inc. 16 2-3 実装例(ナビゲーション) ナビゲーションの種類 • Bottom Navigation
• Navigation Rail • NavigationDrawer ◦ Modal Navigation Drawer ◦ Permanent Navigation Drawer
© ZOZO, Inc. 17 2-3 実装例(ナビゲーション) ナビゲーションの種類 • Bottom Navigation
• Navigation Rail • NavigationDrawer ◦ Modal Navigation Drawer ◦ Permanent Navigation Drawer
© ZOZO, Inc. 18 2-3 実装例(ナビゲーション) ナビゲーションの種類 • Bottom Navigation
• Navigation Rail • NavigationDrawer ◦ Modal Navigation Drawer ◦ Permanent Navigation Drawer enum class ReplyNavigationType { BOTTOM_NAVIGATION, NAVIGATION_RAIL, PERMANENT_NAVIGATION_DRAWER }
© ZOZO, Inc. 19 2-3 実装例(ナビゲーション) @Composable fun ReplyApp( windowSize:
WindowWidthSizeClass, ) { val navigationType = when (windowSize) { WindowWidthSizeClass.Compact -> ReplyNavigationType.BOTTOM_NAVIGATION WindowWidthSizeClass.Medium -> ReplyNavigationType.NAVIGATION_RAIL WindowWidthSizeClass.Expanded -> ReplyNavigationType.PERMANENT_NAVIGATION_DRAWER else -> ReplyNavigationType.BOTTOM_NAVIGATION } ReplyNavigationWrapperUI(navigationType) }
© ZOZO, Inc. 20 2-3 実装例(ナビゲーション) @Composable private fun ReplyNavigationWrapperUI(
navigationType: ReplyNavigationType, ) { if (navigationType == ReplyNavigationType.PERMANENT_NAVIGATION_DRAWER) { PermanentNavigationDrawer( drawerContent = { PermanentDrawerSheet { NavigationDrawerContent() //これは自分で作成 } } ) { ReplyAppContent(navigationType) //さらに子に渡す } }
© ZOZO, Inc. 21 2-3 実装例(ナビゲーション) } else { ModalNavigationDrawer(
drawerContent = { ModalDrawerSheet { NavigationDrawerContent() //これは自分で作成 } }, ) { ReplyAppContent(navigationType) //さらに子に渡す } }
© ZOZO, Inc. 22 2-3 実装例(ナビゲーション) @Composable fun ReplyAppContent( navigationType:
ReplyNavigationType, ) { Row(,,,) { AnimatedVisibility(visible = navigationType == ReplyNavigationType.NAVIGATION_RAIL) { ReplyNavigationRail() //これは自分で作成 } Column(,,,) { ReplyListOnlyContent() AnimatedVisibility(visible = navigationType == ReplyNavigationType.BOTTOM_NAVIGATION) { ReplyBottomNavigationBar() //これは自分で作成 } } } }
© ZOZO, Inc. 23 2-3 実装例(ペイン) ペインとは → 区画のこと 1つ 2つ
© ZOZO, Inc. enum class ReplyContentType { LIST_ONLY, LIST_AND_DETAIL }
24 2-3 実装例(ペイン) ペインとは → 区画のこと LIST_ONLY LIST_AND_DETAIL
© ZOZO, Inc. 25 2-3 実装例(ペイン) @Composable fun ReplyApp( windowSize:
WindowWidthSizeClass, ) { val contentType = when (windowSize) { WindowWidthSizeClass.Compact -> ReplyContentType.LIST_ONLY WindowWidthSizeClass.Medium -> ReplyContentType.LIST_ONLY WindowWidthSizeClass.Expanded -> ReplyContentType.LIST_AND_DETAIL else -> ReplyContentType.LIST_ONLY } ReplyNavigationWrapperUI(contentType) // ReplyContent()に渡すのみ }
© ZOZO, Inc. 26 2-3 実装例(ペイン) @Composable fun ReplyAppContent( contentType:
ReplyContentType, ) { Row(,,,) { Column(,,,) { if (contentType == ReplyContentType.LIST_AND_DETAIL) { ReplyListAndDetailContent() //これは自分で作成 } else { ReplyListOnlyContent() //これは自分で作成 } } } }
© ZOZO, Inc. 27 3 その他の手法 3-1 ListDetailPaneScaffold 3-2 NavigationSuiteScaffold
※どちらもalpha版 https://medium.com/androiddevelopers/new-apis-for-adaptive-layouts-in-jetpack-compose-f27cace48bcd
© ZOZO, Inc. 28 3-1 ListDetailPaneScaffold ListDetailPaneScaffold( ,,, listPane =
{ MyList(,,,) }, detailPane = { MyDetails(,,,) }, ) https://medium.com/androiddevelopers/new-apis-for-adaptive-layouts-in-jetpack-compose-f27cace48bcd implementation "androidx.compose.material3:material3-adaptive-android:1.0.0-alpha01"
© ZOZO, Inc. 29 3-2 NavigationSuiteScaffold NavigationSuiteScaffold( navigationSuiteItems = {
navItems.forEachIndexed {,,, -> item( icon = {,,,}, label = {,,,}, selected = ,,,, onClick = {,,,} ) } } ) { // Screen content. Text(,,,) } https://medium.com/androiddevelopers/new-apis-for-adaptive-layouts-in-jetpack-compose-f27cace48bcd implementation "androidx.compose.material3:material3-adaptive-navigation-suite-android:1.0.0-alpha01"
© ZOZO, Inc. 30 4 まとめ • 様々な画面サイズに対応する場合、対応する形を最初に決める • 画面サイズ対応する際はWindowSizeClassのコールバックを活用する
• 取得したサイズごとにナビゲーションやペインを出し分けることで対応 • 今後、より実装しやすくなることに期待
None