Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Swift 5: String.UTF16View.Index(encodedOffset: l) deprecated

Tags:

swift

swift5

I'm using this code to insert hyphens into a string for better word-wrapping. With Swift 5 I get the info that

String.UTF16View.Index(encodedOffset: l)

would be deprecated. But I can not figure out the correct parameters. Any ideas?

import Foundation

extension String {

    func hyphenated(languageCode: String) -> String {
        let locale = Locale(identifier: languageCode)
        return self.hyphenated(locale: locale)
    }

    func hyphenated(locale: Locale) -> String {
        guard CFStringIsHyphenationAvailableForLocale(locale as CFLocale) else { return self }

        var s = self

        let fullRange = CFRangeMake(0, s.utf16.count)
        var hyphenationLocations = [CFIndex]()
        for (i, _) in s.utf16.enumerated() {
            let location: CFIndex = CFStringGetHyphenationLocationBeforeIndex(s as CFString, i, fullRange, 0, locale as CFLocale, nil)
            if hyphenationLocations.last != location {
                hyphenationLocations.append(location)
            }
        }

        for l in hyphenationLocations.reversed() {
            guard l > 0 else { continue }
            let strIndex = String.UTF16View.Index(encodedOffset: l)
            // insert soft hyphen:
            s.insert("\u{00AD}", at: strIndex)
            // or insert a regular hyphen to debug:
            // s.insert("-", at: strIndex)
        }

        return s
    }
}
like image 450
netshark1000 Avatar asked Mar 27 '19 13:03

netshark1000


People also ask

What are the different types of string encoding in Swift?

These include the UTF-8 encoding form (which encodes a string as 8-bit code units), the UTF-16 encoding form (which encodes a string as 16-bit code units), and the UTF-32 encoding form (which encodes a string as 32-bit code units). Swift provides several different ways to access Unicode representations of strings.

Why can’t I Index a string in Swift?

For this reason, Swift strings can’t be indexed by integer values. Use the startIndex property to access the position of the first Character of a String. The endIndex property is the position after the last character in a String. As a result, the endIndex property isn’t a valid argument to a string’s subscript.

Are string and character comparisons in Swift locale-sensitive?

The characters are visually similar, but don’t have the same linguistic meaning: print ( "These two characters aren't equivalent." ) // Prints "These two characters aren't equivalent." String and character comparisons in Swift aren’t locale-sensitive.

What is a string literal in Swift?

A string literal is a sequence of characters surrounded by double quotation marks ( " ). Use a string literal as an initial value for a constant or variable: Note that Swift infers a type of String for the someString constant because it’s initialized with a string literal value.


1 Answers

l is the offset in UTF-16 code units in the string s, so you can replace

let strIndex = String.UTF16View.Index(encodedOffset: l)

by

let strIndex = s.utf16.index(s.utf16.startIndex, offsetBy: l)

or use

let strIndex = String.Index(utf16Offset: l, in: s)

which was introduced in Swift 5 with SE-0241 Deprecate String Index Encoded Offsets.

like image 113
Martin R Avatar answered Nov 08 '22 11:11

Martin R