Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(785)

Side by Side Diff: content/public/android/java/src/org/chromium/content/browser/input/ImeAdapter.java

Issue 699333003: Support InputMethodManager#updateCursorAnchorInfo for Android 5.0 (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Address comments from jdduke@ and aelias@ Created 6 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2012 The Chromium Authors. All rights reserved. 1 // Copyright 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 package org.chromium.content.browser.input; 5 package org.chromium.content.browser.input;
6 6
7 import android.annotation.TargetApi;
8 import android.graphics.Matrix;
9 import android.os.Build;
7 import android.os.Handler; 10 import android.os.Handler;
8 import android.os.ResultReceiver; 11 import android.os.ResultReceiver;
9 import android.os.SystemClock; 12 import android.os.SystemClock;
10 import android.text.Editable; 13 import android.text.Editable;
11 import android.text.SpannableString; 14 import android.text.SpannableString;
12 import android.text.style.BackgroundColorSpan; 15 import android.text.style.BackgroundColorSpan;
13 import android.text.style.CharacterStyle; 16 import android.text.style.CharacterStyle;
14 import android.text.style.UnderlineSpan; 17 import android.text.style.UnderlineSpan;
15 import android.view.KeyCharacterMap; 18 import android.view.KeyCharacterMap;
16 import android.view.KeyEvent; 19 import android.view.KeyEvent;
17 import android.view.View; 20 import android.view.View;
21 import android.view.inputmethod.CursorAnchorInfo;
18 import android.view.inputmethod.EditorInfo; 22 import android.view.inputmethod.EditorInfo;
23 import android.view.inputmethod.InputConnection;
24 import android.view.inputmethod.InputMethodManager;
19 25
20 import org.chromium.base.CalledByNative; 26 import org.chromium.base.CalledByNative;
21 import org.chromium.base.JNINamespace; 27 import org.chromium.base.JNINamespace;
22 import org.chromium.base.VisibleForTesting; 28 import org.chromium.base.VisibleForTesting;
29 import org.chromium.cc.SelectionBoundType;
23 import org.chromium.ui.picker.InputDialogContainer; 30 import org.chromium.ui.picker.InputDialogContainer;
24 31
25 import java.lang.CharSequence; 32 import java.lang.CharSequence;
33 import java.util.Arrays;
34
35 import javax.annotation.Nonnull;
36 import javax.annotation.Nullable;
26 37
27 /** 38 /**
28 * Adapts and plumbs android IME service onto the chrome text input API. 39 * Adapts and plumbs android IME service onto the chrome text input API.
29 * ImeAdapter provides an interface in both ways native <-> java: 40 * ImeAdapter provides an interface in both ways native <-> java:
30 * 1. InputConnectionAdapter notifies native code of text composition state and 41 * 1. InputConnectionAdapter notifies native code of text composition state and
31 * dispatch key events from java -> WebKit. 42 * dispatch key events from java -> WebKit.
32 * 2. Native ImeAdapter notifies java side to clear composition text. 43 * 2. Native ImeAdapter notifies java side to clear composition text.
33 * 44 *
34 * The basic flow is: 45 * The basic flow is:
35 * 1. When InputConnectionAdapter gets called with composition or result text: 46 * 1. When InputConnectionAdapter gets called with composition or result text:
(...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after
136 private long mNativeImeAdapterAndroid; 147 private long mNativeImeAdapterAndroid;
137 private InputMethodManagerWrapper mInputMethodManagerWrapper; 148 private InputMethodManagerWrapper mInputMethodManagerWrapper;
138 private AdapterInputConnection mInputConnection; 149 private AdapterInputConnection mInputConnection;
139 private final ImeAdapterDelegate mViewEmbedder; 150 private final ImeAdapterDelegate mViewEmbedder;
140 private final Handler mHandler; 151 private final Handler mHandler;
141 private DelayedDismissInput mDismissInput = null; 152 private DelayedDismissInput mDismissInput = null;
142 private int mTextInputType; 153 private int mTextInputType;
143 private int mTextInputFlags; 154 private int mTextInputFlags;
144 private String mLastComposeText; 155 private String mLastComposeText;
145 156
157 /**
158 * Minimum data set that is required to construct {@link CursorAnchorInfo} o bject.
jdduke (slow) 2014/11/12 19:05:06 This is a non-trivial code addition, would it make
yukawa 2014/12/05 07:42:19 Sounds reasonable. Now the logic here is complete
159 */
160 private static final class CursorAnchorInfoSource {
161 /**
162 * Special sequence ID that is never returned from {@link #getSequenceNo ()}.
163 */
164 public static int INVALID_SEQUENCE_NO = 0;
165
166 private boolean mHasFrameInfo = false;
167 private String mText;
168 private int mSelectionStart;
169 private int mSelectionEnd;
170 private int mCompositionStart;
171 private int mCompositionEnd;
172 private float[] mCompositionCharacterBounds;
173 private boolean mHasInsertionMarker;
174 private float mInsertionMarkerHorizontal;
175 private float mInsertionMarkerTop;
176 private float mInsertionMarkerBottom;
177 private float mScale;
178 private float mTranslationX;
179 private float mTranslationY;
180 private int mSequenceNo = INVALID_SEQUENCE_NO + 1;
181
182
183 /**
184 * Resets the internal state.
185 */
186 public void reset() {
187 mHasFrameInfo = false;
188 mText = null;
189 mSelectionStart = -1;
190 mSelectionEnd = -1;
191 mCompositionStart = -1;
192 mCompositionEnd = -1;
193 mCompositionCharacterBounds = null;
194 mHasInsertionMarker = false;
195 mInsertionMarkerHorizontal = Float.NaN;
196 mInsertionMarkerTop = Float.NaN;
197 mInsertionMarkerBottom = Float.NaN;
198 mScale = 1.0f;
199 mTranslationX = 0.0f;
200 mTranslationY = 0.0f;
201 }
202
203 /**
204 * @return {@code true} if
205 * {@link #setFrameInfo(float, float, float, int, float, float, float)} was called after
206 * the object was instantiated or reinitialized by {@link #reset()}.
207 */
jdduke (slow) 2015/01/21 19:16:42 Do these accessors need public visibility? Where a
208 public boolean hasFrameInfo() {
209 return mHasFrameInfo;
210 }
211
212 /**
213 * @return Current composing text (if any). {@code null}.
214 */
215 @Nullable
216 public CharSequence getComposingText() {
217 if (mText == null) {
218 return null;
219 }
220 if (0 <= mCompositionStart && mCompositionStart <= mText.length()) {
221 return mText.subSequence(mCompositionStart, mCompositionEnd);
222 }
223 return "";
224 }
225
226 /**
227 * @return Selection start index (inclusive) that was specified in
228 * {@link #setTextAndSelection(String, int, int, int, int)}.
229 */
230 public int getSelectionStart() {
231 return mSelectionStart;
232 }
233
234 /**
235 * @return Selection end index (exclusive) that was specified in
236 * {@link #setTextAndSelection(String, int, int, int, int)}.
237 */
238 public int getSelectionEnd() {
239 return mSelectionEnd;
240 }
241
242 /**
243 * @return Composing text start index (inclusive) that was specified in
244 * {@link #setTextAndSelection(String, int, int, int, int)}.
245 */
246 public int getCompositionStart() {
247 return mCompositionStart;
248 }
249
250 /**
251 * @return Array of local coordinates for each character bounds in the c omposing text.
252 */
253 @Nullable
254 public float[] getCompositionCharacterBounds() {
255 return mCompositionCharacterBounds;
256 }
257
258 /**
259 * @return {@code true} if an insertion marker is displayed.
260 */
261 public boolean hasInsertionMarker() {
262 return mHasInsertionMarker;
263 }
264
265 /**
266 * @return Horizontal position of the text insertion marker, in local co ordinates.
267 */
268 public float getInsertionMarkerHorizontal() {
269 return mInsertionMarkerHorizontal;
270 }
271
272 /**
273 * @return Top position of the text insertion marker, in local coordinat es.
274 */
275 public float getInsertionMarkerTop() {
276 return mInsertionMarkerTop;
277 }
278
279 /**
280 * @return Bottom position of the text insertion marker, in local coordi nates.
281 */
282 public float getInsertionMarkerBottom() {
283 return mInsertionMarkerBottom;
284 }
285
286 /**
287 * @return Scaling factor from CSS (document) coordinates to Physical (s creen) coordinates.
288 */
289 public float getScale() {
290 return mScale;
291 }
292
293 /**
294 * @return Horizontal offset from CSS (document) coordinates to View-loc al Physical (screen)
295 * coordinates. To obtain the display coordinates, add an offset returne d from
296 * {@link View#getLocationOnScreen(int[])}.
297 */
298 public float getTranslationX() {
299 return mTranslationX;
300 }
301
302 /**
303 * @return Vertical offset from CSS (document) coordinates to View-local Physical (screen)
304 * coordinates. To obtain the display coordinates, add an offset returne d from
305 * {@link View#getLocationOnScreen(int[])}.
306 */
307 public float getTranslationY() {
308 return mTranslationY;
309 }
310
311 /**
312 * @return The sequence number that will be updated when any of the fiel ds is changed.
313 * Never returns {@link #INVALID_SEQUENCE_NO}.
314 */
315 public int getSequenceNo() {
316 return mSequenceNo;
317 }
318
319 private void incrementSequenceNo() {
320 ++mSequenceNo;
321 if (mSequenceNo == INVALID_SEQUENCE_NO) {
322 ++mSequenceNo;
323 }
324 }
325
326 /**
327 * Sets positional information of composing text as an array of characte r bounds.
328 * @param compositionCharacterBounds Array of character bounds in local coordinates.
329 */
330 public void setCompositionCharacterBounds(float[] compositionCharacterBo unds) {
331 if (!Arrays.equals(compositionCharacterBounds, mCompositionCharacter Bounds)) {
332 incrementSequenceNo();
333 }
334 mCompositionCharacterBounds = compositionCharacterBounds;
335 }
336
337 /**
338 * Sets text in the focused text area, selection range, and the composin g text range.
339 * @param text Text in the focused text field.
340 * @param selectionStart Index where the text selection starts. {@code - 1} if there is no
341 * selection.
342 * @param selectionEnd Index where the text selection ends. {@code -1} i f there is no
343 * selection.
344 * @param compositionStart Index where the text composition starts. {@co de -1} if there is
345 * no selection.
346 * @param compositionEnd Index where the text composition ends. {@code - 1} if there is no
347 * selection.
348 */
349 public void setTextAndSelection(String text, int selectionStart, int sel ectionEnd,
350 int compositionStart, int compositionEnd) {
351 if (text != mText || selectionStart != mSelectionStart || selectionE nd != mSelectionEnd
352 || compositionStart != mCompositionStart || compositionEnd ! = mCompositionEnd) {
353 incrementSequenceNo();
354 }
355 mText = text;
356 mSelectionStart = selectionStart;
357 mSelectionEnd = selectionEnd;
358 mCompositionStart = compositionStart;
359 mCompositionEnd = compositionEnd;
360 }
361
362 /**
363 * Sets coordinates system parameters and selection marker information.
364 * @param scale Scaling factor from CSS (document) coordinates to Physic al (screen)
365 * coordinates.
366 * @param translationX Horizontal offset from CSS (document) coordinates to
367 * View-local Physical (screen) coordinates.
368 * @param translationY Vertical offset from CSS (document) coordinates t o View-local
369 * Physical (screen) coordinates.
370 * @param frameMetadataSelectionStartType Type code that is defined in
371 * {@link SelectionBoundType}
372 * @param frameMetadataSelectionStartEdgeTopX X coordinate of the top of the first selection
373 * marker.
374 * @param frameMetadataSelectionStartEdgeTopY Y coordinate of the top of the first selection
375 * marker.
376 * @param frameMetadataSelectionStartEdgeBottomY Y coordinate of the bot tom of the first
377 * selection marker.
378 */
379 public void setFrameInfo(float scale, float translationX, float translat ionY,
380 int frameMetadataSelectionStartType, float frameMetadataSelectio nStartEdgeTopX,
381 float frameMetadataSelectionStartEdgeTopY,
382 float frameMetadataSelectionStartEdgeBottomY) {
383 // We are interested only in zero width selection bounds here becaus e non-zero width
384 // selection bounds cannot be represented in CursorAnchorInfo API in Android Framework
385 // as of API Level 21. Actually supporting non-zero width selection bounds in
386 // CursorAnchorInfo API was once considered in the design phase of t hat API, but the
387 // idea was abandoned because the IME is still able to retrieve the same information
388 // from the following parameters in
389 // CursorAnchorInfo:
390 // - CursorAnchorInfo#getCharacterBounds and
391 // - CursorAnchorInfo#getSelection{Start, End}.
392 final boolean hasInsertionMarker =
393 frameMetadataSelectionStartType == SelectionBoundType.SELECT ION_BOUND_CENTER;
394 if (scale != mScale || translationX != mTranslationX || translationY != mTranslationY) {
395 incrementSequenceNo();
396 } else if (hasInsertionMarker) {
397 if (!mHasInsertionMarker
398 || frameMetadataSelectionStartEdgeTopX != mInsertionMark erHorizontal
399 || frameMetadataSelectionStartEdgeTopY != mInsertionMark erTop
400 || frameMetadataSelectionStartEdgeBottomY != mInsertionM arkerBottom) {
401 incrementSequenceNo();
402 }
403 } else if (mHasInsertionMarker) {
404 incrementSequenceNo();
405 }
406 mHasInsertionMarker = hasInsertionMarker;
407 if (mHasInsertionMarker) {
408 mInsertionMarkerHorizontal = frameMetadataSelectionStartEdgeTopX ;
409 mInsertionMarkerTop = frameMetadataSelectionStartEdgeTopY;
410 mInsertionMarkerBottom = frameMetadataSelectionStartEdgeBottomY;
411 }
412 mScale = scale;
413 mTranslationX = translationX;
414 mTranslationY = translationY;
415 mHasFrameInfo = true;
416 }
417 }
418 private CursorAnchorInfoSource mCursorAnchorInfoSource = new CursorAnchorInf oSource();
419
420 private static class CursorAnchorInfoBuilderWrapper {
421
422 public static boolean isSupported() {
423 return false;
424 }
425
426 public static CursorAnchorInfoBuilderWrapper create() {
427 return new CursorAnchorInfoBuilderWrapper();
428 }
429
430 protected CursorAnchorInfoBuilderWrapper() {
431 }
432
433 /**
434 * Calls {@link InputConnection#updateCursorAnchorInfo(View, CursorAncho rInfo)} iff the API
435 * is available and the current IME actually requested it.
436 * @param inputMethodManagerWrapper Compatibility wrapper of {@link Inpu tConnection}.
437 * @param source Data source from which {@link CursorAnchorInfo} is crea ted.
438 * @param view {@link View} object that should be passed to
439 * {@link InputConnection#updateCursorAnchorInfo(View, CursorAnchorInfo) }.
440 */
441 @SuppressWarnings("unused")
442 public void send(@Nonnull InputMethodManagerWrapper inputMethodManagerWr apper,
jdduke (slow) 2015/01/21 19:16:41 I don't quite understand this function?
443 @Nonnull CursorAnchorInfoSource source, @Nonnull View view) {
444 // This is a stub for platforms that do not support CursorAnchorInfo .
445 }
446 }
447
448 private final CursorAnchorInfoBuilderWrapper mCursorAnchorInfoBuilder =
449 CursorAnchorInfoBuilderWrapper.create();
450 private boolean mCursorAnchorInfoMonitorEnabled = false;
451 private boolean mOneshotUpdateCursorAnchorInfoEnabled = false;
452
146 @VisibleForTesting 453 @VisibleForTesting
147 int mLastSyntheticKeyCode; 454 int mLastSyntheticKeyCode;
148 455
149 @VisibleForTesting 456 @VisibleForTesting
150 boolean mIsShowWithoutHideOutstanding = false; 457 boolean mIsShowWithoutHideOutstanding = false;
151 458
152 /** 459 /**
153 * @param wrapper InputMethodManagerWrapper that should receive all the call directed to 460 * @param wrapper InputMethodManagerWrapper that should receive all the call directed to
154 * InputMethodManager. 461 * InputMethodManager.
155 * @param embedder The view that is used for callbacks from ImeAdapter. 462 * @param embedder The view that is used for callbacks from ImeAdapter.
(...skipping 458 matching lines...) Expand 10 before | Expand all | Expand 10 after
614 /** 921 /**
615 * Send a request to the native counterpart of ImeAdapter to paste the text from the clipboard. 922 * Send a request to the native counterpart of ImeAdapter to paste the text from the clipboard.
616 * @return Whether the native counterpart of ImeAdapter received the call. 923 * @return Whether the native counterpart of ImeAdapter received the call.
617 */ 924 */
618 public boolean paste() { 925 public boolean paste() {
619 if (mNativeImeAdapterAndroid == 0) return false; 926 if (mNativeImeAdapterAndroid == 0) return false;
620 nativePaste(mNativeImeAdapterAndroid); 927 nativePaste(mNativeImeAdapterAndroid);
621 return true; 928 return true;
622 } 929 }
623 930
931 /**
932 * @return Whether the {@link CursorAnchorInfo} is available or not on this device.
933 */
934 public boolean isCursorAnchorInfoSupported() {
935 return CursorAnchorInfoBuilderWrapper.isSupported();
936 }
937
938 /**
939 * Start or stop calling
940 * {@link InputMethodManager#updateCursorAnchorInfo(View, CursorAnchorInfo)} .
941 * @param enabled {@code true} if {@link InputConnection#requestCursorUpdate s(int)} is called
942 * with {@link InputConnection#CURSOR_UPDATE_MONITOR} bit.
943 */
944 public void setCursorAnchorInfoMonitorEnabled(boolean enabled) {
945 mCursorAnchorInfoMonitorEnabled = enabled;
946 }
947
948 /**
949 * Make sure {@link InputMethodManager#updateCursorAnchorInfo(View, CursorAn chorInfo)} is called
950 * at least once immediately when the latest position becomes available.
951 * @param view The view to be passed to
952 * {@link InputMethodManager#updateCursorAnchorInfo(View, CursorAnchorInfo)} if the latest
953 * position is already available. Otherwise ignored.
954 */
955 public void scheduleOneshotUpdateCursorAnchorInfo(View view) {
956 if (!mCursorAnchorInfoSource.hasFrameInfo()) {
jdduke (slow) 2015/01/21 19:16:41 Where is this method called?
957 // If there is no frame info, send the data later when it becomes av ailable.
958 mOneshotUpdateCursorAnchorInfoEnabled = true;
959 return;
960 }
961 mCursorAnchorInfoBuilder.send(mInputMethodManagerWrapper, mCursorAnchorI nfoSource,
962 mViewEmbedder.getAttachedView());
963 mOneshotUpdateCursorAnchorInfoEnabled = false;
964 }
965
966 /**
967 * Update the parameters that are to be passed to the IME through
968 * {@link InputMethodManager#updateCursorAnchorInfo(View, CursorAnchorInfo)} .
969 * @param text Text in the focused text field.
970 * @param selectionStart Index where the text selection starts. {@code -1} i f there is no
971 * selection.
972 * @param selectionEnd Index where the text selection ends. {@code -1} if th ere is no
973 * selection.
974 * @param compositionStart Index where the text composition starts. {@code - 1} if there is no
975 * selection.
976 * @param compositionEnd Index where the text composition ends. {@code -1} i f there is no
977 * selection.
978 */
979 public void updateTextAndSelection(String text, int selectionStart, int sele ctionEnd,
980 int compositionStart, int compositionEnd) {
981 mCursorAnchorInfoSource.setTextAndSelection(text, selectionStart, select ionEnd,
982 compositionStart, compositionEnd);
983 }
984
985 public void onUpdateFrameInfo(float scale, float translationX, float transla tionY,
986 int frameMetadataSelectionStartType, float frameMetadataSelectionSta rtEdgeTopX,
987 float frameMetadataSelectionStartEdgeTopY,
988 float frameMetadataSelectionStartEdgeBottomY) {
989 mCursorAnchorInfoSource.setFrameInfo(scale, translationX, translationY,
990 frameMetadataSelectionStartType, frameMetadataSelectionStartEdge TopX,
991 frameMetadataSelectionStartEdgeTopY, frameMetadataSelectionStart EdgeBottomY);
992 if (!mCursorAnchorInfoMonitorEnabled && !mOneshotUpdateCursorAnchorInfoE nabled) {
993 return;
994 }
995 mCursorAnchorInfoBuilder.send(mInputMethodManagerWrapper, mCursorAnchorI nfoSource,
996 mViewEmbedder.getAttachedView());
997 mOneshotUpdateCursorAnchorInfoEnabled = false;
998 }
999
624 // Calls from C++ to Java 1000 // Calls from C++ to Java
625 1001
626 @CalledByNative 1002 @CalledByNative
627 private static void initializeWebInputEvents(int eventTypeRawKeyDown, int ev entTypeKeyUp, 1003 private static void initializeWebInputEvents(int eventTypeRawKeyDown, int ev entTypeKeyUp,
628 int eventTypeChar, int modifierShift, int modifierAlt, int modifierC trl, 1004 int eventTypeChar, int modifierShift, int modifierAlt, int modifierC trl,
629 int modifierCapsLockOn, int modifierNumLockOn) { 1005 int modifierCapsLockOn, int modifierNumLockOn) {
630 sEventTypeRawKeyDown = eventTypeRawKeyDown; 1006 sEventTypeRawKeyDown = eventTypeRawKeyDown;
631 sEventTypeKeyUp = eventTypeKeyUp; 1007 sEventTypeKeyUp = eventTypeKeyUp;
632 sEventTypeChar = eventTypeChar; 1008 sEventTypeChar = eventTypeChar;
633 sModifierShift = modifierShift; 1009 sModifierShift = modifierShift;
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after
692 } 1068 }
693 1069
694 @CalledByNative 1070 @CalledByNative
695 private void cancelComposition() { 1071 private void cancelComposition() {
696 if (mInputConnection != null) mInputConnection.restartInput(); 1072 if (mInputConnection != null) mInputConnection.restartInput();
697 mLastComposeText = null; 1073 mLastComposeText = null;
698 } 1074 }
699 1075
700 @CalledByNative 1076 @CalledByNative
701 private void setCharacterBounds(float[] characterBounds) { 1077 private void setCharacterBounds(float[] characterBounds) {
702 // TODO(yukawa): Implement this. 1078 mCursorAnchorInfoSource.setCompositionCharacterBounds(characterBounds);
703 } 1079 }
704 1080
705 @CalledByNative 1081 @CalledByNative
706 void detach() { 1082 void detach() {
707 if (mDismissInput != null) { 1083 if (mDismissInput != null) {
708 mHandler.removeCallbacks(mDismissInput); 1084 mHandler.removeCallbacks(mDismissInput);
709 mDismissInput.detach(); 1085 mDismissInput.detach();
710 } 1086 }
711 mNativeImeAdapterAndroid = 0; 1087 mNativeImeAdapterAndroid = 0;
712 mTextInputType = 0; 1088 mTextInputType = 0;
1089 mCursorAnchorInfoSource.reset();
713 } 1090 }
714 1091
715 private native boolean nativeSendSyntheticKeyEvent(long nativeImeAdapterAndr oid, 1092 private native boolean nativeSendSyntheticKeyEvent(long nativeImeAdapterAndr oid,
716 int eventType, long timestampMs, int keyCode, int modifiers, int uni codeChar); 1093 int eventType, long timestampMs, int keyCode, int modifiers, int uni codeChar);
717 1094
718 private native boolean nativeSendKeyEvent(long nativeImeAdapterAndroid, KeyE vent event, 1095 private native boolean nativeSendKeyEvent(long nativeImeAdapterAndroid, KeyE vent event,
719 int action, int modifiers, long timestampMs, int keyCode, boolean is SystemKey, 1096 int action, int modifiers, long timestampMs, int keyCode, boolean is SystemKey,
720 int unicodeChar); 1097 int unicodeChar);
721 1098
722 private static native void nativeAppendUnderlineSpan(long underlinePtr, int start, int end); 1099 private static native void nativeAppendUnderlineSpan(long underlinePtr, int start, int end);
(...skipping 18 matching lines...) Expand all
741 private native void nativeDeleteSurroundingText(long nativeImeAdapterAndroid , 1118 private native void nativeDeleteSurroundingText(long nativeImeAdapterAndroid ,
742 int before, int after); 1119 int before, int after);
743 1120
744 private native void nativeUnselect(long nativeImeAdapterAndroid); 1121 private native void nativeUnselect(long nativeImeAdapterAndroid);
745 private native void nativeSelectAll(long nativeImeAdapterAndroid); 1122 private native void nativeSelectAll(long nativeImeAdapterAndroid);
746 private native void nativeCut(long nativeImeAdapterAndroid); 1123 private native void nativeCut(long nativeImeAdapterAndroid);
747 private native void nativeCopy(long nativeImeAdapterAndroid); 1124 private native void nativeCopy(long nativeImeAdapterAndroid);
748 private native void nativePaste(long nativeImeAdapterAndroid); 1125 private native void nativePaste(long nativeImeAdapterAndroid);
749 private native void nativeResetImeAdapter(long nativeImeAdapterAndroid); 1126 private native void nativeResetImeAdapter(long nativeImeAdapterAndroid);
750 } 1127 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698