1 /* 2 * Copyright (C) 2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.internal.view; 18 19 import android.annotation.NonNull; 20 import android.annotation.Nullable; 21 import android.compat.annotation.UnsupportedAppUsage; 22 import android.os.Build; 23 import android.os.Bundle; 24 import android.os.Handler; 25 import android.os.Looper; 26 import android.os.Message; 27 import android.os.RemoteException; 28 import android.util.Log; 29 import android.view.KeyEvent; 30 import android.view.inputmethod.CompletionInfo; 31 import android.view.inputmethod.CorrectionInfo; 32 import android.view.inputmethod.ExtractedTextRequest; 33 import android.view.inputmethod.InputConnection; 34 import android.view.inputmethod.InputConnectionInspector; 35 import android.view.inputmethod.InputConnectionInspector.MissingMethodFlags; 36 import android.view.inputmethod.InputContentInfo; 37 38 import com.android.internal.annotations.GuardedBy; 39 import com.android.internal.os.SomeArgs; 40 41 public abstract class IInputConnectionWrapper extends IInputContext.Stub { 42 private static final String TAG = "IInputConnectionWrapper"; 43 private static final boolean DEBUG = false; 44 45 private static final int DO_GET_TEXT_AFTER_CURSOR = 10; 46 private static final int DO_GET_TEXT_BEFORE_CURSOR = 20; 47 private static final int DO_GET_SELECTED_TEXT = 25; 48 private static final int DO_GET_CURSOR_CAPS_MODE = 30; 49 private static final int DO_GET_EXTRACTED_TEXT = 40; 50 private static final int DO_COMMIT_TEXT = 50; 51 private static final int DO_COMMIT_COMPLETION = 55; 52 private static final int DO_COMMIT_CORRECTION = 56; 53 private static final int DO_SET_SELECTION = 57; 54 private static final int DO_PERFORM_EDITOR_ACTION = 58; 55 private static final int DO_PERFORM_CONTEXT_MENU_ACTION = 59; 56 private static final int DO_SET_COMPOSING_TEXT = 60; 57 private static final int DO_SET_COMPOSING_REGION = 63; 58 private static final int DO_FINISH_COMPOSING_TEXT = 65; 59 private static final int DO_SEND_KEY_EVENT = 70; 60 private static final int DO_DELETE_SURROUNDING_TEXT = 80; 61 private static final int DO_DELETE_SURROUNDING_TEXT_IN_CODE_POINTS = 81; 62 private static final int DO_BEGIN_BATCH_EDIT = 90; 63 private static final int DO_END_BATCH_EDIT = 95; 64 private static final int DO_PERFORM_PRIVATE_COMMAND = 120; 65 private static final int DO_CLEAR_META_KEY_STATES = 130; 66 private static final int DO_REQUEST_UPDATE_CURSOR_ANCHOR_INFO = 140; 67 private static final int DO_CLOSE_CONNECTION = 150; 68 private static final int DO_COMMIT_CONTENT = 160; 69 70 @GuardedBy("mLock") 71 @Nullable 72 @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P, trackingBug = 115609023) 73 private InputConnection mInputConnection; 74 75 private Looper mMainLooper; 76 private Handler mH; 77 @UnsupportedAppUsage 78 private Object mLock = new Object(); 79 @GuardedBy("mLock") 80 private boolean mFinished = false; 81 82 class MyHandler extends Handler { MyHandler(Looper looper)83 MyHandler(Looper looper) { 84 super(looper); 85 } 86 87 @Override handleMessage(Message msg)88 public void handleMessage(Message msg) { 89 executeMessage(msg); 90 } 91 } 92 IInputConnectionWrapper(Looper mainLooper, @NonNull InputConnection inputConnection)93 public IInputConnectionWrapper(Looper mainLooper, @NonNull InputConnection inputConnection) { 94 mInputConnection = inputConnection; 95 mMainLooper = mainLooper; 96 mH = new MyHandler(mMainLooper); 97 } 98 99 @Nullable getInputConnection()100 public InputConnection getInputConnection() { 101 synchronized (mLock) { 102 return mInputConnection; 103 } 104 } 105 isFinished()106 protected boolean isFinished() { 107 synchronized (mLock) { 108 return mFinished; 109 } 110 } 111 isActive()112 abstract protected boolean isActive(); 113 getTextAfterCursor(int length, int flags, int seq, IInputContextCallback callback)114 public void getTextAfterCursor(int length, int flags, int seq, IInputContextCallback callback) { 115 dispatchMessage(obtainMessageIISC(DO_GET_TEXT_AFTER_CURSOR, length, flags, seq, callback)); 116 } 117 getTextBeforeCursor(int length, int flags, int seq, IInputContextCallback callback)118 public void getTextBeforeCursor(int length, int flags, int seq, IInputContextCallback callback) { 119 dispatchMessage(obtainMessageIISC(DO_GET_TEXT_BEFORE_CURSOR, length, flags, seq, callback)); 120 } 121 getSelectedText(int flags, int seq, IInputContextCallback callback)122 public void getSelectedText(int flags, int seq, IInputContextCallback callback) { 123 dispatchMessage(obtainMessageISC(DO_GET_SELECTED_TEXT, flags, seq, callback)); 124 } 125 getCursorCapsMode(int reqModes, int seq, IInputContextCallback callback)126 public void getCursorCapsMode(int reqModes, int seq, IInputContextCallback callback) { 127 dispatchMessage(obtainMessageISC(DO_GET_CURSOR_CAPS_MODE, reqModes, seq, callback)); 128 } 129 getExtractedText(ExtractedTextRequest request, int flags, int seq, IInputContextCallback callback)130 public void getExtractedText(ExtractedTextRequest request, 131 int flags, int seq, IInputContextCallback callback) { 132 dispatchMessage(obtainMessageIOSC(DO_GET_EXTRACTED_TEXT, flags, 133 request, seq, callback)); 134 } 135 commitText(CharSequence text, int newCursorPosition)136 public void commitText(CharSequence text, int newCursorPosition) { 137 dispatchMessage(obtainMessageIO(DO_COMMIT_TEXT, newCursorPosition, text)); 138 } 139 commitCompletion(CompletionInfo text)140 public void commitCompletion(CompletionInfo text) { 141 dispatchMessage(obtainMessageO(DO_COMMIT_COMPLETION, text)); 142 } 143 commitCorrection(CorrectionInfo info)144 public void commitCorrection(CorrectionInfo info) { 145 dispatchMessage(obtainMessageO(DO_COMMIT_CORRECTION, info)); 146 } 147 setSelection(int start, int end)148 public void setSelection(int start, int end) { 149 dispatchMessage(obtainMessageII(DO_SET_SELECTION, start, end)); 150 } 151 performEditorAction(int id)152 public void performEditorAction(int id) { 153 dispatchMessage(obtainMessageII(DO_PERFORM_EDITOR_ACTION, id, 0)); 154 } 155 performContextMenuAction(int id)156 public void performContextMenuAction(int id) { 157 dispatchMessage(obtainMessageII(DO_PERFORM_CONTEXT_MENU_ACTION, id, 0)); 158 } 159 setComposingRegion(int start, int end)160 public void setComposingRegion(int start, int end) { 161 dispatchMessage(obtainMessageII(DO_SET_COMPOSING_REGION, start, end)); 162 } 163 setComposingText(CharSequence text, int newCursorPosition)164 public void setComposingText(CharSequence text, int newCursorPosition) { 165 dispatchMessage(obtainMessageIO(DO_SET_COMPOSING_TEXT, newCursorPosition, text)); 166 } 167 finishComposingText()168 public void finishComposingText() { 169 dispatchMessage(obtainMessage(DO_FINISH_COMPOSING_TEXT)); 170 } 171 sendKeyEvent(KeyEvent event)172 public void sendKeyEvent(KeyEvent event) { 173 dispatchMessage(obtainMessageO(DO_SEND_KEY_EVENT, event)); 174 } 175 clearMetaKeyStates(int states)176 public void clearMetaKeyStates(int states) { 177 dispatchMessage(obtainMessageII(DO_CLEAR_META_KEY_STATES, states, 0)); 178 } 179 deleteSurroundingText(int beforeLength, int afterLength)180 public void deleteSurroundingText(int beforeLength, int afterLength) { 181 dispatchMessage(obtainMessageII(DO_DELETE_SURROUNDING_TEXT, 182 beforeLength, afterLength)); 183 } 184 deleteSurroundingTextInCodePoints(int beforeLength, int afterLength)185 public void deleteSurroundingTextInCodePoints(int beforeLength, int afterLength) { 186 dispatchMessage(obtainMessageII(DO_DELETE_SURROUNDING_TEXT_IN_CODE_POINTS, 187 beforeLength, afterLength)); 188 } 189 beginBatchEdit()190 public void beginBatchEdit() { 191 dispatchMessage(obtainMessage(DO_BEGIN_BATCH_EDIT)); 192 } 193 endBatchEdit()194 public void endBatchEdit() { 195 dispatchMessage(obtainMessage(DO_END_BATCH_EDIT)); 196 } 197 performPrivateCommand(String action, Bundle data)198 public void performPrivateCommand(String action, Bundle data) { 199 dispatchMessage(obtainMessageOO(DO_PERFORM_PRIVATE_COMMAND, action, data)); 200 } 201 requestUpdateCursorAnchorInfo(int cursorUpdateMode, int seq, IInputContextCallback callback)202 public void requestUpdateCursorAnchorInfo(int cursorUpdateMode, int seq, 203 IInputContextCallback callback) { 204 dispatchMessage(obtainMessageISC(DO_REQUEST_UPDATE_CURSOR_ANCHOR_INFO, cursorUpdateMode, 205 seq, callback)); 206 } 207 closeConnection()208 public void closeConnection() { 209 dispatchMessage(obtainMessage(DO_CLOSE_CONNECTION)); 210 } 211 commitContent(InputContentInfo inputContentInfo, int flags, Bundle opts, int seq, IInputContextCallback callback)212 public void commitContent(InputContentInfo inputContentInfo, int flags, Bundle opts, 213 int seq, IInputContextCallback callback) { 214 dispatchMessage(obtainMessageIOOSC(DO_COMMIT_CONTENT, flags, inputContentInfo, opts, seq, 215 callback)); 216 } 217 dispatchMessage(Message msg)218 void dispatchMessage(Message msg) { 219 // If we are calling this from the main thread, then we can call 220 // right through. Otherwise, we need to send the message to the 221 // main thread. 222 if (Looper.myLooper() == mMainLooper) { 223 executeMessage(msg); 224 msg.recycle(); 225 return; 226 } 227 228 mH.sendMessage(msg); 229 } 230 executeMessage(Message msg)231 void executeMessage(Message msg) { 232 switch (msg.what) { 233 case DO_GET_TEXT_AFTER_CURSOR: { 234 SomeArgs args = (SomeArgs)msg.obj; 235 try { 236 final IInputContextCallback callback = (IInputContextCallback) args.arg6; 237 final int callbackSeq = args.argi6; 238 InputConnection ic = getInputConnection(); 239 if (ic == null || !isActive()) { 240 Log.w(TAG, "getTextAfterCursor on inactive InputConnection"); 241 callback.setTextAfterCursor(null, callbackSeq); 242 return; 243 } 244 callback.setTextAfterCursor(ic.getTextAfterCursor( 245 msg.arg1, msg.arg2), callbackSeq); 246 } catch (RemoteException e) { 247 Log.w(TAG, "Got RemoteException calling setTextAfterCursor", e); 248 } finally { 249 args.recycle(); 250 } 251 return; 252 } 253 case DO_GET_TEXT_BEFORE_CURSOR: { 254 SomeArgs args = (SomeArgs)msg.obj; 255 try { 256 final IInputContextCallback callback = (IInputContextCallback) args.arg6; 257 final int callbackSeq = args.argi6; 258 InputConnection ic = getInputConnection(); 259 if (ic == null || !isActive()) { 260 Log.w(TAG, "getTextBeforeCursor on inactive InputConnection"); 261 callback.setTextBeforeCursor(null, callbackSeq); 262 return; 263 } 264 callback.setTextBeforeCursor(ic.getTextBeforeCursor( 265 msg.arg1, msg.arg2), callbackSeq); 266 } catch (RemoteException e) { 267 Log.w(TAG, "Got RemoteException calling setTextBeforeCursor", e); 268 } finally { 269 args.recycle(); 270 } 271 return; 272 } 273 case DO_GET_SELECTED_TEXT: { 274 SomeArgs args = (SomeArgs)msg.obj; 275 try { 276 final IInputContextCallback callback = (IInputContextCallback) args.arg6; 277 final int callbackSeq = args.argi6; 278 InputConnection ic = getInputConnection(); 279 if (ic == null || !isActive()) { 280 Log.w(TAG, "getSelectedText on inactive InputConnection"); 281 callback.setSelectedText(null, callbackSeq); 282 return; 283 } 284 callback.setSelectedText(ic.getSelectedText( 285 msg.arg1), callbackSeq); 286 } catch (RemoteException e) { 287 Log.w(TAG, "Got RemoteException calling setSelectedText", e); 288 } finally { 289 args.recycle(); 290 } 291 return; 292 } 293 case DO_GET_CURSOR_CAPS_MODE: { 294 SomeArgs args = (SomeArgs)msg.obj; 295 try { 296 final IInputContextCallback callback = (IInputContextCallback) args.arg6; 297 final int callbackSeq = args.argi6; 298 InputConnection ic = getInputConnection(); 299 if (ic == null || !isActive()) { 300 Log.w(TAG, "getCursorCapsMode on inactive InputConnection"); 301 callback.setCursorCapsMode(0, callbackSeq); 302 return; 303 } 304 callback.setCursorCapsMode(ic.getCursorCapsMode(msg.arg1), 305 callbackSeq); 306 } catch (RemoteException e) { 307 Log.w(TAG, "Got RemoteException calling setCursorCapsMode", e); 308 } finally { 309 args.recycle(); 310 } 311 return; 312 } 313 case DO_GET_EXTRACTED_TEXT: { 314 SomeArgs args = (SomeArgs)msg.obj; 315 try { 316 final IInputContextCallback callback = (IInputContextCallback) args.arg6; 317 final int callbackSeq = args.argi6; 318 InputConnection ic = getInputConnection(); 319 if (ic == null || !isActive()) { 320 Log.w(TAG, "getExtractedText on inactive InputConnection"); 321 callback.setExtractedText(null, callbackSeq); 322 return; 323 } 324 callback.setExtractedText(ic.getExtractedText( 325 (ExtractedTextRequest)args.arg1, msg.arg1), callbackSeq); 326 } catch (RemoteException e) { 327 Log.w(TAG, "Got RemoteException calling setExtractedText", e); 328 } finally { 329 args.recycle(); 330 } 331 return; 332 } 333 case DO_COMMIT_TEXT: { 334 InputConnection ic = getInputConnection(); 335 if (ic == null || !isActive()) { 336 Log.w(TAG, "commitText on inactive InputConnection"); 337 return; 338 } 339 ic.commitText((CharSequence)msg.obj, msg.arg1); 340 return; 341 } 342 case DO_SET_SELECTION: { 343 InputConnection ic = getInputConnection(); 344 if (ic == null || !isActive()) { 345 Log.w(TAG, "setSelection on inactive InputConnection"); 346 return; 347 } 348 ic.setSelection(msg.arg1, msg.arg2); 349 return; 350 } 351 case DO_PERFORM_EDITOR_ACTION: { 352 InputConnection ic = getInputConnection(); 353 if (ic == null || !isActive()) { 354 Log.w(TAG, "performEditorAction on inactive InputConnection"); 355 return; 356 } 357 ic.performEditorAction(msg.arg1); 358 return; 359 } 360 case DO_PERFORM_CONTEXT_MENU_ACTION: { 361 InputConnection ic = getInputConnection(); 362 if (ic == null || !isActive()) { 363 Log.w(TAG, "performContextMenuAction on inactive InputConnection"); 364 return; 365 } 366 ic.performContextMenuAction(msg.arg1); 367 return; 368 } 369 case DO_COMMIT_COMPLETION: { 370 InputConnection ic = getInputConnection(); 371 if (ic == null || !isActive()) { 372 Log.w(TAG, "commitCompletion on inactive InputConnection"); 373 return; 374 } 375 ic.commitCompletion((CompletionInfo)msg.obj); 376 return; 377 } 378 case DO_COMMIT_CORRECTION: { 379 InputConnection ic = getInputConnection(); 380 if (ic == null || !isActive()) { 381 Log.w(TAG, "commitCorrection on inactive InputConnection"); 382 return; 383 } 384 ic.commitCorrection((CorrectionInfo)msg.obj); 385 return; 386 } 387 case DO_SET_COMPOSING_TEXT: { 388 InputConnection ic = getInputConnection(); 389 if (ic == null || !isActive()) { 390 Log.w(TAG, "setComposingText on inactive InputConnection"); 391 return; 392 } 393 ic.setComposingText((CharSequence)msg.obj, msg.arg1); 394 return; 395 } 396 case DO_SET_COMPOSING_REGION: { 397 InputConnection ic = getInputConnection(); 398 if (ic == null || !isActive()) { 399 Log.w(TAG, "setComposingRegion on inactive InputConnection"); 400 return; 401 } 402 ic.setComposingRegion(msg.arg1, msg.arg2); 403 return; 404 } 405 case DO_FINISH_COMPOSING_TEXT: { 406 if (isFinished()) { 407 // In this case, #finishComposingText() is guaranteed to be called already. 408 // There should be no negative impact if we ignore this call silently. 409 if (DEBUG) { 410 Log.w(TAG, "Bug 35301295: Redundant finishComposingText."); 411 } 412 return; 413 } 414 InputConnection ic = getInputConnection(); 415 // Note we do NOT check isActive() here, because this is safe 416 // for an IME to call at any time, and we need to allow it 417 // through to clean up our state after the IME has switched to 418 // another client. 419 if (ic == null) { 420 Log.w(TAG, "finishComposingText on inactive InputConnection"); 421 return; 422 } 423 ic.finishComposingText(); 424 return; 425 } 426 case DO_SEND_KEY_EVENT: { 427 InputConnection ic = getInputConnection(); 428 if (ic == null || !isActive()) { 429 Log.w(TAG, "sendKeyEvent on inactive InputConnection"); 430 return; 431 } 432 ic.sendKeyEvent((KeyEvent)msg.obj); 433 return; 434 } 435 case DO_CLEAR_META_KEY_STATES: { 436 InputConnection ic = getInputConnection(); 437 if (ic == null || !isActive()) { 438 Log.w(TAG, "clearMetaKeyStates on inactive InputConnection"); 439 return; 440 } 441 ic.clearMetaKeyStates(msg.arg1); 442 return; 443 } 444 case DO_DELETE_SURROUNDING_TEXT: { 445 InputConnection ic = getInputConnection(); 446 if (ic == null || !isActive()) { 447 Log.w(TAG, "deleteSurroundingText on inactive InputConnection"); 448 return; 449 } 450 ic.deleteSurroundingText(msg.arg1, msg.arg2); 451 return; 452 } 453 case DO_DELETE_SURROUNDING_TEXT_IN_CODE_POINTS: { 454 InputConnection ic = getInputConnection(); 455 if (ic == null || !isActive()) { 456 Log.w(TAG, "deleteSurroundingTextInCodePoints on inactive InputConnection"); 457 return; 458 } 459 ic.deleteSurroundingTextInCodePoints(msg.arg1, msg.arg2); 460 return; 461 } 462 case DO_BEGIN_BATCH_EDIT: { 463 InputConnection ic = getInputConnection(); 464 if (ic == null || !isActive()) { 465 Log.w(TAG, "beginBatchEdit on inactive InputConnection"); 466 return; 467 } 468 ic.beginBatchEdit(); 469 return; 470 } 471 case DO_END_BATCH_EDIT: { 472 InputConnection ic = getInputConnection(); 473 if (ic == null || !isActive()) { 474 Log.w(TAG, "endBatchEdit on inactive InputConnection"); 475 return; 476 } 477 ic.endBatchEdit(); 478 return; 479 } 480 case DO_PERFORM_PRIVATE_COMMAND: { 481 final SomeArgs args = (SomeArgs) msg.obj; 482 try { 483 final String action = (String) args.arg1; 484 final Bundle data = (Bundle) args.arg2; 485 InputConnection ic = getInputConnection(); 486 if (ic == null || !isActive()) { 487 Log.w(TAG, "performPrivateCommand on inactive InputConnection"); 488 return; 489 } 490 ic.performPrivateCommand(action, data); 491 } finally { 492 args.recycle(); 493 } 494 return; 495 } 496 case DO_REQUEST_UPDATE_CURSOR_ANCHOR_INFO: { 497 SomeArgs args = (SomeArgs)msg.obj; 498 try { 499 final IInputContextCallback callback = (IInputContextCallback) args.arg6; 500 final int callbackSeq = args.argi6; 501 InputConnection ic = getInputConnection(); 502 if (ic == null || !isActive()) { 503 Log.w(TAG, "requestCursorAnchorInfo on inactive InputConnection"); 504 callback.setRequestUpdateCursorAnchorInfoResult(false, callbackSeq); 505 return; 506 } 507 callback.setRequestUpdateCursorAnchorInfoResult( 508 ic.requestCursorUpdates(msg.arg1), callbackSeq); 509 } catch (RemoteException e) { 510 Log.w(TAG, "Got RemoteException calling requestCursorAnchorInfo", e); 511 } finally { 512 args.recycle(); 513 } 514 return; 515 } 516 case DO_CLOSE_CONNECTION: { 517 // Note that we do not need to worry about race condition here, because 1) mFinished 518 // is updated only inside this block, and 2) the code here is running on a Handler 519 // hence we assume multiple DO_CLOSE_CONNECTION messages will not be handled at the 520 // same time. 521 if (isFinished()) { 522 return; 523 } 524 try { 525 InputConnection ic = getInputConnection(); 526 // Note we do NOT check isActive() here, because this is safe 527 // for an IME to call at any time, and we need to allow it 528 // through to clean up our state after the IME has switched to 529 // another client. 530 if (ic == null) { 531 return; 532 } 533 @MissingMethodFlags 534 final int missingMethods = InputConnectionInspector.getMissingMethodFlags(ic); 535 if ((missingMethods & MissingMethodFlags.CLOSE_CONNECTION) == 0) { 536 ic.closeConnection(); 537 } 538 } finally { 539 synchronized (mLock) { 540 mInputConnection = null; 541 mFinished = true; 542 } 543 } 544 return; 545 } 546 case DO_COMMIT_CONTENT: { 547 final int flags = msg.arg1; 548 SomeArgs args = (SomeArgs) msg.obj; 549 try { 550 final IInputContextCallback callback = (IInputContextCallback) args.arg6; 551 final int callbackSeq = args.argi6; 552 InputConnection ic = getInputConnection(); 553 if (ic == null || !isActive()) { 554 Log.w(TAG, "commitContent on inactive InputConnection"); 555 callback.setCommitContentResult(false, callbackSeq); 556 return; 557 } 558 final InputContentInfo inputContentInfo = (InputContentInfo) args.arg1; 559 if (inputContentInfo == null || !inputContentInfo.validate()) { 560 Log.w(TAG, "commitContent with invalid inputContentInfo=" 561 + inputContentInfo); 562 callback.setCommitContentResult(false, callbackSeq); 563 return; 564 } 565 final boolean result = 566 ic.commitContent(inputContentInfo, flags, (Bundle) args.arg2); 567 callback.setCommitContentResult(result, callbackSeq); 568 } catch (RemoteException e) { 569 Log.w(TAG, "Got RemoteException calling commitContent", e); 570 } finally { 571 args.recycle(); 572 } 573 return; 574 } 575 } 576 Log.w(TAG, "Unhandled message code: " + msg.what); 577 } 578 obtainMessage(int what)579 Message obtainMessage(int what) { 580 return mH.obtainMessage(what); 581 } 582 obtainMessageII(int what, int arg1, int arg2)583 Message obtainMessageII(int what, int arg1, int arg2) { 584 return mH.obtainMessage(what, arg1, arg2); 585 } 586 obtainMessageO(int what, Object arg1)587 Message obtainMessageO(int what, Object arg1) { 588 return mH.obtainMessage(what, 0, 0, arg1); 589 } 590 obtainMessageISC(int what, int arg1, int callbackSeq, IInputContextCallback callback)591 Message obtainMessageISC(int what, int arg1, int callbackSeq, IInputContextCallback callback) { 592 final SomeArgs args = SomeArgs.obtain(); 593 args.arg6 = callback; 594 args.argi6 = callbackSeq; 595 return mH.obtainMessage(what, arg1, 0, args); 596 } 597 obtainMessageIISC(int what, int arg1, int arg2, int callbackSeq, IInputContextCallback callback)598 Message obtainMessageIISC(int what, int arg1, int arg2, int callbackSeq, 599 IInputContextCallback callback) { 600 final SomeArgs args = SomeArgs.obtain(); 601 args.arg6 = callback; 602 args.argi6 = callbackSeq; 603 return mH.obtainMessage(what, arg1, arg2, args); 604 } 605 obtainMessageIOOSC(int what, int arg1, Object objArg1, Object objArg2, int callbackSeq, IInputContextCallback callback)606 Message obtainMessageIOOSC(int what, int arg1, Object objArg1, Object objArg2, int callbackSeq, 607 IInputContextCallback callback) { 608 final SomeArgs args = SomeArgs.obtain(); 609 args.arg1 = objArg1; 610 args.arg2 = objArg2; 611 args.arg6 = callback; 612 args.argi6 = callbackSeq; 613 return mH.obtainMessage(what, arg1, 0, args); 614 } 615 obtainMessageIOSC(int what, int arg1, Object arg2, int callbackSeq, IInputContextCallback callback)616 Message obtainMessageIOSC(int what, int arg1, Object arg2, int callbackSeq, 617 IInputContextCallback callback) { 618 final SomeArgs args = SomeArgs.obtain(); 619 args.arg1 = arg2; 620 args.arg6 = callback; 621 args.argi6 = callbackSeq; 622 return mH.obtainMessage(what, arg1, 0, args); 623 } 624 obtainMessageIO(int what, int arg1, Object arg2)625 Message obtainMessageIO(int what, int arg1, Object arg2) { 626 return mH.obtainMessage(what, arg1, 0, arg2); 627 } 628 obtainMessageOO(int what, Object arg1, Object arg2)629 Message obtainMessageOO(int what, Object arg1, Object arg2) { 630 final SomeArgs args = SomeArgs.obtain(); 631 args.arg1 = arg1; 632 args.arg2 = arg2; 633 return mH.obtainMessage(what, 0, 0, args); 634 } 635 } 636