Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
Jetpack Compose drag gesture and pinch gesture
Search
Moyuru Aizawa
April 21, 2023
Programming
4.4k
1
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
Jetpack Compose drag gesture and pinch gesture
Moyuru Aizawa
April 21, 2023
More Decks by Moyuru Aizawa
See All by Moyuru Aizawa
BLUETOOTH_SCAN and iBeacon
lvla
1
160
graphicsLayer
lvla
0
320
BluetoothDevice.getName()に裏切られた話
lvla
0
440
Jetpack Composeで画像クロップ機能を実装する
lvla
0
1.3k
Jetpack Compose Layout API
lvla
1
740
BLEを使ったアプリを継続的に開発するために
lvla
0
1.1k
RecyclerView.ItemAnimator
lvla
1
390
RecycledViewPool
lvla
1
320
CameraX
lvla
2
2.6k
Other Decks in Programming
See All in Programming
Getting Started with Vibe Coding
miccheng
0
180
あなたの await、OS まで届いてる? strace で覗く JavaScript の非同期
hasutosasaki
1
1.9k
JIS keyboard support in Omarchy
lef237
0
180
DroidKnights 2026 Android A2UI Jetpack Compose 기반의 안전한 AI UI 렌더링 - 박제창
itsmedreamwalker
1
150
Python Lambdaにおけるテストしやすい設計とAI支援の活用 / Designing Testable Python Lambda Functions with AI
kitano_yuichi
1
290
SODA - FACT BOOK(EN)
sodainc
1
200
graphql-ruby を Spinel で速くしようとした話
mtsmfm
0
140
우리의 Nitro Modules는 당신의 Turbo Modules보다 아름답다
l2hyunwoo
0
250
AI時代のIaC入門 〜なぜインフラをコードで管理したいのか?〜 / Introduction to IaC in the AI Era
akihisaikeda
6
1.4k
React Native에 현대적인 빌드 도구 더하기: Rollipop 구현기
leegeunhyeok
0
180
Web Framework Benchmark Battle 2026, Any%
a_matsuda
3
3.1k
Optunaを作ったときにやりたかったこと、その後 (2026/10/16, Optuna Meetup #3)
iwiwi
4
1.4k
Featured
See All Featured
Imperfection Machines: The Place of Print at Facebook
scottboms
270
14k
GitHub's CSS Performance
jonrohan
1033
470k
A Guide to Academic Writing Using Generative AI - A Workshop
ks91
PRO
1
550
Have SEOs Ruined the Internet? - User Awareness of SEO in 2025
akashhashmi
0
540
Efficient Content Optimization with Google Search Console & Apps Script
katarinadahlin
PRO
1
970
Impact Scores and Hybrid Strategies: The future of link building
tamaranovitovic
0
480
Building an army of robots
kneath
307
47k
We Have a Design System, Now What?
morganepeng
55
8.4k
Into the Great Unknown - MozCon
thekraken
41
2.8k
Building Experiences: Design Systems, User Experience, and Full Site Editing
marktimemedia
1
650
The Success of Rails: Ensuring Growth for the Next 100 Years
eileencodes
47
8.4k
<Decoding/> the Language of Devs - We Love SEO 2024
nikkihalliwell
1
380
Transcript
Jetpack Compose Drag Gesture / Pinch Gesture @MoyuruAizawa
Moyuru Aizawa Software Engineer of Catlog, RABO. Previously at Azit,
CyberAgent, and Eureka. Love Metal, Hardcore and EDM. MoyuruAizawa
github.com/MoyuruAizawa/Cropify
࠷ۙࣄͰ Drag Gestureͱ͔Pinch Gestureͱ͔ ѻͬͨͷͰͦͷհ
CatlogͬͯԿ? Catlog Catlog Board ŮŧŠźƃɺͪΌΜͱ͏Μͨ͜͠?͓ͬͨ͜͠͠? සͩͬͨΓ͠ͳ͍? ମॏͷٸܹͳ૿ݮͱ͔ͯ͠ͳ͍? ͬͯͷ͕͔Δੌ͍IoT൘ ŮŧŠźƃɺӡಈͯ͠Δ?ͪΌΜͱ͝൧৯ͯΔ?Α͘৸ΕͯΔ? ͬͯͷ͕͔Δੌ͍IoTϖϯμϯτ
None
ݩؾείΞମॏτϨϯυɺτΠϨճ ɺ৯ࣄճͳͲ ͋ΒΏΔCatlogσʔλΛγΣΞͯ͠͏ͪ ͷࢠࣗຫͰ͖Δػೳ
‣ ༷ʑͳσʔλΛεςοΧʔԽͯ͠ஔ ‣ υϥοάͯ͠ҠಈͰ͖ΔΑ ‣ ը໘্ΑΓ্ʹυϥοάͨ͠ΒআͰ͖ΔΑ ‣ ϐϯνͨ͠ΒζʔϜͰ͖ΔΑ ‣ CenterVerticallyͱ͔CenterHorizontallyʹεφοϓͰ͖ΔΑ
͜ͷը໘ͷΤϯδχΞత໘നΈ
Ͳ͏Μͷ?
‣ Modifier#pointerInput ‣ PointerInputScope#detectDragGesture ‣ PointerInputScope#detectTransformGesture ॆ࣮ͷgesture API
modifier .pointerInput(Unit) { detectDragGestures { change, dragAmount -> state.offset +=
dragAmount } } .graphicsLayer { translationX = state.offset.x translationY = state.offset.y } PointerInput#detectDragGestures
modifier .pointerInput(Unit) { detectTransformGestures { centroid, pan, zoom, rotation ->
state.scale *= zoom } } .graphicsLayer { scaleX = state.scale scaleY = state.scale } PointerInput#detectTransformGestures
‣ PointerInputScope#detectDragGesture ‣ Drag͚͖͍ͩͨ͞ͳΒ͍ͭ͜Λ͑OK ‣ PointerInputScope#detectTransformGesture ‣ DragҎ֎ʹZoomRotationѻ͍͍ͨͳΒ͜Ε ‣ ֤δΣενϟʔͷ͕ಉ࣌ʹ͘ΔͷͰͲͷδΣενϟʔ͕ܧଓதͳ
ͷ͔ผ͍͠ ‣ Zoom͠ͳ͕ΒDragͱ͔Ͱ͖ͪΌ͏ ‣ onGestureStart, onGestureEndίʔϧόοΫແ͍ APIੇධ
suspend fun PointerInputScope.detectTransformGestures( onGestureStart: (GestureType) -> Unit, onGestureEnd: (GestureType) ->
Unit, onDrag: (dragAmount: Offset) -> Unit, onZoom: (zoom: Float) -> Unit, ) { forEachGesture { awaitPointerEventScope { awaitFirstDown(requireUnconsumed = false) val gestureType = detectGesture() ?: return@awaitPointerEventScope onGestureStart(gestureType) do { val event = awaitPointerEvent() when (gestureType) { GestureType.DRAG -> { val dragChange = event.calculatePan() if (dragChange != Offset.Zero) onDrag(dragChange) } GestureType.ZOOM -> { val zoomChange = event.calculateZoom() if (zoomChange != 1f) onZoom(zoomChange) } } event.changes.fastForEach { if (it.positionChanged()) it.consume() } } while (event.changes.fastAny { it.pressed }) onGestureEnd(gestureType) } } } private suspend fun AwaitPointerEventScope.detectGesture(): GestureType? { var zoom = 1f var pan = Offset.Zero val touchSlop = viewConfiguration.touchSlop var gestureType: GestureType? = null do { val event = awaitPointerEvent() zoom *= event.calculateZoom() pan += event.calculatePan() val zoomMotion = abs(1 - zoom) * event.calculateCentroidSize(useCurrent = false) val panMotion = pan.getDistance() if (zoomMotion > touchSlop) { gestureType = GestureType.ZOOM break } if (panMotion > touchSlop) { gestureType = GestureType.DRAG break } } while (event.changes.fastAny { it.pressed }) return gestureType } enum class GestureType { DRAG, ZOOM } ΞϓϦͷཁ݅Λຬͨͤͳ͍ͷͰdetectؔΛࣗͰॻ͍ͨ ※Ջͳͱ͖ʹݟͯͶ https://bit.ly/composegesture
‣ Catlogͷཁ݅తʹdetect͔ؔΒॻ͍ͨ ‣ ը໘֎ͷυϥοάෆՄ ‣ εςοΧʔ͔Βը໘·ͰͷڑΛܭࢉɺͦΕΛ͑Δ dragAmountΔ ‣ υϥοάதʹCenterVertically |
CenterHorizontallyۙʹ͖ͨΒͦ ͜εφοϓ ‣ ը໘ͱεφοϓΛߟྀͯ͠࠷ऴతͳdragAmountΛܾఆ͢Δ ‣ ը໘ͰZoomͨ͠Βը໘֎ʹΈग़ͪΌ͍·͢ΑͶ ‣ Ͱ͔͘ͳͬͯը໘֎ʹग़ͯ͠·ͬͨը໘ͣΒͯ͋͛͠Δ ͩΔ͔ͬͨࣄ
δΣενϟʔ࣮͢Δ͚ͩͳΒ؆୯ ΞϓϦͷཁ݅ʹΑͬͯͪΐͬͱμϧ͍
Thank you