零知两轮小车入门版(零知mini主控)教程-程序控制电机开跑

本系列教程讲解零知小车套件以零知迷你板为主控,使用零知开源平台进行智能小车开发。

使用的硬件:零知智能小车套件

实现的功能:红外循迹、超声避障、直线运行等基本功能。

扩展:可以在小车上加入其它传感器模块进行扩展,比如加入摄像头模块进行监控、加入火焰传感器做灭火小车、加入更多超声波模块实现自动跟随...

本系列教程目录

零知两轮小车入门版(零知mini主控)系列教程-小车组装


零知两轮小车入门版(零知mini主控)系列教程-程序控制电机开跑


零知两轮小车入门版(零知mini主控)系列教程-红外循迹走S弯


零知两轮小车入门版(零知mini主控)系列教程-超声波自动避障


零知两轮小车入门版(零知mini主控)系列教程-使用PID走直线

一、准备工作

(1)组装好的智能小车


二、电机驱动说明

这里使用电机驱动为DRV8833型号,我们需要根据它的逻辑表来驱动电机:

其完整的datasheet文件:http://www.ti.com/lit/ds/symlink/drv8833.pdf


三、程序代码

我们根据电机的驱动,使用PWM进行控制,程序如下:
							
							
		
		/**********************************************************
		*    文件: lzsmartcar_v1.ino  
		*by 零知实验室([url=http://www.lingzhilab.com]www.lingzhilab.com[/url])
		*    -^^- 零知开源,让电子制作变得更简单! -^^-
		*    时间: 2019/11/20 15:50
		*    说明: 零知智能小车-迷你板
		************************************************************/
		  
		//调试信息
		#define DEBUG_PRINT
		  
		#include 
		Servo UltraServo;
		  
		/***************************************************************/
		//引脚说明
		  
		//蓝牙模块
		#define BTSerial            Serial2
		  
		//电机模块
		#define MotorIN1            2
		#define MotorIN2            3
		#define MotorIN3            4
		#define MotorIN4            5
		  
		#define MotorIN5            8
		#define MotorIN6            9
		#define MotorIN7            10
		#define MotorIN8            11
		  
		//循迹
		#define TracePin1           18
		#define TracePin2           17
		//#define TracePin3         rst///
		#define TracePin4           12
		#define TracePin5           13
		  
		//舵机
		#define ServoPWM1           15
		#define ServoPWM2           16
		#define ServoPWM3           21
		#define ServoPWM4           24
		  
		//迷你传感器
		#define MiniSensorWire      Wire
		  
		//测速模块 
		#define SM1Pin              29
		#define SM2Pin              28
		  
		//超声波
		#define UltraTrigPin        31
		#define UltraEchoPin        30
		/***************************************************************/
		  
		//小车运行方向
		enum carDirec{
		    carForward = 1,
		    carBack,
		    carLeft,
		    carRight,
		    carStop
		};
		  
		//速度调节
		#define MotorSpeedNormal        140//正常前进速度
		#define MotorSpeedRotate        240
		#define MotorSpeedFast          80 //
		  
		void motorRun(byte motorNum, bool forward, int speed){
		    if(motorNum == 1){
		        if(forward){
		           
					analogWrite(MotorIN1,255);
		            analogWrite(MotorIN2,speed);
		        }else{
		            analogWrite(MotorIN1,speed);
		            analogWrite(MotorIN2,255);
		        }
		    }
		      
		    if(motorNum == 2){
		        if(forward){
		            analogWrite(MotorIN3,speed);
		            analogWrite(MotorIN4,255);
		        }else{
		            analogWrite(MotorIN3,255);
		            analogWrite(MotorIN4,speed);
		        }
		    }
		}
		  
		void motorStop()
		{
		    analogWrite(MotorIN1,255);
		    analogWrite(MotorIN2,255);
		    analogWrite(MotorIN3,255);
		    analogWrite(MotorIN4,255);
		}
		  
		//小车根据命令运行
		void carGo(byte cmd){
		    switch(cmd){
		        case carForward:
		        #ifdef DEBUG_PRINT
		        Serial.println("方向->前进");
		        #endif
		        motorRun(1,true,MotorSpeedNormal);
		        motorRun(2,true,MotorSpeedNormal);
		        motorRun(3,true,MotorSpeedNormal);
		        motorRun(4,true,MotorSpeedNormal);
		        break;
		        case carBack:
		        #ifdef DEBUG_PRINT
		        Serial.println("方向->后退");
		        #endif
		        motorRun(1,false,MotorSpeedNormal);
		        motorRun(2,false,MotorSpeedNormal);
		        motorRun(3,false,MotorSpeedNormal);
		        motorRun(4,false,MotorSpeedNormal);
		        break;
		        case carLeft:
		        #ifdef DEBUG_PRINT
		        Serial.println("方向->左转");
		        #endif
		        motorRun(1,true,MotorSpeedRotate);
		        motorRun(2,true,MotorSpeedFast);
		        motorRun(3,true,MotorSpeedRotate);
		        motorRun(4,true,MotorSpeedFast);
		        break;
		        case carRight:
		        #ifdef DEBUG_PRINT
		        Serial.println("方向->右转");
		        #endif
		        motorRun(1,true,MotorSpeedFast);
		        motorRun(2,true,MotorSpeedRotate);
		        motorRun(3,true,MotorSpeedFast);
		        motorRun(4,true,MotorSpeedRotate);
		        break;
		        case carStop:
		        #ifdef DEBUG_PRINT
		        Serial.println("方向->停止");
		        #endif
		        motorStop();
		        break;
		        default:
		        motorStop();
		        break;
		    }
		}
		  
		  
		// 复位或上电后运行一次:
		void setup() {
		    //在这里加入初始化相关代码,只运行一次:
		      
		    //串口调试
		    Serial.begin(9600);
		      
		    //设置引脚
		    pinMode(MotorIN1,OUTPUT);
		    pinMode(MotorIN2,OUTPUT);
		    pinMode(MotorIN3,OUTPUT);
		    pinMode(MotorIN4,OUTPUT);
		      
		    //默认状态
		    carGo(carStop);
		      
		}
		  
		//一直循环执行:
		void loop() {
		    //测试motor
		    if(Serial.available()){
		        char cmd = Serial.read();
		        if(cmd == '1'){
		            carGo(carForward);
		        }
		        else if(cmd == '2'){
		            carGo(carLeft);
		        }
		        else if(cmd == '3'){
		            carGo(carRight);
		        }
		        else if(cmd == '4'){
		            carGo(carBack);
		        }
		        else{
		            carGo(carStop);
		        }
		    }
		}
							
							

将以上代码验证上传至小车,然后我们在串口调试窗口发送不同的命令,看小车是否按照我们预期的动作运转,如果有冲突是很正常的,因为有时候安装电机的方向不一样,这时候我们就可以根据实际情况修改上述代码,使之和我们安装好的小车运行情况一致。