简介

这是由DFRobot与OYMotion合作推出的一款肌电传感器模块。本传感器模块通过检测人体的表面肌电信号(sEMG),进而反应出人体肌肉和神经的活动情况。

本传感器模块集成了滤波、放大电路,将范围在±1.5mV内的微弱人体表面肌电信号进行1000倍放大,并通过差分输入、模拟滤波电路的方式对噪音(特别是工频干扰)进行有效抑制。输出信号为模拟量形式,以1.5V为基准电压,0~3.0V量程的输出。输出信号的大小取决于选定肌肉的活动量,输出信号的波形可显著指示被观察位置皮下肌肉的情况,方便做肌电信号的分析与研究,如使用Arduino作为控制器检测肌肉活动情况,如肌肉是否紧绷,强度如何,是否疲劳等。

本产品是一种主动感应传感器,能提供高质量的信号搜集,且易于使用。不论是被用到静态还是动态的应用领域,仅需要一些极为简单的准备工作即可。本产品使用干电极,无须导电凝胶也可得到良好的信号质量,因此具有寿命长、使用简单方便等特点,更适合普通用户。而采用凝胶探头的医用电极通常为一次性,使用起来较为麻烦。

本产品的测量具有非侵入性、无创伤、操作简单等优点,可用于人机交互等相关应用。虽然测量肌肉活动历来被用于医学研究,然而随着不断缩小但功能更强大的微控制器和集成电路的完善,肌电图电路和传感器也逐渐被应用于各种控制系统。

供电电压在3.3~5.5V之间,供电电流不小于20mA,纹波与其他噪音要小。推荐使用经过稳压的直流电压。

肌电信号的有效频谱范围为20Hz~500Hz,推荐采用分辨率不低于8bit、有效采样频率不低于1KHz的模数转换器(ADC)进行采样与数字化,以保留尽量多的原始信息。

采用配套的金属干电极板,需将电极板保持和肌肉方向一致。

本品并非专业医疗仪器,不能作为辅助配件参与诊断和治疗。

技术规格

信号处理板供电电压:+3.3V~5.5V

工作电压:+3.0V

检测范围:+/-1.5mV

电极接口:PJ-342

模块接口:PH2.0-3P

输出范围:0~3.0V

工作温度:0~50℃

板子尺寸:22 * 35 mm

干电极板电极接口:PJ-342

电极线长:50cm

板子尺寸:22 * 35 mm

重量:36g

引脚说明

肌电传感器信号处理板管脚定义

标号

名称

功能描述

1

A

模拟信号输出端(0~3.0V)

2

+

电源输入正极(3.3~5.5V)

3

-

电源输入负极

4

PJ-342

电极连线接口

肌电传感器信号处理板管脚定义

使用教程

本教程将演示如何使用这款肌电传感器,通过Arduino IDE的Serial Plotter打印出肌电波形。

准备

硬件1 x Arduino UNO控制板(或类似)

1 x 肌电传感器信号处理板

1 x 肌电传感器干电极

1 x 干电极连接线

1 x 3P模拟信号线

若干 杜邦线

软件Arduino IDE(推荐1.8.2及以上), 点击下载Arduino IDE

接线图

样例代码

本样例代码需要EMGFilters库文件,请先下载库文件后并安装。

如何安装库?

/*

* Copyright 2017, OYMotion Inc.

* All rights reserved.

*

* Redistribution and use in source and binary forms, with or without

* modification, are permitted provided that the following conditions

* are met:

*

* 1. Redistributions of source code must retain the above copyright

* notice, this list of conditions and the following disclaimer.

*

* 2. Redistributions in binary form must reproduce the above copyright

* notice, this list of conditions and the following disclaimer in

* the documentation and/or other materials provided with the

* distribution.

*

* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS

* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT

* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS

* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE

* COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,

* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,

* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS

* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED

* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,

* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF

* THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH

* DAMAGE.

*

*/

#if defined(ARDUINO) && ARDUINO >= 100

#include "Arduino.h"

#else

#include "WProgram.h"

#endif

#include "EMGFilters.h"

#define TIMING_DEBUG 1

#define SensorInputPin A0 // input pin number

EMGFilters myFilter;

// discrete filters must works with fixed sample frequence

// our emg filter only support "SAMPLE_FREQ_500HZ" or "SAMPLE_FREQ_1000HZ"

// other sampleRate inputs will bypass all the EMG_FILTER

int sampleRate = SAMPLE_FREQ_1000HZ;

// For countries where power transmission is at 50 Hz

// For countries where power transmission is at 60 Hz, need to change to

// "NOTCH_FREQ_60HZ"

// our emg filter only support 50Hz and 60Hz input

// other inputs will bypass all the EMG_FILTER

int humFreq = NOTCH_FREQ_50HZ;

// Calibration:

// put on the sensors, and release your muscles;

// wait a few seconds, and select the max value as the threshold;

// any value under threshold will be set to zero

static int Threshold = 0;

unsigned long timeStamp;

unsigned long timeBudget;

void setup() {

/* add setup code here */

myFilter.init(sampleRate, humFreq, true, true, true);

// open serial

Serial.begin(115200);

// setup for time cost measure

// using micros()

timeBudget = 1e6 / sampleRate;

// micros will overflow and auto return to zero every 70 minutes

}

void loop() {

/* add main program code here */

// In order to make sure the ADC sample frequence on arduino,

// the time cost should be measured each loop

/*------------start here-------------------*/

timeStamp = micros();

int Value = analogRead(SensorInputPin);

// filter processing

int DataAfterFilter = myFilter.update(Value);

int envlope = sq(DataAfterFilter);

// any value under threshold will be set to zero

envlope = (envlope > Threshold) ? envlope : 0;

timeStamp = micros() - timeStamp;

if (TIMING_DEBUG) {

// Serial.print("Read Data: "); Serial.println(Value);

// Serial.print("Filtered Data: ");Serial.println(DataAfterFilter);

Serial.print("Squared Data: ");

Serial.println(envlope);

// Serial.print("Filters cost time: "); Serial.println(timeStamp);

// the filter cost average around 520 us

}

/*------------end here---------------------*/

// if less than timeBudget, then you still have (timeBudget - timeStamp) to

// do your work

delayMicroseconds(500);

// if more than timeBudget, the sample rate need to reduce to

// SAMPLE_FREQ_500HZ

}

校准

推荐每次使用时都校准一次,因为即使是同一个人,不同位置的肌电信号也是不同的。

1. 将样例代码中的Threshold变量改成0,即:static int Threshold = 0;

2. 上传样例代码至arduino控制板中,然后打开arduino IDE的串口监视器,观察打印的数值。

3. 放松手臂上的肌肉,观察串口打印的数值。身心平静,让肌肉放松一会,观察串口监视器打印的最大数值,并记录之。如果数值太大,比如1000以上,可尝试微调干电极的放置位置。

4. 将样例代码中的Threshold变量改成刚才记录的最大数值,重新上传样例代码至arduino主控板。5. 打开arduino IDE的Serial Plotter,即可看到肌电波形。一般情况下,肌肉放松时,是一条值始终为0的直线,如下图所示。如偶尔有几个尖峰波形出现,也属正常现象。

用力握拳的过程中,可看到明显的肌电波形,如下图所示。

基础应用演示

本应用通过对握拳次数进行计数的演示,来说明如何识别是否有肌电信号产生。识别是否有肌电信号,是对肌肉活动进行计数,可用于俯卧撑计数、哑铃计数等场合,也可用于人机交互,如用握拳产生的肌电信号玩Flappy Bird游戏等。

本应用使用的硬件连接、传感器位置放置可参考本维库中第四章的“4.1 准备”与“4.2 接线图”。

本样例代码需要EMGFilters库文件,如还没有下载,请先下载库文件后并安装。

如何安装库?

/*

Copyright 2017, OYMotion Inc.

All rights reserved.

Redistribution and use in source and binary forms, with or without

modification, are permitted provided that the following conditions

are met:

1. Redistributions of source code must retain the above copyright

notice, this list of conditions and the following disclaimer.

2. Redistributions in binary form must reproduce the above copyright

notice, this list of conditions and the following disclaimer in

the documentation and/or other materials provided with the

distribution.

THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS

"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT

LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS

FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE

COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,

INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,

BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS

OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED

AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,

OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF

THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH

DAMAGE.

*/

#if defined(ARDUINO) && ARDUINO >= 100

#include "Arduino.h"

#else

#include "WProgram.h"

#endif

#include "EMGFilters.h"

#define SensorInputPin A0 //sensor input pin number

/*

Define the `threshold` variable as 0 to calibrate the baseline value of input sEMG signals first.

After wiring the sEMG sensors to the Arduino board, wear the sEMG sensors. Relax your muscles for a few seconds,

you will be able to see a series of squared sEMG signals values get printed on your serial terminal.

Choose the maximal one as the baseline by setting the `threshold` variable. Then rebuild this project.

The `envelope`, which is the squared sEMG signal data, will be printed to the serial line.

The developer can plot it using the Arduino SerialPlotter.

Note:

After calibration, Any squared value of sEMG sigal below the baseline will be treated as zero.

It is recommended that you do calibration every time you wear the sEMG sensor.

*/

unsigned long threshold = 0; // threshold: Relaxed baseline values.(threshold=0:in the calibration process)

unsigned long EMG_num = 0; // EMG_num: The number of statistical signals

EMGFilters myFilter;

/*

Set the input frequency.

The filters work only with fixed sample frequency of

`SAMPLE_FREQ_500HZ` or `SAMPLE_FREQ_1000HZ`.

Inputs at other sample rates will bypass

*/

SAMPLE_FREQUENCY sampleRate = SAMPLE_FREQ_500HZ;

/*

Set the frequency of power line hum to filter out.

For countries with 60Hz power line, change to "NOTCH_FREQ_60HZ"

*/

NOTCH_FREQUENCY humFreq = NOTCH_FREQ_50HZ;

void setup()

{

myFilter.init(sampleRate, humFreq, true, true, true);

Serial.begin(115200);

}

void loop()

{

int data = analogRead(SensorInputPin);

int dataAfterFilter = myFilter.update(data); // filter processing

int envelope = sq(dataAfterFilter); //Get envelope by squaring the input

envelope = (envelope > threshold) ? envelope : 0; // The data set below the base value is set to 0, indicating that it is in a relaxed state

/* if threshold=0,explain the status it is in the calibration process,the code bollow not run.

if get EMG singal,number++ and print

*/

if (threshold > 0)

{

if (getEMGCount(envelope))

{

EMG_num++;

Serial.print("EMG_num: ");

Serial.println(EMG_num);

}

}

else {

Serial.println(envelope);

}

delayMicroseconds(500);

}

/*

if get EMG signal,return 1;

*/

int getEMGCount(int gforce_envelope)

{

static long integralData = 0;

static long integralDataEve = 0;

static bool remainFlag = false;

static unsigned long timeMillis = 0;

static unsigned long timeBeginzero = 0;

static long fistNum = 0;

static int TimeStandard = 200;

/*

The integral is processed to continuously add the signal value

and compare the integral value of the previous sampling to determine whether the signal is continuous

*/

integralDataEve = integralData;

integralData += gforce_envelope;

/*

If the integral is constant, and it doesn't equal 0, then the time is recorded;

If the value of the integral starts to change again, the remainflag is true, and the time record will be re-entered next time

*/

if ((integralDataEve == integralData) && (integralDataEve != 0))

{

timeMillis = millis();

if (remainFlag)

{

timeBeginzero = timeMillis;

remainFlag = false;

return 0;

}

/* If the integral value exceeds 200 ms, the integral value is clear 0,return that get EMG signal */

if ((timeMillis - timeBeginzero) > TimeStandard)

{

integralDataEve = integralData = 0;

return 1;

}

return 0;

}

else {

remainFlag = true;

return 0;

}

}

推荐每次使用时都校准一次,因为即使是同一个人,不同位置的肌电信号也是不同的。

1. 本代码中,threshold变量的值默认为0,表示处于校准模式。改成非零值,则退出校准模式。因此,如要重新进行校准,将代码中的threshold变量改成0即可,即:unsigned long threshold = 0;

2. 上传代码至arduino控制板中,然后打开arduino IDE的Serial Plotter,观察y轴数值的最大值。

3. 轻轻的握紧拳头,再轻轻的松开拳头,如此循环。观察Serial Plotter中y轴出现的最大值并记录之。将如下图,最大值为400左右。

4. 将代码中的threshold变量改成刚才记录的最大数值。推荐改成:最大值+100,提升抗干扰能力。重新上传样例代码至arduino主控板。

5. 打开arduino IDE的Serial Monitor,用力握拳并松开一次,即可看到打印出的计数。轻轻的握拳是不会计数的。用力紧握拳不放,计数也不会累加,必须握紧后并松开才能计数。通过这种方式,就实现了对握拳进行精确计数。

如发现松拳时,计数多次累加,则是阀值设置的较低,引起误判。可将代码中的threshold变量值再加100,重新上传样例代码至arduino主控板,再次查看效果,直到把threshold变量加到满意效果为止。

将传感器放置在需要检测肌肉活动的位置,再进行校准,就可对肌肉活动进行精确计数,如用于俯卧撑计数、哑铃计数等健身场合,也可用于人机交互,如用握拳产生的肌电信号玩Flappy Bird游戏等。

除了这个基础功能,该传感器也能通过判断每次信号的强度来检测肌肉活动强度。更多应用,请参考本维库下方的“更多资料”。

常见问题

Q1. 手臂上什么地方可以放置干电极?有什么要求吗?

A. 一般来说,采用配套的三金属干电极板,无需关注参考电平,只需将电极板保持和肌肉方向一致即可。放置位置可参考下图:

更多问题及有趣的应用,可以 访问论坛 进行查阅或发帖。

更多资料

盒仔机器人_DFROBOT SEN0240 肌电传感器 OYMotion 产品资料 使用教程相关推荐

  1. 了解【泰科】协作机器人产品资料大全

    了解[泰科]协作机器人产品资料大全 协作机器人 关于泰科 随着近些年市场对小批量.多样化的定制需求越来越多,企业对机器人高效率.柔性化和复杂作业自动化需求有了很大的提高,可以灵活在多项工作任务中快速切 ...

  2. 计算机控制技术(机器人方向)理论与实践补充资料和复习说明(2019版)

    计算机控制技术(机器人方向)理论与实践补充资料和复习说明(2019版) 如何完成将求解课本习题----解决实际问题的转变(理论-实际),是实现学员----工程师的重要节点. 这个其实主要靠自身努力,无 ...

  3. 微信群聊小机器人的服务器,微信群里自动聊天的机器人是怎么弄的?有没有操作教程?...

    原标题:微信群里自动聊天的机器人是怎么弄的?有没有操作教程? 很多人在做微信营销的时候都在群里放了个"机器人",这个机器人到底是什么来头,有这么神奇,这么智能吗? 其实这个机器人只 ...

  4. MLX90640 红外热成像仪测温传感器模块PC端操作教程

    河北稳控科技MLX90640 红外热成像仪测温传感器模块PC端操作教程 1.驱动程序安装 本设备没有自带显示设备(屏幕),若要进行实时图像查看或者参数修改需要连接到计算机或者手机,并由对应的工具软件完 ...

  5. 小米扫地机器人 贴膜_扫地变拖扫:石头T4小米扫地机器人第三方拖地组件两代产品对比测试...

    扫地变拖扫:石头T4&小米扫地机器人第三方拖地组件两代产品对比测试 2019-06-28 11:45:00 267点赞 1383收藏 286评论 关注话题#下单前必看的对比评测#(点击关注). ...

  6. diy 扫地机器人 滚刷_霍尔传感器在扫地机器人中的作用

    推荐阅读 现代社会,目之所及之处我们都会发现扫地机的品类已经越来越多了.市场的繁荣得益于科技的发展,以及消费者对生活质量更深的解读.随着扫地机硬件供应链和导航方案的快速成熟,进入门槛在逐渐降低,产品端 ...

  7. 机器人技术-HC-SR04超声波传感器数据及机器人避障的应用

    比较详细的HC-SR04超声波传感器数据及机器人避障的应用方法 言.超声波传感器概述 超声波传感器型号繁多,价格从几元钱到几百元不等,主要用于检测距离,同时根据声速计算出物体的距离.但超声波传感器有四 ...

  8. 工业级洗地机器人_基于多传感器融合的自动洗地机器人避障研究

    龙源期刊网 http://www.qikan.com.cn 基于多传感器融合的自动洗地机器人避障研 究 作者:杨建峰 杨丽英 刘珍娜 来源:<山东工业技术> 2019 年第 13 期 摘 ...

  9. 机器人上使用超声波传感器的原理

    超声波传感器的原理? 超声波传感器是用来测量物体的距离.首先,超声波传感器会发射一组高频声波,一般为40-45KHz,当声波遇到物体后,就会被反弹回,并被接受到.通过计算声波从发射到返回的时间,再乘以 ...

  10. 【转】机器人上用的传感器的介绍

    感知系统是机器人能够实现自主化的必须部分.这一章,将介绍一下移动机器人中所采用的传感器以及如何从传感器系统中采集所需要的信号. 根据传感器的作用分,一般传感器分为: 内部传感器(体内传感器):主要测量 ...

最新文章

  1. hypervisor简介
  2. C#中数据类型转换-隐式转换
  3. 你应该知道的计算机网络知识
  4. linux 下,解决tomcat服务器接收中文乱码的问题
  5. AVFoundation 文本转语音和音频录制 播放
  6. 递归三:变态蛙跳台阶
  7. 简单的多目标遗传算法实现
  8. 关于MYSQL 的 AUTO-INC Locks
  9. 她半年内举报了755篇问题论文,专挑中国“下手”?还牵扯到北大副校长.........
  10. 阿里云物联网平台 > 设备接入 > 使用开放协议自主接入 > MQTT协议接入 >
  11. linux windows死机,linux死机的处理方式
  12. 《linux c编程指南》学习手记1
  13. react-native-echarts 解决数据刷新闪烁,不能动态连续绘制问题(转载)
  14. 闪烁指示灯监控方案_机房温湿度监控检测方案【斯必得智慧机房】
  15. 一如此前的回应,王劲将景驰科技总部搬到了广州
  16. 【大数据课程设计】出租车轨迹数据分析
  17. java中三个基本框架_javaweb框架主要的三大基本框架是哪些?作用分别是什么?...
  18. ubuntu22.04 运行qq音乐闪退
  19. PPT是在投影仪或者计算机上进行演示,如何将幻灯片PPT转换成视频播放
  20. 程序员坐牢了,会被安排去写代码吗?

热门文章

  1. 2021李宏毅机器学习笔记
  2. 胖子哥的大数据之路(二)- 大数据结构化数据存储应用模式
  3. 人工智能能为旅游业带来多大的想象空间?
  4. STM32F407 硬件IIC驱动MCP4017 数字电位器
  5. armv6 armv7 armv7s架构的区别
  6. 博文视点“阿里云全系列技术图书”隆重亮相2021云栖大会
  7. 常见ActiveX控件下载大全
  8. 测试工具之 LoadRunner WinRunner
  9. 中国妇女儿童统计资料(2014-2020年)
  10. php中adodb中文手册,[转载]ADODB中文手册(4)