arduino蓝牙小车

include <SCoop.h>
int leftMotor1=9;//设置不同电机串口
int leftMotor2=8;
int rightMotor3=11;
int rightMotor4=10;
int track1=7;//设置红外线串口从左向右依次为1 2 3 4
int track2=6;
int track3=5;
int track4=4;
int ECH=12;//设置超声波串口
int TRI=13;
void forward();//声明函数前进
void backword();//声明函数后退
void right();//声明函数左转
void left();//声明函数右转
void stop1();//声明函数停止
void trackright();//声明函数单侧右转
void trackleft();//声明函数单侧左转
void turnon(char cmd);//声明电机启动状态并可赋值
void tracing();//声明函数循迹
int TE();//声明函数超声波测距,返回距离“d”

#define NOTE_F1 350
#define NOTE_F2 393
#define NOTE_F3 441
#define NOTE_F4 495
#define NOTE_F5 556
#define NOTE_F6 624
#define NOTE_F7 661
#define NOTE_0  0
#define NOTE_FL1 175
#define NOTE_FL2 196
#define NOTE_FL3 221
#define NOTE_FL4 234
#define NOTE_FL5 262
#define NOTE_FL6 294
#define NOTE_FL7 330

#define NOTE_FH1 700
#define NOTE_FH2 786
#define NOTE_FH3 882
#define NOTE_FH4 935
#define NOTE_FH5 1049
#define NOTE_FH6 1178
#define NOTE_FH7 1322
#define WHOLE 1
#define HALF 0.5
#define QUARTER 0.25
#define EIGHTH 0.25
#define SIXTEENTH 0.625
int tune[] = //简谱频率
{
  NOTE_F4,NOTE_F4,NOTE_F4,NOTE_F4,NOTE_F6,NOTE_F6,NOTE_F6,NOTE_F6,
  NOTE_F5,NOTE_F5,NOTE_F5,NOTE_F5,NOTE_FH1,NOTE_FH1,NOTE_FH1,NOTE_FH1,
  NOTE_FH2,NOTE_FH2,NOTE_FH2,NOTE_FH2,NOTE_FH2,NOTE_FH2,NOTE_FH2,NOTE_FH2,
  NOTE_F5,NOTE_F4,NOTE_F3,NOTE_F1,NOTE_F2,NOTE_0,NOTE_F2,NOTE_F6,
  NOTE_F5,NOTE_0,NOTE_F4,NOTE_0,NOTE_F3,NOTE_0,NOTE_F3,NOTE_F3,NOTE_F5,NOTE_0,NOTE_F4,NOTE_F3,NOTE_F2,NOTE_0,NOTE_F2,NOTE_FH4,
  NOTE_FH3, NOTE_FH4, NOTE_FH3, NOTE_FH4, NOTE_F2, NOTE_0,NOTE_F2,NOTE_FH4, NOTE_FH3, NOTE_FH4, NOTE_FH3, NOTE_FH4, NOTE_F2, NOTE_0,NOTE_F2,NOTE_F6,
  NOTE_F5,NOTE_0,NOTE_F4,NOTE_0,NOTE_F3,NOTE_0,NOTE_F3,NOTE_F3,NOTE_F5,NOTE_0,NOTE_F4,NOTE_F3,NOTE_F2,NOTE_0,NOTE_F2,NOTE_FH4,
  NOTE_FH3, NOTE_FH4, NOTE_FH3, NOTE_FH4, NOTE_F2, NOTE_0,NOTE_F2,NOTE_FH4,NOTE_FH3, NOTE_FH4, NOTE_FH3, NOTE_FH4,
};
float durt[]=                   //根据简谱列出各节拍
{
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5,
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5, 
  0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5
};

int length;//这里定义一个变量,后面用来表示共有多少个音符 
int tonepin=3;//蜂鸣器的pin  
defineTask(TaskTest1);//定义子线程1
defineTask(TaskTest2);//定义子线程2
void TaskTest1::setup()//线程1设定
{
Serial.begin(9600);
pinMode(leftMotor1,OUTPUT);//设置直流电机串口为输出
pinMode(leftMotor2,OUTPUT);
pinMode(rightMotor3,OUTPUT);
pinMode(rightMotor4,OUTPUT);
pinMode(track1,INPUT);//设置红外线串口为输入
pinMode(track2,INPUT);
pinMode(track3,INPUT);
pinMode(track4,INPUT);
//pinMode(track5,INPUT);
//pinMode(track6,INPUT);
pinMode(ECH,INPUT);//要检测引脚输入的脉冲宽度,需先设置为输入状态
pinMode(TRI,OUTPUT);
}
void TaskTest1::loop()//线程1循环(快速定义)
 {
  a://跳转的终止位置
    if(Serial.available())//如果串口缓冲区有数据则执行
     {
        char cmd=Serial.read();//将读取串口缓冲区一个字节的数据赋值给cmd
        if(cmd=='T')//如果读取数据为“T”
         {
        tracing();
         }
        else if (cmd=='K')//如果读取数据为“K”
         {
           while(TE())//如果超声波测距返回有值进行指令
                {
                  if(TE()<=35)
                       {
                          stop1();
                          left();
                          delay(300);
                       }
                else if(Serial.read()=='Q')//如果在串口缓冲区读到的值为‘Q’则执行
                       {
                         goto a;//跳转
                       }  
                else 
                       {
                          forward();
                       }
                 
                 }
         }
       else
          {
             turnon(cmd);//电机激活但并不启动
          }
     }    
 }

void TaskTest2::setup()//线程2设定
{
    pinMode(tonepin,OUTPUT);//设置蜂鸣器的pin为输出模式   
  length = sizeof(tune)/sizeof(tune[0]);//这里用了一个sizeof函数,可以查出
}
void TaskTest2::loop()//线程2循环
{
  b:
   if(Serial.read()=='M')
    {
       for(int x=0;x<length;x++)
            {
               tone(tonepin,tune[x]);
               delay(500*durt[x]);   //这里用来根据节拍调节延时,500这个指数可以自己调整,在该音乐中,我发现用500比较合适。
               noTone(tonepin);
            }  
     }
  else if(Serial.read()=='C')
     {
         Serial.println("12i");
         goto b;
      }
 }

void setup() 
  {
      mySCoop.start();
  }

void loop()
  {
      yield();
  }
 void turnon(char cmd)//电机启动并输入一个值
  {
     switch(cmd)
     {
     case'W':
        forward();
        break;
     case'S':
        backward();
        break;
     case'Q':
        stop1();
        break;
     case'D':
        right();
        break;
     case'A':
        left();
     break;
      }
  }
  void tracing()//红外循迹
  {
     int t1;
     int t2;
     int t3;
     int t4;
    
 红外线循迹///    
 
  while(Serial.available()==0)//如果串口缓冲区值为零进行指令
 {
  t1=digitalRead(track1);
  t2=digitalRead(track2);
  t3=digitalRead(track3);
  t4=digitalRead(track4);

 if(t1==1&&t2==1&&t3==1&&t4==1)//从左至右依次为t1  t2   t3  t4 
  {
    stop1();//停止
  }
 else if(t1==1||t2==1)
  {
    trackleft(); //单侧左转
  }
 else if(t3==1||t4==1)
  {  
    trackright();
  }
else if(t1==0&&t2==0&&t3==0&&t4==0)
  {
  forward();
  }
}
 }
子函数    
    
    void forward()//前进
    {
    Serial.println("FORWARD");//输出状态
    digitalWrite(leftMotor1,HIGH);
    digitalWrite(leftMotor2,LOW);
    digitalWrite(rightMotor3,HIGH);
    digitalWrite(rightMotor4,LOW);
    }
   void backward()//后退
    {
    Serial.println("BACKWORD");//输出状态
    digitalWrite(leftMotor1,LOW);
    digitalWrite(leftMotor2,HIGH);
    digitalWrite(rightMotor3,LOW);
    digitalWrite(rightMotor4,HIGH);}
  void right()
   {
   Serial.println("RIGHT");//输出状态
   digitalWrite(leftMotor1,HIGH);
   digitalWrite(leftMotor2,LOW);
   digitalWrite(rightMotor3,LOW);
   digitalWrite(rightMotor4,HIGH);}
  void left()//左转
   {
   Serial.println("LEFT");//输出状态
   digitalWrite(leftMotor1,LOW);
   digitalWrite(leftMotor2,HIGH);
   digitalWrite(rightMotor3,HIGH);
   digitalWrite(rightMotor4,LOW);}
  void stop1()//停止
   {
   Serial.println("STOP");//输出状态
   digitalWrite(leftMotor1,LOW);
   digitalWrite(leftMotor2,LOW);
   digitalWrite(rightMotor3,LOW);
   digitalWrite(rightMotor4,LOW);
   }
  void trackright()//单侧右转
   {
  digitalWrite(leftMotor1,HIGH);
   digitalWrite(leftMotor2,LOW);
   digitalWrite(rightMotor3,HIGH);
   digitalWrite(rightMotor4,HIGH);}

  void trackleft()//单侧左转
   {
   digitalWrite(leftMotor1,HIGH);
   digitalWrite(leftMotor2,HIGH);
   digitalWrite(rightMotor3,HIGH);
   digitalWrite(rightMotor4,LOW);
   }

  int TE()//超声波测距并返回距离“d”
   {
  float d;
  digitalWrite(TRI,LOW);
  delayMicroseconds(8);
  digitalWrite(TRI,HIGH);
  delayMicroseconds(10);
  digitalWrite(TRI,LOW);
  d=pulseIn(ECH,HIGH)/58.30;
  Serial.print("Distance:");
  Serial.print(d);
  Serial.println("cm");
  return d;
  }

# 实现了超声波避障,蓝牙,红外循迹(功能一般),蜂鸣器,忘记是否改过,可能是单片机功能问题,在执行循迹以及避障时播放音乐会卡住,主体结构没问题,最多就是电机正反转有问题

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值