|
@@ -0,0 +1,482 @@
|
|
|
+
|
|
|
+#include "online_motion.h"
|
|
|
+#include <iostream>
|
|
|
+#include <algorithm>
|
|
|
+#include "math.h"
|
|
|
+
|
|
|
+void top_point(deque<int> &left_front_mag_queue , int &top_index, int &left_index, int &right_index)
|
|
|
+{
|
|
|
+ int left_top_index = left_front_mag_queue.size() - 1;
|
|
|
+ //std::cout << "int left_top_index = left_front_mag_queue.size() - 1" << std::endl;
|
|
|
+ while (left_top_index > 2 &&
|
|
|
+ (left_front_mag_queue[left_top_index] < left_front_mag_queue[left_top_index - 1] ||
|
|
|
+ left_front_mag_queue[left_top_index] < left_front_mag_queue[left_top_index - 2] ||
|
|
|
+ left_front_mag_queue[left_top_index] < left_front_mag_queue[left_top_index - 3]))
|
|
|
+ {
|
|
|
+ left_top_index--;
|
|
|
+
|
|
|
+ //std::cout << "left_top_index--;" << std::endl;
|
|
|
+ }
|
|
|
+
|
|
|
+ int k = left_top_index;
|
|
|
+
|
|
|
+ left_index = k;
|
|
|
+ int dist = 40000;
|
|
|
+ while (k > 2)
|
|
|
+ {
|
|
|
+
|
|
|
+ if (left_front_mag_queue[k] > left_front_mag_queue[k - 1] ||
|
|
|
+ left_front_mag_queue[k] > left_front_mag_queue[k - 2] ||
|
|
|
+ left_front_mag_queue[k] > left_front_mag_queue[k - 3])
|
|
|
+ {
|
|
|
+ if (dist > abs(left_front_mag_queue.back() - left_front_mag_queue[k - 1]))
|
|
|
+ {
|
|
|
+ dist = abs(left_front_mag_queue.back() - left_front_mag_queue[k - 1]);
|
|
|
+ left_index = k-1;
|
|
|
+ }
|
|
|
+ k--;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ break;
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ k = left_front_mag_queue.size() - 1;
|
|
|
+
|
|
|
+ right_index = k;
|
|
|
+
|
|
|
+ /*while (k > left_top_index)
|
|
|
+ {
|
|
|
+ if (dist > abs(left_front_mag_queue[k] - left_front_mag_queue[left_index]))
|
|
|
+ {
|
|
|
+ dist = abs(left_front_mag_queue[k] - left_front_mag_queue[left_index]);
|
|
|
+
|
|
|
+ right_index = k;
|
|
|
+ }
|
|
|
+ k--;
|
|
|
+ }*/
|
|
|
+
|
|
|
+ top_index = left_top_index;
|
|
|
+
|
|
|
+}
|
|
|
+
|
|
|
+//最小值滤波
|
|
|
+int online_motion::min_window_val(deque<int>& press_deque, int mid_window_size)
|
|
|
+{
|
|
|
+ deque<int> press_deque_temp = press_deque;
|
|
|
+
|
|
|
+ if (press_deque_temp.size() >= mid_window_size)
|
|
|
+ {
|
|
|
+ std::sort(press_deque_temp.begin(), press_deque_temp.end());
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ return press_deque.back();
|
|
|
+ }
|
|
|
+
|
|
|
+ //return press_deque[press_deque_temp.size() / 2];
|
|
|
+
|
|
|
+ return press_deque_temp[0];
|
|
|
+}
|
|
|
+
|
|
|
+int online_motion::back_press_up_trend(deque<int>& left_press_deque, deque<int>& right_press_deque)
|
|
|
+{
|
|
|
+ if (left_press_deque.size() >= 20)
|
|
|
+ {
|
|
|
+ int i = left_press_deque.size() - 1;
|
|
|
+
|
|
|
+ while (i > 10 && (left_press_deque[i] >= left_press_deque[i - 1] || left_press_deque[i] >= left_press_deque[i - 2]
|
|
|
+ || left_press_deque[i] >= left_press_deque[i - 3]) &&
|
|
|
+ (right_press_deque[i] >= right_press_deque[i - 1] || right_press_deque[i] >= right_press_deque[i - 2]
|
|
|
+ || right_press_deque[i] >= right_press_deque[i - 3])
|
|
|
+ && left_press_deque[i] > 12000 && right_press_deque[i] > 12000)
|
|
|
+ {
|
|
|
+ i--;
|
|
|
+ }
|
|
|
+
|
|
|
+ if (left_press_deque.back() > left_press_deque[i] + 1000 && right_press_deque.back() > right_press_deque[i] + 1000)
|
|
|
+ {
|
|
|
+ return 1;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|
|
|
+int online_motion::online_detect_down(int right_front_mag, int left_front_mag, int right_back_mag, int left_back_mag,
|
|
|
+ int* right_acc, int* left_acc)
|
|
|
+{
|
|
|
+
|
|
|
+ //滑动窗口补充
|
|
|
+ left_press_filter_window.push_back(left_back_mag);
|
|
|
+ right_press_filter_window.push_back(right_back_mag);
|
|
|
+
|
|
|
+ //采用最小值滤波, 较好的过滤毛刺
|
|
|
+ if (left_press_filter_window.size() > 5)
|
|
|
+ {
|
|
|
+ left_press_filter_window.pop_front();
|
|
|
+ right_press_filter_window.pop_front();
|
|
|
+
|
|
|
+ left_back_mag = min_window_val(left_press_filter_window, 5);
|
|
|
+ right_back_mag = min_window_val(right_press_filter_window, 5);
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ if (right_back_mag_queue.size() > 20)
|
|
|
+ {
|
|
|
+ right_back_mag_queue.pop_front();
|
|
|
+ left_back_mag_queue.pop_front();
|
|
|
+
|
|
|
+ right_front_mag_queue.pop_front();
|
|
|
+ left_front_mag_queue.pop_front();
|
|
|
+
|
|
|
+ left_front_acc.pop_front();
|
|
|
+ right_front_acc.pop_front();
|
|
|
+
|
|
|
+ }
|
|
|
+ right_back_mag_queue.push_back(right_back_mag);
|
|
|
+ left_back_mag_queue.push_back(left_back_mag);
|
|
|
+
|
|
|
+ right_front_mag_queue.push_back(right_front_mag);
|
|
|
+ left_front_mag_queue.push_back(left_front_mag);
|
|
|
+
|
|
|
+ /*left_front_acc.push_back(left_acc[2]);
|
|
|
+ right_front_acc.push_back(right_acc[2]);*/
|
|
|
+
|
|
|
+ left_front_acc.push_back(sqrt(left_acc[0] * left_acc[0] + left_acc[1] * left_acc[1]));
|
|
|
+ right_front_acc.push_back(sqrt(right_acc[0] * right_acc[0] + right_acc[1] * right_acc[1]));
|
|
|
+
|
|
|
+
|
|
|
+ deque<int> right_back_temp{ right_back_mag };
|
|
|
+ deque<int> left_back_temp{ left_back_mag };
|
|
|
+
|
|
|
+ int left_acc_z_max = left_front_acc.back();
|
|
|
+ int left_acc_z_min = left_front_acc.back();
|
|
|
+
|
|
|
+ int right_acc_z_max = right_front_acc.back();
|
|
|
+ int right_acc_z_min = right_front_acc.back();
|
|
|
+
|
|
|
+ int back_down = 0;
|
|
|
+ if (right_back_mag_queue.size() >= 20)
|
|
|
+ {
|
|
|
+ back_down = back_press_up_trend(left_back_mag_queue, right_back_mag_queue);
|
|
|
+
|
|
|
+ if (back_down)
|
|
|
+ {
|
|
|
+ if (top_back_press_valid_time == 0)
|
|
|
+ {
|
|
|
+ left_top_back_press = left_back_mag_queue.back();
|
|
|
+ right_top_back_press = right_back_mag_queue.back();
|
|
|
+
|
|
|
+ top_back_press_valid_time = 60;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+
|
|
|
+ if (left_top_back_press > left_back_mag_queue.back() || right_top_back_press > right_back_mag_queue.back())
|
|
|
+ {
|
|
|
+ back_down = 0;
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ left_top_back_press = left_back_mag_queue.back();
|
|
|
+ right_top_back_press = right_back_mag_queue.back();
|
|
|
+
|
|
|
+ top_back_press_valid_time = 60;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if (top_back_press_valid_time > 0)
|
|
|
+ {
|
|
|
+ top_back_press_valid_time--;
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ deque<int> right_front_temp{ right_front_mag };
|
|
|
+ deque<int> left_front_temp{ left_front_mag };
|
|
|
+
|
|
|
+ left_acc_z_max = left_front_acc.back();
|
|
|
+ left_acc_z_min = left_front_acc.back();
|
|
|
+
|
|
|
+ right_acc_z_max = right_front_acc.back();
|
|
|
+ right_acc_z_min = right_front_acc.back();
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ int front_down = 0;
|
|
|
+ if (right_front_mag_queue.size() > 20)
|
|
|
+ for (int i = right_front_mag_queue.size() - 1; i > right_front_mag_queue.size() -11; i--)
|
|
|
+ {
|
|
|
+ if ((left_front_mag_queue[i] > left_front_mag_queue[i - 1]+100 || left_front_mag_queue[i] > left_front_mag_queue[i - 2] + 100
|
|
|
+ || left_front_mag_queue[i] > left_front_mag_queue[i - 3]) + 100 &&
|
|
|
+ (right_front_mag_queue[i] > right_front_mag_queue[i - 1] + 100 || right_front_mag_queue[i] > right_front_mag_queue[i - 2] + 100
|
|
|
+ || right_front_mag_queue[i] < right_front_mag_queue[i - 3] + 100))
|
|
|
+ {
|
|
|
+ right_front_temp.push_back(right_front_mag_queue[i]);
|
|
|
+ left_front_temp.push_back(left_front_mag_queue[i]);
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ break;
|
|
|
+ }
|
|
|
+
|
|
|
+ if (*max_element(left_front_acc.begin() + 10 , left_front_acc.end()) - *min_element(left_front_acc.begin() + 10, left_front_acc.end()) < 256
|
|
|
+ && *max_element(right_front_acc.begin() + 10, right_front_acc.end()) - *min_element(right_front_acc.begin() + 10, right_front_acc.end()) < 256)
|
|
|
+ {
|
|
|
+ if (right_front_temp.size() > 5 && left_front_temp.size() > 5 && left_front_temp.front() > left_front_temp.back() + 1500
|
|
|
+ && right_front_temp.front() > right_front_temp.back() + 1500
|
|
|
+ && abs(left_front_temp.front() - right_front_temp.front()) < 6000)
|
|
|
+ {
|
|
|
+ front_down = 1;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ //继续补充 微小变动的
|
|
|
+ int little_front_down = 0;
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ if (left_front_acc.size() > 20)
|
|
|
+ {
|
|
|
+ if (*max_element(left_front_acc.end() - 5, left_front_acc.end())
|
|
|
+ - *min_element(left_front_acc.end() - 5, left_front_acc.end()) < 256
|
|
|
+ && *max_element(right_front_acc.end() - 5, right_front_acc.end())
|
|
|
+ - *min_element(right_front_acc.end() - 5, right_front_acc.end()) < 256)
|
|
|
+ {
|
|
|
+
|
|
|
+ if (right_front_mag_canve_queue.size() == 0)
|
|
|
+ {
|
|
|
+ for (int k = right_front_mag_queue.size() - 6; k < right_front_mag_queue.size(); k++)
|
|
|
+ {
|
|
|
+ right_front_mag_canve_queue.push_back(right_front_mag_queue[k]);
|
|
|
+ left_front_mag_canve_queue.push_back(left_front_mag_queue[k]);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ right_front_mag_canve_queue.push_back(right_front_mag_queue.back());
|
|
|
+ left_front_mag_canve_queue.push_back(left_front_mag_queue.back());
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ right_front_mag_canve_queue.clear();
|
|
|
+ left_front_mag_canve_queue.clear();
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if (right_front_mag_canve_queue.size() > 20)
|
|
|
+ {
|
|
|
+ right_front_mag_canve_queue.pop_front();
|
|
|
+ left_front_mag_canve_queue.pop_front();
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ if (left_front_mag_canve_queue.size() > 9)
|
|
|
+ {
|
|
|
+ //1、补充蹲,检测到一个完成的波视为蹲就好
|
|
|
+
|
|
|
+ int left_top_index;
|
|
|
+ int left_foot_left_side_index, left_foot_right_side_index;
|
|
|
+ top_point(left_front_mag_canve_queue, left_top_index, left_foot_left_side_index, left_foot_right_side_index);
|
|
|
+
|
|
|
+ int right_top_index;
|
|
|
+ int right_foot_left_side_index, right_foot_right_side_index;
|
|
|
+ top_point(right_front_mag_canve_queue, right_top_index, right_foot_left_side_index, right_foot_right_side_index);
|
|
|
+
|
|
|
+ if (
|
|
|
+ abs(left_top_index - right_top_index) < 4 //保持定点位置不要相差太多
|
|
|
+ &&left_front_mag_canve_queue[left_top_index] > left_front_mag_canve_queue[left_foot_left_side_index] + 700
|
|
|
+ && left_front_mag_canve_queue[left_top_index] > left_front_mag_canve_queue[left_foot_right_side_index] + 700
|
|
|
+ && right_front_mag_canve_queue[right_top_index] > right_front_mag_canve_queue[right_foot_left_side_index] + 700
|
|
|
+ && right_front_mag_canve_queue[right_top_index] > right_front_mag_canve_queue[right_foot_right_side_index] + 700)
|
|
|
+ {
|
|
|
+ little_front_down = 1;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if (right_front_mag_queue.size() > 20)
|
|
|
+ {
|
|
|
+ int i = right_front_mag_queue.size() - 1;
|
|
|
+
|
|
|
+ if ((left_front_mag_queue[i] > left_front_mag_queue[i - 1] ) &&
|
|
|
+ (right_front_mag_queue[i] > right_front_mag_queue[i - 1]))
|
|
|
+ {
|
|
|
+ if (last_back_down || last_front_down)
|
|
|
+ {
|
|
|
+ front_down = 1;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if (right_front_mag_queue.size() > 20)
|
|
|
+ {
|
|
|
+ int i = right_front_mag_queue.size() - 1;
|
|
|
+
|
|
|
+ if ((left_front_mag_queue[i] < left_front_mag_queue[i - 1] || left_front_mag_queue[i] < left_front_mag_queue[i - 2]
|
|
|
+ || left_front_mag_queue[i] < left_front_mag_queue[i - 3]) &&
|
|
|
+ (right_front_mag_queue[i] < right_front_mag_queue[i - 1] || right_front_mag_queue[i] < right_front_mag_queue[i - 2]
|
|
|
+ || right_front_mag_queue[i] < right_front_mag_queue[i - 3]))
|
|
|
+ {
|
|
|
+ if (last_little_front_down)
|
|
|
+ {
|
|
|
+ little_front_down = 1;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ int res = 0;
|
|
|
+ if (back_down == 1)
|
|
|
+ {
|
|
|
+ res |= 0x02;
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ if (front_down == 1)
|
|
|
+ {
|
|
|
+ res |= 0x01;
|
|
|
+ }
|
|
|
+
|
|
|
+ if (little_front_down == 1)
|
|
|
+ {
|
|
|
+ res |= 0x04;
|
|
|
+ }
|
|
|
+
|
|
|
+ last_back_down = back_down;
|
|
|
+ last_front_down = front_down;
|
|
|
+ last_little_front_down = little_front_down;
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ return res;
|
|
|
+
|
|
|
+}
|
|
|
+
|
|
|
+/*
|
|
|
+* 检测触地的一个东西
|
|
|
+*/
|
|
|
+
|
|
|
+void online_motion::push_press_queue(deque<int>& press_queue, int press, int queue_size)
|
|
|
+{
|
|
|
+ press_queue.push_back(press);
|
|
|
+
|
|
|
+ if (press_queue.size() > queue_size)
|
|
|
+ {
|
|
|
+ press_queue.pop_front();
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+int online_motion::check_press_queue_up(deque<int>& press_queue, int thresh_hold)
|
|
|
+{
|
|
|
+ int k = press_queue.size() - 1;
|
|
|
+
|
|
|
+ while (k > 0)
|
|
|
+ {
|
|
|
+ if (!(press_queue[k] >= press_queue[k - 1]))
|
|
|
+ {
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ k--;
|
|
|
+ }
|
|
|
+
|
|
|
+ if(press_queue.back() - press_queue[k] > thresh_hold)
|
|
|
+ {
|
|
|
+ return 1;
|
|
|
+ }
|
|
|
+
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|
|
|
+
|
|
|
+int online_motion::online_detect_touch_floor(int right_front_mag, int left_front_mag, int right_back_mag, int left_back_mag)
|
|
|
+{
|
|
|
+ push_press_queue(left_front_press_queue_touch_floor, left_front_mag, 10);
|
|
|
+
|
|
|
+ push_press_queue(right_front_press_queue_touch_floor, right_front_mag, 10);
|
|
|
+
|
|
|
+ push_press_queue(left_back_press_queue_touch_floor, left_back_mag, 10);
|
|
|
+
|
|
|
+ push_press_queue(right_back_press_queue_touch_floor, right_back_mag, 10);
|
|
|
+
|
|
|
+ int right_foot_on_floor = 0;
|
|
|
+ if (check_press_queue_up(right_front_press_queue_touch_floor, 1000) || check_press_queue_up(right_back_press_queue_touch_floor, 1000))
|
|
|
+ {
|
|
|
+ right_foot_on_floor = 1;
|
|
|
+ }
|
|
|
+
|
|
|
+ int left_foot_on_floor = 0;
|
|
|
+ if (check_press_queue_up(left_front_press_queue_touch_floor, 1000) || check_press_queue_up(left_back_press_queue_touch_floor, 1000))
|
|
|
+ {
|
|
|
+ left_foot_on_floor = 1;
|
|
|
+ }
|
|
|
+
|
|
|
+ return right_foot_on_floor << 1 | left_foot_on_floor;
|
|
|
+
|
|
|
+
|
|
|
+}
|
|
|
+
|
|
|
+
|
|
|
+/*
|
|
|
+* 在线检测跳
|
|
|
+*/
|
|
|
+
|
|
|
+int online_motion::online_detect_jump(int right_front_mag, int left_front_mag, int right_back_mag, int left_back_mag,
|
|
|
+ int* right_acc, int* left_acc)
|
|
|
+{
|
|
|
+ right_front_jump_mag_queue.push_back(right_front_mag);
|
|
|
+ left_front_jump_mag_queue.push_back(left_front_mag);
|
|
|
+
|
|
|
+ right_acc_z_queue.push_back(right_acc[2]);
|
|
|
+ left_acc_z_queue.push_back(left_acc[2]);
|
|
|
+
|
|
|
+ if (right_front_jump_mag_queue.size() > 10)
|
|
|
+ {
|
|
|
+ right_front_jump_mag_queue.pop_front();
|
|
|
+ left_front_jump_mag_queue.pop_front();
|
|
|
+
|
|
|
+ right_acc_z_queue.pop_front();
|
|
|
+ left_acc_z_queue.pop_front();
|
|
|
+ }
|
|
|
+
|
|
|
+ int k = left_front_jump_mag_queue.size() - 1;
|
|
|
+ while (k > 0)
|
|
|
+ {
|
|
|
+ if (!(left_front_jump_mag_queue[k] < left_front_jump_mag_queue[k - 1] + 100
|
|
|
+ && right_front_jump_mag_queue[k] < right_front_jump_mag_queue[k - 1] + 100))
|
|
|
+ {
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ k--;
|
|
|
+ }
|
|
|
+
|
|
|
+ int res = 0;
|
|
|
+
|
|
|
+ if (left_front_jump_mag_queue[k] - left_front_jump_mag_queue.back() > 4000
|
|
|
+ && right_front_jump_mag_queue[k] - right_front_jump_mag_queue.back() > 4000)
|
|
|
+ {
|
|
|
+ auto left_max_element = max_element(left_acc_z_queue.begin(), left_acc_z_queue.end());
|
|
|
+ auto left_min_element = min_element(left_acc_z_queue.begin(), left_acc_z_queue.end());
|
|
|
+
|
|
|
+ auto right_max_element = max_element(right_acc_z_queue.begin(), right_acc_z_queue.end());
|
|
|
+ auto right_min_element = min_element(right_acc_z_queue.begin(), right_acc_z_queue.end());
|
|
|
+
|
|
|
+ if (left_max_element < left_min_element && right_max_element < right_min_element &&
|
|
|
+ *left_max_element - *left_min_element > 1500 && *right_max_element - *right_min_element > 1500)
|
|
|
+ {
|
|
|
+ res = 1;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return res;
|
|
|
+
|
|
|
+}
|
|
|
+
|