Skip to content

Instantly share code, notes, and snippets.

@wotjd
Forked from jegnux/ProxyPropertyWrapper.swift
Created July 31, 2020 15:27
Show Gist options
  • Save wotjd/d07086bbd4510533e0afa00d82b208bc to your computer and use it in GitHub Desktop.
Save wotjd/d07086bbd4510533e0afa00d82b208bc to your computer and use it in GitHub Desktop.
@propertyWrapper
public struct Proxy<EnclosingSelf, Value> {
private let keyPath: ReferenceWritableKeyPath<EnclosingSelf, Value>
public init(_ keyPath: ReferenceWritableKeyPath<EnclosingSelf, Value>) {
self.keyPath = keyPath
}
@available(*, unavailable)
public var wrappedValue: Value {
get { fatalError() }
set { fatalError() }
}
public static subscript(
_enclosingInstance observed: EnclosingSelf,
wrapped wrappedKeyPath: ReferenceWritableKeyPath<EnclosingSelf, Value>,
storage storageKeyPath: ReferenceWritableKeyPath<EnclosingSelf, Self>
) -> Value {
get {
let storageValue = observed[keyPath: storageKeyPath]
let value = observed[keyPath: storageValue.keyPath]
return value
}
set {
let storageValue = observed[keyPath: storageKeyPath]
observed[keyPath: storageValue.keyPath] = newValue
}
}
}
@propertyWrapper
public struct DefaultProxy<EnclosingSelf, Value> {
private let keyPath: ReferenceWritableKeyPath<EnclosingSelf, Value?>
let defaultValue: Value
public init(
_ keyPath: ReferenceWritableKeyPath<EnclosingSelf, Value?>,
defaultValue: Value
) {
self.keyPath = keyPath
self.defaultValue = defaultValue
}
@available(*, unavailable)
public var wrappedValue: Value {
get { fatalError() }
set { fatalError() }
}
public static subscript(
_enclosingInstance observed: EnclosingSelf,
wrapped wrappedKeyPath: ReferenceWritableKeyPath<EnclosingSelf, Value>,
storage storageKeyPath: ReferenceWritableKeyPath<EnclosingSelf, Self>
) -> Value {
get {
let storageValue = observed[keyPath: storageKeyPath]
return observed[keyPath: storageValue.keyPath] ?? storageValue.defaultValue
}
set {
let storageValue = observed[keyPath: storageKeyPath]
observed[keyPath: storageValue.keyPath] = newValue
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment