学了arduino一段时间,抽了点时间把避障小车做了一下,现在把小车的制作过程在这里记录一下,以便日后查阅。
首先说一下用到的材料:
1、小车底盘一套(淘宝淘的现成的,其实也可以自己做)
2、18650电池盒一个(可装三节电池 12V)
3、超声波模块(HC-SR04)一个
4、红外模块(E18-D50NK)一个
5、红外模块(E18-D80NK)一个(之前只用了超声波和D50模块,结果效果不怎么好,又多买了一个红外模块,50跟80的区别貌似在于测量的最大距离不同)
6、L298N点击驱动模块一个
7、自制的arduino模块一个(也可以用其它版本现成的arduino模块)
8、无线蓝牙模块一个
用到的就是以上这些模块,拼接完成后如下图:
线路图这里就不做说明了,大家可以看代码的引脚定义接线,这里有几点要特别说明一下
小车代码支持两种控制模式,见代码
- //定义模式 1-手动模式 2-自动避障模式
- int MODE = 1;
手动模式可以使用手机连接蓝牙设备进行控制,这里提供一个控制软件itead studio【点击下载】,当小车设置为自动模式时,小车会自动避障移动,可在软件中将A和B分别设置为1和2,就可以任意切换小车模式了代码如下:
- #include <SoftwareSerial.h>
- //定义电机控制引脚
- #define IN1 5
- #define IN2 6
- #define IN3 7
- #define IN4 8
- //定义电机PWM引脚
- #define speedPinA 9
- #define speedPinB 10
- //定义红外测距模块E18数据引脚
- #define E18D50Pin 3
- #define E18D80Pin 4
- //定义超声波数据引脚
- const int TrigPin = 2;
- const int EchoPin = 11;
- //超声波模块测出的距离
- float distance = 0;
- //蓝牙模块接收的数据
- char rec= ' ';
- //定义模式 1-手动模式 2-自动避障模式
- int MODE = 1;
- //定义软串口,数据测试用
- SoftwareSerial mySerial(12, 13); // RX, TX
- void setup()
- {
- //初始化串口
- Serial.begin(9600);
- mySerial.begin(4800);
- //初始化电机引脚
- _initmPin();
- //初始化超声波引脚
- _initSR04Pin();
- //电机保持不动。
- _cStop();
- }
- void loop()
- {
- if(MODE==1){
- while(Serial.available()){
- rec=Serial.read();
- if(rec=='1'){
- MODE=1;
- }else if(rec=='2'){
- MODE=2;
- }
- if(MODE!=1)
- break;
- if(rec=='f'){
- _cForward();
- setFSpeed();
- }else if(rec=='b'){
- _cBack();
- setBSpeed();
- }else if(rec=='l'){
- _cLeft();
- setLSpeed();
- }else if(rec=='r'){
- _cRight();
- setRSpeed();
- }else{
- _cStop();
- }
- //设置电机转速
- rec= ' ';
- }
- }
- if(MODE==2){
- if(Serial.available()){
- rec=Serial.read();
- if(rec=='1'){
- MODE=1;
- }
- else if(rec=='2'){
- MODE=2;
- }
- }
- _getDistance();
- mySerial.println(distance);
- if(distance>25.0&&digitalRead(E18D50Pin)==HIGH&&digitalRead(E18D80Pin)==HIGH){
- _cForward();
- setFSpeed();
- }else{
- _cRight();
- setRSpeed();
- }
- }
- //设置电机转速
- rec= ' ';
- }
- //由于买的电机速度不同,这里用pwm的方式调了一下速
- void setFSpeed(){
- _mSetSpeed(speedPinA,65);
- _mSetSpeed(speedPinB,70);
- }
- void setLSpeed(){
- _mSetSpeed(speedPinA,47);
- _mSetSpeed(speedPinB,50);
- }
- void setRSpeed(){
- _mSetSpeed(speedPinA,47);
- _mSetSpeed(speedPinB,50);
- }
- void setBSpeed(){
- _mSetSpeed(speedPinA,69);
- _mSetSpeed(speedPinB,70);
- }
- //通过超声波模块获取障碍物距离
- void _getDistance(){
- // 产生一个10us的高脉冲去触发TrigPin
- digitalWrite(TrigPin, LOW);
- delayMicroseconds(2);
- digitalWrite(TrigPin, HIGH);
- delayMicroseconds(10);
- digitalWrite(TrigPin, LOW);
- // 检测脉冲宽度,并计算出距离
- distance = pulseIn(EchoPin, HIGH) / 58.00;
- delay(100);
- }
- //初始化电机引脚
- void _initmPin(){
- pinMode(IN1,OUTPUT);
- pinMode(IN2,OUTPUT);
- pinMode(IN3,OUTPUT);
- pinMode(IN4,OUTPUT);
- pinMode(speedPinA,OUTPUT);
- pinMode(speedPinB,OUTPUT);
- }
- //初始化微波模块引脚
- void _initSR04Pin(){
- pinMode(TrigPin,OUTPUT);
- pinMode(EchoPin,INPUT);
- }
- void _cForward()//小车向前移动
- {
- _mRight(IN1,IN2);
- _mRight(IN3,IN4);
- }
- void _cBack()//小车向后移动
- {
- _mLeft(IN1,IN2);
- _mLeft(IN3,IN4);
- }
- void _cStop()//小车停止
- {
- _mStop(IN1,IN2);
- _mStop(IN3,IN4);
- }
- void _cLeft()//小车向左旋转
- {
- _mRight(IN1,IN2);
- _mLeft(IN3,IN4);
- }
- void _cRight()//小车向右旋转
- {
- _mLeft(IN1,IN2);
- _mRight(IN3,IN4);
- }
- //
- void _mRight(int pin1,int pin2)//电机右转,电机到底是右转还是左转取决于电机端的接线和控制脚的顺序
- {
- digitalWrite(pin1,HIGH);
- digitalWrite(pin2,LOW);
- }
- void _mLeft(int pin1,int pin2)//电机左转,电机到底是右转还是左转取决于电机端的接线和控制脚的顺序
- {
- digitalWrite(pin1,LOW);
- digitalWrite(pin2,HIGH);
- }
- void _mStop(int pin1,int pin2)//电机停止
- {
- digitalWrite(pin1,HIGH);
- digitalWrite(pin2,HIGH);
- }
- void _mSetSpeed(int pinPWM,int SpeedValue)//控制电机速度
- {
- analogWrite(pinPWM,SpeedValue);
- }
欢迎加入QQ群:254267969,共同交流学习~~~~
联系客服