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
No Story, No Board
Search
Elvis Shi
June 23, 2017
Programming
3k
0
Share
No Story, No Board
Elvis Shi
June 23, 2017
More Decks by Elvis Shi
See All by Elvis Shi
@Environment(\.keyPath)那么好我不允许你们不知道! / atEnvironment keyPath is so good and you should know it!
lovee
0
420
ゼロから始めるPreferenceの実装 / Let's implement Preferences from scratch
lovee
0
140
Kotlin エンジニアへ送る:Swift 案件に参加させられる日に備えて~似てるけど色々違う Swift の仕様 / from Kotlin to Swift
lovee
1
380
個人アプリを2年ぶりにアプデしたから褒めて / I just updated my personal app, praise me!
lovee
0
710
How did I build an Open-Source SwiftUI Toast Library
lovee
1
170
SwiftUIで使いやすいToastの作り方 / How to build a Toast system which is easy to use in SwiftUI
lovee
3
1.3k
SwiftUIで二重スクロール作ってみた / When I tried to make a dual-scroll-ish view in SwiftUI
lovee
1
380
Observation のあれこれ / A brief introduction about Observation
lovee
3
440
ChatGPT 時代の勉強 / Learning under ChatGPT era
lovee
27
9k
Other Decks in Programming
See All in Programming
AlarmKitで明後日起きれるアラームアプリを作る
trickart
0
150
「OSSがあるなら自作するな」は AI時代も正しいか ── Build vs Adopt の新しい判断基準
kumorn5s
7
2.9k
OCRを使ってゲームのアイテムをデータ化する
kishikawakatsumi
0
110
不変条件と整合性境界—ビジネスが決める設計判断と実現パターン / Invariants and Consistency Boundaries
nrslib
0
210
These Five Tricks Can Make Your Apps Greener, Cheaper, & Nicer
hollycummins
0
180
バックエンドにElysiaJSを採用して気付いた、良い点・悪い点
wanko_it
1
170
今さら聞けないCancellationToken
htkym
0
180
関係性から理解する"同一性"の型用語たち
pvcresin
2
520
TypeSpec で繋ぐ複数プロダクトの型安全
maroon8021
1
240
ローカルLLMでどこまでコードが書けるか / How much code can be written on a local LLM
kishida
2
410
ビジネスモデルから紐解く、AI+型駆動開発
hirokiomote
2
1.8k
Augmenting AI with the Power of Jakarta EE
ivargrimstad
0
130
Featured
See All Featured
Fight the Zombie Pattern Library - RWD Summit 2016
marcelosomers
234
17k
Lessons Learnt from Crawling 1000+ Websites
charlesmeaden
PRO
1
1.2k
A better future with KSS
kneath
240
18k
How to Align SEO within the Product Triangle To Get Buy-In & Support - #RIMC
aleyda
2
1.5k
Lightning talk: Run Django tests with GitHub Actions
sabderemane
0
180
Data-driven link building: lessons from a $708K investment (BrightonSEO talk)
szymonslowik
1
1.1k
How GitHub (no longer) Works
holman
316
150k
Raft: Consensus for Rubyists
vanstee
141
7.4k
From Legacy to Launchpad: Building Startup-Ready Communities
dugsong
0
210
Chasing Engaging Ingredients in Design
codingconduct
0
190
HDC tutorial
michielstock
2
670
Utilizing Notion as your number one productivity tool
mfonobong
4
310
Transcript
No Story No Board for iOS UI࣮ษڧձ
override init() { super.init() emplyedBy = "MAGES. 5pb. Game div"
job = "iOS Developer" twitter = "@lovee" qiita = "@lovee" github = "el-hoshino" additionalInfo = "ʮAuto Layout ઈରࡴ͢ϚϯʯͰ͢" class Speaker: Developer { } }
ࠓ·ͰͷาΈ
ࠓ·ͰͷาΈ ͓ɺͬͺΈΜͳ Storyboard ݏ͍Μ͚ !
ࠓ·ͰͷาΈ
ࠓ·ͰͷาΈ ٸͳొஃͰ͔ͨ͠Β४උෆͰશવΕͳ͔ͬͨ "
ࠓ·ͰͷาΈ
ࠓ·ͰͷาΈ HITMAN ʹϋϚͬͯͦͦ४උͰ͖ͳ͔ͬͨ "
ࡾͷਖ਼ʹͳΔͷ͔"
໔໌ ͜ͷൃද Storyboard Λ dis ΔൃදͰ͢ ͕ɺผʹօʹ͜ͷߟ͑Λԡ͚͍ͨ͠ͱࢥΘͳ͍ ͜ͷൃදϋʔυίʔσΟϯά࠷ߴͱݴ͍ͬͯͳ͍ Storyboard ϋʔυίʔσΟϯάͦΕͧΕͷ᠘͕͋Δ
ͦͦࢲ GUI Ͱ GUI Λ࡞Δ͜ͱࣗମʹେࢍ ͨͩ Storyboard ͷ࣮͕೦͗͢ΔͱࢥͬͯΔ͚ͩ
ࢲ͕ Storyboard ΛΘͳ͍ཧ༝ʢ1ʣ Auto Layout ͷ੍Λ͏ View ͕૿͑Δͱ੍͕രൃ తʹ૿͑Δ ʮ͜ͷ
View ͷ͜ͷ੍ʯ͕ ୳ͮ͠Β͍
ࢲ͕ Storyboard ΛΘͳ͍ཧ༝ʢ2ʣ Swift ͳͷʹ IUO Λ͏ UIViewController ͷϥΠϑ αΠΫϧΛѲ͠ͳ͍ͱ
མͪΔ͜ͱ͋Δ ؾ࣋ͪѱ͍
ৄ͘͠ http://qiita.com/lovee/items/acfc9d0f1ffa7207b38b Λ͝ཡ͍ͩ͘͞#
One more thing!
UIStackView Auto Layout LayoutKit Manual Layout PinLayout ※ग़యɿhttps://github.com/mirego/PinLayout/blob/master/docs/Benchmark.md 銙闗#WVQ.C[QWV闖㢚閴聮閳闋闇#
ͦΕͰ Auto Layout ͍͍ͨํ PureLayout macOS / iOS ྆ํͰར༻Ͱ ͖Δ
Swift / Objective-C ྆ํͰ ར༻Ͱ͖Δ AutoLayout ੍Λ؆ܿʹɺ ͔ͭൺֱతʹ͔Γ͢ ͘ॻ͚Δ ͔ͳΓॆ࣮͍ͯ͠Δࢿྉ
ͦΕͰ Auto Layout ͍͍ͨํ SnapKit macOS / iOS / tvOS
શ෦ར ༻Ͱ͖Δ Swift ͷߏจಛΛ࠷େݶ ʹҾ͖ग़͍ͯ͠Δ গ͘͠ͳΔ͕ɺඇৗʹ ͔Γ͍͢จ๏ ඇৗʹॆ࣮͍ͯ͠Δެࣜ ࢿྉ
–Elvis Shi lͬͺΓɺ"VUP-BZPVUΛΘͣʹ ίʔυͰ6*ΛΈ͍ͨz
㘦㖽㘼㗧㙟㘗㘕㘙㘻㘒ଡ଼㘀㘬㘬㙔 UIView / UIViewController ͷϥΠϑαΠΫϧΛཧղ͢Δ ରΛ࿔Δɺରʹৄ͘͠ͳΔඞཁ͕͋Δ ϨΠΞτΛઃఆ͢ΔϓϩύςΟʔΛཧղ͢Δ ؒҧͬͨϓϩύςΟʔͷॻ͖ࠐΈࢥΘ͵όάΛট͘ αʔυύʔςΟʔϥΠϒϥϦʔΛཧղ͢Δ ศརͳ໘ɺࢥͬͯΔͷͱಈ͖͕ҧ͏Մೳੑ͋Δ
UIView / UIViewController ͷϥΠϑαΠΫϧΛཧղ͢Δ UIViewController UIView loadView() viewDidLoad() viewWillAppear() viewWillLayoutSubviews()
layoutSubviews() viewDidLayoutSubviews() viewDidAppear() layout runloop viewWillDisappear() viewDidDisappear() layoutIfNeeded() Needs layout? sleep viewWillLayoutSubviews() layoutSubviews() viewDidLayoutSubviews() Disappear? no yes yes no Needs layout?
UIView / UIViewController ͷϥΠϑαΠΫϧΛཧղ͢Δ Ͳ͏ͬͯఆ͍ͯ͠Δͷ͔ʁ Needs layout? setNeedsLayout() Λݺͼग़ͨ͠ σόΠε͕ճసͨ͠
ࢠϏϡʔΛՃআΛͨ͠ ʢUIScrollView Ͱ͋ΔࢠϏϡʔʣ͕εΫϩʔϧͨ͠ ࣗͷࢠϏϡʔͷ frame transform ͳͲ͕มߋ͞Εͨ ͳͲͳͲ…
UIView / UIViewController ͷϥΠϑαΠΫϧΛཧղ͢Δ Ͳ͏ͬͯఆ͍ͯ͠Δͷ͔ʁ Needs layout? setNeedsLayout() Λݺͼग़ͨ͠ σόΠε͕ճసͨ͠
ࢠϏϡʔΛՃআΛͨ͠ ʢUIScrollView Ͱ͋ΔࢠϏϡʔʣ͕εΫϩʔϧͨ͠ ࣗͷࢠϏϡʔͷ frame transform ͳͲ͕มߋ͞Εͨ ͳͲͳͲ… ࣗͷ frame transform Λมߋ͢Ε ͷ layoutSubviews() ݺΕΔʂ ࣗͷ frame transform ඞͣʹมߋͯ͠Β͓͏ʂ
–Elvis Shi l6*7JFXͷGSBNFUSBOTGPSNɺ ࣗͷͰͳ͘ɺͷͷz
ϨΠΞτΛઃఆ͢ΔϓϩύςΟʔΛཧղ͢Δ view.frame = CGRect(x: 0, y: 0, width: 200, height:
200)
ϨΠΞτΛઃఆ͢ΔϓϩύςΟʔΛཧղ͢Δ view.frame = CGRect(x: 0, y: 0, width: 200, height:
200) view.transform = view.transform.rotated(by: .pi / 4)
ϨΠΞτΛઃఆ͢ΔϓϩύςΟʔΛཧղ͢Δ view.frame = CGRect(x: 0, y: 0, width: 200, height:
200) view.transform = view.transform.rotated(by: .pi / 4) view.frame.size.width = 100
ϨΠΞτΛઃఆ͢ΔϓϩύςΟʔΛཧղ͢Δ view.frame = CGRect(x: 0, y: 0, width: 200, height:
200) view.transform = view.transform.rotated(by: .pi / 4) view.frame.size.width = 100 Α͘ΒΜ͕ frame.size.width Λʹͨ͠Β ෯ߴཱͪ͞Ґஔશ͕ͯมΘͬͨ"
※ग़యɿhttps://developer.apple.com/documentation/uikit/uiview/1622621-frame
͠ transform ϓϩύςΟʔ͕ identity Ͱͳ͚Εɺ ͜ͷϓϩύςΟʔͷະఆٛͱͳΓɺ ແࢹ͖͢Ͱ͋Δɻ ʢҙ༁ɿ৮Δͳ΄ͬͱ͚ʂʣ ※ग़యɿhttps://developer.apple.com/documentation/uikit/uiview/1622621-frame
frame Λ࿔Γ͍ͨͳΒ ΘΓʹ center ͱ bounds.size ͷํΛ ࿔Εʂ ※ग़యɿhttps://developer.apple.com/documentation/uikit/uiview/1622621-frame
ϨΠΞτΛઃఆ͢ΔϓϩύςΟʔΛཧղ͢Δ view.bounds.size = CGSize(width: 100, height: 100) view.center = CGPoint(x:
base.bounds.midX, y: base.bounds.midY)
ϨΠΞτΛઃఆ͢ΔϓϩύςΟʔΛཧղ͢Δ view.bounds.size = CGSize(width: 100, height: 100) view.center = CGPoint(x:
base.bounds.midX, y: base.bounds.midY) view.layer.anchorPoint.y = 0
ϨΠΞτΛઃఆ͢ΔϓϩύςΟʔΛཧղ͢Δ view.bounds.size = CGSize(width: 100, height: 100) view.center = CGPoint(x:
base.bounds.midX, y: base.bounds.midY) view.layer.anchorPoint.y = 0 Α͘ΒΜ͕ layer.anchorPoint Λมߋͨ͠Β ࣗͷॴ͕มΘͬͨ"
※ग़యɿhttps://developer.apple.com/library/content/documentation/Cocoa/Conceptual/CoreAnimation_guide/CoreAnimationBasics/ CoreAnimationBasics.html#//apple_ref/doc/uid/TP40004514-CH2-SW3
anchorPoint ͱϨΠϠʔͷ ϙδγϣχϯάͷؔʹ͍ͭͯ ʢҙ༁ɿcenter ͕ࢦͯ͠Δͷ anchorPoint ͷ ॴͳΜʂʣ ※ग़యɿhttps://developer.apple.com/library/content/documentation/Cocoa/Conceptual/CoreAnimation_guide/CoreAnimationBasics/ CoreAnimationBasics.html#//apple_ref/doc/uid/TP40004514-CH2-SW3
–Elvis Shi lUSBOTGPSN͕ॳظ͡Όͳ͍Մೳੑ͕͋Εɺ GSBNFΛઃఆͤͣʹ CPVOETTJ[FͱDFOUFSΛઃఆ͠Α͏z
αʔυύʔςΟʔϥΠϒϥϦʔΛཧղ͢Δ
αʔυύʔςΟʔϥΠϒϥϦʔΛཧղ͢Δ ݟͨײ͡ͰͲ͏Β frame ʹॻ͖ࠐΜͰͦ͏$
αʔυύʔςΟʔϥΠϒϥϦʔΛཧղ͢Δ segmented.transform = segmented.transform.rotated(by: .pi/4)
αʔυύʔςΟʔϥΠϒϥϦʔΛཧղ͢Δ segmented.transform = segmented.transform.rotated(by: .pi/4) Γ transform Λ࿔ͬͨΒ ϨΠΞτͰόάͬͨ"
NotAutoLayout https://github.com/el-hoshino/NotAutoLayout
αʔυύʔςΟʔϥΠϒϥϦʔΛཧղ͢Δ segmented.transform = segmented.transform.rotated(by: .pi/4)
αʔυύʔςΟʔϥΠϒϥϦʔΛཧղ͢Δ segmented.transform = segmented.transform.rotated(by: .pi/4) bounds.size ͱ center Λઃఆ͍ͯ͠ΔͷͰɺ transform
Λมߋͯ͠ϨΠΞτ่Ε͠ͳ͍
let titleViewLayout = Layout .makeCustom(x: { _ in 0 },
y: { _ in 0 }, width: { $0.width }, height: { _ in 60 }) baseView.addSubview(titleView, constantLayout: titleViewLayout) NotAutoLayout 1.0
baseView.nal.setupSubview(titleView) { $0 .setDefaultLayout { $0 .pinTopCenter(to: baseView, s: .topCenter)
.setWidth(to: baseView, s: .width) .setHeight(to: 60) } .addToSelf() .commit() } NotAutoLayout 2.0ʢԾʣ
–Elvis Shi l/PU"VUP-BZPVUΛͥͻࢼͯ͠Έ͍ͯͩ͘͞ 'FFECBDLͱ4UBSΛ͓͓ͪͯ͠Γ·͢z