手势(Gesture)的增加和识别

Android除了提供手势检测之外,还允许把用户手势添加到指定文件中,以备以后使用,当用户再次画出该手势时,系统可识别该手势。Android使用GestureLibrary代表手势库,提供GestureLibraries工具类来创建手势库。GestureLibraries提供如下4个静态方法从不同位置加载手势库:

一旦程序中获得了GestureLibrary对象后,就可以用如下方法来添加、识别手势:

另外Android还提供了一个手势编辑组件:GestureOverlayView,用户可以在上面绘制手势。然后对它绑定事件监听器,响应手势事件开始、结束、完成、取消等事件。下面通过一个简单实例来演示手势的添加以及识别自定义手势,代码如下:

AddGestureActiv:

package com.lovo.activity;

import android.app.Activity;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.gesture.Gesture;
import android.gesture.GestureLibraries;
import android.gesture.GestureLibrary;
import android.gesture.GestureOverlayView;
import android.gesture.GestureOverlayView.OnGesturePerformedListener;
import android.graphics.Bitmap;
import android.graphics.Color;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;

import com.lovo.addgesture.R;

public class AddGestureActivity extends Activity {
	private GestureOverlayView gestureView;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.main);
		// 获取手势编辑视图
		gestureView = (GestureOverlayView) findViewById(R.id.main_gesture);
		// 设置手势绘制的颜色
		gestureView.setGestureColor(Color.RED);
		// 设置手势的绘制宽度
		gestureView.setGestureStrokeWidth(4);
		// 为 gesture的手势完成事件绑定事件监听器
		gestureView.addOnGesturePerformedListener(new OnGesturePerformedListener() {

					@Override
					public void onGesturePerformed(GestureOverlayView overlay,
							final Gesture gesture) {
					// 加载save.xml界面布局代表的视图
					View saveDialog = getLayoutInflater().inflate(R.layout.save, null);
					// 获取saveDialog里的show组件
					ImageView imageView = (ImageView) saveDialog.findViewById(R.id.save_iv_show);
						// 获取saveDialog里的gesture_name组件
						final EditText gestureName = (EditText) saveDialog
								.findViewById(R.id.save_et_gesture_name);
						// 根据Gesture包含的手势创建一个位图
						Bitmap bitmap = gesture.toBitmap(128, 128, 10,0xFFFF0000);
						imageView.setImageBitmap(bitmap);
						// 使用对话框显示saveDialog组件
						new AlertDialog.Builder(AddGestureActivity.this)
							.setView(saveDialog)
							.setPositiveButton("保存",
							new android.content.DialogInterface.OnClickListener() {

							 @Override
							public void onClick(
							DialogInterface dialog,int which) {
							// 获取指定文件对应的手势库
							GestureLibrary gestureLib = GestureLibraries
							 .fromFile(AddGestureActivity.this
							 .getFilesDir()+ "/gestures");
							// 添加手势
							gestureLib.addGesture(gestureName.getText().toString(),gesture);
							// 保存手势库
							boolean isSave = gestureLib.save();
							String result = isSave ? "保存成功": "保存失败";
						Log.i("isSave", result);
						}
					  }).setNegativeButton("取消", null).show();
					}
				});
		Button turnBtn = (Button) findViewById(R.id.main_btn_turn);
		turnBtn.setOnClickListener(new OnClickListener() {

			@Override
			public void onClick(View v) {
				Intent intent = new Intent(AddGestureActivity.this,
						RecogniseGestureActivity.class);
				startActivity(intent);
			}
		});
	}
}

Add布局XML:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_gravity="center_horizontal"
    android:orientation="vertical" >

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal" >

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="请在下面屏幕上绘制手势" />

        <Button
            android:id="@+id/main_btn_turn"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginLeft="10dp"
            android:text="跳转到手势识别界面" />
    </LinearLayout>
    <!-- 使用手势绘制组件 -->

    <android.gesture.GestureOverlayView
        android:id="@+id/main_gesture"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:gestureStrokeType="multiple" />

</LinearLayout>

识别手势的Activity:

package com.lovo.activity;

import java.util.ArrayList;

import android.app.Activity;
import android.app.AlertDialog;
import android.gesture.Gesture;
import android.gesture.GestureLibraries;
import android.gesture.GestureLibrary;
import android.gesture.GestureOverlayView;
import android.gesture.GestureOverlayView.OnGesturePerformedListener;
import android.gesture.Prediction;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.Toast;

import com.lovo.addgesture.R;

public class RecogniseGestureActivity extends Activity {
	// 定义手势编辑组件
	private GestureOverlayView gestureView;
	// 记录手机上已有的手势库
	GestureLibrary gestureLibrary;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.recognise);
		// 读取上一个程序所创建的手势库
		gestureLibrary = GestureLibraries.fromFile(this.getFilesDir()
				+ "/gestures");
		if (gestureLibrary.load()) {
			Toast.makeText(this, "手势文件装载成功!", Toast.LENGTH_SHORT).show();
		} else {
			Toast.makeText(this, "手势文件装载失败!", Toast.LENGTH_SHORT).show();
		}
		// 获取手势编辑组件
		gestureView = (GestureOverlayView) findViewById(R.id.recognise_gesture);
		// 为手势编辑组件绑定事件监听器
		gestureView
				.addOnGesturePerformedListener(new OnGesturePerformedListener() {

					@Override
					public void onGesturePerformed(GestureOverlayView overlay,
							Gesture gesture) {
						// 识别用户刚刚所绘制的手势
						ArrayList<Prediction> predictions = gestureLibrary
								.recognize(gesture);
						ArrayList<String> result = new ArrayList<String>();
						// 遍历所有找到的Prediction对象
						for (Prediction pred : predictions) {
							// 只有相似度大于2.0的手势才会被输出
							if (pred.score > 2.0) {
								result.add("与手势【" + pred.name + "】的相似度为"
										+ pred.score);
							}
						}
						if (result.size() > 0) {
							ArrayAdapter adapter = new ArrayAdapter(
									RecogniseGestureActivity.this,
									android.R.layout.simple_dropdown_item_1line,
									result.toArray());
							// 使用一个带List的对话框来显示所有匹配的手势
							new AlertDialog.Builder(
									RecogniseGestureActivity.this)
									.setAdapter(adapter, null)
									.setPositiveButton("保存", null).show();
						} else {
							Toast.makeText(RecogniseGestureActivity.this,
									"无法找到匹配的手势!", Toast.LENGTH_SHORT).show();
						}

					}
				});
		Button turnBtn = (Button) findViewById(R.id.recognise_btn_turn);
		turnBtn.setOnClickListener(new OnClickListener() {

			@Override
			public void onClick(View v) {
				finish();
			}
		});
	}
}

识别手势的布局XML:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_gravity="center_horizontal"
    android:orientation="vertical" >

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal" >

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="请在下面屏幕上绘制手势" />

        <Button
            android:id="@+id/recognise_btn_turn"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginLeft="10dp"
            android:text="返回到增加手势界面" />
    </LinearLayout>
    <!-- 使用手势绘制组件 -->

    <android.gesture.GestureOverlayView
        android:id="@+id/recognise_gesture"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:gestureStrokeType="multiple" />

</LinearLayout>





 

原文地址:https://www.cnblogs.com/dyllove98/p/3174544.html