Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Speaker Deck
PRO
Sign in
Sign up for free
安定的 60 fps をめざす / the way to 60 fps
Taishi Ikai
January 29, 2018
Technology
19
4.8k
安定的 60 fps をめざす / the way to 60 fps
iOS app
at Otemachi.swift x Kyobashi.swift #02
https://kyobashi-swift.connpass.com/event/75379/
Taishi Ikai
January 29, 2018
Tweet
Share
More Decks by Taishi Ikai
See All by Taishi Ikai
日経電子版でApp内課金を導入した話 / Nikkei uses In-App Purchase
ikait
2
2.2k
紙面ビューアーを支える サーバーレスアーキテクチャ / serverless architecture supports Nikkei's paper viewer
ikait
43
38k
SwiftとCoreTextと文字組み
ikait
1
490
Typography and Fonts と日本語フォントまわり
ikait
2
2.8k
Other Decks in Technology
See All in Technology
ジョブ管理システムをAWS Step Functionsに移行する時の勘所
non97
0
450
インフラのテストに VPC Reachability Analyzer は外せないという話
nulabinc
PRO
2
640
COSCUP x KCD Taiwan 2020 - 那些年我們在開源社群的日子 - Cloud Native Taiwan
pohsien
0
110
QuickSight 触ってみた
tomuro
0
350
ソフトウェアアーキテクチャの基礎: Software Architecture in a Nutshell
snoozer05
25
7.8k
GCCP Creator @ COSCUP 2022
line_developers_tw
PRO
0
1.4k
Backlog × RPAでいろいろ捗った話
z_tetsu
0
360
テスト自動化を最速で軌道に乗せるために
nozomiito
0
110
Oracle Cloud Infrastructure:2022年7月度サービス・アップデート
oracle4engineer
PRO
0
150
VS Code Meetup #21 - もう一度知りたい基礎編 - ファイル操作、コーディングの基本編
74th
0
130
hey BOOK
heyinc
26
290k
Autonomous Database Cloud 技術詳細 / adb-s_technical_detail_jp
oracle4engineer
PRO
10
19k
Featured
See All Featured
Bash Introduction
62gerente
598
210k
Raft: Consensus for Rubyists
vanstee
127
5.5k
Thoughts on Productivity
jonyablonski
44
2.4k
Side Projects
sachag
450
37k
Product Roadmaps are Hard
iamctodd
35
6.8k
Robots, Beer and Maslow
schacon
152
7.1k
Designing on Purpose - Digital PM Summit 2013
jponch
106
5.7k
Designing for Performance
lara
597
63k
Stop Working from a Prison Cell
hatefulcrawdad
262
17k
The Power of CSS Pseudo Elements
geoffreycrofte
47
4k
Designing with Data
zakiwarfel
91
4k
Visualizing Your Data: Incorporating Mongo into Loggly Infrastructure
mongodb
29
4.4k
Transcript
1 ҆ఆత 60 fps ΛΊ͟͢ ழࣂ େࢤ ຊܦࡁ৽ฉࣾ Otemachi.swift x
Kyobashi.swift #02
<ಈը>
3 FPS Frames Per Second ͷུ 1 ඵؒʹදࣔ͢ΔϑϨʔϜ ͜Ε͕େ͖͍ͱɺΒ͔ʹݟ͑ΔʢňψϧψϧʼnײɺUX
ʹӨڹ͢ΔԾઆʣ UIScreen.main.maximumFramesPerSecond ࠷େ FPS Λऔಘ͢ΔɻiOS σόΠεͰɺ௨ৗ 60 ϝΠϯεϨουͰߦ͏ॲཧͷͱॏ͞ΛۃྗݮΒͯ͠ɺ࣮ݱΛࢦ͢ ࠓ͔ΒɺҰൠతͳઓུͱɺView ଆʹϑΥʔΧεͨ͠Λ͠·͢ FPS ʹ͍ͭͯ
4 ඞཁͳ͜ͱ͚ͩ͢Δ UIεϨουΛܰ͘͢ΔɺϒϩοΫ͠ͳ͍ Կ͠ͳ͍ ͘͢Δ ༧ΊΔ → Instruments Λݟͳ͕Βɺॏ͍ͱ͜Ζ͔ΒରԠΛ͍ͯ͘͠ FPS
ࢹʹΑΔ֬ೝɺInstruments ͷ Core Animation Ͱ֬ೝ ՄೳͳݶΓݹ͍Λར༻ ํ
5 ͦͷ࣌ͰෆཁͳσʔλΛ֎͢ ͍ͬͯͳ͍ϩδοΫΛফ͢ ֤ͰΔඞཁ͕͋Δͷ͚ͩड͚औΔ ͲͷͰಉ͡ॲཧʹͳΔͳΒɺ API Ͱܗ͓ͯ͘͠ unixtime Ͱड͚औΔͳͲ Ͳ͏ͯ͠
UI εϨου͡Όͳ͍ͱͰ͖ͳ͍͜ͱ͚ͩΔ ❌ ௨৴σΟεΫॻ͖ࠐΈ ❌ NSAttributedString ͷੜɺηϧͷߴ͞ͷܭࢉɺΦϑεΫϦʔϯඳը ඞཁͳ͜ͱ͚ͩΔ
6 UITableViewCell, UITableView(Header|Footer)View ͳͲ࠶ར༻͢Δ εΫϩʔϧͷͨͼʹੜ͢Δͱ݁ߏॏ͍ ϖʔδ UI ͳΒɺVC ࠶ར༻Ͱ͖Δͱྑͦ͞͏ ಉ͡ΧϥʔɺϑΥϯτɺਖ਼نදݱɺϑΥʔϚολʔ࠶ར༻͢Δ
UIColor, UIFont, NSRegularExpression, DateFormatter, NumberFormatter ຖੜ͢Δඞཁͳ͚ΕఆԽ͢ΔɺΩϟογϡ͢Δ Computed property ຖճධՁ͞ΕΔ νϦπϞͰ݁ߏͳϘτϧωοΫʹͳ͍ͬͯΔ͜ͱ Կ͠ͳ͍
7 ߴͳ DBɺΩϟογϡɺπʔϧΛ͏ Realm ͳͲ ंྠͷ࠶ൃ໌͍ͯ͠ͳ͍͔ UITableViewCell ͷߴ͞ܭࢉɺcell ͷͳͲɺԆͤ͞ʹ͍͘ ؤுͬͯ͘Δɺࣄલʹϩʔυ͢Δ
͘Δ
8 UITableView ͷଓ͖ΛಡΉͱ͖ͳͲɺUITableView ʹηϧΛՃ͢Δલʹɺ ઌʹߴ͞Λܭࢉ͓ͯ͘͠ & ΦϑεΫϦʔϯඳըͪ͠Ό͏ ϝϞϦޮͷͰɺඍົ͔͠Εͳ͍? ༧ΊΔ
۩ମతʹ 9
UITableViewCell Λܧঝ͢ΔΫϥεͰ init() ͳͲͰ UILabel, UIImageView Λ contentView ʹՃ Constraints,
StackView Λ͔ͭͬͯஔ cellForRow(at indexPath:) ͷதͰ dequeueReusableCell(withIdentifier identifier:, for indexPath:) Ͱ ηϧΛऔಘ (όοΫάϥϯυͰ) ը૾Λऔಘͯ͠ UIImageView ʹ͢ ηϧͷཁૉ͕૿͑Δʹ࿈Εͯɺॏ͘ͳͬͯ͘Δ 10 UITableView Ͱͷσʔλදࣔ
UITableViewCell Λܧঝ͢ΔΫϥεͰ init() ͳͲͰ UILabel, UIImageView Λ contentView ʹՃ Constraints,
StackView Λ͔ͭͬͯஔ cellForRow(at indexPath:) ͷதͰ dequeueReusableCell(withIdentifier identifier:, for indexPath:) Ͱ ηϧΛऔಘ (όοΫάϥϯυͰ) ը૾Λऔಘͯ͠ UIImageView ʹ͢ ηϧͷཁૉ͕૿͑Δʹ࿈Εͯɺॏ͘ͳͬͯ͘Δ 11 UITableView Ͱͷσʔλදࣔ
12 ҆ఆత 60 fps Λ࣮ݱ͢ΔʹɺAuto Layoutɺ Stack View Ͱ͍͠ ൺֱత৽͍͠Ͱɺཁૉ
(view) ͕ଟ͘ͳΔͱΧΫ͍ͭͯ͘Δ ಛʹຊޠ͕ೖΔͱɺϑΥϯτબ Auto LayoutɺखಈϨΠΞτͷਏΈ ηϧͷߴ͞ܭࢉΛࣗͰߦ͏ Ϩϕϧ 1 → 3 ʹ͚͓ͯ͠͠·͢ Auto Layout ΛΊΔ
13 UILabel, UIImageView ͷ frame ΛࣗͰܭࢉͯ͠ஔ͍ͯ͘͠ ߹ʹΑͬͯ Auto Resizing Mask
Λར༻ Auto Layout Ҏલͷ࣌Ͱओྲྀ ίʔυߦׂΓͱ૿Ճ ߴ͞ܭࢉखಈ UILabel, UIImageView ϝΠϯεϨουͰ৮ΕΔඞཁ͕͋ΔͷͰɺ NSString, NSAttributedString ͷ boundingRect Λར༻ Ϩϕϧ1: खಈϨΠΞτ + Auto Resizing Mask
14 UILabel, UIImageView ΛΘͣʹɺखಈͰඳը͢Δ શͯखಈͰϨΠΞτ UIView (, UITableViewCell) ͷ draw(_:)
Λ্ॻ͖ͯ͠ɺ NSString, NSAttributedString ͷ draw ܥͰॻ͖ࠐΉ NSAttributedString ɺόοΫάϥϯυͰ০͓ͯ͘͠ Ϩϕϧ2: ඳ͘
15 override func draw(_ rect: CGRect) { guard let context
= UIGraphicsGetCurrentContext() else { return nil } var remainRect = rect var attributedStringRect = self.attributedString.boundingRectCached( scope: "emblem", size: remainRect.size, options: [.usesLineFragmentOrigin, .truncatesLastVisibleLine]) self.attributedString.draw( with: remainRect, options: [.usesLineFragmentOrigin, .truncatesLastVisibleLine], context: nil ) remainRect.origin.y += attributedStringRect.bounds.height remainRect.size.height -= attributedStringRect.bounds.height // // ཁૉͷ܁Γฦ͢ // UIGraphicsEndImageContext() }
16 UILabel, UIImageView ΛΘͣʹɺखಈͰඳը͢Δ drawRect ͤͣʹɺόοΫάϥϯυͰ UIGraphicsBeginImageContextWithOptions ͯ͠ɺίϯςΩετΛ࡞Γɺͦ͜ʹॻ͖ࠐΉ ࠷ऴతʹɺඳըྖҬͷ CGImage
Λ࡞͓͍ͬͯͯɺ ͦΕΛΩϟογϡ͓ͯ͘͠ ॾʑͷॲཧΛ࣮֬ʹόοΫάϥϯυʹ ࿈Ε͍͚ͯΔͱ͍͏ϝϦοτ Ϩϕϧ3: CGImage ΛόοΫάϥϯυͰͭͬͯ͘షΔ
17 Func getImage(with bounds: CGSize) -> CGImage { if let
image = CacheStore.get(/* ݅ */) { return image } // όοΫάϥϯυΩϡʔͰɺcontext Λ࡞ UIGraphicsBeginImageContextWithOptions(bounds.size, false, 0) guard let context = UIGraphicsGetCurrentContext() else { return nil } // ࣗͰߴ͞ܭࢉΛ͠ͳ͕ΒɺNSAttributedString ͷ draw ͳͲͰ context ʹॻ͖ࠐΜͰ͍͘ attributedString.draw(with: bounds, options: drawingOptions, context: nil) // ऴΘͬͨΒ makeImage() ͯ͠ context Λऴ͑Δ let image = context.makeImage() UIGraphicsEndImageContext() if let image = image { CacheStore.set(image, forKey: key) } return image } ը૾όοΫάϥϯυͰऔಘͯ͠ɺ CGLayer ͷ cgImage ʹషΔ
18 UIView Ͱ backgroundColor Λ୯৭ʹ UIView Ͱ opaque: true ޮՌ͋·Γ࣮ײͰ͖ͣ...
> Blended view layers often cause slow table scrolling. https://developer.apple.com/library/content/documentation/DeveloperTools/Conceptual/InstrumentsUserGuide/MeasuringGraphicsPerformance.html Blended Layers Λͳ͘͢
ϝΠϯεϨουΛۃྗΘͳ͍ҙ͕ࣝॏཁ όοΫάϥϯυͰ CGImage ʹॻ͖ࠐΉͷޮՌ͋ͬͨ ඳըʹؔΘΔॲཧΛશͯόοΫάϥϯυʹ͍͚ͬͯͨ ͘ͳΓ͗͢Δͱന͍ηϧ͕ը໘ʹͰͯ͘Δ Auto Layout, StackView Ίͯɺ͍ͩͿૣ͘ͳͬͨ
খ͍͞Օॴ͕ੵͬͯҾ͔͔ͬΔ͜ͱ͕ଟʑ͋ͬͨ NSAttributedString UIFont ͰΩϟογϡ͔ఆԽ 19 ·ͱΊ 20% 10% 40% 30% खಈϨΠΞτ CGImage νϦ
Pinterest ͷਓ͕ͨͪத৺ʹ։ൃ͍ͯ͠Δඇಉظతͷ UI ඳըϑϨʔϜϫʔΫ RxSwift ͱΈ߹Θͤͯ͏ࣄྫ͕গͳ͔ͬͨ & View ·ΘΓ૯ͱ͔͕ͬ͑ඞཁͦ͏ͩͬͨͷͰݟૹͬͨ "Native"
Ͱ͋Δҙٛͱͯ͠ 60 fps ͷୡΛҙ͍ࣝͯ͠Δ Core Text ͳͲϨΠϠʔͳ API ʹׂΓͱ৮͍ͬͯͨ & ݟ͕গͳ͘ϦϦʔεʹؒʹ߹ΘͤΔࣗ৴͕࣋ͯͣɺݟૹͬͨ 20 ࠓޙݕ౼͍ͨ͠ چ໊শ: AsyncDisplayKit
21 ழࣂ େࢤʢ͍͔͍ ͍ͨ͠ʣ ຊܦࡁ৽ฉࣾॴଐͷΤϯδχΞ ͍ͭͬͯ͘Δͷ: iPhone ͷܦిࢠ൛ΞϓϦ iPhone /
iPad ͷࢴ໘ϏϡʔΞʔΞϓϦ ΞϓϦͷόοΫΤϯυܥ (w/αʔόʔϨε) About me