【Arduino】实现超声波测距,性能稳定且测度距离精确

由于超声波指向性强,能量消耗缓慢,在介质中传播的距离较远,因而超声波经常用于距离的测量,如测距仪和物位测量仪等都可以通过超声波来实现。利用超声波检测往往比较迅速、方便、计算简单、易于做到实时控制,并且在测量精度方面能达到工业实用的要求,因此在移动机器人研制上也得到了广泛的应用。

我们今天来学习一下超声波(HC-SR04)模块,超声波是频率很高的声音,其频率超出人类可以听到的声音的频率范围。超声波传感器发出的超声波脉冲频率是42kHz,人类平均可听到的频率上限是20kHz

HC-SR04模块性能稳定,测度距离精确,模块高精度,盲区小。多应用于机器人避障;物体测距;公共安防;停车场车位检测等领域。

工作原理:当一个控制口发一个至少10US以上的高电平,就会触发SR04的测距功能,触发后,模块会自动发送8个40KHZ的超声波脉冲,并且自动检测是否有信号返回。这一步骤会有模块内部自动完成。另一个控制口高电平持续的时间就是此次测距的时间,方可算出距离.如此不断的周期测,即可以达到你移动测量的值.

实验所用的代码如下:

/***********************************************************
File name: _36_UltrasonicDistanceSensorModule.ino
Description: When you move the obstacle in front of the 
             ultrasonic module,you can see the data on 
             the serial montiol.
Website: www.adeept.com
E-mail: support@adeept.com
Author: Tom
Date: 2017/03/18 
***********************************************************/
const int pingPin = 5;  // pin connected to Echo Pin in the ultrasonic distance sensor
const int trigPin = 6;  // pin connected to trig Pin in the ultrasonic distance sensor
const int stbPin = 7;  //the segment display module STB pin connected to digital pin 7
const int clkPin = 9;  //the segment display module CLK pin connected to digital pin 9
const int dioPin = 8;  //the segment display module DIO pin connected to digital pin 8



void sendCommand(uint8_t value) 
{ 
   digitalWrite(stbPin, LOW);                   //pin low.  To begin receiving data
   shiftOut(dioPin, clkPin, LSBFIRST, value);   //send data(value) to the segment display module
   digitalWrite(stbPin, HIGH);                  //pin high.  Stop receiving data
}


void setup() 
{
   pinMode(pingPin, INPUT); //Set the connection pin output mode Echo pin
   pinMode(trigPin, OUTPUT);//Set the connection pin output mode trog pin
   pinMode(stbPin, OUTPUT); //initialize the stbPin as an output
   pinMode(clkPin, OUTPUT); //initialize the clkPin as an output
   pinMode(dioPin, OUTPUT); //initialize the dioPin as an output
   sendCommand(0x8f);       //activate 
   Serial.begin(115200);     //opens serial port, sets data rate to 9600 bps
} 
                     /*0*/ /*1*/ /*2*/ /*3*/ /*4*/ /*5*/ /*6*/ /*7*/ /*8*/ /*9*/ 
 uint8_t digits[] = { 0x3f, 0x06, 0x5b, 0x4f, 0x66, 0x6d, 0x7d, 0x07, 0x7f, 0x6f };

     
int ping(int pingPin) 
{ 
   // establish variables for duration of the ping, 
   // and the distance result in inches and centimeters: 
   long duration, cm; 
   // The PING))) is triggered by a HIGH pulse of 2 or more microseconds. 
   // Give a short LOW pulse beforehand to ensure a clean HIGH pulse: 
 
   digitalWrite(trigPin, LOW); 
   delayMicroseconds(2); 
   digitalWrite(trigPin, HIGH); 
   delayMicroseconds(5); 
   digitalWrite(trigPin, LOW);

   
   duration = pulseIn(pingPin, HIGH);

   // convert the time into a distance 
   cm = microsecondsToCentimeters(duration); 
   return cm ; 
}

long microsecondsToCentimeters(long microseconds) 
{ 
   // The speed of sound is 340 m/s or 29 microseconds per centimeter. 
   // The ping travels out and back, so to find the distance of the 
   // object we take half of the distance travelled. 
   return microseconds / 29 / 2; 
}

void loop() 
{ 
   int cm = ping(pingPin); 
   Serial.print("distance: "); // Print a message of "Temp: "to the serial montiol.
   Serial.print(cm);           // Print a centigrade temperature to the serial montiol. 
   Serial.println(" cm");      // Print the unit of the centigrade temperature to the serial montiol.

     sendCommand(0x40);                                       //setting the Write Data Command,using automatic address genuine.
   digitalWrite(stbPin, LOW);                               //pin low.  To begin receiving data
   shiftOut(dioPin, clkPin, LSBFIRST, 0xc0);                //Set the start address 0C0H
   if(cm >= 1000 )
   {
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm/1000%10]);//thousand data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data  
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm/100%10]); //hundred data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data 
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm/10%10]);  //ten data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm%10]);     //bit data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data 
   }
          
   else if(cm >= 100 && cm <=1000)
   {   
      shiftOut(dioPin, clkPin, LSBFIRST, digits[0]);//thousand data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data  
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm/100%10]); //hundred data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data 
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm/10%10]);  //ten data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm%10]);     //bit data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data 
   }
 
   else  if(cm >= 10 && cm <=100)
   {  
      shiftOut(dioPin, clkPin, LSBFIRST, digits[0]);//thousand data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data  
     shiftOut(dioPin, clkPin, LSBFIRST, digits[0]); //hundred data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data 
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm/10%10]);  //ten data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm%10]);     //bit data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data 
   }
  
  else  if(cm > 0 && cm <=10)
   {
      shiftOut(dioPin, clkPin, LSBFIRST, digits[0]);//thousand data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data  
     shiftOut(dioPin, clkPin, LSBFIRST, digits[0]); //hundred data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data 
     shiftOut(dioPin, clkPin, LSBFIRST, digits[0]);  //ten data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data
     shiftOut(dioPin, clkPin, LSBFIRST, digits[cm%10]);     //bit data
     shiftOut(dioPin, clkPin, LSBFIRST, 0x00);                //filling high 8-bit data  
   }
  
   digitalWrite(stbPin, HIGH);                              //pin high.  Stop receiving data
   
   
   delay(500);
}
跳至工具栏