Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to know if two emojis will be displayed as one emoji?

The emoji 👍🏼 consists of 2 unicodeScalars 👍 U+1F44D, 🏼 U+1F3FC.

How can this be identified as 1 'displayed' emoji as it will be displayed as such on iOS?

like image 861
Manuel Avatar asked Aug 23 '16 14:08

Manuel


Video Answer


1 Answers

Update for Swift 4 (Xcode 9)

As of Swift 4, a "Emoji sequence" is treated as a single grapheme cluster (according to the Unicode 9 standard):

let s = "a👍🏼b👨‍❤️‍💋‍👨"
print(s.count) // 4

so the other workarounds are not needed anymore.


(Old answer for Swift 3 and earlier:)

A possible option is to enumerate and count the "composed character sequences" in the string:

let s = "a👍🏼b👨‍❤️‍💋‍👨"
var count = 0
s.enumerateSubstringsInRange(s.startIndex..<s.endIndex,
                             options: .ByComposedCharacterSequences) {
                                (char, _, _, _) in
                                if let char = char {
                                    count += 1
                                }
}
print(count) // 4

Another option is to find the range of the composed character sequences at a given index:

let s = "👨‍❤️‍💋‍👨"
if s.rangeOfComposedCharacterSequenceAtIndex(s.startIndex) == s.characters.indices {
    print("This is a single composed character")
}

As String extension methods:

// Swift 2.2:
extension String {
    var composedCharacterCount: Int {
        var count = 0
        enumerateSubstringsInRange(characters.indices, options: .ByComposedCharacterSequences) {
            (_, _, _, _) in count += 1
        }
        return count
    }

    var isSingleComposedCharacter: Bool {
        return rangeOfComposedCharacterSequenceAtIndex(startIndex) == characters.indices
    }
}

// Swift 3:
extension String {
    var composedCharacterCount: Int {
        var count = 0
        enumerateSubstrings(in: startIndex..<endIndex, options: .byComposedCharacterSequences) {
            (_, _, _, _) in count += 1
        }
        return count
    }

    var isSingleComposedCharacter: Bool {
        return rangeOfComposedCharacterSequence(at: startIndex) == startIndex..<endIndex
    }
}

Examples:

"👍🏼".composedCharacterCount // 1
"👍🏼".characters.count       // 2

"👨‍❤️‍💋‍👨".composedCharacterCount // 1
"👨‍❤️‍💋‍👨".characters.count       // 4

"🇩🇪🇨🇦".composedCharacterCount // 2
"🇩🇪🇨🇦".characters.count       // 1

As you see, the number of Swift characters (extended grapheme clusters) can be more or less than the number of composed character sequences.

like image 197
Martin R Avatar answered Oct 18 '22 02:10

Martin R