Skip to content

Instantly share code, notes, and snippets.

@T1T4N
Last active September 17, 2019 14:35
Show Gist options
  • Save T1T4N/3369af58b2b412500b17197a6905a05c to your computer and use it in GitHub Desktop.
Save T1T4N/3369af58b2b412500b17197a6905a05c to your computer and use it in GitHub Desktop.
A generic wrapper for observing changes from a Combine Publisher - Xcode 11 GM
import Foundation
import Combine
import SwiftUI
@available(OSX 10.15, iOS 13.0, tvOS 13.0, watchOS 6.0, *)
class ObservablePublisher<Output>: ObservableObject {
var bag: [AnyCancellable] = []
@Published public internal(set) var value: Output?
init(erased publisher: AnyPublisher<Output, Never>) {
publisher
.receive(on: RunLoop.main)
.sink { [weak self] in
self?.value = $0
}
.store(in: &bag)
}
// Segmentation fault: 11 if this generic constructor is not `convenience`
public convenience init<PublisherType: Publisher>
(_ publisher: PublisherType)
where PublisherType.Output == Output, PublisherType.Failure == Never {
self.init(erased: publisher.eraseToAnyPublisher())
}
}
@available(OSX 10.15, iOS 13.0, tvOS 13.0, watchOS 6.0, *)
extension Publisher where Failure == Never {
func observableObject() -> ObservablePublisher<Output> {
return ObservablePublisher(self)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment