1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40
| class KeyValueObserver { let source: NSObject let keyPath: String private let observer: KVObserveChange private var defaultKVODispatcher = KVODispatcher() init(source: NSObject, keyPath: String, options: NSKeyValueObservingOptions, observer: @escaping KVObserveChange) { self.source = source self.keyPath = keyPath self.observer = observer source.addObserver(defaultKVODispatcher, forKeyPath: keyPath, options: options, context: self.pointer) } func __conversion() -> UnsafeMutablePointer<KeyValueObserver> { return pointer } private lazy var pointer: UnsafeMutablePointer<KeyValueObserver> = { return UnsafeMutablePointer<KeyValueObserver>(Unmanaged<KeyValueObserver>.passUnretained(self).toOpaque().assumingMemoryBound(to: KeyValueObserver.self)) }() private class func fromPointer(pointer: UnsafeMutablePointer<KeyValueObserver>) -> KeyValueObserver { return Unmanaged<KeyValueObserver>.fromOpaque(UnsafeRawPointer(pointer)).takeUnretainedValue() } static func observe(pointer: UnsafeMutablePointer<KeyValueObserver>, change: [NSObject : AnyObject]) { let kvo = fromPointer(pointer: pointer) kvo.observer(kvo, change) } deinit { source.removeObserver(defaultKVODispatcher, forKeyPath: keyPath, context: self.pointer) print("deinit...\(self.pointer)") } }
class KVODispatcher : NSObject { override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) { KeyValueObserver.observe(pointer: (UnsafeMutablePointer<KeyValueObserver>.init(mutating: context?.bindMemory(to: KeyValueObserver.self, capacity: MemoryLayout<KeyValueObserver>.stride)))!, change: change! as [NSObject : AnyObject]) } }
|