OSDN Git Service

Delete gender-balanced emoji sequence by one backspace key event.
authorSeigo Nonaka <nona@google.com>
Mon, 27 Jun 2016 03:21:27 +0000 (12:21 +0900)
committerSeigo Nonaka <nona@google.com>
Tue, 28 Jun 2016 04:54:19 +0000 (13:54 +0900)
The gender-balanced emojis are made with ZWJ sequence and emoji
modifiers.  For example, U+1F469 U+1F3FD U+200D U+1F4BC should be
deleted at the same time by single backsapce key event.  Here, U+1F469
is WOMAN, U+1F3FD is EMOJI MODIFIER FITZPATRICK TYPE-4, U+200D is ZERO
WIDTH JOINER, U+1F4BC is BRIEFCASE.

This CL also renames the state name from STATE_BEFORE_ZWJ_EMOJI to
STATE_BEFORE_EMOJI since now all emoji can be a part of ZWJ sequence
after I572dad42ee108476962d4b3fe9f3a6019cb50098

BUG: 29728397
Change-Id: Ib114295db45c6592f1c65a0773ab236f8bf35209

core/java/android/text/method/BaseKeyListener.java
core/tests/coretests/src/android/text/method/BackspaceTest.java

index b618f4e..14e0b4f 100644 (file)
@@ -129,8 +129,8 @@ public abstract class BaseKeyListener extends MetaKeyKeyListener
         // The offset is immediately before a variation selector.
         final int STATE_BEFORE_VS = 6;
 
-        // The offset is immediately before a ZWJ emoji.
-        final int STATE_BEFORE_ZWJ_EMOJI = 7;
+        // The offset is immediately before an emoji.
+        final int STATE_BEFORE_EMOJI = 7;
         // The offset is immediately before a ZWJ that were seen before a ZWJ emoji.
         final int STATE_BEFORE_ZWJ = 8;
         // The offset is immediately before a variation selector and a ZWJ that were seen before a
@@ -169,7 +169,7 @@ public abstract class BaseKeyListener extends MetaKeyKeyListener
                     } else if (codePoint == Emoji.COMBINING_ENCLOSING_KEYCAP) {
                         state = STATE_BEFORE_KEYCAP;
                     } else if (Emoji.isEmoji(codePoint)) {
-                        state = STATE_BEFORE_ZWJ_EMOJI;
+                        state = STATE_BEFORE_EMOJI;
                     } else {
                         state = STATE_FINISHED;
                     }
@@ -233,7 +233,7 @@ public abstract class BaseKeyListener extends MetaKeyKeyListener
                 case STATE_BEFORE_VS:
                     if (Emoji.isEmoji(codePoint)) {
                         deleteCharCount += Character.charCount(codePoint);
-                        state = STATE_BEFORE_ZWJ_EMOJI;
+                        state = STATE_BEFORE_EMOJI;
                         break;
                     }
 
@@ -243,7 +243,7 @@ public abstract class BaseKeyListener extends MetaKeyKeyListener
                     }
                     state = STATE_FINISHED;
                     break;
-                case STATE_BEFORE_ZWJ_EMOJI:
+                case STATE_BEFORE_EMOJI:
                     if (codePoint == Emoji.ZERO_WIDTH_JOINER) {
                         state = STATE_BEFORE_ZWJ;
                     } else {
@@ -253,7 +253,8 @@ public abstract class BaseKeyListener extends MetaKeyKeyListener
                 case STATE_BEFORE_ZWJ:
                     if (Emoji.isEmoji(codePoint)) {
                         deleteCharCount += Character.charCount(codePoint) + 1;  // +1 for ZWJ.
-                        state = STATE_BEFORE_ZWJ_EMOJI;
+                        state = Emoji.isEmojiModifier(codePoint) ?
+                                STATE_BEFORE_EMOJI_MODIFIER : STATE_BEFORE_EMOJI;
                     } else if (isVariationSelector(codePoint)) {
                         lastSeenVSCharCount = Character.charCount(codePoint);
                         state = STATE_BEFORE_VS_AND_ZWJ;
@@ -266,7 +267,7 @@ public abstract class BaseKeyListener extends MetaKeyKeyListener
                         // +1 for ZWJ.
                         deleteCharCount += lastSeenVSCharCount + 1 + Character.charCount(codePoint);
                         lastSeenVSCharCount = 0;
-                        state = STATE_BEFORE_ZWJ_EMOJI;
+                        state = STATE_BEFORE_EMOJI;
                     } else {
                         state = STATE_FINISHED;
                     }
index ee5ec41..a4c88e7 100644 (file)
@@ -174,6 +174,11 @@ public class BackspaceTest extends KeyListenerTestCase {
         backspace(state, 0);
         state.assertEquals("|");
 
+        // Emoji modifier can be appended to the first emoji.
+        state.setByString("U+1F469 U+1F3FB U+200D U+1F4BC |");
+        backspace(state, 0);
+        state.assertEquals("|");
+
         // End with ZERO WIDTH JOINER
         state.setByString("U+1F441 U+200D |");
         backspace(state, 0);
@@ -445,13 +450,6 @@ public class BackspaceTest extends KeyListenerTestCase {
         backspace(state, 0);
         state.assertEquals("|");
 
-        // Emoji modifier + ZERO WIDTH JOINER
-        state.setByString("U+1F466 U+1F3FB U+200D U+1F469 |");
-        backspace(state, 0);
-        state.assertEquals("U+1F466 |");
-        backspace(state, 0);
-        state.assertEquals("|");
-
         // Regional indicator symbol + Emoji modifier
         state.setByString("U+1F1FA U+1F3FB |");
         backspace(state, 0);