From c2badb0447accaa39e4f7b3d8ebb43601f2f5d8f Mon Sep 17 00:00:00 2001 From: Luke Shumaker Date: Wed, 7 May 2014 02:30:27 -0400 Subject: Start implementing modifiers, for a great reduction in code size. --- res/values/strings.xml | 4 +- src/us/minak/IMEGestureOverlayView.java | 74 ++++++++++++++--------- src/us/minak/IMEModifier.java | 23 ++------ src/us/minak/IMEModifierCircle.java | 37 ------------ src/us/minak/IMEModifiers.java | 55 +++++++++++------ src/us/minak/IMEService.java | 40 +------------ src/us/minak/IMEView.java | 88 +++------------------------- src/us/minak/InputConnectionGetter.java | 14 +++++ src/us/minak/OnBackspacePressedListener.java | 26 -------- src/us/minak/StringReciever.java | 5 -- 10 files changed, 115 insertions(+), 251 deletions(-) delete mode 100644 src/us/minak/IMEModifierCircle.java create mode 100644 src/us/minak/InputConnectionGetter.java delete mode 100644 src/us/minak/OnBackspacePressedListener.java delete mode 100644 src/us/minak/StringReciever.java diff --git a/res/values/strings.xml b/res/values/strings.xml index d3352bc..60803b0 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -36,9 +36,7 @@ Could not load %s. Make sure you have storage available. - - Shift + - Space diff --git a/src/us/minak/IMEGestureOverlayView.java b/src/us/minak/IMEGestureOverlayView.java index 37724b9..4cfc4b5 100644 --- a/src/us/minak/IMEGestureOverlayView.java +++ b/src/us/minak/IMEGestureOverlayView.java @@ -1,20 +1,5 @@ -/* - ******************************************************************************** - * Copyright (c) 2012 Samsung Electronics, Inc. - * All rights reserved. - * - * This software is a confidential and proprietary information of Samsung - * Electronics, Inc. ("Confidential Information"). You shall not disclose such - * Confidential Information and shall use it only in accordance with the terms - * of the license agreement you entered into with Samsung Electronics. - ******************************************************************************** - */ - package us.minak; -import java.util.LinkedList; -import java.util.List; - import android.content.Context; import android.gesture.Gesture; import android.gesture.GestureLibrary; @@ -23,16 +8,18 @@ import android.gesture.GestureOverlayView.OnGesturePerformedListener; import android.gesture.Prediction; import android.graphics.Canvas; import android.util.AttributeSet; +import android.view.KeyEvent; +import android.view.MotionEvent; +import android.view.inputmethod.InputConnection; + +import java.util.List; -/** - * Represent a space where drawing gestures are performed. - */ public class IMEGestureOverlayView extends GestureOverlayView implements OnGesturePerformedListener { private static final double SCORE_TRESHOLD = 3.0; private final GestureLibrary mGestureLibrary; - private StringReciever mOnGestureRecognizedListener; - public List circles = new LinkedList(); + private InputConnectionGetter icGetter = new InputConnectionGetter.NullGetter(); private final IMEModifiers modifiers = new IMEModifiers(); + float x = -1, y = -1; public IMEGestureOverlayView(Context context, AttributeSet attrs) { super(context, attrs); @@ -41,10 +28,14 @@ public class IMEGestureOverlayView extends GestureOverlayView implements OnGestu addOnGesturePerformedListener(this); } - public void setOnGestureRecognizedListener(StringReciever onGestureRecognizedListener) { - mOnGestureRecognizedListener = onGestureRecognizedListener; + public void setInputConnectionGetter(InputConnectionGetter icGetter) { + this.icGetter = icGetter; } + /** + * This function is pretty strongly based on the code in + * Samsung's "Penboard" whitepaper. + */ @Override public void onGesturePerformed(GestureOverlayView overlay, Gesture gesture) { final List predictions = mGestureLibrary.recognize(gesture); @@ -52,13 +43,23 @@ public class IMEGestureOverlayView extends GestureOverlayView implements OnGestu if (!predictions.isEmpty()) { bestPrediction = predictions.get(0); } - if (mOnGestureRecognizedListener != null && bestPrediction != null) { - if (bestPrediction.score > SCORE_TRESHOLD) { - mOnGestureRecognizedListener.putString(bestPrediction.name); - } else { - clear(false); + + InputConnection ic = icGetter.getCurrentInputConnection(); + if (ic != null) { + if (bestPrediction != null) { + if (bestPrediction.score > SCORE_TRESHOLD) { + ic.commitText(bestPrediction.name, 1); + } else { + clear(false); + } + } + for (IMEModifier modifier : modifiers.getSelection()) { + ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_UP, modifier.keycode)); } } + modifiers.clearSelection(); + invalidate(); + x = y = -1; } @Override @@ -66,4 +67,23 @@ public class IMEGestureOverlayView extends GestureOverlayView implements OnGestu float d = Math.min(canvas.getWidth(), canvas.getHeight()); modifiers.draw(canvas, d/2, d/2, d*.47F); } + + @Override + public boolean onTouchEvent (MotionEvent event) { + if (x < 0 && y < 0 && event.getActionMasked() == MotionEvent.ACTION_DOWN) { + x = event.getX(); + y = event.getY(); + modifiers.setSelectionPoint(x, y); + invalidate(); + + InputConnection ic = icGetter.getCurrentInputConnection(); + if (ic != null) { + for (IMEModifier modifier : modifiers.getSelection()) { + ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN, modifier.keycode)); + } + return true; + } + } + return false; + } } diff --git a/src/us/minak/IMEModifier.java b/src/us/minak/IMEModifier.java index 6b5ee67..a3ea3fc 100644 --- a/src/us/minak/IMEModifier.java +++ b/src/us/minak/IMEModifier.java @@ -1,24 +1,11 @@ package us.minak; public class IMEModifier { - public static enum State { - ON, OFF, LOCK - } - - public State state; - private String value; - - public String getValue() { - //however we want to do return this - return this.value; - } - - public void setValue(String value) { - this.value = value; - } + public final String name; + public final int keycode; - IMEModifier(String value) { - this.value = value; - this.state = State.OFF; + public IMEModifier(String name, int keycode) { + this.name = name; + this.keycode = keycode; } } diff --git a/src/us/minak/IMEModifierCircle.java b/src/us/minak/IMEModifierCircle.java deleted file mode 100644 index 246036f..0000000 --- a/src/us/minak/IMEModifierCircle.java +++ /dev/null @@ -1,37 +0,0 @@ -package us.minak; - -/* - * Not sure if this should be drawable or what. - * - */ -public class IMEModifierCircle { - private IMEModifier metaExpression; - public float x; - public float y; - public float radius; - public int color; - public boolean expanded; - public int expansion; //the level of expansion (if multiple circles are expanded, this decides precidence) - - IMEModifierCircle(float x, float y, float radius, int color, IMEModifier metaExpr) { - this.setMetaExpression(metaExpr); - this.x = x; - this.y = y; - this.radius = radius; - this.color = color; - this.expanded = false; - this.expansion = 0; - } - - public boolean containsPoint(float x, float y) { - return Math.pow(x - this.x, 2) + Math.pow(y - this.y, 2) < Math.pow(this.radius, 2) ? true : false; - } - - public IMEModifier getMetaExpression() { - return metaExpression; - } - - public void setMetaExpression(IMEModifier metaExpr) { - this.metaExpression = metaExpr; - } -} diff --git a/src/us/minak/IMEModifiers.java b/src/us/minak/IMEModifiers.java index d4cc6d3..645ae4a 100644 --- a/src/us/minak/IMEModifiers.java +++ b/src/us/minak/IMEModifiers.java @@ -3,20 +3,30 @@ package us.minak; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; -import java.util.List; +import android.view.KeyEvent; import java.util.ArrayList; +import java.util.List; public class IMEModifiers { - private final String[] modifiers = { "shift", "ctrl", "alt" }; + // FIXME: hard-coded configuration + private final IMEModifier[] modifiers = { + new IMEModifier("Shift", KeyEvent.KEYCODE_SHIFT_LEFT), + new IMEModifier("Ctrl" , KeyEvent.KEYCODE_CTRL_LEFT ), + new IMEModifier("Alt" , KeyEvent.KEYCODE_ALT_LEFT )}; + + // Static drawing resources private final Paint colorPaint = new Paint(Paint.ANTI_ALIAS_FLAG); private final Paint textPaint = new Paint(Paint.ANTI_ALIAS_FLAG); + // Pre-calculated graphics stuff private float cx = 0; private float cy = 0; private double innerR = 0; private double outerR = 0; private double radEach = 0; + // The current state + ArrayList selected = new ArrayList(); public IMEModifiers() { textPaint.setColor(Color.BLACK); @@ -39,21 +49,23 @@ public class IMEModifiers { hsv[0] = (float)Math.toDegrees(rad); colorPaint.setColor(Color.HSVToColor(0x80, hsv)); - canvas.drawCircle( - (float)(cx+innerR*Math.cos(rad)), - (float)(cy+innerR*Math.sin(rad)), - (float)outerR, - colorPaint); - canvas.drawText( - modifiers[i], - (float)(cx+textR*Math.cos(rad)), - (float)(cy+textR*Math.sin(rad)), - textPaint); - } + if (selected.contains(modifiers[i])) { + canvas.drawRect(0, 0, canvas.getWidth(), canvas.getHeight(), colorPaint); + } else { + canvas.drawCircle((float)(cx+innerR*Math.cos(rad)), + (float)(cy+innerR*Math.sin(rad)), + (float)outerR, + colorPaint); + } + canvas.drawText(modifiers[i].name, + (float)(cx+textR*Math.cos(rad)), + (float)(cy+textR*Math.sin(rad)), + textPaint); + } } - public List getModifiersAtPoint(float x, float y) { - ArrayList ret = new ArrayList(); + public void setSelectionPoint(float x, float y) { + selected.clear(); double mx; double my; @@ -63,9 +75,16 @@ public class IMEModifiers { mx = cx+innerR*Math.cos(rad); my = cy+innerR*Math.sin(rad); - if (Math.sqrt(Math.pow(mx-x,2)+Math.pow(my-y, 2)) > outerR) - ret.add(modifiers[i]); + if (Math.sqrt(Math.pow(mx-x,2)+Math.pow(my-y, 2)) < outerR) + selected.add(modifiers[i]); } - return ret; + } + + public List getSelection() { + return selected; + } + + public void clearSelection() { + selected.clear(); } } diff --git a/src/us/minak/IMEService.java b/src/us/minak/IMEService.java index a0a9ece..f8a3660 100644 --- a/src/us/minak/IMEService.java +++ b/src/us/minak/IMEService.java @@ -1,52 +1,16 @@ -/* - ******************************************************************************** - * Copyright (c) 2012 Samsung Electronics, Inc. - * All rights reserved. - * - * This software is a confidential and proprietary information of Samsung - * Electronics, Inc. ("Confidential Information"). You shall not disclose such - * Confidential Information and shall use it only in accordance with the terms - * of the license agreement you entered into with Samsung Electronics. - ******************************************************************************** - */ - package us.minak; -import java.util.Queue; - import android.inputmethodservice.InputMethodService; import android.view.View; -import android.view.inputmethod.EditorInfo; /** * Represent the application input service. */ -public class IMEService extends InputMethodService { - private IMEView mIMEView; - +public class IMEService extends InputMethodService implements InputConnectionGetter { @Override public View onCreateInputView() { final IMEView minakView = (IMEView) getLayoutInflater().inflate(R.layout.ime, null); - - minakView.setOnCharacterEnteredListener(new StringReciever() { - @Override - public void putString(String character) { - getCurrentInputConnection().commitText(character, 1); - } - }); - - mIMEView = minakView; + minakView.setInputConnectionGetter(this); return minakView; } - - @Override - public void onStartInput(EditorInfo attribute, boolean restarting) { - if (mIMEView != null) { - final Queue symbolsQueue = mIMEView.getSymbolsQueue(); - while (!symbolsQueue.isEmpty()) { - final Character character = symbolsQueue.poll(); - getCurrentInputConnection().commitText(String.valueOf(character), 1); - } - } - } } diff --git a/src/us/minak/IMEView.java b/src/us/minak/IMEView.java index a992011..dd2fb69 100644 --- a/src/us/minak/IMEView.java +++ b/src/us/minak/IMEView.java @@ -1,54 +1,14 @@ -/* - ******************************************************************************** - * Copyright (c) 2012 Samsung Electronics, Inc. - * All rights reserved. - * - * This software is a confidential and proprietary information of Samsung - * Electronics, Inc. ("Confidential Information"). You shall not disclose such - * Confidential Information and shall use it only in accordance with the terms - * of the license agreement you entered into with Samsung Electronics. - ******************************************************************************** - */ - package us.minak; -import java.util.LinkedList; -import java.util.Queue; - import android.content.Context; import android.util.AttributeSet; -import android.view.MotionEvent; -import android.view.View; import android.widget.RelativeLayout; +import android.view.inputmethod.InputConnection; /** * Represents the container for the drawing space and the two side panels. */ -public class IMEView extends RelativeLayout { - private StringReciever mOnCharacterEnteredListener; - private final Queue mSymbolsQueue = new LinkedList(); - - private float x; - private float y; - private boolean ongoingGesture = false; - - public boolean setTouchLocation(float x, float y) { - if (!ongoingGesture) { - this.x = x; - this.y = y; - return true; - } - return false; - } - - public void setState(boolean state) { - ongoingGesture = state; - } - - public boolean getState() { - return ongoingGesture; - } - +public class IMEView extends RelativeLayout implements InputConnectionGetter { public IMEView(Context context, AttributeSet attrs) { super(context, attrs); } @@ -56,45 +16,15 @@ public class IMEView extends RelativeLayout { @Override protected void onFinishInflate() { IMEGestureOverlayView gestureOverlayView = (IMEGestureOverlayView) findViewById(R.id.drawing_space); - gestureOverlayView.setOnGestureRecognizedListener(new StringReciever() { - @Override - public void putString(String character) { - enterCharacter(character); - } - }); - } - - public void setOnCharacterEnteredListener(StringReciever onCharacterEnteredListener) { - mOnCharacterEnteredListener = onCharacterEnteredListener; + gestureOverlayView.setInputConnectionGetter(this); } - public Queue getSymbolsQueue() { - return mSymbolsQueue; + private InputConnectionGetter icGetter = new InputConnectionGetter.NullGetter(); + public void setInputConnectionGetter(InputConnectionGetter icGetter) { + this.icGetter = icGetter; } - - private final OnTouchListener mOnTouchListener = new OnTouchListener() { - @Override - public boolean onTouch(View v, MotionEvent event) { - return setTouchLocation(event.getX(), event.getY()); - } - }; - - /** - * Passes the given character to the input service. - * - * @param character - * The character to enter - */ - private void enterCharacter(String character) { - /* - for (MetaCircle circle : ((IMEGestureOverlayView) findViewById(R.id.drawing_space)).circles) { - //go through circles and check if they are applicable - if (circle.containsPoint(this.x, this.y) && circle.getMetaExpression().state != MetaExpression.State.OFF) { - //TODO: apply the Meta-key here - ; - } - } - */ - mOnCharacterEnteredListener.putString(character); + @Override + public InputConnection getCurrentInputConnection() { + return icGetter.getCurrentInputConnection(); } } diff --git a/src/us/minak/InputConnectionGetter.java b/src/us/minak/InputConnectionGetter.java new file mode 100644 index 0000000..237eefc --- /dev/null +++ b/src/us/minak/InputConnectionGetter.java @@ -0,0 +1,14 @@ +package us.minak; + +import android.view.inputmethod.InputConnection; + +public interface InputConnectionGetter { + public InputConnection getCurrentInputConnection(); + + public static class NullGetter implements InputConnectionGetter{ + @Override + public InputConnection getCurrentInputConnection() { + return null; + } + } +} diff --git a/src/us/minak/OnBackspacePressedListener.java b/src/us/minak/OnBackspacePressedListener.java deleted file mode 100644 index b4cf974..0000000 --- a/src/us/minak/OnBackspacePressedListener.java +++ /dev/null @@ -1,26 +0,0 @@ -/* - ******************************************************************************** - * Copyright (c) 2012 Samsung Electronics, Inc. - * All rights reserved. - * - * This software is a confidential and proprietary information of Samsung - * Electronics, Inc. ("Confidential Information"). You shall not disclose such - * Confidential Information and shall use it only in accordance with the terms - * of the license agreement you entered into with Samsung Electronics. - ******************************************************************************** - */ - -package us.minak; - -/** - * A simple interface for handling pressing the backspace button. - */ -public interface OnBackspacePressedListener { - /** - * Invoked when the backspace button is pressed. - * - * @param isLongClick - * if the button is long pressed - */ - void backspacePressed(boolean isLongClick); -} diff --git a/src/us/minak/StringReciever.java b/src/us/minak/StringReciever.java deleted file mode 100644 index 2b91da1..0000000 --- a/src/us/minak/StringReciever.java +++ /dev/null @@ -1,5 +0,0 @@ -package us.minak; - -public interface StringReciever { - void putString(String character); -} -- cgit v1.2.3