Chromium Code Reviews| Index: content/public/android/java/src/org/chromium/content/browser/input/AdapterInputConnection.java |
| diff --git a/content/public/android/java/src/org/chromium/content/browser/input/AdapterInputConnection.java b/content/public/android/java/src/org/chromium/content/browser/input/AdapterInputConnection.java |
| index 19bcb89d1ecde85d5ac9d5fce66f463b7e10e045..136a878158ec80c583e08a4018421f2d3a556978 100644 |
| --- a/content/public/android/java/src/org/chromium/content/browser/input/AdapterInputConnection.java |
| +++ b/content/public/android/java/src/org/chromium/content/browser/input/AdapterInputConnection.java |
| @@ -10,6 +10,7 @@ import android.text.InputType; |
| import android.text.Selection; |
| import android.text.TextUtils; |
| import android.util.Log; |
| +import android.view.KeyCharacterMap; |
| import android.view.KeyEvent; |
| import android.view.View; |
| import android.view.inputmethod.BaseInputConnection; |
| @@ -39,6 +40,7 @@ public class AdapterInputConnection extends BaseInputConnection { |
| private boolean mSingleLine; |
| private int mNumNestedBatchEdits = 0; |
| + private int mPendingAccent; |
| private int mLastUpdateSelectionStart = INVALID_SELECTION; |
| private int mLastUpdateSelectionEnd = INVALID_SELECTION; |
| @@ -215,6 +217,8 @@ public class AdapterInputConnection extends BaseInputConnection { |
| mLastUpdateSelectionEnd = selectionEnd; |
| mLastUpdateCompositionStart = compositionStart; |
| mLastUpdateCompositionEnd = compositionEnd; |
| + // Change in selection or cursor position invalidates any pending accent. |
| + mPendingAccent = 0; |
|
Ted C
2014/12/03 02:30:14
do we need to do this as well on restartInput (or
bcwhite
2014/12/03 15:49:09
Seems the smart thing to do. Done.
|
| } |
| /** |
| @@ -368,6 +372,50 @@ public class AdapterInputConnection extends BaseInputConnection { |
| if (DEBUG) { |
| Log.w(TAG, "sendKeyEvent [" + event.getAction() + "] [" + event.getKeyCode() + "]"); |
| } |
| + |
| + if (KeyEvent.isModifierKey(event.getKeyCode())) { |
| + return mImeAdapter.translateAndSendNativeEvents(event, 0); |
| + } |
| + |
| + // Physical keyboards also have their events come through here though not |
| + // by BaseInputConnection. In order to support "accent" key sequences |
| + // such as "~n" or "^o" we have to record that one has been pressed |
| + // and, if an accentable letter follows, delete the accent glyph and |
| + // insert the composed character. |
| + |
| + int unicodeChar = event.getUnicodeChar(); |
| + int pendingAccent = mPendingAccent; |
| + int nextAccent = pendingAccent; |
|
Ted C
2014/12/03 02:30:14
In what cases is this used? Just wondering what c
bcwhite
2014/12/03 15:49:09
It's used to keep all the accent-processing code a
|
| + |
| + if ((unicodeChar & KeyCharacterMap.COMBINING_ACCENT) != 0) { |
| + pendingAccent = 0; |
| + nextAccent = unicodeChar & KeyCharacterMap.COMBINING_ACCENT_MASK; |
| + } else if (pendingAccent != 0) { |
| + if (event.getAction() == KeyEvent.ACTION_DOWN) { |
| + int combined = KeyEvent.getDeadChar(pendingAccent, unicodeChar); |
| + if (combined != 0) { |
| + // Previous accent combines with new character to create |
| + // a new accented character. First delete the displayed |
| + // accent so it appears overwritten by the composition. |
| + // Note that deleting the displayed accent will cause an |
| + // update and clearing of mPendingAccent which is why we've |
| + // copied it to a local variable above. |
| + super.deleteSurroundingText(1, 0); |
| + mImeAdapter.deleteSurroundingText(1, 0); |
| + } else { |
| + // Previous accent doesn't combine with this character |
| + // so assume both are completely independent. |
| + pendingAccent = 0; |
| + nextAccent = 0; |
| + } |
| + } |
| + |
| + if (event.getAction() == KeyEvent.ACTION_UP) { |
| + // Forget accent after release of key being accented. |
| + nextAccent = 0; |
| + } |
| + } |
| + |
| // If this is a key-up, and backspace/del or if the key has a character representation, |
| // need to update the underlying Editable (i.e. the local representation of the text |
| // being edited). |
| @@ -378,26 +426,30 @@ public class AdapterInputConnection extends BaseInputConnection { |
| } else if (event.getKeyCode() == KeyEvent.KEYCODE_FORWARD_DEL) { |
| deleteSurroundingText(0, 1); |
| return true; |
| - } else { |
| - int unicodeChar = event.getUnicodeChar(); |
| - if (unicodeChar != 0) { |
| - int selectionStart = Selection.getSelectionStart(mEditable); |
| - int selectionEnd = Selection.getSelectionEnd(mEditable); |
| - if (selectionStart > selectionEnd) { |
| - int temp = selectionStart; |
| - selectionStart = selectionEnd; |
| - selectionEnd = temp; |
| + } else if (unicodeChar != 0) { |
| + int combinedChar = unicodeChar; |
| + if (pendingAccent != 0) { |
| + combinedChar = KeyEvent.getDeadChar(pendingAccent, unicodeChar); |
| + if (combinedChar == 0) { |
| + combinedChar = unicodeChar; |
| } |
| - mEditable.replace(selectionStart, selectionEnd, |
| - Character.toString((char) unicodeChar)); |
| } |
| + int selectionStart = Selection.getSelectionStart(mEditable); |
| + int selectionEnd = Selection.getSelectionEnd(mEditable); |
| + if (selectionStart > selectionEnd) { |
| + int temp = selectionStart; |
| + selectionStart = selectionEnd; |
| + selectionEnd = temp; |
| + } |
| + mEditable.replace(selectionStart, selectionEnd, |
| + Character.toString((char) combinedChar)); |
| } |
| } else if (event.getAction() == KeyEvent.ACTION_DOWN) { |
| // TODO(aurimas): remove this workaround when crbug.com/278584 is fixed. |
| if (event.getKeyCode() == KeyEvent.KEYCODE_ENTER) { |
| beginBatchEdit(); |
| finishComposingText(); |
| - mImeAdapter.translateAndSendNativeEvents(event); |
| + mImeAdapter.translateAndSendNativeEvents(event, 0); |
| endBatchEdit(); |
| return true; |
| } else if (event.getKeyCode() == KeyEvent.KEYCODE_DEL) { |
| @@ -406,7 +458,8 @@ public class AdapterInputConnection extends BaseInputConnection { |
| return true; |
| } |
| } |
| - mImeAdapter.translateAndSendNativeEvents(event); |
| + mImeAdapter.translateAndSendNativeEvents(event, pendingAccent); |
| + mPendingAccent = nextAccent; |
| return true; |
| } |