1. 程式人生 > >Android Instrumentation 模擬點選、拖拽、傳送keycode、焦點異常丟失。

Android Instrumentation 模擬點選、拖拽、傳送keycode、焦點異常丟失。

Instrumentation模擬點選,拖拽,向系統傳送keycode。

需要注意的幾點:

  1. Android系統座標系,X軸正方向為右,Y軸正方向為下(與數學座標系相反)
  2. 所有事件在傳送時均需要在Thread中執行,否則會報異常。
  3. 模擬輸入法種特殊符號時,需要帶上shift,同正常鍵盤操作。
public void simulateClick() {

        final float clickX = mPositionX + mHalfScreenWidth;
        final float clickY = mPositionY + mHalfScreenHeight;

        long
downTime = SystemClock.uptimeMillis(); inst.sendPointerSync(MotionEvent.obtain(downTime, downTime + 100, MotionEvent.ACTION_DOWN, clickX, clickY, 0)); inst.sendPointerSync(MotionEvent.obtain(downTime, downTime + 100, MotionEvent.ACTION_UP, clickX, clickY, 0)); }
 public void simulateTouch
(int event, float x, float y) { mPositionX += x; mPositionY += y; if (mPositionX > mHalfScreenWidth) { mPositionX = mHalfScreenWidth; } else if (mPositionX < (-mHalfScreenWidth)) { mPositionX = -mHalfScreenWidth; } if (mPositionY > mHalfScreenHeight) { mPositionY = mHalfScreenHeight; } else
if (mPositionY < (-mHalfScreenHeight)) { mPositionY = -mHalfScreenHeight; } float moveX = mPositionX + mHalfScreenWidth; float moveY = mPositionY + mHalfScreenHeight; long downTime = SystemClock.uptimeMillis(); MotionEvent motionEvent = MotionEvent.obtain(downTime, downTime + 100, event, moveX, moveY, 0); try { inst.sendPointerSync(motionEvent); } catch (Exception e) { e.printStackTrace(); Log.e(TAG, "Exception = " + e); } }
private static boolean simulateKeystroke(int KeyCode) {

        try {
            Instrumentation inst = new Instrumentation();

            if (shift) {
                inst.sendKeySync(new KeyEvent(0, 0, KeyEvent.ACTION_DOWN, KeyCode, 0, KeyEvent.META_SHIFT_ON));
                inst.sendKeySync(new KeyEvent(0, 0, KeyEvent.ACTION_UP, KeyCode, 0, KeyEvent.META_SHIFT_ON));
                //  shift = false;
            } else {
                inst.sendKeyDownUpSync(KeyCode);
            }

            return true;
        } catch (Exception e) {
            // TODO: handle exception
            return false;
        }
    }

Android 裝置啟動後,會預設為Touch模式。如果你做過Android TV開發,發現開機後launcher的焦點丟失,或者有異常情況。請參考如下程式碼。

   Instrumentation instrumentation = new Instrumentation();
        instrumentation.setInTouchMode(false);