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
lightweight introducing with reactive cocoa
Search
Hiroki Kumamoto
June 25, 2015
0
59
lightweight introducing with reactive cocoa
Reactive Cocoaを自作iOSに組みこんだときのtips
Hiroki Kumamoto
June 25, 2015
Tweet
Share
More Decks by Hiroki Kumamoto
See All by Hiroki Kumamoto
How to implement timetable view on iOS
kumabook
0
110
Promiseを実装してみよう
kumabook
0
320
bff_tips.pdf
kumabook
0
86
Tips of server-side rendering with react + redux
kumabook
0
81
プロトコルを使って複数サービスを跨いだmusic playerを実装する
kumabook
2
610
emacs helm likeな WebExtensions を作った話
kumabook
0
160
merges sort
kumabook
0
79
basic_sort
kumabook
0
72
git_peco_tips
kumabook
0
31
Featured
See All Featured
The Cost Of JavaScript in 2023
addyosmani
55
9.3k
Statistics for Hackers
jakevdp
799
230k
Designing Experiences People Love
moore
142
24k
Templates, Plugins, & Blocks: Oh My! Creating the theme that thinks of everything
marktimemedia
31
2.6k
Leading Effective Engineering Teams in the AI Era
addyosmani
8
1.1k
Building Flexible Design Systems
yeseniaperezcruz
329
39k
Product Roadmaps are Hard
iamctodd
PRO
55
12k
XXLCSS - How to scale CSS and keep your sanity
sugarenia
249
1.3M
Fashionably flexible responsive web design (full day workshop)
malarkey
407
66k
Side Projects
sachag
455
43k
A designer walks into a library…
pauljervisheath
210
24k
The Art of Delivering Value - GDevCon NA Keynote
reverentgeek
16
1.8k
Transcript
Reactive Cocoa Λ SwiftͰ ΊͪΌϥΠτʹಋೖͯ͠Έͨ ͳ͠ 2015/06/16 potato tips #18
Hiroki Kumamoto (@kumabook)
Who am I ? • Hiroki Kumamoto • @kumabook •
ษڧձॳࢀՃʂ • झຯͰΞϓϦͭͬͯ͘·͢ • Իָ༻RSSϦʔμ iOSΞϓϦ MusicFav • https://github.com/kumabook/MusicFav/ • Feedly Cloud API libraryҰॹʹ࡞ • https://github.com/kumabook/FeedlyKit
ΊͪΌϥΠτ? • FRPతʹΘͣϥΠϒϥϦతʹ • ͦͷ̍ɿ௨৴ॲཧΛϓϩϛε෩ʹ • ͦͷ̎ɿObserver pattern (not binding)
ͦͷ1ɿϓϩϛε෩ʹ͔ͭ͏ • AFNetworkingΛϥοϓ͢Δ • callback ελΠϧ͔Β ϓϩϛε෩ʹ • SignalProducer (چColdSignal)
func getAllBlogs(#onSuccess: [Entry] -> Void, onFailure: NSError -> Void) ->
Request func getAllBlogs() -> SignalProducer<[Entry], NSError>
func getAllBlogs() -> SignalProducer<[Blog], NSError> { return SignalProducer { (sink,
disposable) in let manager = AFHTTPRequestOperationManager() let url = String(format: "%@/get_all_blogs", self.baseUrl + self.apiRoot) let operation = manager.GET(url, parameters: [:], success: { (operation:AFHTTPRequestOperation!, response:AnyObject!) -> Void in sink.put(.Next(Box(JSON(response).arrayValue.map({ Blog(json: $0) })))) sink.put(.Completed) }, failure: { (operation:AFHTTPRequestOperation!, error:NSError!) -> Void in sink.put(.Error(Box(error))) }) disposable.addDisposable { operation.cancel() } }
func start(error: (E -> ())? = default, completed: (() ->
())? = default, interrupted: (() -> ())? = default, next: (T -> ())? = default) -> Disposable fetchAllBlogs().start(next: { blogs in doSomething(blogs) }, error: {e in … }, completed: { … })
͍͚ͦ͏ʂ ͏গ͠౿ΈࠐΜͰ ͬͯΈΑ͏ ˠ when తͳͭ
• ෳͷॲཧ͕ऴΘͬͨޙʹҰ͚ͩॲཧΛ͢Δ • SignalProducer#concatͰ݁߹Ͱ͖Δ • Array#reduceͱΈ߹ΘͤΕ ͍͍ײ͡ʹͰ͖ͦ͏ • [SignalProducer<T, E>]
͔Β SignalProducer<T, E>ม͢Δ
var signal = signals.reduce(SignalProducer<Entry, NSError>.empty, combine: { (currentSignal, nextSignal) in
currentSignal |> concat(nextSignal) }) • ॳظ SignalProducer<Entry,NSError>.empty •Next が複数回きて最後にCompletedがくる
• ͜ͷล͔ΒͩΜͩΜָ͘͠ͳͬͯ͘Δ • ͱΓ͋͑ͣͳΜͰSignalProducerΛฦͨ͘͠ͳΔ ˠܕΤϥʔʹ·͞ΕΔ
SignalProducer methods • SignalProducerΛอͬͨ··Λม͍͑ͨ ˠɹ|> map Λ͏ • ೖΕࢠʹͳͬͯ͠·ͬͨ ˠ
|> flatten Λ͏ • unittest ͱ͔ Carthageͷιʔεͱ͔͕ࢀߟʹͳΔ
Observe Binding • Signal (چHotSignal) • Data binding ͱ͍͏ΑΓ
Observerύλʔϯతʹ༻
ViewModel observe observe put Event enum Event { }
• ͍ͬͯΔ͜ͱNSNotificationCenterͱ͔ͱมΘΒͳ͍͕ ܕνΣοΫ͕ޮ͘ͷ͕҆৺ײ͋Δ • observeͨ͠ͷdispose͢Δ • deinitΛ௨͍ͬͯΔ͔Ͱmemory leakνΣοΫ • Dead
lock ͨ͠߹ • b _NSLockErrorͰϒϨΠΫϙΠϯτுΔ • RealmͷDAOͷϝιουͰEventΛput
·ͱΊ • SignalProducerͱSignalΛத৺ʹϥΠτʹಋೖ • SignalProducerϓϩϛεతʹ • SignalObserverతʹ • Action, Property,
Binding (<~)FRPΛษڧͯ͠ ঃʑʹಋೖ͍͖͍ͯͨ͠
͋Γ͕ͱ͏͍͟͝·ͨ͠