Swift 4 - Xcode 9 beta 4 - NSKernAttributeName vs NSAttributedStringKey
IOS Deployment Target: iOS 9.3, Base SDK: Latest iOS (iOS 11.0), Xcode 9 Beta 4, Swift 4
The following code builds and runs in Swift 3, Xcode 8:
let kern = (CTRunGetAttributes(run) as? [String : Any])?
[NSKernAttributeName] as? CGFloat ?? 0
However, the Swift 4 migrator converts it to this:
let kern = (CTRunGetAttributes(run) as? [String : Any])?
[NSAttributedStringKey.kern] as? CGFloat ?? 0
Xcode 9 now complains:
Cannot subscript a value of type '[String : Any]' with an index of type 'NSAttributedStringKey'
According to the inspector, " NSAttributedStringKey
" is only available in iOS 11. (Note that I'm targeting iOS 9).
If I replace ' NSAttributedStringKey.kern
with NSKernAttributeName
', the error remains.
By clicking on the " NSKernAttributeName
" button , I am told that its availability is iOS 6. However, the inspector also claims that its type is " NSAttributedStringKey
", which is only available in iOS 11. I don't know if it's just an API view artifact or stuffing or something. what I am missing.
Question: How can I use NSKernAttributeName
(or an upgraded version of it) backward compatible with iOS 9 with Swift 4?
Thanks for any help.
source to share
Enter the dictionary as [NSAttributedStringKey: Any] instead of [String: Any]. These are all sugar in the Swift layer, so it should work even on older versions of macOS / OS X.
EDIT: I have to clarify the last sentence a bit. NSAttributedStringKey as well as all the other new "key" types in Swift 4 only exist in Swift, not Objective-C. When a dictionary with NSAttributedStringKey is connected to Objective-C, all keys will be converted to NSStrings. Since the actual Foundation, UIKit, etc. frameworks you are working with are written in C / Objective-C, this will โjust workโ and you donโt have to worry about documentation requiring the NSAttributedStringKey to be 10.11.
source to share