Last active
February 8, 2017 16:22
-
-
Save gonzalezreal/1217293bfb1dc7cbbbf6 to your computer and use it in GitHub Desktop.
Type safe NSValueTransformer
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
func stringToInt(value: String) -> Int? { | |
return value.toInt() | |
} | |
func intToString(value: Int) -> String? { | |
return "\(value)" | |
} | |
NSValueTransformer.setValueTransformerWithName("StringToInt", transform: stringToInt, reverseTransform: intToString) |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import Foundation | |
private class ValueTransformer: NSValueTransformer { | |
let transform: (AnyObject?) -> (AnyObject?) | |
init(transform: (AnyObject?) -> (AnyObject?)) { | |
self.transform = transform | |
} | |
// MARK: NSValueTransformer | |
override class func allowsReverseTransformation() -> Bool { | |
return false; | |
} | |
override class func transformedValueClass() -> AnyClass { | |
return NSObject.self | |
} | |
override func transformedValue(value: AnyObject?) -> AnyObject? { | |
return transform(value) | |
} | |
} | |
private class ReversibleValueTransformer: ValueTransformer { | |
let reverseTransform: (AnyObject?) -> (AnyObject?) | |
init(transform: (AnyObject?) -> (AnyObject?), reverseTransform: (AnyObject?) -> (AnyObject?)) { | |
self.reverseTransform = reverseTransform | |
super.init(transform: transform) | |
} | |
// MARK: NSValueTransformer | |
override class func allowsReverseTransformation() -> Bool { | |
return true; | |
} | |
override func reverseTransformedValue(value: AnyObject?) -> AnyObject? { | |
return reverseTransform(value) | |
} | |
} | |
public extension NSValueTransformer { | |
/** | |
Registers a value transformer with a given name and transform function. | |
:param: name The name of the transformer. | |
:param: transform The function that performs the transformation. | |
*/ | |
class func setValueTransformerWithName<T, U>(name: String, transform: (T) -> (U?)) { | |
let transformer = ValueTransformer { value in | |
return (value as? T).flatMap { | |
transform($0) as? AnyObject | |
} | |
} | |
self.setValueTransformer(transformer, forName: name) | |
} | |
/** | |
Registers a reversible value transformer with a given name and transform functions. | |
:param: name The name of the transformer. | |
:param: transform The function that performs the forward transformation. | |
:param: reverseTransform The function that performs the reverse transformation. | |
*/ | |
class func setValueTransformerWithName<T, U>(name: String, transform: (T) -> (U?), reverseTransform: (U) -> (T?)) { | |
let transformer = ReversibleValueTransformer(transform: { value in | |
return (value as? T).flatMap { | |
transform($0) as? AnyObject | |
} | |
}, reverseTransform: { value in | |
return (value as? U).flatMap { | |
reverseTransform($0) as? AnyObject | |
} | |
}) | |
self.setValueTransformer(transformer, forName: name) | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
FYI - I've created a version that works in Swift 3 here: https://gist.github.com/tomduckering/6976e984f575249b7f66320ac1d978f2