summaryrefslogtreecommitdiffstats
path: root/tests/sketch/src/com/android/gesture/Gesture.java
diff options
context:
space:
mode:
Diffstat (limited to 'tests/sketch/src/com/android/gesture/Gesture.java')
-rwxr-xr-xtests/sketch/src/com/android/gesture/Gesture.java457
1 files changed, 202 insertions, 255 deletions
diff --git a/tests/sketch/src/com/android/gesture/Gesture.java b/tests/sketch/src/com/android/gesture/Gesture.java
index 29c07ad..a5e7a25 100755
--- a/tests/sketch/src/com/android/gesture/Gesture.java
+++ b/tests/sketch/src/com/android/gesture/Gesture.java
@@ -18,343 +18,290 @@ package com.android.gesture;
import android.graphics.Bitmap;
import android.graphics.Canvas;
-import android.graphics.Matrix;
import android.graphics.Paint;
import android.graphics.Path;
-import android.graphics.PointF;
import android.graphics.RectF;
import android.os.Parcel;
import android.os.Parcelable;
-import com.android.gesture.recognizer.RecognitionUtil;
-
import org.xmlpull.v1.XmlSerializer;
import java.io.IOException;
import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.StringTokenizer;
/**
- * A single stroke gesture.
+ * A gesture can have a single or multiple strokes
*/
public class Gesture implements Parcelable {
- private RectF mBBX;
- private float mLength = 0;
- private int mColor;
- private float mWidth;
- private ArrayList<PointF> mPtsBuffer = new ArrayList<PointF>();
- private long mTimestamp = 0;
- private long mID;
-
- private static final long systemStartupTime = System.currentTimeMillis();
- private static int instanceCount = 0;
+ private static final long GESTURE_ID_BASE = System.currentTimeMillis();
+
+ private static final int BITMAP_RENDERING_WIDTH = 2;
+
+ private static final boolean BITMAP_RENDERING_ANTIALIAS = true;
+
+ private static final boolean BITMAP_RENDERING_DITHER = true;
+
+ private static int sGestureCount = 0;
+
+ private RectF mBoundingBox;
+
+ // the same as its instance ID
+ private long mGestureID;
+
+ private ArrayList<GestureStroke> mStrokes = new ArrayList<GestureStroke>();
public Gesture() {
- mID = systemStartupTime + instanceCount++;
+ mGestureID = GESTURE_ID_BASE + sGestureCount++;
}
- public void setColor(int c) {
- mColor = c;
- }
-
- public void setStrokeWidth(float w) {
- mWidth = w;
- }
-
- public int getColor() {
- return mColor;
- }
-
- public float getStrokeWidth() {
- return mWidth;
- }
-
- public ArrayList<PointF> getPoints() {
- return this.mPtsBuffer;
+ /**
+ * @return all the strokes of the gesture
+ */
+ public ArrayList<GestureStroke> getStrokes() {
+ return mStrokes;
}
-
- public int numOfPoints() {
- return this.mPtsBuffer.size();
+
+ /**
+ * @return the number of strokes included by this gesture
+ */
+ public int getStrokesCount() {
+ return mStrokes.size();
}
- public void addPoint(float x, float y) {
- mPtsBuffer.add(new PointF(x, y));
- if (mBBX == null) {
- mBBX = new RectF();
- mBBX.top = y;
- mBBX.left = x;
- mBBX.right = x;
- mBBX.bottom = y;
- mLength = 0;
- }
- else {
- PointF lst = mPtsBuffer.get(mPtsBuffer.size()-2);
- mLength += Math.sqrt(Math.pow(x-lst.x, 2)+Math.pow(y-lst.y, 2));
- mBBX.union(x, y);
+ /**
+ * Add a stroke to the gesture
+ *
+ * @param stroke
+ */
+ public void addStroke(GestureStroke stroke) {
+ mStrokes.add(stroke);
+
+ if (mBoundingBox == null) {
+ mBoundingBox = new RectF(stroke.boundingBox);
+ } else {
+ mBoundingBox.union(stroke.boundingBox);
}
- mTimestamp = System.currentTimeMillis();
}
/**
+ * Get the total length of the gesture. When there are multiple strokes in
+ * the gesture, this returns the sum of the lengths of all the strokes
+ *
* @return the length of the gesture
*/
public float getLength() {
- return this.mLength;
+ int len = 0;
+ ArrayList<GestureStroke> strokes = mStrokes;
+ int count = strokes.size();
+ for (int i = 0; i < count; i++) {
+ GestureStroke stroke = strokes.get(i);
+ len += stroke.length;
+ }
+ return len;
}
-
- public RectF getBBX() {
- return mBBX;
+
+ /**
+ * @return the bounding box of the gesture
+ */
+ public RectF getBoundingBox() {
+ return mBoundingBox;
}
-
- public void setID(long id) {
- mID = id;
+
+ /**
+ * Set the id of the gesture
+ *
+ * @param id
+ */
+ void setID(long id) {
+ mGestureID = id;
}
-
+
+ /**
+ * @return the id of the gesture
+ */
public long getID() {
- return mID;
+ return mGestureID;
}
-
- public long getTimeStamp() {
- return mTimestamp;
- }
-
- public void setTimestamp(long t) {
- this.mTimestamp = t;
- }
-
+
/**
* draw the gesture
+ *
* @param canvas
*/
- public void draw(Canvas canvas) {
- Paint paint = new Paint();
- paint.setAntiAlias(true);
- paint.setDither(true);
- paint.setColor(mColor);
- paint.setStyle(Paint.Style.STROKE);
- paint.setStrokeJoin(Paint.Join.ROUND);
- paint.setStrokeCap(Paint.Cap.ROUND);
- paint.setStrokeWidth(mWidth);
-
- Path path = null;
- float mX = 0, mY = 0;
- Iterator<PointF> it = mPtsBuffer.iterator();
- while (it.hasNext()) {
- PointF p = it.next();
- float x = p.x;
- float y = p.y;
- if (path == null) {
- path = new Path();
- path.moveTo(x, y);
- mX = x;
- mY = y;
- } else {
- float dx = Math.abs(x - mX);
- float dy = Math.abs(y - mY);
- if (dx >= 3 || dy >= 3) {
- path.quadTo(mX, mY, (x + mX)/2, (y + mY)/2);
- mX = x;
- mY = y;
- }
- }
+ void draw(Canvas canvas, Paint paint) {
+ ArrayList<GestureStroke> strokes = mStrokes;
+ int count = strokes.size();
+ for (int i = 0; i < count; i++) {
+ GestureStroke stroke = strokes.get(i);
+ stroke.draw(canvas, paint);
}
-
- canvas.drawPath(path, paint);
}
-
+
/**
- * convert the gesture to a Path
- * @param width the width of the bounding box of the target path
- * @param height the height of the bounding box of the target path
- * @param numSample the num of points needed
- * @return the path
+ * Create a bitmap of the gesture with a transparent background
+ *
+ * @param width width of the target bitmap
+ * @param height height of the target bitmap
+ * @param edge the edge
+ * @param numSample
+ * @param color
+ * @return the bitmap
*/
- public Path toPath(float width, float height, int numSample) {
- float[] pts = RecognitionUtil.resample(this, numSample);
- RectF rect = this.getBBX();
- float scale = height / rect.height();
- Matrix matrix = new Matrix();
- matrix.setTranslate(-rect.left, -rect.top);
- Matrix scalem = new Matrix();
- scalem.setScale(scale, scale);
- matrix.postConcat(scalem);
- Matrix translate = new Matrix();
- matrix.postConcat(translate);
- matrix.mapPoints(pts);
-
- Path path = null;
- float mX = 0, mY = 0;
- for (int i=0; i<pts.length-1; i+=2) {
- float x = pts[i];
- float y = pts[i+1];
- if (path == null) {
- path = new Path();
- path.moveTo(x, y);
- mX = x;
- mY = y;
- } else {
- float dx = Math.abs(x - mX);
- float dy = Math.abs(y - mY);
- if (dx >= 3 || dy >= 3) {
- path.quadTo(mX, mY, (x + mX)/2, (y + mY)/2);
- mX = x;
- mY = y;
- }
- }
+ public Bitmap toBitmap(int width, int height, int edge, int numSample, int color) {
+ RectF bbx = getBoundingBox();
+ Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
+ Canvas canvas = new Canvas(bitmap);
+ canvas.translate(edge, edge);
+ Paint paint = new Paint();
+ paint.setAntiAlias(BITMAP_RENDERING_ANTIALIAS);
+ paint.setDither(BITMAP_RENDERING_DITHER);
+ paint.setColor(color);
+ paint.setStyle(Paint.Style.STROKE);
+ paint.setStrokeJoin(Paint.Join.ROUND);
+ paint.setStrokeCap(Paint.Cap.ROUND);
+ paint.setStrokeWidth(BITMAP_RENDERING_WIDTH);
+ ArrayList<GestureStroke> strokes = mStrokes;
+ int count = strokes.size();
+ for (int i = 0; i < count; i++) {
+ GestureStroke stroke = strokes.get(i);
+ Path path = stroke.toPath(width - 2 * edge, height - 2 * edge, numSample);
+ canvas.drawPath(path, paint);
}
- return path;
+
+ return bitmap;
}
-
+
/**
- * get a bitmap thumbnail of the gesture with a transparent background
- * @param w
- * @param h
+ * Create a bitmap of the gesture with a transparent background
+ *
+ * @param width
+ * @param height
* @param edge
- * @param numSample
- * @param foreground
- * @return
+ * @param color
+ * @return the bitmap
*/
- public Bitmap toBitmap(int w, int h,
- int edge, int numSample) {
- RectF bbx = this.getBBX();
- Bitmap bitmap = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);
- Path path = this.toPath(w - 2 * edge, h - 2 * edge, numSample);
- Canvas c = new Canvas(bitmap);
- //c.drawColor(background);
- c.translate(edge, edge);
+ public Bitmap toBitmap(int width, int height, int edge, int color) {
+ RectF bbx = getBoundingBox();
+ Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
+ Canvas canvas = new Canvas(bitmap);
+ canvas.translate(edge, edge);
Paint paint = new Paint();
- paint.setAntiAlias(true);
- paint.setDither(true);
- paint.setColor(mColor);
+ paint.setAntiAlias(BITMAP_RENDERING_ANTIALIAS);
+ paint.setDither(BITMAP_RENDERING_DITHER);
+ paint.setColor(color);
paint.setStyle(Paint.Style.STROKE);
paint.setStrokeJoin(Paint.Join.ROUND);
paint.setStrokeCap(Paint.Cap.ROUND);
- paint.setStrokeWidth(2);
- c.drawPath(path, paint);
+ paint.setStrokeWidth(BITMAP_RENDERING_WIDTH);
+ ArrayList<GestureStroke> strokes = mStrokes;
+ int count = strokes.size();
+ for (int i = 0; i < count; i++) {
+ GestureStroke stroke = strokes.get(i);
+ stroke.draw(canvas, paint);
+ }
+
return bitmap;
}
-
+
/**
- * save the gesture as XML
+ * Save the gesture as XML
+ *
* @param namespace
* @param serializer
* @throws IOException
*/
- public void toXML(String namespace, XmlSerializer serializer) throws IOException {
- serializer.startTag(namespace, "stroke");
- serializer.attribute(namespace, "timestamp", Long.toString(mTimestamp));
- serializer.attribute(namespace, "id", Long.toString(mID));
- serializer.attribute(namespace, "color", Integer.toString(mColor));
- serializer.attribute(namespace, "width", Float.toString(mWidth));
- Iterator it = this.mPtsBuffer.iterator();
- String pts = "";
- while (it.hasNext()) {
- PointF fp = (PointF)it.next();
- if (pts.length() > 0)
- pts += ",";
- pts += fp.x + "," + fp.y;
+ void toXML(String namespace, XmlSerializer serializer) throws IOException {
+ serializer.startTag(namespace, GestureConstants.XML_TAG_GESTURE);
+ serializer.attribute(namespace, GestureConstants.XML_TAG_ID, Long.toString(mGestureID));
+ ArrayList<GestureStroke> strokes = mStrokes;
+ int count = strokes.size();
+ for (int i = 0; i < count; i++) {
+ GestureStroke stroke = strokes.get(i);
+ stroke.toXML(namespace, serializer);
}
- serializer.text(pts);
- serializer.endTag(namespace, "stroke");
+ serializer.endTag(namespace, GestureConstants.XML_TAG_GESTURE);
}
-
-
+
+ /**
+ * Create the gesture from a string
+ *
+ * @param str
+ */
public void createFromString(String str) {
- StringTokenizer st = new StringTokenizer(str, "#");
-
- String para = st.nextToken();
- StringTokenizer innerst = new StringTokenizer(para, ",");
- this.mBBX = new RectF();
- this.mBBX.left = Float.parseFloat(innerst.nextToken());
- this.mBBX.top = Float.parseFloat(innerst.nextToken());
- this.mBBX.right = Float.parseFloat(innerst.nextToken());
- this.mBBX.bottom = Float.parseFloat(innerst.nextToken());
-
- para = st.nextToken();
- innerst = new StringTokenizer(para, ",");
- while (innerst.hasMoreTokens()) {
- String s = innerst.nextToken().trim();
- if (s.length()==0)
- break;
- float x = Float.parseFloat(s);
- float y = Float.parseFloat(innerst.nextToken());
- this.mPtsBuffer.add(new PointF(x, y));
+ int startIndex = 0;
+ int endIndex;
+ while ((endIndex = str.indexOf(GestureConstants.STRING_GESTURE_DELIIMITER, startIndex + 1)) != -1) {
+ String token = str.substring(startIndex, endIndex);
+ if (startIndex > 0) { // stroke tokens
+ addStroke(GestureStroke.createFromString(token));
+ } else { // id token
+ mGestureID = Long.parseLong(token);
+ }
+ startIndex = endIndex + 1;
}
-
- para = st.nextToken();
- this.mColor = Integer.parseInt(para);
-
- para = st.nextToken();
- this.mWidth = Float.parseFloat(para);
-
- para = st.nextToken();
- this.mLength = Float.parseFloat(para);
-
- para = st.nextToken();
- this.mTimestamp = Long.parseLong(para);
}
-
+
+ /**
+ * Convert the gesture to string
+ */
@Override
public String toString() {
- String str = "";
-
- str += "#" + this.mBBX.left + "," + this.mBBX.top + "," +
- this.mBBX.right + "," + this.mBBX.bottom;
-
- str += "#";
- Iterator<PointF> it = this.mPtsBuffer.iterator();
- while (it.hasNext()) {
- PointF fp = it.next();
- str += fp.x + "," + fp.y + ",";
+ StringBuilder str = new StringBuilder();
+ str.append(mGestureID);
+ ArrayList<GestureStroke> strokes = mStrokes;
+ int count = strokes.size();
+ for (int i = 0; i < count; i++) {
+ GestureStroke stroke = strokes.get(i);
+ str.append(GestureConstants.STRING_GESTURE_DELIIMITER);
+ str.append(stroke.toString());
}
- str += "#";
- str += this.mColor;
-
- str += "#";
- str += this.mWidth;
-
- str += "#";
- str += this.mLength;
-
- str += "#";
- str += this.mTimestamp;
-
- return str;
+ return str.toString();
}
-
- public static final Parcelable.Creator CREATOR = new Parcelable.Creator() {
+
+ public static final Parcelable.Creator<Gesture> CREATOR = new Parcelable.Creator<Gesture>() {
public Gesture createFromParcel(Parcel in) {
String str = in.readString();
- Gesture stk = new Gesture();
- stk.createFromString(str);
- return stk;
+ Gesture gesture = new Gesture();
+ gesture.createFromString(str);
+ return gesture;
}
-
+
public Gesture[] newArray(int size) {
return new Gesture[size];
}
};
-
- public static Gesture buildFromArray(byte[] bytes) {
+
+ /**
+ * Build a gesture from a byte array
+ *
+ * @param bytes
+ * @return the gesture
+ */
+ static Gesture buildFromArray(byte[] bytes) {
String str = new String(bytes);
- Gesture stk = new Gesture();
- stk.createFromString(str);
- return stk;
+ Gesture gesture = new Gesture();
+ gesture.createFromString(str);
+ return gesture;
}
-
- public static byte[] saveToArray(Gesture stk) {
- String str = stk.toString();
+
+ /**
+ * Save a gesture to a byte array
+ *
+ * @param stroke
+ * @return the byte array
+ */
+ static byte[] saveToArray(Gesture stroke) {
+ String str = stroke.toString();
return str.getBytes();
}
-
+
public void writeToParcel(Parcel out, int flags) {
- out.writeString(this.toString());
+ out.writeString(toString());
}
-
+
public int describeContents() {
return CONTENTS_FILE_DESCRIPTOR;
}