2011-12-22 2 views
7

Android에서 가상 키보드 높이를 감지하려고합니다.Android에서 포인터 이벤트를 보내는 방법

내가 그것을 얻을 수있는 방법을 발견 : 저자가 높이를 감지 할 수있는 방법을 찾을 것 같다 Get the height of virtual keyboard in Android

:

나는 유사한 주제를 발견했다. 가상 키보드를 열어달라고 요청한 후 내가 생성 한 포인터 이벤트를 보냅니다. 그들의 y 좌표는 높이에서 시작하여 장치의 높이가 감소합니다.

나는 그 방법을 모르겠다.

답변

3

난 당신이 게시 된 링크에서 제공되는 코드를 사용할 것입니다 :

// Declare Variables 

int softkeyboard_height = 0; 
boolean calculated_keyboard_height; 
Instrumentation instrumentation; 

// Initialize instrumentation sometime before starting the thread 
instrumentation = new Instrumentation(); 

mainScreenView는 기준 뷰, 활동의 견해이다. m (ACTION_DOWN) 및 m1 (ACTION_UP)은 Instrumentation#sendPointerSync(MotionEvent)을 사용하여 전달되는 터치 이벤트입니다.

이 java.lang.SecurityException : 논리는 MotionEvent가 표시되고 키보드가 SecurityException 다음을 유발하는 곳으로 파견한다는 것입니다 다른 응용 프로그램으로 주입하는 것은

그래서, 우리가 시작 INJECT_EVENTS 권한이 필요합니다 화면의 하단에있는 루프를 반복 할 때마다 (y을 감소시킴으로써) 길을 만듭니다. 특정 횟수의 반복에 대해 SecurityException을 얻게 될 것입니다. 이는 키보드를 통해 MotionEvent가 발생하고 있음을 의미합니다. 순간 y는 충분히 작은 얻는다 (때의 바로 키보드 위), 우리는 루프의 탈옥 및 사용하여 키보드의 높이를 계산합니다 :

softkeyboard_height = mainScreenView.getHeight() - y; 

코드 :

Thread t = new Thread(){ 
     public void run() { 
      int y = mainScreenView.getHeight()-2; 
      int x = 10; 
      int counter = 0; 
      int height = y; 
      while (true){ 
       final MotionEvent m = MotionEvent.obtain(
         SystemClock.uptimeMillis(), 
         SystemClock.uptimeMillis(), 
         MotionEvent.ACTION_DOWN, 
         x, 
         y, 
         1); 
       final MotionEvent m1 = MotionEvent.obtain(
         SystemClock.uptimeMillis(), 
         SystemClock.uptimeMillis(), 
         MotionEvent.ACTION_UP, 
         x, 
         y, 
         1); 
       boolean pointer_on_softkeyboard = false; 
       try { 
        instrumentation.sendPointerSync(m); 
        instrumentation.sendPointerSync(m1); 
       } catch (SecurityException e) { 
        pointer_on_softkeyboard = true; 
       } 
       if (!pointer_on_softkeyboard){ 
        if (y == height){ 
         if (counter++ < 100){ 
          Thread.yield(); 
          continue; 
         } 
        } else if (y > 0){ 
         softkeyboard_height = mainScreenView.getHeight() - y; 
         Log.i("", "Soft Keyboard's height is: " + softkeyboard_height); 
        } 
        break; 
       } 
       y--; 

      } 
      if (softkeyboard_height > 0){ 
       // it is calculated and saved in softkeyboard_height 
      } else { 
       calculated_keyboard_height = false; 
      } 
     } 
    }; 
    t.start(); 

Instrumentation#sendPointerSync(MotionEvent) :

포인터 이벤트를 전달하십시오. 수신자 이 이벤트 처리에서 복귀 한 후 어느 시점에서 완료되었지만 이 이벤트에서 완전히 반응을 나타내지 않을 수 있습니다 (예 : 이 결과로 디스플레이를 업데이트해야하는 경우). 그 일을하는 과정은 입니다.

+0

공개 API입니까? INTERNAL_POINTER_META_STATE에 대한 설명서를 찾을 수 없습니다. – rid

+0

@rid 죄송합니다. INTERNAL_POINTER_META_STATE는 정수 상수입니다. 질문의 목적을 위해, 정수 값을 사용하면 효과가 있습니다. 위의 코드를 편집했습니다. 그것을 지적 주셔서 감사합니다. – Vikram

+0

Android의 향후 버전에서 기능이 사라지지 않으면이 기능을 사용해도 안전한가요? 그 '1'은 항상 동일하게 보장됩니까? Google이 공식적으로 문서화 한 곳인가요? 취성 코드 생성에 대한 두려움없이 이것을 의지 할 수 있습니까? – rid

1

OnGlobalLayoutListener를 사용하면 완벽하게 작동합니다.

관련 문제