Merge "Get rid of key index from ProxymityInfo"
This commit is contained in:
commit
510ebb9b16
4 changed files with 38 additions and 44 deletions
|
@ -19,14 +19,12 @@ package com.android.inputmethod.keyboard;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
public class KeyDetector {
|
public class KeyDetector {
|
||||||
private static final String TAG = KeyDetector.class.getSimpleName();
|
private static final String TAG = KeyDetector.class.getSimpleName();
|
||||||
private static final boolean DEBUG = false;
|
private static final boolean DEBUG = false;
|
||||||
|
|
||||||
public static final int NOT_A_CODE = -1;
|
public static final int NOT_A_CODE = -1;
|
||||||
private static final int NOT_A_KEY = -1;
|
|
||||||
|
|
||||||
private final int mKeyHysteresisDistanceSquared;
|
private final int mKeyHysteresisDistanceSquared;
|
||||||
|
|
||||||
|
@ -39,7 +37,7 @@ public class KeyDetector {
|
||||||
// working area
|
// working area
|
||||||
private static final int MAX_NEARBY_KEYS = 12;
|
private static final int MAX_NEARBY_KEYS = 12;
|
||||||
private final int[] mDistances = new int[MAX_NEARBY_KEYS];
|
private final int[] mDistances = new int[MAX_NEARBY_KEYS];
|
||||||
private final int[] mIndices = new int[MAX_NEARBY_KEYS];
|
private final Key[] mNeighborKeys = new Key[MAX_NEARBY_KEYS];
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This class handles key detection.
|
* This class handles key detection.
|
||||||
|
@ -122,7 +120,7 @@ public class KeyDetector {
|
||||||
|
|
||||||
private void initializeNearbyKeys() {
|
private void initializeNearbyKeys() {
|
||||||
Arrays.fill(mDistances, Integer.MAX_VALUE);
|
Arrays.fill(mDistances, Integer.MAX_VALUE);
|
||||||
Arrays.fill(mIndices, NOT_A_KEY);
|
Arrays.fill(mNeighborKeys, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -130,14 +128,14 @@ public class KeyDetector {
|
||||||
* If the distance of two keys are the same, the key which the point is on should be considered
|
* If the distance of two keys are the same, the key which the point is on should be considered
|
||||||
* as a closer one.
|
* as a closer one.
|
||||||
*
|
*
|
||||||
* @param keyIndex index of the key.
|
* @param key the key to be inserted into the nearby keys buffer.
|
||||||
* @param distance distance between the key's edge and user touched point.
|
* @param distance distance between the key's edge and user touched point.
|
||||||
* @param isOnKey true if the point is on the key.
|
* @param isOnKey true if the point is on the key.
|
||||||
* @return order of the key in the nearby buffer, 0 if it is the nearest key.
|
* @return order of the key in the nearby buffer, 0 if it is the nearest key.
|
||||||
*/
|
*/
|
||||||
private int sortNearbyKeys(int keyIndex, int distance, boolean isOnKey) {
|
private int sortNearbyKeys(Key key, int distance, boolean isOnKey) {
|
||||||
final int[] distances = mDistances;
|
final int[] distances = mDistances;
|
||||||
final int[] indices = mIndices;
|
final Key[] neighborKeys = mNeighborKeys;
|
||||||
for (int insertPos = 0; insertPos < distances.length; insertPos++) {
|
for (int insertPos = 0; insertPos < distances.length; insertPos++) {
|
||||||
final int comparingDistance = distances[insertPos];
|
final int comparingDistance = distances[insertPos];
|
||||||
if (distance < comparingDistance || (distance == comparingDistance && isOnKey)) {
|
if (distance < comparingDistance || (distance == comparingDistance && isOnKey)) {
|
||||||
|
@ -145,11 +143,11 @@ public class KeyDetector {
|
||||||
if (nextPos < distances.length) {
|
if (nextPos < distances.length) {
|
||||||
System.arraycopy(distances, insertPos, distances, nextPos,
|
System.arraycopy(distances, insertPos, distances, nextPos,
|
||||||
distances.length - nextPos);
|
distances.length - nextPos);
|
||||||
System.arraycopy(indices, insertPos, indices, nextPos,
|
System.arraycopy(neighborKeys, insertPos, neighborKeys, nextPos,
|
||||||
indices.length - nextPos);
|
neighborKeys.length - nextPos);
|
||||||
}
|
}
|
||||||
distances[insertPos] = distance;
|
distances[insertPos] = distance;
|
||||||
indices[insertPos] = keyIndex;
|
neighborKeys[insertPos] = key;
|
||||||
return insertPos;
|
return insertPos;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -157,21 +155,20 @@ public class KeyDetector {
|
||||||
}
|
}
|
||||||
|
|
||||||
private void getNearbyKeyCodes(final int[] allCodes) {
|
private void getNearbyKeyCodes(final int[] allCodes) {
|
||||||
final List<Key> keys = getKeyboard().mKeys;
|
final Key[] neighborKeys = mNeighborKeys;
|
||||||
final int[] indices = mIndices;
|
|
||||||
|
|
||||||
// allCodes[0] should always have the key code even if it is a non-letter key.
|
// allCodes[0] should always have the key code even if it is a non-letter key.
|
||||||
if (indices[0] == NOT_A_KEY) {
|
if (neighborKeys[0] == null) {
|
||||||
allCodes[0] = NOT_A_CODE;
|
allCodes[0] = NOT_A_CODE;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
int numCodes = 0;
|
int numCodes = 0;
|
||||||
for (int j = 0; j < indices.length && numCodes < allCodes.length; j++) {
|
for (int j = 0; j < neighborKeys.length && numCodes < allCodes.length; j++) {
|
||||||
final int index = indices[j];
|
final Key key = neighborKeys[j];
|
||||||
if (index == NOT_A_KEY)
|
if (key == null)
|
||||||
break;
|
break;
|
||||||
final int code = keys.get(index).mCode;
|
final int code = key.mCode;
|
||||||
// filter out a non-letter key from nearby keys
|
// filter out a non-letter key from nearby keys
|
||||||
if (code < Keyboard.CODE_SPACE)
|
if (code < Keyboard.CODE_SPACE)
|
||||||
continue;
|
continue;
|
||||||
|
@ -191,18 +188,16 @@ public class KeyDetector {
|
||||||
* @return The nearest key
|
* @return The nearest key
|
||||||
*/
|
*/
|
||||||
public Key getKeyAndNearbyCodes(int x, int y, final int[] allCodes) {
|
public Key getKeyAndNearbyCodes(int x, int y, final int[] allCodes) {
|
||||||
final List<Key> keys = getKeyboard().mKeys;
|
|
||||||
final int touchX = getTouchX(x);
|
final int touchX = getTouchX(x);
|
||||||
final int touchY = getTouchY(y);
|
final int touchY = getTouchY(y);
|
||||||
|
|
||||||
initializeNearbyKeys();
|
initializeNearbyKeys();
|
||||||
Key primaryKey = null;
|
Key primaryKey = null;
|
||||||
for (final int index : mKeyboard.getNearestKeys(touchX, touchY)) {
|
for (final Key key: mKeyboard.getNearestKeys(touchX, touchY)) {
|
||||||
final Key key = keys.get(index);
|
|
||||||
final boolean isOnKey = key.isOnKey(touchX, touchY);
|
final boolean isOnKey = key.isOnKey(touchX, touchY);
|
||||||
final int distance = key.squaredDistanceToEdge(touchX, touchY);
|
final int distance = key.squaredDistanceToEdge(touchX, touchY);
|
||||||
if (isOnKey || (mProximityCorrectOn && distance < mProximityThresholdSquare)) {
|
if (isOnKey || (mProximityCorrectOn && distance < mProximityThresholdSquare)) {
|
||||||
final int insertedPosition = sortNearbyKeys(index, distance, isOnKey);
|
final int insertedPosition = sortNearbyKeys(key, distance, isOnKey);
|
||||||
if (insertedPosition == 0 && isOnKey) {
|
if (insertedPosition == 0 && isOnKey) {
|
||||||
primaryKey = key;
|
primaryKey = key;
|
||||||
}
|
}
|
||||||
|
|
|
@ -225,13 +225,13 @@ public class Keyboard {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the indices of the keys that are closest to the given point.
|
* Returns the array of the keys that are closest to the given point.
|
||||||
* @param x the x-coordinate of the point
|
* @param x the x-coordinate of the point
|
||||||
* @param y the y-coordinate of the point
|
* @param y the y-coordinate of the point
|
||||||
* @return the array of integer indices for the nearest keys to the given point. If the given
|
* @return the array of the nearest keys to the given point. If the given
|
||||||
* point is out of range, then an array of size zero is returned.
|
* point is out of range, then an array of size zero is returned.
|
||||||
*/
|
*/
|
||||||
public int[] getNearestKeys(int x, int y) {
|
public Key[] getNearestKeys(int x, int y) {
|
||||||
return mProximityInfo.getNearestKeys(x, y);
|
return mProximityInfo.getNearestKeys(x, y);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -106,8 +106,8 @@ public class LatinKeyboard extends Keyboard {
|
||||||
}
|
}
|
||||||
|
|
||||||
private static class LatinKeyboardParams extends KeyboardParams {
|
private static class LatinKeyboardParams extends KeyboardParams {
|
||||||
public Key mSpaceKey = null;
|
Key mSpaceKey = null;
|
||||||
public Key mShortcutKey = null;
|
Key mShortcutKey = null;
|
||||||
|
|
||||||
LatinKeyboardParams() {}
|
LatinKeyboardParams() {}
|
||||||
|
|
||||||
|
@ -323,7 +323,7 @@ public class LatinKeyboard extends Keyboard {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int[] getNearestKeys(int x, int y) {
|
public Key[] getNearestKeys(int x, int y) {
|
||||||
// Avoid dead pixels at edges of the keyboard
|
// Avoid dead pixels at edges of the keyboard
|
||||||
return super.getNearestKeys(Math.max(0, Math.min(x, mOccupiedWidth - 1)),
|
return super.getNearestKeys(Math.max(0, Math.min(x, mOccupiedWidth - 1)),
|
||||||
Math.max(0, Math.min(y, mOccupiedHeight - 1)));
|
Math.max(0, Math.min(y, mOccupiedHeight - 1)));
|
||||||
|
|
|
@ -30,7 +30,7 @@ public class ProximityInfo {
|
||||||
public static final int MAX_PROXIMITY_CHARS_SIZE = 16;
|
public static final int MAX_PROXIMITY_CHARS_SIZE = 16;
|
||||||
/** Number of key widths from current touch point to search for nearest keys. */
|
/** Number of key widths from current touch point to search for nearest keys. */
|
||||||
private static float SEARCH_DISTANCE = 1.2f;
|
private static float SEARCH_DISTANCE = 1.2f;
|
||||||
private static final int[] EMPTY_INT_ARRAY = new int[0];
|
private static final Key[] EMPTY_KEY_ARRAY = new Key[0];
|
||||||
|
|
||||||
private final int mKeyHeight;
|
private final int mKeyHeight;
|
||||||
private final int mGridWidth;
|
private final int mGridWidth;
|
||||||
|
@ -41,7 +41,7 @@ public class ProximityInfo {
|
||||||
// TODO: Find a proper name for mKeyboardMinWidth
|
// TODO: Find a proper name for mKeyboardMinWidth
|
||||||
private final int mKeyboardMinWidth;
|
private final int mKeyboardMinWidth;
|
||||||
private final int mKeyboardHeight;
|
private final int mKeyboardHeight;
|
||||||
private final int[][] mGridNeighbors;
|
private final Key[][] mGridNeighbors;
|
||||||
|
|
||||||
ProximityInfo(int gridWidth, int gridHeight, int minWidth, int height, int keyWidth,
|
ProximityInfo(int gridWidth, int gridHeight, int minWidth, int height, int keyWidth,
|
||||||
int keyHeight, List<Key> keys, TouchPositionCorrection touchPositionCorrection) {
|
int keyHeight, List<Key> keys, TouchPositionCorrection touchPositionCorrection) {
|
||||||
|
@ -53,7 +53,7 @@ public class ProximityInfo {
|
||||||
mKeyboardMinWidth = minWidth;
|
mKeyboardMinWidth = minWidth;
|
||||||
mKeyboardHeight = height;
|
mKeyboardHeight = height;
|
||||||
mKeyHeight = keyHeight;
|
mKeyHeight = keyHeight;
|
||||||
mGridNeighbors = new int[mGridSize][];
|
mGridNeighbors = new Key[mGridSize][];
|
||||||
if (minWidth == 0 || height == 0) {
|
if (minWidth == 0 || height == 0) {
|
||||||
// No proximity required. Keyboard might be mini keyboard.
|
// No proximity required. Keyboard might be mini keyboard.
|
||||||
return;
|
return;
|
||||||
|
@ -86,16 +86,16 @@ public class ProximityInfo {
|
||||||
float[] sweetSpotCenterX, float[] sweetSpotCenterY, float[] sweetSpotRadii);
|
float[] sweetSpotCenterX, float[] sweetSpotCenterY, float[] sweetSpotRadii);
|
||||||
private native void releaseProximityInfoNative(long nativeProximityInfo);
|
private native void releaseProximityInfoNative(long nativeProximityInfo);
|
||||||
|
|
||||||
private final void setProximityInfo(int[][] gridNeighborKeyIndexes, int keyboardWidth,
|
private final void setProximityInfo(Key[][] gridNeighborKeys, int keyboardWidth,
|
||||||
int keyboardHeight, List<Key> keys,
|
int keyboardHeight, List<Key> keys,
|
||||||
TouchPositionCorrection touchPositionCorrection) {
|
TouchPositionCorrection touchPositionCorrection) {
|
||||||
int[] proximityCharsArray = new int[mGridSize * MAX_PROXIMITY_CHARS_SIZE];
|
int[] proximityCharsArray = new int[mGridSize * MAX_PROXIMITY_CHARS_SIZE];
|
||||||
Arrays.fill(proximityCharsArray, KeyDetector.NOT_A_CODE);
|
Arrays.fill(proximityCharsArray, KeyDetector.NOT_A_CODE);
|
||||||
for (int i = 0; i < mGridSize; ++i) {
|
for (int i = 0; i < mGridSize; ++i) {
|
||||||
final int proximityCharsLength = gridNeighborKeyIndexes[i].length;
|
final int proximityCharsLength = gridNeighborKeys[i].length;
|
||||||
for (int j = 0; j < proximityCharsLength; ++j) {
|
for (int j = 0; j < proximityCharsLength; ++j) {
|
||||||
proximityCharsArray[i * MAX_PROXIMITY_CHARS_SIZE + j] =
|
proximityCharsArray[i * MAX_PROXIMITY_CHARS_SIZE + j] =
|
||||||
keys.get(gridNeighborKeyIndexes[i][j]).mCode;
|
gridNeighborKeys[i][j].mCode;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
final int keyCount = keys.size();
|
final int keyCount = keys.size();
|
||||||
|
@ -171,7 +171,7 @@ public class ProximityInfo {
|
||||||
final int thresholdBase = (int) (defaultWidth * SEARCH_DISTANCE);
|
final int thresholdBase = (int) (defaultWidth * SEARCH_DISTANCE);
|
||||||
final int threshold = thresholdBase * thresholdBase;
|
final int threshold = thresholdBase * thresholdBase;
|
||||||
// Round-up so we don't have any pixels outside the grid
|
// Round-up so we don't have any pixels outside the grid
|
||||||
final int[] indices = new int[keys.size()];
|
final Key[] neighborKeys = new Key[keys.size()];
|
||||||
final int gridWidth = mGridWidth * mCellWidth;
|
final int gridWidth = mGridWidth * mCellWidth;
|
||||||
final int gridHeight = mGridHeight * mCellHeight;
|
final int gridHeight = mGridHeight * mCellHeight;
|
||||||
for (int x = 0; x < gridWidth; x += mCellWidth) {
|
for (int x = 0; x < gridWidth; x += mCellWidth) {
|
||||||
|
@ -179,24 +179,23 @@ public class ProximityInfo {
|
||||||
final int centerX = x + mCellWidth / 2;
|
final int centerX = x + mCellWidth / 2;
|
||||||
final int centerY = y + mCellHeight / 2;
|
final int centerY = y + mCellHeight / 2;
|
||||||
int count = 0;
|
int count = 0;
|
||||||
for (int i = 0; i < keys.size(); i++) {
|
for (final Key key : keys) {
|
||||||
final Key key = keys.get(i);
|
|
||||||
if (key.isSpacer()) continue;
|
if (key.isSpacer()) continue;
|
||||||
if (key.squaredDistanceToEdge(centerX, centerY) < threshold)
|
if (key.squaredDistanceToEdge(centerX, centerY) < threshold) {
|
||||||
indices[count++] = i;
|
neighborKeys[count++] = key;
|
||||||
}
|
}
|
||||||
final int[] cell = new int[count];
|
}
|
||||||
System.arraycopy(indices, 0, cell, 0, count);
|
mGridNeighbors[(y / mCellHeight) * mGridWidth + (x / mCellWidth)] =
|
||||||
mGridNeighbors[(y / mCellHeight) * mGridWidth + (x / mCellWidth)] = cell;
|
Arrays.copyOfRange(neighborKeys, 0, count);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
setProximityInfo(mGridNeighbors, mKeyboardMinWidth, mKeyboardHeight, keys,
|
setProximityInfo(mGridNeighbors, mKeyboardMinWidth, mKeyboardHeight, keys,
|
||||||
touchPositionCorrection);
|
touchPositionCorrection);
|
||||||
}
|
}
|
||||||
|
|
||||||
public int[] getNearestKeys(int x, int y) {
|
public Key[] getNearestKeys(int x, int y) {
|
||||||
if (mGridNeighbors == null) {
|
if (mGridNeighbors == null) {
|
||||||
return EMPTY_INT_ARRAY;
|
return EMPTY_KEY_ARRAY;
|
||||||
}
|
}
|
||||||
if (x >= 0 && x < mKeyboardMinWidth && y >= 0 && y < mKeyboardHeight) {
|
if (x >= 0 && x < mKeyboardMinWidth && y >= 0 && y < mKeyboardHeight) {
|
||||||
int index = (y / mCellHeight) * mGridWidth + (x / mCellWidth);
|
int index = (y / mCellHeight) * mGridWidth + (x / mCellWidth);
|
||||||
|
@ -204,6 +203,6 @@ public class ProximityInfo {
|
||||||
return mGridNeighbors[index];
|
return mGridNeighbors[index];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return EMPTY_INT_ARRAY;
|
return EMPTY_KEY_ARRAY;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue