Sonar example with callbacks.

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

00001 #include "mbed.h"
00002 
00003 /**
00004  *  Sonar class for the HC-SR04
00005  */
00006 class Sonar {
00007     DigitalOut   trigger;
00008     InterruptIn  echo;     // calls a callback when a pin changes
00009     Timer        timer;
00010     Timeout      timeout;  // calls a callback once when a timeout expires
00011     Ticker       ticker;   // calls a callback repeatedly with a timeout
00012     int32_t      begin;
00013     int32_t      end;
00014     float        distance;
00015 
00016 public:
00017     /**
00018      *  Sonar constructor
00019      *  Creates a sonar object on a set of provided pins
00020      *  @param trigger_pin  Pin used to trigger reads from the sonar device
00021      *  @param echo_pin     Pin used to receive the sonar's distance measurement
00022      */
00023     Sonar(PinName trigger_pin, PinName echo_pin) : trigger(trigger_pin), echo(echo_pin) {
00024         trigger = 0;
00025         distance = -1;
00026 
00027         echo.rise(callback(this, &Sonar::echo_in));    // Attach handler to the rising interruptIn edge
00028         echo.fall(callback(this, &Sonar::echo_fall));  // Attach handler to the falling interruptIn edge
00029     }
00030 
00031     /**
00032      *  Start the background task to trigger sonar reads every 100ms
00033      */
00034     void start(void) {
00035         ticker.attach(callback(this, &Sonar::background_read), 0.01f);
00036     }
00037 
00038     /**
00039      *  Stop the background task that triggers sonar reads
00040      */
00041     void stop(void) {
00042         ticker.detach();
00043     }
00044 
00045     /**
00046      *  Interrupt pin rising edge interrupt handler. Reset and start timer
00047      */
00048     void echo_in(void) {
00049         timer.reset();
00050         timer.start();
00051         begin = timer.read_us();
00052     }
00053 
00054     /**
00055      *  Interrupt pin falling edge interrupt handler. Read and disengage timer.
00056      *  Calculate raw echo pulse length
00057      */
00058     void echo_fall(void) {
00059         end = timer.read_us();
00060         timer.stop();
00061         distance = end - begin;
00062     }
00063 
00064     /**
00065      *  Wrapper function to set the trigger pin low. Callbacks cannot take in both object and argument pointers.
00066      *  See use of this function in background_read().
00067      */
00068     void trigger_toggle(void) {
00069         trigger = 0;
00070     }
00071 
00072     /**
00073      *  Background callback task attached to the periodic ticker that kicks off sonar reads
00074      */
00075     void background_read(void) {
00076         trigger = 1;
00077         timeout.attach(callback(this, &Sonar::trigger_toggle), 10.0e-6);
00078     }
00079 
00080     /**
00081      *  Public read function that returns the scaled distance result in cm
00082      */
00083     float read(void) {
00084         return distance / 58.0f;
00085     }
00086 };
00087 
00088 
00089 int main() {
00090     // Create sonar object on pins D5 and D6
00091     Sonar sonar(D5, D6);
00092     // Begin background thread sonar acquires
00093     sonar.start();
00094 
00095     while(1) {
00096         wait(0.1f);
00097         // Periodically print results from sonar object
00098         printf("%f\r\n", sonar.read());
00099     }
00100 }