让旧手机成为arduino最方便的传感器-Arduino中文社区 - Powered by Discuz! Archiver

xmile 发表于 2019-3-25 08:45

让旧手机成为arduino最方便的传感器

本帖最后由 xmile 于 2019-7-5 16:17 编辑

这个项目主要是通过手机app通过usb串口发送加速度传感器的数据给arduino并且给arduino供电,而电机则由额外的独立电源供电


材料清单:
小车底盘套间一套(某宝可以搜到,十几块钱可以解决)
杜邦线若干
L293d电机驱动扩展板国产ardunio uno r3(usb驱动为ch341)
usb mini转打印线(用来连接arduino和手机)5号电池4个(我用的是充电电池)
旧安卓手机一台

进度:
调试中硬件
写了一个简单的测试程序,看看各个硬件是否连接正常,又没有接触不良
当接收到加速度为正数时向后退
加速度为负时前进以下为我调试的视频(我调试的时候直接用了手机电源来带动电机,这样其实不对的,而且从视频上可以看到手机的电源带不动电机,所以还是老老实实用电池吧)
https://v.youku.com/v_show/id_XNDExMTE2MTgyNA==.html?spm=a2hzp.8244740.0.0

目前还在pid上折腾,红米1没有角速度传感器,无法直接套用网上pid代码

。。。
好吧,搞错了红米1s是有角速度传感器的,毕竟是内置陀螺仪,不可能只含其中一个的

上一段测试代码



#include <ArduinoJson.h>
String json="";
boolean join=false;
int n = 0;
unsigned char temp=0;
int latchPin = 4;
int clockPin =7;
int dataPin = 8; //这里定义了那三个脚
int LED1 =13;
int LED2=12;
int LED3 =11;
int LED4 =10;
float ax = 0 ;
float ay = 0 ;
int readint = {1,2,3,4};

unsigned char Dis_table[] = {0xC0,0xF9,0xA4,0xB0,0x99,0x92,0x82,0xF8,0X80,0X90};//LED状态显示的变量
unsigned char Dis_table_point[] = {0x40,0x79,0x24,0x30,0x19,0x12,0x02,0x78,0X00,0X10};//LED状态显示的变量带小数点
unsigned char Dis_buf[]   = {0xF1,0xF2,0xF4,0xF8};

void setup() {
// put your setup code here, to run once:
pinMode(latchPin,OUTPUT);
pinMode(clockPin,OUTPUT);
pinMode(dataPin,OUTPUT); //让三个脚都是输出状态
Serial.begin(9600);
//pinMode(LED1,OUTPUT);
//pinMode(LED2,OUTPUT);
//pinMode(LED3,OUTPUT); //让三个脚都是输出状态
   //pinMode(LED4,OUTPUT);
   LED1=0;
   LED2=0;
   LED3=0;
   LED4=0;
//Serial.println("{\"accel\":}");
int2char(0);
}

void loop() {
// put your main code here, to run repeatedly:
//if(Serial.available()){
//Serial.print("proteus recived:");
//Serial.println(Serial.read());
//delay(1000);}
temp = Serial.read();
//Serial.write(temp);
if(temp==254){
    //Serial.println(join);
    join=1-join;
    n++;
}

if(join&&temp>0&&temp<254){
    //json[] += "{\"sensor\":\"gps\",\"time\":1351824120,\"data\":}";
    //{"accel":}
    json += char(temp);
}
if(n==2){
    StaticJsonBuffer<200> jsonBuffer;
    JsonObject& root = jsonBuffer.parseObject(json);
    ax= root["accelermeter"];
    ay= root["accelermeter"];
    Serial.println(ax);
    int2char((int)(ax*100));
    //Serial.println(json);
    delay(1000);
    n=0;
    json="";
}
    for(char i=0; i<=3; i++)//扫描四个数码管
{
    digitalWrite(latchPin,LOW); //将ST_CP口上面加低电平让芯片准备好接收数据
    //shiftOut(dataPin,clockPin,MSBFIRST,Dis_table); //发送显示码 0-3
    shiftOut(dataPin,clockPin,MSBFIRST,i==1?Dis_table_point] : Dis_table]);
    shiftOut(dataPin,clockPin,MSBFIRST,Dis_buf[ i ] );//发送通值                        //串行数据输入引脚为dataPin,时钟引脚为clockPin,执行MSB有限发送,发送数据table
    digitalWrite(latchPin,HIGH); //将ST_CP这个针脚恢复到高电平
    delay(2);       //延时2ms
}
}



void int2char(int i){
//Serial.println(i);
for(int j=4;j>0;j--){
    readint = (int)((i%(int)ipow(10,j))/(int)ipow(10,(j-1)));
    //Serial.println((int)ipow(10,j));
    //Serial.print(":");
    //Serial.println((int)pow(10,j));
}
}

int ipow(int base, int exp)
{
    int result = 1;
    for (;;)
    {
      if (exp & 1)
            result *= base;
      exp >>= 1;
      if (!exp)
            break;
      base *= base;
    }
    return result;
}


2019-06-24更新,上面这段测试代码是通过串口接收缓存里的字符然后再拼接成json,而拼接的方法就是用不需用到的字符(unsigned char) 0XFE 作为开头和结尾,
也就是把需要发给arduino的json字符串用0XFE包裹起来,
这样arduino在接收的时候读到0XFE就开始拼字符串,再次读到0XFE的时候就停止拼接,得到的字符串就是我们需要json字符串。
用json的好处是可以一次发送多个数据,而且还不用哪个担心要如何做好对应的问题,不过记得arduino要先安装好ArduinoJson的库
上面的程序我已经在proteus的仿真中验证过,是可行的

2019-07-04 踩了很多坑,包括pow函数不等于实际幂函数的坑,重新认真学习了移位寄存器的原理
然后将上面的例子更新了,增加了数码管的显示,可以在arduino上查看json解析出来的数是不是跟预期的一样

另外,吐槽一下论坛的代码格式,老是吞我的 '[ i ' 非要我中间打个空格才显示出来

2019-07-05 补上上面做仿真时候的视频,原视频高清的,但是上传到优酷之后就只有标清,代码那里会看不清
https://v.youku.com/v_show/id_XNDI1OTU1OTk0NA==.html?spm=a2hzp.8244740.0.0


更新中。。。






lijing777 发表于 2019-7-25 12:00

还是很厉害的,拿手机当做传感器了,实际上可能手机的算力比arduino强多了,开发安卓可能难度有点大。能够学到东西就好

超能可可 发表于 2020-4-18 15:09

建议在b站发视频,清晰度首先没问题
页: [1]
查看完整版本: 让旧手机成为arduino最方便的传感器