10b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller/* 20b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Copyright (C) 2010 Google Inc. 30b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * 40b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Licensed under the Apache License, Version 2.0 (the "License"); you may not 50b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * use this file except in compliance with the License. You may obtain a copy of 60b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * the License at 70b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * 80b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * http://www.apache.org/licenses/LICENSE-2.0 90b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * 100b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Unless required by applicable law or agreed to in writing, software 110b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 120b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 130b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * License for the specific language governing permissions and limitations under 140b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * the License. 150b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller */ 160b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 170b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerpackage com.android.internal.widget; 180b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 190b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerimport java.util.Locale; 200b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerimport android.content.Context; 210b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerimport android.content.res.Resources; 220b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerimport android.content.res.XmlResourceParser; 230b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerimport android.graphics.drawable.Drawable; 240b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerimport android.inputmethodservice.Keyboard; 250b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerimport android.inputmethodservice.KeyboardView; 260b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerimport com.android.internal.R; 270b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 280b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller/** 290b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * A basic, embed-able keyboard designed for password entry. Allows entry of all Latin-1 characters. 300b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * 310b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * It has two modes: alpha and numeric. In alpha mode, it allows all Latin-1 characters and enables 320b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * an additional keyboard with symbols. In numeric mode, it shows a 12-key DTMF dialer-like 330b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * keypad with alpha characters hints. 340b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller */ 350b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Millerpublic class PasswordEntryKeyboard extends Keyboard { 360b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private static final int SHIFT_OFF = 0; 370b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private static final int SHIFT_ON = 1; 380b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private static final int SHIFT_LOCKED = 2; 390b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public static final int KEYCODE_SPACE = ' '; 400b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 410b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private Drawable mShiftIcon; 420b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private Drawable mShiftLockIcon; 436465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller 446465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller // These two arrays must be the same length 456465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller private Drawable[] mOldShiftIcons = { null, null }; 466465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller private Key[] mShiftKeys = { null, null }; 476465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller 480b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private Key mEnterKey; 490b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private Key mF1Key; 500b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private Key mSpaceKey; 510b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private int mShiftState = SHIFT_OFF; 520b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 530b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller static int sSpacebarVerticalCorrection; 540b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 550b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public PasswordEntryKeyboard(Context context, int xmlLayoutResId) { 560b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller this(context, xmlLayoutResId, 0); 570b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 580b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 598171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung public PasswordEntryKeyboard(Context context, int xmlLayoutResId, int width, int height) { 608171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung this(context, xmlLayoutResId, 0, width, height); 618171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung } 628171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung 630b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public PasswordEntryKeyboard(Context context, int xmlLayoutResId, int mode) { 640b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller super(context, xmlLayoutResId, mode); 658171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung init(context); 668171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung } 678171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung 688171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung public PasswordEntryKeyboard(Context context, int xmlLayoutResId, int mode, 698171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung int width, int height) { 708171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung super(context, xmlLayoutResId, mode, width, height); 718171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung init(context); 728171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung } 738171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung 748171b5182f5f07d33c9dfdf2dd8f0f6ae9588039Jae Yong Sung private void init(Context context) { 750b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller final Resources res = context.getResources(); 760b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mShiftIcon = res.getDrawable(R.drawable.sym_keyboard_shift); 770b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mShiftLockIcon = res.getDrawable(R.drawable.sym_keyboard_shift_locked); 780b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller sSpacebarVerticalCorrection = res.getDimensionPixelOffset( 790b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller R.dimen.password_keyboard_spacebar_vertical_correction); 800b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 810b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 820b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public PasswordEntryKeyboard(Context context, int layoutTemplateResId, 830b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller CharSequence characters, int columns, int horizontalPadding) { 840b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller super(context, layoutTemplateResId, characters, columns, horizontalPadding); 850b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 860b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 870b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller @Override 880b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller protected Key createKeyFromXml(Resources res, Row parent, int x, int y, 890b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller XmlResourceParser parser) { 900b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller LatinKey key = new LatinKey(res, parent, x, y, parser); 910b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller final int code = key.codes[0]; 920b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (code >=0 && code != '\n' && (code < 32 || code > 127)) { 93ec52eedc2ceb623b503f6b82eb560c0e9a6e4619Jim Miller // Log.w(TAG, "Key code for " + key.label + " is not latin-1"); 940b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller key.label = " "; 950b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller key.setEnabled(false); 960b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 970b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller switch (key.codes[0]) { 980b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller case 10: 990b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey = key; 1000b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller break; 1010b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller case PasswordEntryKeyboardView.KEYCODE_F1: 1020b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mF1Key = key; 1030b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller break; 1040b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller case 32: 1050b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mSpaceKey = key; 1060b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller break; 1070b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1080b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller return key; 1090b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1100b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 1110b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller /** 1120b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Allows enter key resources to be overridden 1130b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * @param res resources to grab given items from 1140b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * @param previewId preview drawable shown on enter key 1150b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * @param iconId normal drawable shown on enter key 1160b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * @param labelId string shown on enter key 1170b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller */ 1180b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller void setEnterKeyResources(Resources res, int previewId, int iconId, int labelId) { 1190b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (mEnterKey != null) { 1200b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller // Reset some of the rarely used attributes. 1210b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.popupCharacters = null; 1220b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.popupResId = 0; 1230b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.text = null; 1240b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 1250b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.iconPreview = res.getDrawable(previewId); 1260b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.icon = res.getDrawable(iconId); 1270b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.label = res.getText(labelId); 1280b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 1290b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller // Set the initial size of the preview icon 1300b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (mEnterKey.iconPreview != null) { 1310b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.iconPreview.setBounds(0, 0, 1320b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.iconPreview.getIntrinsicWidth(), 1330b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnterKey.iconPreview.getIntrinsicHeight()); 1340b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1350b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1360b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1370b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 1380b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller /** 1390b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Allows shiftlock to be turned on. See {@link #setShiftLocked(boolean)} 1400b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * 1410b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller */ 1420b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller void enableShiftLock() { 1436465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller int i = 0; 1446465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller for (int index : getShiftKeyIndices()) { 1456465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller if (index >= 0 && i < mShiftKeys.length) { 1466465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mShiftKeys[i] = getKeys().get(index); 1476465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller if (mShiftKeys[i] instanceof LatinKey) { 1486465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller ((LatinKey)mShiftKeys[i]).enableShiftLock(); 1496465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller } 1506465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mOldShiftIcons[i] = mShiftKeys[i].icon; 1516465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller i++; 1520b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1530b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1540b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1550b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 1560b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller /** 1570b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Turn on shift lock. This turns on the LED for this key, if it has one. 1580b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * It should be followed by a call to {@link KeyboardView#invalidateKey(int)} 1590b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * or {@link KeyboardView#invalidateAllKeys()} 1600b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * 1610b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * @param shiftLocked 1620b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller */ 1630b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller void setShiftLocked(boolean shiftLocked) { 1646465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller for (Key shiftKey : mShiftKeys) { 1656465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller if (shiftKey != null) { 1666465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller shiftKey.on = shiftLocked; 1676465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller shiftKey.icon = mShiftLockIcon; 1680b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1690b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1706465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mShiftState = shiftLocked ? SHIFT_LOCKED : SHIFT_ON; 1710b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 1720b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 1730b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller /** 1740b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Turn on shift mode. Sets shift mode and turns on icon for shift key. 1750b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * It should be followed by a call to {@link KeyboardView#invalidateKey(int)} 1760b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * or {@link KeyboardView#invalidateAllKeys()} 1770b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * 1780b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * @param shiftLocked 1790b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller */ 1800b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller @Override 1810b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public boolean setShifted(boolean shiftState) { 1820b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller boolean shiftChanged = false; 1836465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller if (shiftState == false) { 1846465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller shiftChanged = mShiftState != SHIFT_OFF; 1856465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mShiftState = SHIFT_OFF; 1866465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller } else if (mShiftState == SHIFT_OFF) { 1876465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller shiftChanged = mShiftState == SHIFT_OFF; 1886465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mShiftState = SHIFT_ON; 1896465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller } 1906465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller for (int i = 0; i < mShiftKeys.length; i++) { 1916465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller if (mShiftKeys[i] != null) { 1926465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller if (shiftState == false) { 1936465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mShiftKeys[i].on = false; 1946465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mShiftKeys[i].icon = mOldShiftIcons[i]; 1956465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller } else if (mShiftState == SHIFT_OFF) { 1966465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mShiftKeys[i].on = false; 1976465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller mShiftKeys[i].icon = mShiftIcon; 1986465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller } 1996465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller } else { 2006465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller // return super.setShifted(shiftState); 2010b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2020b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2030b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller return shiftChanged; 2040b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2050b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 2060b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller /** 2070b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Whether or not keyboard is shifted. 2080b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * @return true if keyboard state is shifted. 2090b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller */ 2100b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller @Override 2110b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public boolean isShifted() { 2126465f7753783a614948fb3ffbd8c072345b4eea1Jim Miller if (mShiftKeys[0] != null) { 2130b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller return mShiftState != SHIFT_OFF; 2140b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } else { 2150b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller return super.isShifted(); 2160b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2170b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2180b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 2190b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller static class LatinKey extends Keyboard.Key { 2200b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private boolean mShiftLockEnabled; 2210b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller private boolean mEnabled = true; 2220b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 2230b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public LatinKey(Resources res, Keyboard.Row parent, int x, int y, 2240b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller XmlResourceParser parser) { 2250b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller super(res, parent, x, y, parser); 2260b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (popupCharacters != null && popupCharacters.length() == 0) { 2270b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller // If there is a keyboard with no keys specified in popupCharacters 2280b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller popupResId = 0; 2290b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2300b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2310b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 2320b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller void setEnabled(boolean enabled) { 2330b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mEnabled = enabled; 2340b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2350b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 2360b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller void enableShiftLock() { 2370b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller mShiftLockEnabled = true; 2380b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2390b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 2400b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller @Override 2410b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public void onReleased(boolean inside) { 2420b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (!mShiftLockEnabled) { 2430b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller super.onReleased(inside); 2440b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } else { 2450b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller pressed = !pressed; 2460b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2470b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2480b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller 2490b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller /** 2500b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller * Overriding this method so that we can reduce the target area for certain keys. 2510b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller */ 2520b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller @Override 2530b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller public boolean isInside(int x, int y) { 2540b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (!mEnabled) { 2550b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller return false; 2560b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2570b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller final int code = codes[0]; 2580b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (code == KEYCODE_SHIFT || code == KEYCODE_DELETE) { 2590b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller y -= height / 10; 2600b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (code == KEYCODE_SHIFT) x += width / 6; 2610b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller if (code == KEYCODE_DELETE) x -= width / 6; 2620b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } else if (code == KEYCODE_SPACE) { 2630b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller y += PasswordEntryKeyboard.sSpacebarVerticalCorrection; 2640b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2650b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller return super.isInside(x, y); 2660b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2670b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller } 2680b31970cac04259a6e20dfc6d6e42cd9532528e3Jim Miller} 269