From 358e485b14938fbcb5af5be75aa29f2b73674100 Mon Sep 17 00:00:00 2001 From: Amith Yamasani Date: Thu, 22 Oct 2009 14:51:39 -0700 Subject: [PATCH] Experimental Extension keyboard Slide up on keyboard to get an extended keyboard for numbers and punctuations. This is work in progress... --- res/xml/kbd_extension.xml | 61 +++++++++ .../inputmethod/latin/KeyboardSwitcher.java | 7 ++ .../inputmethod/latin/LatinKeyboard.java | 10 ++ .../inputmethod/latin/LatinKeyboardView.java | 116 +++++++++++++++++- 4 files changed, 191 insertions(+), 3 deletions(-) create mode 100755 res/xml/kbd_extension.xml diff --git a/res/xml/kbd_extension.xml b/res/xml/kbd_extension.xml new file mode 100755 index 000000000..c64f666d0 --- /dev/null +++ b/res/xml/kbd_extension.xml @@ -0,0 +1,61 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/com/android/inputmethod/latin/KeyboardSwitcher.java b/src/com/android/inputmethod/latin/KeyboardSwitcher.java index c82587b71..c7f90946d 100644 --- a/src/com/android/inputmethod/latin/KeyboardSwitcher.java +++ b/src/com/android/inputmethod/latin/KeyboardSwitcher.java @@ -147,6 +147,13 @@ public class KeyboardSwitcher { if (!mKeyboards.containsKey(id)) { LatinKeyboard keyboard = new LatinKeyboard( mContext, id.mXml, id.mMode); + if (id.mMode == KEYBOARDMODE_NORMAL + || id.mMode == KEYBOARDMODE_URL + || id.mMode == KEYBOARDMODE_IM + || id.mMode == KEYBOARDMODE_EMAIL) { + keyboard.setExtension(R.xml.kbd_extension); + } + if (id.mEnableShiftLock) { keyboard.enableShiftLock(); } diff --git a/src/com/android/inputmethod/latin/LatinKeyboard.java b/src/com/android/inputmethod/latin/LatinKeyboard.java index 9b04aa264..e68e01ded 100644 --- a/src/com/android/inputmethod/latin/LatinKeyboard.java +++ b/src/com/android/inputmethod/latin/LatinKeyboard.java @@ -31,6 +31,8 @@ public class LatinKeyboard extends Keyboard { private Drawable mOldShiftPreviewIcon; private Key mShiftKey; private Key mEnterKey; + + private int mExtensionResId; private static final int SHIFT_OFF = 0; private static final int SHIFT_ON = 1; @@ -191,6 +193,14 @@ public class LatinKeyboard extends Keyboard { } } + public void setExtension(int resId) { + mExtensionResId = resId; + } + + public int getExtension() { + return mExtensionResId; + } + static class LatinKey extends Keyboard.Key { private boolean mShiftLockEnabled; diff --git a/src/com/android/inputmethod/latin/LatinKeyboardView.java b/src/com/android/inputmethod/latin/LatinKeyboardView.java index d9ff0aa8c..ecbd1adfb 100644 --- a/src/com/android/inputmethod/latin/LatinKeyboardView.java +++ b/src/com/android/inputmethod/latin/LatinKeyboardView.java @@ -16,6 +16,8 @@ package com.android.inputmethod.latin; +import java.util.List; + import android.content.Context; import android.graphics.Canvas; import android.inputmethodservice.Keyboard; @@ -25,9 +27,9 @@ import android.os.Handler; import android.os.Message; import android.os.SystemClock; import android.util.AttributeSet; +import android.view.LayoutInflater; import android.view.MotionEvent; - -import java.util.List; +import android.widget.PopupWindow; public class LatinKeyboardView extends KeyboardView { @@ -66,7 +68,115 @@ public class LatinKeyboardView extends KeyboardView { } } - + private boolean mExtensionVisible; + private LatinKeyboardView mExtension; + private PopupWindow mExtensionPopup; + private boolean mFirstEvent; + + @Override + public boolean onTouchEvent(MotionEvent me) { + if (((LatinKeyboard) getKeyboard()).getExtension() == 0) { + return super.onTouchEvent(me); + } + if (me.getY() < 0) { + if (mExtensionVisible) { + int action = me.getAction(); + if (mFirstEvent) action = MotionEvent.ACTION_DOWN; + mFirstEvent = false; + MotionEvent translated = MotionEvent.obtain(me.getEventTime(), me.getEventTime(), + action, + me.getX(), me.getY() + mExtension.getHeight(), me.getMetaState()); + boolean result = mExtension.onTouchEvent(translated); + translated.recycle(); + if (me.getAction() == MotionEvent.ACTION_UP + || me.getAction() == MotionEvent.ACTION_CANCEL) { + closeExtension(); + } + return result; + } else { + if (openExtension()) { + MotionEvent cancel = MotionEvent.obtain(me.getDownTime(), me.getEventTime(), + MotionEvent.ACTION_CANCEL, me.getX() - 100, me.getY() - 100, 0); + super.onTouchEvent(cancel); + cancel.recycle(); + if (mExtension.getHeight() > 0) { + MotionEvent translated = MotionEvent.obtain(me.getEventTime(), + me.getEventTime(), + MotionEvent.ACTION_DOWN, + me.getX(), me.getY() + mExtension.getHeight(), + me.getMetaState()); + mExtension.onTouchEvent(translated); + translated.recycle(); + } else { + mFirstEvent = true; + } + } + return true; + } + } else if (mExtensionVisible) { + closeExtension(); + // Send a down event into the main keyboard first + MotionEvent down = MotionEvent.obtain(me.getEventTime(), me.getEventTime(), + MotionEvent.ACTION_DOWN, + me.getX(), me.getY(), me.getMetaState()); + super.onTouchEvent(down); + down.recycle(); + // Send the actual event + return super.onTouchEvent(me); + } else { + return super.onTouchEvent(me); + } + } + + private boolean openExtension() { + if (((LatinKeyboard) getKeyboard()).getExtension() == 0) return false; + makePopupWindow(); + mExtensionVisible = true; + return true; + } + + private void makePopupWindow() { + if (mExtensionPopup == null) { + int[] windowLocation = new int[2]; + mExtensionPopup = new PopupWindow(getContext()); + mExtensionPopup.setBackgroundDrawable(null); + LayoutInflater li = (LayoutInflater) getContext().getSystemService( + Context.LAYOUT_INFLATER_SERVICE); + mExtension = (LatinKeyboardView) li.inflate(R.layout.input, null); + mExtension.setOnKeyboardActionListener((LatinIME) getContext()); + mExtension.setPopupParent(this); + mExtension.setPopupOffset(0, -windowLocation[1]); + Keyboard keyboard; + mExtension.setKeyboard(keyboard = new LatinKeyboard(getContext(), + ((LatinKeyboard) getKeyboard()).getExtension())); + mExtensionPopup.setContentView(mExtension); + mExtensionPopup.setWidth(getWidth()); + mExtensionPopup.setHeight(keyboard.getHeight()); + getLocationInWindow(windowLocation); + // TODO: Fix the "- 30". + mExtension.setPopupOffset(0, -windowLocation[1] - 30); + mExtensionPopup.showAtLocation(this, 0, 0, -keyboard.getHeight() + + windowLocation[1]); + } else { + mExtension.setVisibility(VISIBLE); + } + } + + @Override + public void closing() { + super.closing(); + if (mExtensionPopup != null && mExtensionPopup.isShowing()) { + mExtensionPopup.dismiss(); + mExtensionPopup = null; + } + } + + private void closeExtension() { + mExtension.setVisibility(INVISIBLE); + mExtension.closing(); + mExtensionVisible = false; + } + /**************************** INSTRUMENTATION *******************************/ static final boolean DEBUG_AUTO_PLAY = false;