Android_基于g-sensor的坐下动作的的识别

基于g-sensor的坐下的姿势识别。手机需要放在口袋里,手机拿在手上的暂时还不支持。

如果看不明白,可以先学习这篇文章

计步算法识别:http://blog.csdn.net/finnfu/article/details/45273183


算法流程:

1.五阶移动均值滤波

2.波谷峰值检测

3.根据波形特征判断是起立还是坐下


核心代码:

package com.research.sensor.finnfu.gesturedetector.detector;

import android.os.Environment;
import android.util.Log;

import com.research.sensor.finnfu.gesturedetector.MyApp;

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;


/**
 * Created by finnfu on 2017/6/3.
 * 坐下
 */



public class SitDownDetector {
    /*
    * 五阶的均值滤波
    * 第一阶是NUM1个数的均值
    * 第二阶以第一阶的均值为输入,再进行NUM2个数的均值
    * 第三阶以第二阶的均值为输入,再进行NUM2个数的均值
    * 第四阶以第三阶的均值为输入,再进行NUM2个数的均值
    * 第五阶以第四阶的均值为输入,再进行NUM2个数的均值
    * */
    public static final int NUM1 = 8;//取平均值的个数
    public static final int NUM2 = 3;//取平均值的个数
    float[] values1 = new float[NUM1];//一阶滤波,NUM1个值
    float[] values2 = new float[NUM2];//二阶滤波,NUM2个值
    float[] values3 = new float[NUM2];//三阶滤波,NUM2个值
    float[] values4 = new float[NUM2];//四阶滤波,NUM2个值
    float[] values5 = new float[NUM2];//五阶滤波,NUM2个值
    int count1 = 0;
    int count2 = 0;
    int count3 = 0;
    int count4 = 0;
    int count5 = 0;

    ArrayList keyValuelist = new ArrayList();//存放连续的波峰波谷值
    public static final String KEY_NAME_VALUE = "value";
    public static final String KEY_NAME_TIMEMILLIS = "timemillis";
    public static final String KEY_NAME_TYPE = "type";//1代表波峰,-1代表波谷


    //检测波谷相关
    boolean isDirectionDecline = false;
    int continueDeclineCount = 0;
    int formerContinueDeclineCount = 0;
    boolean formerDeclineStatus = false;



    //检测波峰相关
    boolean isDirectionUp = false;
    int continueUpCount = 0;
    int formerContinueUpCount = 0;
    boolean formerUpStatus = false;


    float ValleyPeakThread;
    float ValleyThread;
    int TimeIntervalOfValleyAndPeak = 350;

    float mOldValue = 0;


    public SitDownDetector(){
        ValleyPeakThread  = MyApp.getSitValleyPeakThread();
        ValleyThread = MyApp.getSitValleyThread();
        Log.i("Thread",""+"ValleyPeakThread: "+ValleyPeakThread +" "+"ValleyThread: "+ValleyThread);
    }

    //测试函数
    public void testvalue(){
                try {
            String rootPath = Environment.getExternalStorageDirectory().getAbsolutePath();
            FileReader fileReader = new FileReader(rootPath+"/test.txt");
            BufferedReader bufferedReader = new BufferedReader(fileReader);
            String content = bufferedReader.readLine();
            while (content!=null){
                float v = Float.parseFloat(content);
                inputValue(v);
                content = bufferedReader.readLine();
            }
            fileReader.close();
            bufferedReader.close();
        }catch (IOException e){
            e.printStackTrace();
        }
    }


    public void inputValue(float v){
        //第一次 NUM1个点的均值滤波
        if(count1= 320 && diffValue >= ValleyPeakThread && diffValue <= ValleyPeakThread+1){
                Log.i("result","judgeMaybeSitDown");
                result = true;
            }else{
                Log.i("result","judge sit down failed "+(millis2 - millis1)+" "+diffValue);
                result = false;
            }
        }else{
            Log.i("result","type wrong");
            result = false;
        }
        return result;
    }

    /*
    * 用于检测第一个波谷值,如果检测到符合要求的波谷值,则进行后续的检测
    * 1.持续下降或持平大于等于4个点
    * 2.波谷值小于8.2和7之间
    * */
    public boolean detectFirstValley(float newValue,float oldValue){
        boolean result = false;
        formerDeclineStatus = isDirectionDecline;
        if(newValue < oldValue){
            isDirectionDecline = true;
            continueDeclineCount++;
        }else{
            formerContinueDeclineCount = continueDeclineCount;
            continueDeclineCount = 0;
            isDirectionDecline = false;
        }
        Log.i("process","formerContinueDeclineCount:"+formerContinueDeclineCount +" " +"oldValue:"+oldValue);
        if(!isDirectionDecline && formerDeclineStatus
                && formerContinueDeclineCount >= 6 && oldValue<= ValleyThread+1.2 && oldValue>=ValleyThread){
            long timeMillis = System.currentTimeMillis();
            float valleyValue = oldValue;
            HashMap hashMap = new HashMap();
            hashMap.put(KEY_NAME_TIMEMILLIS,timeMillis);
            hashMap.put(KEY_NAME_VALUE,valleyValue);
            hashMap.put(KEY_NAME_TYPE,-1);
            keyValuelist.add(hashMap);
            Log.i("result","valleyValue"+valleyValue);
            result = true;
        }
        return result;
    }

    /*
    * 用于检测普通的符合要求的波峰
    * */
    public Boolean detectNormalPeak(float newValue,float oldValue){
        Boolean result = false;
        formerUpStatus = isDirectionUp;
        if(newValue > oldValue){
            isDirectionUp = true;
            continueUpCount++;
        }else{
            isDirectionUp =false;
            formerContinueUpCount = continueUpCount;
            continueUpCount = 0;
        }
        if(!isDirectionUp  && formerUpStatus){
            long timeMillis = System.currentTimeMillis();
            float peakValue = oldValue;
            HashMap hashMap = new HashMap();
            hashMap.put(KEY_NAME_TIMEMILLIS,timeMillis);
            hashMap.put(KEY_NAME_VALUE,peakValue);
            hashMap.put(KEY_NAME_TYPE,1);
            keyValuelist.add(hashMap);
            result = true;
        }
        return result;
    }

    public boolean detectNormalValley(float newValue,float oldValue){
        boolean result = false;
        formerDeclineStatus = isDirectionDecline;
        if(newValue < oldValue){
            isDirectionDecline = true;
            continueDeclineCount++;
        }else{
            formerContinueDeclineCount = continueDeclineCount;
            continueDeclineCount = 0;
            isDirectionDecline = false;
        }
        if(!isDirectionDecline && formerDeclineStatus){
            long timeMillis = System.currentTimeMillis();
            float valleyValue = oldValue;
            HashMap hashMap = new HashMap();
            hashMap.put(KEY_NAME_TIMEMILLIS,timeMillis);
            hashMap.put(KEY_NAME_VALUE,valleyValue);
            hashMap.put(KEY_NAME_TYPE,-1);
            keyValuelist.add(hashMap);
            result = true;
        }
        return result;
    }


    //一阶滤波的平移
    public void translate1(float v){
        for(int i=1;i





你可能感兴趣的:(算法)