Simple library for reading distance from SRF02 Ultrasonic Sensor in I2C mode.

Dependents:   Project_A el13jarDistanceSensorProject UltrasonicDistanceSensor-el13jb Distance_Sensor_SRF02 ... more

Committer:
eencae
Date:
Wed Jun 22 15:49:12 2016 +0000
Revision:
2:cb489f486ece
Parent:
0:b729d2ce03bd
Added method to change the address of the sensor on the bus. Address is specified using the constructor method.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
eencae 0:b729d2ce03bd 1 /**
eencae 0:b729d2ce03bd 2 @file SRF02.cpp
eencae 0:b729d2ce03bd 3
eencae 0:b729d2ce03bd 4 @brief Member functions implementations
eencae 0:b729d2ce03bd 5
eencae 0:b729d2ce03bd 6 */
eencae 0:b729d2ce03bd 7 #include "mbed.h"
eencae 0:b729d2ce03bd 8 #include "SRF02.h"
eencae 0:b729d2ce03bd 9
eencae 2:cb489f486ece 10 SRF02::SRF02(PinName sdaPin, PinName sclPin, char addr)
eencae 0:b729d2ce03bd 11 {
eencae 0:b729d2ce03bd 12 i2c = new I2C(sdaPin,sclPin); // create new I2C instance and initialise
eencae 0:b729d2ce03bd 13 i2c->frequency(400000); // I2C Fast Mode - 400kHz
eencae 0:b729d2ce03bd 14 leds = new BusOut(LED4,LED3,LED2,LED1);
eencae 0:b729d2ce03bd 15
eencae 2:cb489f486ece 16 w_addr_ = addr; // set write address of sensor
eencae 2:cb489f486ece 17 r_addr_ = w_addr_ + 1; // read address has the lowest bit set (i.e. + 1)
eencae 2:cb489f486ece 18
eencae 0:b729d2ce03bd 19 }
eencae 0:b729d2ce03bd 20
eencae 0:b729d2ce03bd 21 int SRF02::getDistanceCm()
eencae 0:b729d2ce03bd 22 {
eencae 0:b729d2ce03bd 23 char data[2];
eencae 0:b729d2ce03bd 24
eencae 0:b729d2ce03bd 25 // need to send CM command to command register
eencae 0:b729d2ce03bd 26 data[0] = CMD_REG;
eencae 0:b729d2ce03bd 27 data[1] = CM_CMD;
eencae 2:cb489f486ece 28 int ack = i2c->write(w_addr_,data,2);
eencae 0:b729d2ce03bd 29 if (ack)
eencae 0:b729d2ce03bd 30 error(); // if we don't receive acknowledgement, flash error message
eencae 0:b729d2ce03bd 31
eencae 0:b729d2ce03bd 32 // this will start the sensor ranging, the datasheet suggests a delay of at least 65 ms before reading the result
eencae 0:b729d2ce03bd 33 wait_ms(70);
eencae 0:b729d2ce03bd 34
eencae 0:b729d2ce03bd 35 // we can now read the result - tell the sensor we want the high byte
eencae 0:b729d2ce03bd 36 char reg = RANGE_H_REG;
eencae 2:cb489f486ece 37 ack = i2c->write(w_addr_,&reg,1);
eencae 0:b729d2ce03bd 38 if (ack)
eencae 0:b729d2ce03bd 39 error(); // if we don't receive acknowledgement, flash error message
eencae 0:b729d2ce03bd 40
eencae 0:b729d2ce03bd 41 // if we read two bytes, the register is automatically incremented (H and L)
eencae 2:cb489f486ece 42 ack = i2c->read(r_addr_,data,2);
eencae 0:b729d2ce03bd 43 if (ack)
eencae 0:b729d2ce03bd 44 error(); // if we don't receive acknowledgement, flash error message
eencae 0:b729d2ce03bd 45
eencae 0:b729d2ce03bd 46 // high byte is first, then low byte, so combine into 16-bit value
eencae 0:b729d2ce03bd 47 return (data[0] << 8) | data[1];
eencae 0:b729d2ce03bd 48 }
eencae 0:b729d2ce03bd 49
eencae 2:cb489f486ece 50 void SRF02::changeAddress(char addr) {
eencae 2:cb489f486ece 51
eencae 2:cb489f486ece 52 char data[2];
eencae 2:cb489f486ece 53
eencae 2:cb489f486ece 54 // sequence to change I2C (https://www.robot-electronics.co.uk/htm/srf02techI2C.htm)
eencae 2:cb489f486ece 55 // need to write this sequence to the command register, followed by the new address
eencae 2:cb489f486ece 56
eencae 2:cb489f486ece 57 data[0] = CMD_REG;
eencae 2:cb489f486ece 58 data[1] = 0xA0; // 1st byte in sequence
eencae 2:cb489f486ece 59 int ack = i2c->write(w_addr_,data,2);
eencae 2:cb489f486ece 60 if (ack)
eencae 2:cb489f486ece 61 error(); // if we don't receive acknowledgement, flash error message
eencae 2:cb489f486ece 62
eencae 2:cb489f486ece 63 wait_ms(50); // small delay in between
eencae 2:cb489f486ece 64
eencae 2:cb489f486ece 65 data[0] = CMD_REG;
eencae 2:cb489f486ece 66 data[1] = 0xAA; // 2nd byte in sequence
eencae 2:cb489f486ece 67 ack = i2c->write(w_addr_,data,2);
eencae 2:cb489f486ece 68 if (ack)
eencae 2:cb489f486ece 69 error(); // if we don't receive acknowledgement, flash error message
eencae 2:cb489f486ece 70
eencae 2:cb489f486ece 71 wait_ms(50); // small delay in between
eencae 2:cb489f486ece 72
eencae 2:cb489f486ece 73 data[0] = CMD_REG;
eencae 2:cb489f486ece 74 data[1] = 0xA5; // 3rd byte in sequence
eencae 2:cb489f486ece 75 ack = i2c->write(w_addr_,data,2);
eencae 2:cb489f486ece 76 if (ack)
eencae 2:cb489f486ece 77 error(); // if we don't receive acknowledgement, flash error message
eencae 2:cb489f486ece 78
eencae 2:cb489f486ece 79 wait_ms(50); // small delay in between
eencae 2:cb489f486ece 80
eencae 2:cb489f486ece 81 data[0] = CMD_REG;
eencae 2:cb489f486ece 82 data[1] = addr; // new address
eencae 2:cb489f486ece 83 ack = i2c->write(w_addr_,data,2);
eencae 2:cb489f486ece 84 if (ack)
eencae 2:cb489f486ece 85 error(); // if we don't receive acknowledgement, flash error message
eencae 2:cb489f486ece 86
eencae 2:cb489f486ece 87 wait_ms(50);
eencae 2:cb489f486ece 88
eencae 2:cb489f486ece 89 }
eencae 2:cb489f486ece 90
eencae 0:b729d2ce03bd 91 void SRF02::error()
eencae 0:b729d2ce03bd 92 {
eencae 0:b729d2ce03bd 93 while(1) {
eencae 0:b729d2ce03bd 94 leds->write(15);
eencae 0:b729d2ce03bd 95 wait(0.1);
eencae 0:b729d2ce03bd 96 leds->write(0);
eencae 0:b729d2ce03bd 97 wait(0.1);
eencae 0:b729d2ce03bd 98 }
eencae 0:b729d2ce03bd 99 }