message:
Wearable GPS LED help

I'm very new to Arduino and C++ and have been playing with the Flora Wearable GPS. However, nowhere I've looked has given me any help in setting and changing the color of the LEDs. The tutorial on their site is barebones and doesn't explain how to modify code and make the colors change. I've tried mixing what I know, but none of it results in what I want: one color to show when I'm in range of a a point, and another to show when I'm not.

    // Flora GPS + LED Pixel Code
    //
    // This code shows how to listen to the GPS module in an interrupt
    // which allows the program to have more 'freedom' - just parse
    // when a new NMEA sentence is available! Then access data when
    // desired.
    //
    // Tested and works great with the Adafruit Flora GPS module
    //    ------> http://adafruit.com/products/1059
    // Pick one up today at the Adafruit electronics shop
    // and help support open source hardware & software! -ada

    #include <Adafruit_GPS.h>
    #include <SoftwareSerial.h>
    #include "Adafruit_NeoPixel.h"
    Adafruit_GPS GPS(&Serial1);

    // Set GPSECHO to 'false' to turn off echoing the GPS data to the Serial console
    // Set to 'true' if you want to debug and listen to the raw GPS sentences
    #define GPSECHO false

    #define PIN 6

    // this keeps track of whether we're using the interrupt
    // off by default!
    boolean usingInterrupt = false;

    //--------------------------------------------------|
    //                    WAYPOINTS                     |
    //--------------------------------------------------|
    //Please enter the latitude and longitude of your   |
    //desired destination:                              |
      #define GEO_LAT                44.995012
      #define GEO_LON               -93.228967
    //--------------------------------------------------|

    //--------------------------------------------------|
    //                    DISTANCE                      |
    //--------------------------------------------------|
    //Please enter the distance (in meters) from your   |
    //destination that you want your LEDs to light up:  |
      #define DESTINATION_DISTANCE   20
    //--------------------------------------------------|

    // Navigation location
    float targetLat = GEO_LAT;
    float targetLon = GEO_LON;

    // Trip distance
    float tripDistance;

    boolean isStarted = false;

    // Parameter 1 = number of pixels in strip
    // Parameter 2 = Arduino pin number (most are valid)
    // Parameter 3 = pixel type flags, add together as needed:
    //   NEO_KHZ800  800 KHz bitstream (most NeoPixel products w/WS2812 LEDs)
    //   NEO_KHZ400  400 KHz (classic 'v1' (not v2) FLORA pixels, WS2811 drivers)
    //   NEO_GRB     Pixels are wired for GRB bitstream (most NeoPixel products)
    //   NEO_RGB     Pixels are wired for RGB bitstream (v1 FLORA pixels, not v2)
    Adafruit_NeoPixel strip = Adafruit_NeoPixel(8, PIN, NEO_GRB + NEO_KHZ800);

    uint8_t LED_Breathe_Table[]  = {   80,  87,  95, 103, 112, 121, 131, 141, 151, 161, 172, 182, 192, 202, 211, 220,
                  228, 236, 242, 247, 251, 254, 255, 255, 254, 251, 247, 242, 236, 228, 220, 211,
                  202, 192, 182, 172, 161, 151, 141, 131, 121, 112, 103,  95,  87,  80,  73,  66,
                   60,  55,  50,  45,  41,  38,  34,  31,  28,  26,  24,  22,  20,  20,  20,  20,
                   20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,
                   20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  22,  24,  26,  28,
                   31,  34,  38,  41,  45,  50,  55,  60,  66,  73 };

    #define BREATHE_TABLE_SIZE (sizeof(LED_Breathe_Table))
    #define BREATHE_CYCLE    5000      /*breathe cycle in milliseconds*/
    #define BREATHE_UPDATE    (BREATHE_CYCLE / BREATHE_TABLE_SIZE)
    uint32_t lastBreatheUpdate = 0;
    uint8_t breatheIndex = 0;

    void setup()
    {
      // connect at 115200 so we can read the GPS fast enough and echo without dropping chars
      // also spit it out
      Serial.begin(115200);

      // 9600 NMEA is the default baud rate for Adafruit MTK GPS's- some use 4800
      GPS.begin(9600);

      // uncomment this line to turn on RMC (recommended minimum) and GGA (fix data) including altitude
      GPS.sendCommand(PMTK_SET_NMEA_OUTPUT_RMCGGA);
      // uncomment this line to turn on only the "minimum recommended" data
      //GPS.sendCommand(PMTK_SET_NMEA_OUTPUT_RMCONLY);
      // For parsing data, we don't suggest using anything but either RMC only or RMC+GGA since
      // the parser doesn't care about other sentences at this time

      // Set the update rate
      GPS.sendCommand(PMTK_SET_NMEA_UPDATE_1HZ);   // 1 Hz update rate
      // For the parsing code to work nicely and have time to sort thru the data, and
      // print it out we don't suggest using anything higher than 1 Hz

      delay(1000);
      // Ask for firmware version
      Serial1.println(PMTK_Q_RELEASE);

        // Start up the LED strip
      strip.begin();

      // Update the strip, to start they are all 'off'
      strip.show();
    }

    uint32_t timer = millis();

    void loop()                     // run over and over again
    {
      // read data from the GPS in the 'main loop'
      char c = GPS.read();
      // if you want to debug, this is a good time to do it!
      if (GPSECHO)
          if (c) Serial.print(c);

      // if a sentence is received, we can check the checksum, parse it...
      if (GPS.newNMEAreceived()) {
        // a tricky thing here is if we print the NMEA sentence, or data
        // we end up not listening and catching other sentences!
        // so be very wary if using OUTPUT_ALLDATA and trytng to print out data
        //Serial.println(GPS.lastNMEA());   // this also sets the newNMEAreceived() flag to false

        if (!GPS.parse(GPS.lastNMEA()))   // this also sets the newNMEAreceived() flag to false
          return;  // we can fail to parse a sentence in which case we should just wait for another
      }

        if (GPS.fix) {
          //Serial.print("Location: ");
          //Serial.print(GPS.latitude, 2); Serial.print(GPS.lat);
          //Serial.print(", ");
          //Serial.print(GPS.longitude, 2); Serial.println(GPS.lon);

          float fLat = decimalDegrees(GPS.latitude, GPS.lat);
          float fLon = decimalDegrees(GPS.longitude, GPS.lon);

          if (!isStarted) {
            isStarted = true;
            tripDistance = (double)calc_dist(fLat, fLon, targetLat, targetLon);
          }

          //Uncomment below if you want your Flora to navigate to a certain destination.  Then modify the headingDirection function.
          /*if ((calc_bearing(fLat, fLon, targetLat, targetLon) - GPS.angle) > 0) {
            headingDirection(calc_bearing(fLat, fLon, targetLat, targetLon)-GPS.angle);
           }
          else {
            headingDirection(calc_bearing(fLat, fLon, targetLat, targetLon)-GPS.angle+360);
          }*/

          headingDistance((double)calc_dist(fLat, fLon, targetLat, targetLon));
          //Serial.print("Distance Remaining:"); Serial.println((double)calc_dist(fLat, fLon, targetLat, targetLon));

        }
      //}

    }

    int calc_bearing(float flat1, float flon1, float flat2, float flon2)
    {
      float calc;
      float bear_calc;

      float x = 69.1 * (flat2 - flat1);
      float y = 69.1 * (flon2 - flon1) * cos(flat1/57.3);

      calc=atan2(y,x);

      bear_calc= degrees(calc);

      if(bear_calc<=1){
        bear_calc=360+bear_calc;
      }
      return bear_calc;
    }

    void headingDirection(float heading)
    {
      //Use this part of the code to determine which way you need to go.
      //Remember: this is not the direction you are heading, it is the direction to the destination (north = forward).
      if ((heading > 348.75)||(heading < 11.25)) {
        Serial.println("  N");
        //Serial.println("Forward");
      }

      if ((heading >= 11.25)&&(heading < 33.75)) {
        Serial.println("NNE");
        //Serial.println("Go Right");
      }

      if ((heading >= 33.75)&&(heading < 56.25)) {
        Serial.println(" NE");
        //Serial.println("Go Right");
      }

      if ((heading >= 56.25)&&(heading < 78.75)) {
        Serial.println("ENE");
        //Serial.println("Go Right");
      }

      if ((heading >= 78.75)&&(heading < 101.25)) {
        Serial.println("  E");
        //Serial.println("Go Right");
      }

      if ((heading >= 101.25)&&(heading < 123.75)) {
        Serial.println("ESE");
        //Serial.println("Go Right");
      }

      if ((heading >= 123.75)&&(heading < 146.25)) {
        Serial.println(" SE");
        //Serial.println("Go Right");
      }

      if ((heading >= 146.25)&&(heading < 168.75)) {
        Serial.println("SSE");
        //Serial.println("Go Right");
      }

      if ((heading >= 168.75)&&(heading < 191.25)) {
        Serial.println("  S");
        //Serial.println("Turn Around");
      }

      if ((heading >= 191.25)&&(heading < 213.75)) {
        Serial.println("SSW");
        //Serial.println("Go Left");
      }

      if ((heading >= 213.75)&&(heading < 236.25)) {
        Serial.println(" SW");
        //Serial.println("Go Left");
      }

      if ((heading >= 236.25)&&(heading < 258.75)) {
        Serial.println("WSW");
        //Serial.println("Go Left");
      }

      if ((heading >= 258.75)&&(heading < 281.25)) {
        Serial.println("  W");
        //Serial.println("Go Left");
      }

      if ((heading >= 281.25)&&(heading < 303.75)) {
        Serial.println("WNW");
        //Serial.println("Go Left");
      }

      if ((heading >= 303.75)&&(heading < 326.25)) {
        Serial.println(" NW");
        //Serial.println("Go Left");
      }

      if ((heading >= 326.25)&&(heading < 348.75)) {
        Serial.println("NWN");
        //Serial.println("Go Left");
      }
    }

    void headingDistance(float fDist)
    {
      //Use this part of the code to determine how far you are away from the destination.
      //The total trip distance (from where you started) is divided into five trip segments.
     Serial.println(fDist);
     if ((fDist >= DESTINATION_DISTANCE)) { // You are now within 5 meters of your destination.
        //Serial.println("Trip Distance: 1");
        //Serial.println("Arrived at destination!");
        int i;
        for (i=0; i < strip.numPixels(); i++) {
          strip.setPixelColor(i, 0, 0, 0);
        }
        strip.show();   // write all the pixels out
      }

      if ((fDist < DESTINATION_DISTANCE)) { // You are now within 5 meters of your destination.
        //Serial.println("Trip Distance: 0");
        //Serial.println("Arrived at destination!");
        breath();
      }

    }

    unsigned long calc_dist(float flat1, float flon1, float flat2, float flon2)
    {
      float dist_calc=0;
      float dist_calc2=0;
      float diflat=0;
      float diflon=0;

      diflat=radians(flat2-flat1);
      flat1=radians(flat1);
      flat2=radians(flat2);
      diflon=radians((flon2)-(flon1));

      dist_calc = (sin(diflat/2.0)*sin(diflat/2.0));
      dist_calc2= cos(flat1);
      dist_calc2*=cos(flat2);
      dist_calc2*=sin(diflon/2.0);
      dist_calc2*=sin(diflon/2.0);
      dist_calc +=dist_calc2;

      dist_calc=(2*atan2(sqrt(dist_calc),sqrt(1.0-dist_calc)));

      dist_calc*=6371000.0; //Converting to meters
      return dist_calc;
    }

    // Convert NMEA coordinate to decimal degrees
    float decimalDegrees(float nmeaCoord, char dir) {
      uint16_t wholeDegrees = 0.01*nmeaCoord;
      int modifier = 1;

      if (dir == 'W' || dir == 'S') {
        modifier = -1;
      }

      return (wholeDegrees + (nmeaCoord - 100.0*wholeDegrees)/60.0) * modifier;
    }

    void breath()
    {
      uniformBreathe(LED_Breathe_Table, BREATHE_TABLE_SIZE, BREATHE_UPDATE, 127, 127, 127);
    }

    void uniformBreathe(uint8_t* breatheTable, uint8_t breatheTableSize, uint16_t updatePeriod, uint16_t r, uint16_t g, uint16_t b)
    {
      int i;

      uint8_t breatheBlu;

      if ((millis() - lastBreatheUpdate) > updatePeriod) {
        lastBreatheUpdate = millis();

        for (i=0; i < strip.numPixels(); i++) {
          breatheBlu = (b * breatheTable[breatheIndex]) / 256;
          strip.setPixelColor(i, 0, 0, breatheBlu);
        }
        strip.show();

        breatheIndex++;
        if (breatheIndex > breatheTableSize) {
          breatheIndex = 0;
        }
      }
    }

What gets me the most is this part

    void headingDistance(float fDist)
    {
      //Use this part of the code to determine how far you are away from the destination.
      //The total trip distance (from where you started) is divided into five trip segments.
     Serial.println(fDist);
     if ((fDist >= DESTINATION_DISTANCE)) { // You are now within 5 meters of your destination.
        //Serial.println("Trip Distance: 1");
        //Serial.println("Arrived at destination!");
        int i;
        for (i=0; i < strip.numPixels(); i++) {
          strip.setPixelColor(i, 0, 0, 0);
        }
        strip.show();   // write all the pixels out
      }

      if ((fDist < DESTINATION_DISTANCE)) { // You are now within 5 meters of your destination.
        //Serial.println("Trip Distance: 0");
        //Serial.println("Arrived at destination!");
        breath();
      }

    }

Since the comments say both are for within 5 meters but have opposite conditions and "fDist" isn't defined anywhere that I can see, I don't know which is for near or far or how to set a color to either one. I tried setting colors for the first if statement and they seemed to work, but I couldn't get it to work consistently for some reason.

body:
Three comments:

 1. For someone who is new to Arduino and programming (or perhaps just new
    to C / C++), you have taken on a large challenge.
 2. It should be widely said (but it is not) that not all Arduino
    libraries are compatible with one another.  And that it is up to the
    user (or community) to identify conflicts.  As there are far too
    many combinations for any one person to test them all.
 3. You should ask only 1 question per post.  I think you are most
    interested about programming different colors for a WS2812 LED.  So
    we should not talk about GPS for now.

Most if not all Adafruit.com software source code are available free to the community at github.com.  The [Adafruit_NeoPixel github repository][1]  at github should contain all the source code for this project as well as several files of [example code][2]. In the example code is this segment of code that changes the LED color:

      switch(i){
        case 0: colorWipe(strip.Color(0, 0, 0), 50);    // Black/off
                break;
        case 1: colorWipe(strip.Color(255, 0, 0), 50);  // Red
                break;
        case 2: colorWipe(strip.Color(0, 255, 0), 50);  // Green
                break;
        case 3: colorWipe(strip.Color(0, 0, 255), 50);  // Blue
                break;
    ...removed some code for clarity...
        }

  [1]: https://github.com/adafruit/Adafruit_NeoPixel
  [2]: https://github.com/adafruit/Adafruit_NeoPixel/tree/master/examples


sender: user

sender: assistant

body:
It is not really clear what your actual problem is. I will go with the following:

1. **How to set the colors of the RGB LEDs:** You are already using the `Adafruit_NeoPixel` library. The definition of `Adafruit_Neopixel strip` shows, that you have a strip with 8 LEDs. In setup the sketch calls `strip.begin()` to initiate it. After that, everytime you want to change the color/state of any number of LEDs on the strip, you can set them one by one with `strip.setPixelColor()`, which takes the number of the LED and the color in RGB format as parameters. To make the LEDs show your changes you have to call `strip.show()`, which sends the data to the LEDs.
2. **What your sketch does:** In the function `headingDistance(float fDist)` the colors of the LEDs are set according to the previously calculated distance. `fDist` comes as parameter to this function, so it is declared in the function header. The value comes from the function `calc_dist()`. Now you have 2 if-statements:
  1. The first one (if you are farer away from your target) will set the color of all LEDs to black (turning them off) by calling `strip.setPixelColor(i, 0, 0, 0)` for every LED and then calling `strip.show()`. So this is easy.
  2.  The second one (if you are within the 5m radius) calls the function `breath()`. It will set the intensity of the blue color component for all LEDs dependent on it's parameter `b` and the time that passed since it set the LEDs color the last time (this is done with the `millis()`-if-statement). The function `headingDistance()` is called in `loop()`, whenever the `fix` variable of the GPS is set. Calling the `breath()` function (which is called from `headingDistance()`) very often results in a timed update of the LEDs every `updatePeriod` milliseconds. Refer to the `BlinkWithoutDelay` example in the Arduino IDE for this working principle. It leaves you time to do other things during the wait periods, because it is non-blocking. The `breath()` function is a more complex thing, than simply turning on and of the LEDs with the right color. If you just want to do that, replace it's call in `headingDistance()` with your own code, setting the LEDs like I explained above.

So:
> one color to show when I'm in range of a a point, and another to show when I'm not.

Set the color values in RGB format in the first if-statement, to set for the case that your are not in the range of your GPS point. And replace the `breath()` function by a similar code with the color values in RGB format for the case, that you are within the range of your point.

If it still doesn't work, try if the original sketch works correctly. This would verify, that the measurement and calculation of the distance works as intended.


body:
I think others have addressed the need for you to modify the strip colors based on distance or bearing or... whatever you want to show.

Here's a [NeoGPS](https://github.com/SlashDevin/NeoGPS) version of that sketch.  I think it may be easier to understand what's going on, and where you need to focus:

    // Flora GPS + LED Pixel Code
    //   Modified to use NeoGPS library.
    //
    // Adafruit Flora GPS module
    //    ------> http://adafruit.com/products/1059
    // Pick one up today at the Adafruit electronics shop
    // and help support open source hardware & software! -ada

    #include "Adafruit_NeoPixel.h"
    #include <NMEAGPS.h>

    NMEAGPS gps;
    gps_fix fix;
    #define gpsPort Serial1

    const int NEOPIXEL_PIN = 6;

    //----------------------------------------------------|
    //                     WAYPOINTS                      |
    //----------------------------------------------------|
    // Please enter the latitude and longitude of your    |
    // desired destination:                               |
    NeoGPS::Location_t destination( 449950120L, -932289670L );
    //  To be more accurate, these are degrees * 10000000 |
    //----------------------------------------------------|

    //--------------------------------------------------|
    //                    DISTANCE                      |
    //--------------------------------------------------|
    //Please enter the distance (in meters) from your   |
    //destination that you want your LEDs to light up:  |
    const float DESTINATION_DISTANCE = 20.0;

    //--------------------------------------------------|
    // Parameter 1 = number of pixels in strip
    // Parameter 2 = Arduino pin number (most are valid)
    // Parameter 3 = pixel type flags, add together as needed:
    //   NEO_KHZ800  800 KHz bitstream (most NeoPixel products w/WS2812 LEDs)
    //   NEO_KHZ400  400 KHz (classic 'v1' (not v2) FLORA pixels, WS2811 drivers)
    //   NEO_GRB     Pixels are wired for GRB bitstream (most NeoPixel products)
    //   NEO_RGB     Pixels are wired for RGB bitstream (v1 FLORA pixels, not v2)
    Adafruit_NeoPixel strip = Adafruit_NeoPixel( 8, NEOPIXEL_PIN, NEO_GRB + NEO_KHZ800 );

    uint8_t LED_Breathe_Table[]  =
      {
         80,  87,  95, 103, 112, 121, 131, 141, 151, 161, 172, 182, 192, 202, 211, 220,
        228, 236, 242, 247, 251, 254, 255, 255, 254, 251, 247, 242, 236, 228, 220, 211,
        202, 192, 182, 172, 161, 151, 141, 131, 121, 112, 103,  95,  87,  80,  73,  66,
         60,  55,  50,  45,  41,  38,  34,  31,  28,  26,  24,  22,  20,  20,  20,  20,
         20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,
         20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  20,  22,  24,  26,  28,
         31,  34,  38,  41,  45,  50,  55,  60,  66,  73
      };

    #define BREATHE_TABLE_SIZE (sizeof(LED_Breathe_Table))
    #define BREATHE_CYCLE      5000      /*breathe cycle in milliseconds*/
    #define BREATHE_UPDATE     (BREATHE_CYCLE / BREATHE_TABLE_SIZE)
    uint32_t lastBreatheUpdate = 0;
    size_t   breatheIndex      = 0;

    void setup()
    {
      Serial.begin(115200);
      gpsPort.begin(9600);  // default baud rate for Adafruit MTK GPS's - some use 4800

      gps.send_P( &gpsPort, F("PMTK314,0,1,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0") ); // RMC+GGA
      delay(100);
      gps.send_P( &gpsPort, F("PMTK220,1000") ); // 1Hz
      delay(100);
      gps.send_P( &gpsPort, F("PGCMD,33,0") ); // No antenna status

      strip.begin();
      strip.show();  // Update the strip, to start they are all 'off'
    }

    void loop()
    {
      if (gps.available( gpsPort ) ) {
        fix = gps.read();

        const bool spoof = false; // change to true for spoofing
        if (spoof) {
          float t           = fix.dateTime.seconds / 4.0;  // 15 second cycle (60 / 4)
          float offsetAngle = (TWO_PI / 20.0) * t;         // 20 steps around circle
          float offsetDist  = 0.005 * t / NeoGPS::Location_t::EARTH_RADIUS_KM;
                               // 5m per second, 75m away or less. In RADIANS!
          fix.location = destination; // start here and step away
          fix.location.OffsetBy( offsetDist, offsetAngle );
        }

        //Serial.print( F("Location: ") );
        //Serial.print( fix.latitude(), 5 );
        //Serial.print( F(", ") );
        //Serial.print( fix.longitude(), 5 );

        if (fix.valid.location) {
          float distance = fix.location.DistanceKm( destination ) * 1000.0; // meters

          // Set below to true if you want your Flora to navigate to a
          //  certain destination.  Then modify the showDirection function.
          const bool showNavigationHints = true;

          if (showNavigationHints) {

            float bearing = fix.location.BearingToDegrees( destination );

            //  If we're moving fast enough, show the user which way to go, left or right.
            if (fix.valid.heading and (fix.valid.speed and fix.speed_kph() > 3.0)) {

              float courseCorrection = bearing - fix.heading();
              if (courseCorrection < 0.0)
                courseCorrection += 360.0;

              showDirection( courseCorrection );

            } else {
              // We're not moving very fast, show a compass direction.
              showDirection( bearing );
            }
          }

          showDistance( distance );
        }
      }
    }

    void showDirection( float bearing )
    {
      //  Use this to show which way you need to go.
      //    Some times, it's an absolute compass direction.
      //    Other times, it's a course correction (left or right from current heading)

      const __FlashStringHelper *dir = compassDir( bearing );
      size_t dirLen = strlen_P( (const char *) dir );
      for (uint8_t i = 0; i < (3 - dirLen); i++)
        Serial.print( ' ' );
      Serial.println( dir );
    }

    void showDistance(float distance)
    {
      Serial.println( distance );

      // Are we close enough?
      if (distance >= DESTINATION_DISTANCE) {
        // No.

        const uint8_t level = 0; // you might set this based on distance

        for (int i=0; i < strip.numPixels(); i++) {
          strip.setPixelColor( i, level, level, level );
        }
        strip.show();   // write all the pixels out

      } else {
        // Yes!
        // Serial.println("Arrived at destination!");
        breath();
      }

    }

    //------------------------------------------------------------
    // This is copied from the NeoGPS NMEAaverage.ino example program

    const char nCD  [] PROGMEM = "N";
    const char nneCD[] PROGMEM = "NNE";
    const char neCD [] PROGMEM = "NE";
    const char eneCD[] PROGMEM = "ENE";
    const char eCD  [] PROGMEM = "E";
    const char eseCD[] PROGMEM = "ESE";
    const char seCD [] PROGMEM = "SE";
    const char sseCD[] PROGMEM = "SSE";
    const char sCD  [] PROGMEM = "S";
    const char sswCD[] PROGMEM = "SSW";
    const char swCD [] PROGMEM = "SW";
    const char wswCD[] PROGMEM = "WSW";
    const char wCD  [] PROGMEM = "W";
    const char wnwCD[] PROGMEM = "WNW";
    const char nwCD [] PROGMEM = "NW";
    const char nnwCD[] PROGMEM = "NNW";

    const char * const dirStrings[] PROGMEM =
      { nCD, nneCD, neCD, eneCD, eCD, eseCD, seCD, sseCD,
        sCD, sswCD, swCD, wswCD, wCD, wnwCD, nwCD, nnwCD };

    const __FlashStringHelper *compassDir( uint16_t bearing ) // degrees CW from N
    {
      const int16_t directions    = sizeof(dirStrings)/sizeof(dirStrings[0]);
      const int16_t degreesPerDir = 360 / directions;
            int8_t  dir           = (bearing + degreesPerDir/2) / degreesPerDir;

      while (dir < 0)
        dir += directions;
      while (dir >= directions)
        dir -= directions;

      return (const __FlashStringHelper *) pgm_read_ptr( &dirStrings[ dir ] );

    } // compassDir

    //--------------------------

    void uniformBreathe
      ( uint8_t *breatheTable, size_t breatheTableSize,
        uint16_t updatePeriod,
        uint16_t r, uint16_t g, uint16_t b )
    {

      if ((millis() - lastBreatheUpdate) > updatePeriod) {
        lastBreatheUpdate = millis();

        for (int i=0; i < strip.numPixels(); i++) {
          uint8_t breatheBlu = (b * breatheTable[breatheIndex]) / 256;
          strip.setPixelColor( i, 0, 0, breatheBlu );
        }
        strip.show();

        breatheIndex++;
        if (breatheIndex > breatheTableSize) {
          breatheIndex = 0;
        }
      }
    }

    void breath()
    {
      uniformBreathe(LED_Breathe_Table, BREATHE_TABLE_SIZE, BREATHE_UPDATE, 127, 127, 127);
    }

I am always amazed by how much a little whitespace can improve the readability.
 Good variable and function names are also important.  You are also being misled by bad comments.  :P

I have added some location "spoofing" code that lets you test it without having to walk around.  That spoofing section can be removed when you're done testing.

If you want to try it, NeoGPS is available from the Arduino Library Manager, under the menu **Sketch-> Include Library-> Manage Libraries**.  BTW, this saves about **500 bytes** of RAM.

**To answer your original question**, the `showDistance` and `showDirection` functions should be modified to do whatever you want.


message:
Ribbon sensor resistance slowly drops when released

I recently bought a ribbon sensor ([the one displayed here](https://www.adafruit.com/product/178)), with the intention to use it as a touch-enabled music instrument.

I used it correctly (so it seems), but I have two issues :

- When not pressed, the sensor seems to give random data, as if nothing was plugged to the pin.
- When unpressed, the resistance slowly decreases (and so is my sound pitch). Is that a normal behaviour ?

I don't know how to solve both issues. Has anyone an idea ?

A tinker of my test (Currently corrected thanks to @VE7JRO) can be seen here with my code [here](https://www.tinkercad.com/things/lIbUFHAwG9m) (The ribbon is replaced by a potentiometer but the principle remains the same). The code is also [Available on GitHub](https://github.com/MarcBrillault/arduino/blob/master/projects/touch_instrument/touch_instrument.ino).

body:
The Adafruit website says this:

There is a nominal 10K resistance across the two outer leads. The middle pin resistance with respect to either of the outer pins changes depending on where on the strip one presses. When no pressure is applied, the middle pin floats, so be sure to use some sort of weak pullup, such as 100K ohm.

To use Connect one side pin to ground via a 10K resistor in series. Connect the other side pin to your Vcc power line (3V, 5V etc) via a different 10K resistor in series. Then read the analog voltage on the center pin. It will range from 1/3 Vcc to 2/3 Vcc . Do not connect to Ground and Power directly!

Here is a diagram of how I would connect it to a 5V Arduino Uno.

[![enter image description here][1]][1]

  [1]: https://i.stack.imgur.com/ZSn2V.png


message:
ESP8266 in AP Mode -determining if a station is connected

I have an ESP8266 running in AP mode using softAP and i want to conserve battery life.
I am wanting to turn on wifi and advertise SSID for 20 seconds. If no station connects to the ssid within the 20 seconds, I want to go to sleep for 1 minute, otherwise I do not sleep.

My problem is that I cannot get "WiFi.softAPgetStationNum()" working. when I build i get a message that this is not part of ESP8266WiFi class. I have attached simplified code.

Can someone help me to achieve this please?

    #include <ESP8266WiFi.h>

    //WIFI Access point setup
    const char* Ssid = "SSID";
    const char* Password = "Password";
    IPAddress ip(10,0,0,10);
    IPAddress gateway(10,0,0,1);
    IPAddress subnet(255,255,255,0);
    WiFiServer server(80);                    // Set web server port number to
    80

    // GPIO pins
    const int output_set = 5;
    int delay_loop=0;

    void setup()
    {
      // Data Direction
      pinMode(output_set, OUTPUT);

      // Output initial Values
      digitalWrite(output_set, LOW);

      WiFi.softAPConfig(ip,gateway,subnet);
      WiFi.softAP(Ssid,Password);
      server.begin();

    // check to see if a station is connected to this AP. If no station
    connected within 20 sec timeframe, go to sleep.

    while (WiFi.softAPgetStationNum()==0)              //loop here while no AP is connected to this station
    {
        delay(1);
        delay_loop++;
        if (delay_loop>=20000)
        {

            ESP.deepSleep(60e6);                          //go to sleep for 60 sec -wake pin externally connected to reset pin
        }
    }
    }

    void loop()
    {
       digitalWrite(output_set, HIGH);      //Flash led once station is connected
       delay(200);
       digitalWrite(output_set, LOW);
       delay(400);
    }

body:
Followup answer from comments:

The issue was an outdated version of the ESP8266-Arduino framework. The function `WiFi.softAPgetStationNum()` is available in 2.4.1

For the sake of completeness: The function itself is simply a wrapper for the Espressif non-os SDK function:

<!-- language: lang-cpp -->

    /**
     * Get the count of the Station / client that are connected to the softAP interface
     * @return Stations count
     */
    uint8_t ESP8266WiFiAPClass::softAPgetStationNum() {
        return wifi_softap_get_station_num();
    }

See [Espressif Non-OS SDK API reference][1] chapter 3.5.36.

That function should also be available on older framework versions. However, upgrading is the recommended way to use that function.

  [1]: https://www.espressif.com/sites/default/files/documentation/2c-esp8266_non_os_sdk_api_reference_en.pdf


message:
Is there a way to send data from Tensorflow to Arduino via Bluetooth?

I am not sure if such a question is accepted here. If not please direct me to a more suitable Exchange.

I am planning a small project involving Machine Learning using TensorFlow and Python, which involves GAIT learning of a quadrupedal robotic system. The robotic system will be controlled by a simple Arduino. This will send data to the 8 servo motors located in the 4 legs of the robot. (2 on each leg) The robot is similar to [this.][1]

My question is if there a way to transfer data to and from Tensorflow via Bluetooth to the Arduino.

The Arduino will not be connected serially to my PC, so serial communication is not an option. Bluetooth and Wireless remain, of which, Bluetooth is generally easier.

I have done several projects involving HC-05 modules to transfer data from different systems to an Arduino so that part is not an issue. What I am interested in is if Tensorflow offers this kind of support, or if there is an easier way to do this. Searching online did not yield any results related to what I am after.

Any tips or suggestions would be appreciated.

  [1]: https://www.youtube.com/watch?v=MeIh17FivVM

body:
The question is more "Is there a way to send data from Python ?" than "Is there a way to send them from Tensorflow to an Arduino ?" and the Answer is yes.
In Tensorflow your can recover your result in a tensor (which you can easily transform in a Python array) and then send it with Python through whatever support you want to the Arduino.


message:
connecting 5 mq sensor at a time

I want to take a reading from 5 different mq sensor at a time. do I need an external power source to power these sensors or it will be ok to power sensors from 5v available from the board? I am using arduino uno board .

body:
I only had experience with the MQ2 sensor (more info [here][1]), so I'm going to use it as an example. If you have different sensors double check their datasheets.

Now, the main current consumption for these comes from the heater. Can you turn the heater off to save some power? Apparently not, since they say that

> Please note that the best preheat time for the sensor is above 24
> hours.

So, for the moment, let's consider all five sensors turned on at the same time.

The heater specs say that its resistance is around 33 ohm +/- 5% in the worst case this means 31.35 ohms. At 5V, this means 160mA for each sensor. Five of them are 800mA, and then let's add something like 50mA for the rest of the circuit (just a random number, and highly depends on the rest of the circuit).

Now, how is the UNO powered? If it is powered from the USB, the maximum current you can draw is 500mA (so 850mA is not allowed). So.. No powering from USB. If, on the other hand, the board is powered by the barrel jack, the onboard regulator can dissipate roughly 1-1.5W (taken from [this][2] thread). The power dissipation comes from the input voltage. With a 9V input, about 3V (slightly more) will need to be handled by the regulator. At 850mA, this means 2.5W (Not ok). In both cases you will need an external 5V power supply. With a 7V input (the very minimum you can apply) you will have to dissipate roughly 1.2V, at 850mA this means 1.02W. Please beware that this means something like 80-90°C of temperature increase in that area, so the part will become very hot. And moreover its lifespan will be reduced. So use this path only if really necessary.

If you reduce the performances and start powering just one sensor at a time (this means longer time before having it fully operational, and adding some transistor to switch them on and off) this data can change. I mean, if put a transistor to stop powering it, and then turn on one sensor at a time, you will be able to reduce the maximum current consumption to 210mA.

This means that you will be able to get power from the USB port; moreover you will be able to use the external power connector for voltages up to 10.5V (0.8V on the diode, so 4.7V on the regulator - around 1W). This comes at a price, of course: the heater will work for 1/5 of the time, so it will be harder to reach the temperature required for the measurement

  [1]: http://wiki.seeed.cc/Grove-Gas_Sensor-MQ2/
  [2]: http://forum.arduino.cc/index.php?topic=168964.0


message:
Which EEPROM has a long lifecycle?

I would like to build a box counter for machine, so I'm going to use EEPROM in Arduino to save count. But the lifecycle is limited to 100,000 writes. Please suggest an external EEPROM with a long lifecycle or any other solution.

body:
You can cycle through all the addresses in the EEPROM like a ring buffer.

You'll need to reserve a bit so you can binary search for the head of the buffer during startup.

You can also reduce how often you write in general especially when the count will increment in bursts, try and wait out those bursts instead of writing on every increment.


body:
The [EEPROMs from Microchip][1] have a guaranteed erase count of 1 million. The ones from [ST offer 4 million][2]. So it's not hard to find EEPROMs with a higher endurance.

But for a device which writes a lot, a better solution would be a NVRAM, FRAM or EERAM. Those usually come with virtually no limitations to the write cycles but usually are more expensive than EEPROMs but that might very well be worth it compared to the hassle you can get in otherwise.

Adafruit offers [SPI][3] and [I²C][4] variants for FRAM boards.

  [1]: http://www.microchip.com/design-centers/memory/serial-eeprom/overview
  [2]: http://www.st.com/content/st_com/en/products/memories/serial-eeprom/standard-serial-eeprom.html?querycriteria=productId=SC112
  [3]: https://www.adafruit.com/product/1897
  [4]: https://www.adafruit.com/product/1895


body: If you use something like an SD card, they have internal logic that will move the data around when a call is used up.  This should give you virtually unlimited storage for something as simple as a count.


message:
How to post HTTP POST requests on my website?

I am working on a NodeMCU board to post sensor data on my website service. Basically my project is about POST and GET requests both in single code.

I am succeeding in sending GET requests from my website. However, I just can't post data to my website.

To post I have 2 different links (asp services): one will post data and another will be used to get data same as transmitted by first link.

Here is my code, and also *how to post 2 variables in http post request*?

    #include (ESP8266WiFi.h)
    #include (ESP8266HTTPClient.h)

    const char* ssid = "oppo";
    const char* password = "11111111";
    int giSwitchNum = 1, buttonPin = 2;

    void setup () {
      Serial.begin(115200);
      WiFi.begin(ssid, password);
      pinMode(D1, OUTPUT);
      pinMode(D2, INPUT);
      while (WiFi.status() != WL_CONNECTED) {
        delay(1000);
        Serial.print("Connecting..");
      }
      giSwitchNum = 1;
      Serial.print("Connect");
    }

    void loop() {
      if (WiFi.status() == WL_CONNECTED) { //Check WiFi connection status
        HTTPClient Post;
        Post.begin("http://lemontechnologies.net/Services/Service.svc/SetData");
        Post.addHeader("operator", "text/plain");
        Post.POST("Key=hi&val=jagrut1");
        String payload = Post.getString();
        Post.end();
      }
      delay(500);
    }

body:
    void wifi_connect(){
      WiFi.mode(WIFI_OFF);        //Prevents reconnection issue (taking too long to connect)
      delay(1000);
      WiFi.mode(WIFI_STA);        //This line hides the viewing of ESP as wifi hotspot
      //WIFI_STA It's very important !!!!

      WiFi.begin(ssid, password);     //Connect to your WiFi router
      while(WiFi.status() != WL_CONNECTED){
        delay(1000);
        Serial.print(".");
      }

      Serial.println("Wifi connected");
      Serial.print("IP address: ");
      Serial.println(WiFi.localIP());
      return;
    }


message:
Arduino Mega Sensor shield

I'm using an Arduino Mega Sensor Shield on a Mega 2560 board and so far I have 12 servos attached to it from PWM pins 2 to 13.

I want to add 5 more servos but there are no more PWM pins.

So which pins do I do I use for these.

body:
There seems to be a library called

According to this  [Answer][1] you have some possibilities:

- Using ShiftPWM library
- Using a timer with a generic GPIO

  [1]: https://electronics.stackexchange.com/questions/27014/looking-to-create-36-channels-of-pwm-control-for-led-sculpture


message:
Building an EEZYBOTARM MK1

My bot arm building is complete, I'm using it with Arduino and 2 joysticks with 4 servos ( mg90s), running with the 9v battery, but still, the servos could not lift the bot arm once it is going down and the servo keeps fluctuating. It is a 3d printed bot so it is not so heavy. please help?

body:
Even if your device is not so heavy, a 9V battery has a maximum practical current draw in the 10s of milliamps. It's not a good choice for operating motors.

A better choice would be AA, C, D, or Lithium-Ion/Lithium-Polymer batteries, wired in series to produce the desired voltage.


message:
Trouble using proximity sensor as input and LED output

I was wondering if anyone had any pointers or advice to make this project work. Essentially I would like to have the LED fade (meaning like fade on and off at a calm rate) at one rate when there is nothing close to the proximity sensor, and then to speed up the fade amount when there is something close to the sensor.

    #include <NewPing.h>   //include the library

    int led = 9;           // the PWM pin the LED is attached to
    int brightness = 0;    // how bright the LED is
    int fadeAmount;    // how many points to fade the LED by

    int triggerPin = 12;   //pin conneccted to the Trig pin on the sensor
    int echoPin = 11;       //pin connected to the Echo pin on the sensor
    int maxDistance = 200;  //set the max distance for the sensor to read (helps with errors)
    int distanceVal;        //variable to hold the distance val

    int sampleRate = 200;   //how fast to sample the value
    long lastReading;       //used for the timer

    NewPing proximity1(triggerPin, echoPin, maxDistance);   //sets up the sensor object

    void setup()
    {
      Serial.begin(9600);  //start the serial port
      pinMode(led, OUTPUT);
    }

    void loop() {

        if(millis()-lastReading>=sampleRate) //this very simple statement is the timer,
      {
      distanceVal = proximity1.ping_cm();  //get the distance value in centimeters

      lastReading = millis();

      Serial.print("Distance Reading CM : ");  //print the value to the Serial monitor
      Serial.println(distanceVal);

    if(distanceVal<20){

    fadeAmount = 5;
    }
    else{
      fadeAmount = 2;
    }

      // set the brightness of pin 9:
      analogWrite(led, brightness);

      // change the brightness for next time through the loop:
      brightness = brightness + fadeAmount;

      // reverse the direction of the fading at the ends of the fade:
      if (brightness <= 0 || brightness >= 255) {
        fadeAmount = -fadeAmount;
      }
      // wait for 30 milliseconds to see the dimming effect
      delay(30);
      }
    }

https://github.com/sanaalla/Fade-LED-with-Proximity-sensor

Above is my code, which is not working. I am fairly new to Arduino and so would greatly appreciate some more seasoned wisdom!

body:
You want 2 independant loops, one for the measurement and one for the dimming effect. The latter one must also be able to run when not measuring.

    if(millis()-lastReading>=sampleRate) //this very simple statement is the timer,
    {
      distanceVal = proximity1.ping_cm();  //get the distance value in centimeters

      lastReading = millis();

      Serial.print("Distance Reading CM : ");  //print the value to the Serial monitor
      Serial.println(distanceVal);
    }

    if(millis() - lastFade >= fadeRate) //other timer
    {
      lastFade = millis();
      if(distanceVal<20){
        fadeAmount = 5;
      }else{
        fadeAmount = 2;
      }

      // set the brightness of pin 9:
      analogWrite(led, brightness);

      // change the brightness for next time through the loop:
      brightness = brightness + fadeAmount;

      // reverse the direction of the fading at the ends of the fade:
      if (brightness <= 0 || brightness >= 255) {
        fadeAmount = -fadeAmount;
      }
    }


message:
LED strip problem... getting red when expecting white with lots of pixels. Fine with 1 pixel

I have an Arduino Uno.  I bought this LED strip:  https://www.amazon.com/gp/product/B019DYZNO6/ref=oh_aui_detailpage_o08_s02?ie=UTF8&psc=1

Starting initially using FastLED library. When I tried to set the entire strip to white (255,255,255), it was coming out red. Any color close to white was coming out red.

I thought maybe there was an issue with the library, so I tried the neopixel library. Same thing until... If I just set one pixel to 255,255,255 and don't set any other, it comes out white!  If I set about 10 pixels, they still look white. As I set more pixels, they start to loose their whiteness and become red.

I want to say that maybe this was a power issue... but I tested this both when it was running off my PC and running standalone with a power supply (supplying 5V).

Any suggestions??  I also thought that maybe it's a bum strip, but I also bought https://www.amazon.com/gp/product/B01AG923GI/ref=ask_ql_qh_dp_hza and did the same experiment, and am getting the same results...

body:
According to https://learn.adafruit.com/adafruit-neopixel-uberguide/powering-neopixels a Neopixel can consume 60 mA at full brightness white.

> Each individual NeoPixel draws up to 60 milliamps at maximum brightness white (red + green + blue). In actual use though, it’s rare for all pixels to be turned on that way. When mixing colors and displaying animations, the current draw will be much less. It’s impossible to estimate a single number for all circumstances, but we’ve been using 1/3 this (20 mA per pixel) as a gross rule of thumb with no ill effects. But if you know for a fact that you need every pixel on at maximum brightness, use the full 60 mA figure.

So your 144 Neopixels would require 8.4 **amps**. You would need a pretty solid power supply to supply that much.

One way of confirming that would be to measure the voltage in to the Neopixel strip (at the strip end) when it is displaying all white. I'd be surprised if it measures 5V.

The Amazon page you linked says:

> Voltage: DC 5V
>
> Power: 0.3W ± 0.01% per LED

That agrees with the figure of 60 mA (0.060A * 5V = 0.3W)

---

To put it another way, your power supply would need to supply 43.2W (144 * 0.3W). None of the bench power supplies I have here can put out 43W (or 8A), nor any of the wall-warts. You may have a really massive one, but you haven't specified what sort of power supply you are using.

---

> I run them with a power supply (one that is working as expected, but still have it connected to the PC/USB?

Yes, there is a technique for doing that (similar to powering motors etc.).

[![Powering Neopixels][1]][1]

* You have one low-current supply to the Arduino (this could be your USB port even).
* You have a high-current supply to the pixels/motor/whatever. This would require thicker cables.
* You **connect the grounds** of both supplies so that they have a common ground reference.
* The data line (the pixel information) is sent from the Arduino to the Neopixels

The one power supply can do both roles, just connect the wires together at the power supply end (this automatically connects the grounds, of course).

This way, the heavy-duty current does not go through the Arduino board.

---

If you are using the USB port for logic power you still connect the grounds like this:

[![Powering Neopixels with USB for logic][2]][2]

  [1]: https://i.stack.imgur.com/C3a3C.png
  [2]: https://i.stack.imgur.com/cf7k7.png


message:
Powering servos with external source

I understand why servos and motors require an external power source when run from the Uno, but I've seen a lot of tutorials (for example, [this one][1]), where the servo is connected directly to the Arduino's 5V port. I did this, and I think it fried my servo. This is also the method shown on the official Arduino tutorials for [Knob][2] and [Sweep][3]. In fact, the knob tutorial was the first and last tutorial I tried with my servo -- after trying it, the servo didn't work.

It went like this:

1) Try sweep code without using external supply. Works fine.

2) Try knob code without using external supply. Servo hums without moving and heats up (a lot).

Why do tutorials say to do this if it's not advisable?

  [1]: https://playground.arduino.cc/Learning/SingleServoExample
  [2]: https://www.arduino.cc/en/Tutorial/Knob
  [3]: https://www.arduino.cc/en/Tutorial/Sweep

body:
Most likely you fried the voltage regulator or the diode on your Arduino board (depending in which power source you used), because the servo has drawn too much current.

Many Arduino Kits or Starter Packs come with really small servos. These do not need much power (especially when no mechanical load is attached to them), so you can power them directly from the 5V pin. Greater/stronger Servos draw much more current and cannot be safely run in the 5V pin.

Many tutorials show this, because it is an easy start for a beginner. And with the right servo it works. More sophisticated cases are not covered there.

EDIT:

Since your Arduino works fine, the voltage regulator and/or the diode should be fine. I tested the `Knob` example on my Arduino Nano, while powering the servo on the Arduinos 5V pin (and the Arduino is powered over USB). When the Servo is moving, you can see that there is a significant power draw (The power LED gets a bit dimmer), but not so much, that it would be a problem for the Arduino or USB port. Also the example code works as it should, without the servo heating up. I also used a SG90 Micro Servo (9g, by Tower Pro; same as in the tutorial you linked). I also tried the same with an external power source (5V from a powerful USB charger). It still works as intended, but with more power, since the servo now can draw much more current to produce a higher thrust.

So the only thing, I can think of for your problem is, that you either have corrupt hardware, or you have connected it wrong (for example wrong polarity). My Servo has the same color coding for the wires as in the tutorial you linked. Brown is ground, Red is 5V Vcc and Yellow is for the pulse signal.


message:
How to continuously monitor range finder and immediately interrupt code to run a different code in pedestrian traffic lights setup?

I am currently doing part 2: Pedestrian Mode of my project below:

1. Regular Mode: This is the regular mode of operation. In this mode the
three lights (Red, Yellow and Green LEDs) should operate in the following
order. The Red LED lights for 2 seconds, followed by the Yellow LED for 1
second, the Green LED for 2 seconds and then the Yellow LED again for 1
second. The cycle should repeat until the mode changes.
2. Pedestrian Mode: This mode uses the SRF05 Ultrasonic Range Finder to
detect the proximity of any object. The lights should operate as defined in
the regular mode UNTIL an object is detected less than 10 cm from the
TLC. The buzzer should then beep and the Yellow LED must blink ON/OFF
(flashing intervals of 0.1 sec) repeatedly 10 times. The buzzer should then
stop beeping and the operation of the lights (not the system) must behave
as it would in the regular mode. The operation stays the same until the
mode changes

My code works, however it waits for the entire regular cycle to finish before sensing a pulse with the ultrasonic range sensor to determine if an object is near or not. Therefore, when I put my hand near the sensor, it has to finish running the regular mode before it detects my hand and switches to pedestrian mode. What I would like is for the range finder to **continuously** fire the pulse and **immediately** switch to pedestrian mode when it detects an object less than 10 cm away.

Code below:

    int red_light = 12;
    int yellow_light = 10;
    int green_light = 8;
    int ECHOPIN = 3;
    int TRIGPIN = 5;
    int buzzer = 7;
    float distance;

    void setup() {
      Serial.begin(9600);
      pinMode(red_light, OUTPUT);
      pinMode(yellow_light, OUTPUT);
      pinMode(green_light, OUTPUT);
      pinMode(ECHOPIN, INPUT);
      pinMode(TRIGPIN, OUTPUT);
      pinMode(buzzer, OUTPUT);
    }

    void loop() {
      range_finder();
      if (distance < 10) {
        pedestrian_mode();
      } else {
        regular_mode();
      }
    }

    void regular_mode() {
      digitalWrite(red_light, HIGH);
      delay(2000);
      digitalWrite(red_light, LOW);
      digitalWrite(yellow_light, HIGH);
      delay(1000);
      digitalWrite(yellow_light, LOW);
      digitalWrite(green_light, HIGH);
      delay(2000);
      digitalWrite(green_light, LOW);
      digitalWrite(yellow_light, HIGH);
      delay(1000);
      digitalWrite(yellow_light, LOW);
    }

    void range_finder() {
      digitalWrite(TRIGPIN, LOW);
      delayMicroseconds(2);
      digitalWrite(TRIGPIN,HIGH);
      delayMicroseconds(10);
      digitalWrite(TRIGPIN,LOW);
      distance = pulseIn(ECHOPIN, HIGH);
      // return 0 if no high pulse in 1 sec
      distance = distance/58;
      Serial.print(distance);
      Serial.println("cm");
      delay(200);
    }

    void pedestrian_mode() {
      digitalWrite(buzzer, HIGH);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
      digitalWrite(yellow_light, HIGH);
      delay(100);
      digitalWrite(yellow_light, LOW);
      delay(100);
    }

Also I have a feeling some parts of my code may be unnecessarily long and could be shortened. If so, I would appreciate any advice and how to do that. Thank you.

body:
       digitalWrite(yellow_light, HIGH);
       delay(100);
       digitalWrite(yellow_light, LOW);
       delay(100);

       digitalWrite(yellow_light, HIGH);
       delay(100);
       digitalWrite(yellow_light, LOW);
       delay(100);

    ...

You really need to read up on "for" loops. Make a loop that does it 10 times, don't copy and paste 10 times.

As for your other issue, at the very least you could test the proximity sensor after each delay. Read up on `millis`. Just imagine how you might do it in real life. Would you really delay for two seconds? Or would you check the clock to see if two seconds had elapsed and also check if a pedestrian had arrived?

And better still, replace `delay` with a loop which tests elapsed time, and also tests the distance sensor.

---

I'm not writing more specific code because clearly the exercise is for you to learn how to do this. I already know how to do it, and if I just posted the exact answer you wouldn't have learned how to do it.


body:
You should use an interrupt pin.

Interrupt pins can operate outside the normal void loop().

So you can have a normal loop going on. If an interrupt pin is triggered - it performs a function immediately.

https://www.arduino.cc/reference/en/language/functions/external-interrupts/attachinterrupt/

Or you could consider using a switch case.


message:
Infrared frequency recorded with saleae

i'm trying to decode infrared signal recorded with the saleae. It makes me wonder why saleae shows so low values for the frequencies from 0.1kHz to 0.8kHz. I found that standard for the IR is around 38kHZ. Is there something wrong with my record? Or did i misread the sample?
[![enter image description here][1]][1]

  [1]: https://i.stack.imgur.com/BpXtV.png

body:
What you are looking now is NOT the IR frequency, but the de-modulated signal.

Here is what I'm talking about:

[![Image description here][1]][1]

(image taken from http://www.electronicwings.com/sensors-modules/ir-communication)

As you can see, the various pulses are made of smaller pulses.

In your case you are seeing what is here called "Serial data", which is different from the carrier frequency. What the saleae board is telling you is that the width of the high part is 1.625ms, while the width of the low part is 0.631 ms; as you can see, the waveform is NOT periodic, so the "frequency" is meaningless (it's the reverse of the time marked on the view, which is the sum of one large high value and one low value).

Your plot resembles the NEC protocol (see for instance [here][2]). A logic '0' is a 562.5µs pulse followed by a 562.5µs space, while the logic '1' is a 562.5µs pulse burst followed by a 1.6875ms space (this is similar to by 0.631 ms and 1.625 ms measurement)

  [1]: https://i.stack.imgur.com/S6Rhk.png
  [2]: http://techdocs.altium.com/display/FPGA/NEC+Infrared+Transmission+Protocol


message:
Readings changing in hall effect sensor

I am using a [A1324][1] hall effect sensor for a distance measuring.

The voltage output keeps changing even if the distance between the magnet and sensor does not change. The output changes +-0.200V and I am trying to measure the distances at steps of 0.01V.

  [1]: https://www.allegromicro.com/~/media/Files/Datasheets/A1324-5-6-Datasheet.ashx

body:
From https://www.arduino.cc/reference/en/language/functions/analog-io/analogread/

> `analogRead()`
>
> Reads the value from the specified analog pin. The Arduino board
> contains a 6 channel (8 channels on the Mini and Nano, 16 on the
> Mega), 10-bit analog to digital converter. This means that it will map
> input voltages between 0 and 5 volts into integer values between 0 and
> 1023. This yields a resolution between readings of: 5 volts / 1024 units or, **.0049 volts (4.9 mV) per unit**.

It is likely what you are seeing is noise and is to be expected. The source of the noise is likely multiple and could be environmental physical metallic or magnetic objects some distance away that are moving, electrical wiring (mains) nearby, and noise introduced by the power supply to the Arduino.

If you want to get a stable precise reading that close to the minimum step size, you will want to take several readings and average them. The more you read and average, the more you can eliminate the random effect of the noise, but the tradeoff is that it is slower because you are taking tens or hundreds of readings just for one result.


message:
adafruit LSM9DS0 Library - ok with Uno but compile error with LinkitOne?

I'm calling an adafruit Flora LSM9DS0 magnetometer using the Adafruit library with the following sketch:

            #include <Wire.h>
            #include <SPI.h>
            #include <Adafruit_LSM9DS0.h>
            #include <Adafruit_Sensor.h>  // not used in this demo but required!

            unsigned long timeNow = 0;
            unsigned long mSecInHour = 3600000;
            unsigned long TimeNow =0;
            int millisecs =0;
            int seconds = 0;
            byte minutes = 0;
            byte hours = 0;

            int mag_raw_x;
            int mag_raw_y;
            int mag_raw_z;

            // i2c
            Adafruit_LSM9DS0 lsm = Adafruit_LSM9DS0();

            // You can also use software SPI
            //Adafruit_LSM9DS0 lsm = Adafruit_LSM9DS0(13, 12, 11, 10, 9);
            // Or hardware SPI! In this case, only CS pins are passed in
            //Adafruit_LSM9DS0 lsm = Adafruit_LSM9DS0(10, 9);

            void setupSensor()
            {
              // 2.) Set the magnetometer sensitivity
              lsm.setupMag(lsm.LSM9DS0_MAGGAIN_2GAUSS);
            }

            void setup()
            {
            #ifndef ESP8266
              while (!Serial);     // will pause Zero, Leonardo, etc
            #endif
              Serial.begin(9600);

              // Try to initialise and warn if we couldn't detect the chip
              if (!lsm.begin())
              {

                while (1);
              }
              Serial.println(F("Found LSM9DS0 9DOF, measurements in Gauss"));
             }
             void loop()
            {
              lsm.read();
              TimeNow = millis();
              mag_raw_x = lsm.magData.x;
              mag_raw_y = lsm.magData.y;
              mag_raw_z = lsm.magData.z;

Which compiles and runs fine on the Arduino Uno, but I don't understand why the same sketch causes this compile error in the LSM9DS0 library when I compile for the LinkitOne?

        C:\Users\elbg\Arduino\libraries\arduino_373648\Adafruit_LSM9DS0.cpp: In member function 'bool Adafruit_LSM9DS0::begin()':

        C:\Users\elbg\Arduino\libraries\arduino_373648\Adafruit_LSM9DS0.cpp:77:16: error: 'SPCR' was not declared in this scope

             SPCRback = SPCR;

                        ^

        C:\Users\elbg\Arduino\libraries\arduino_373648\Adafruit_LSM9DS0.cpp: In member function 'void Adafruit_LSM9DS0::write8(boolean, byte, byte)':

        C:\Users\elbg\Arduino\libraries\arduino_373648\Adafruit_LSM9DS0.cpp:365:18: error: 'SPCR' was not declared in this scope

               SPCRback = SPCR;

                          ^

        C:\Users\elbg\Arduino\libraries\arduino_373648\Adafruit_LSM9DS0.cpp:374:7: error: 'SPCR' was not declared in this scope

               SPCR = SPCRback;

               ^

        C:\Users\elbg\Arduino\libraries\arduino_373648\Adafruit_LSM9DS0.cpp: In member function 'byte Adafruit_LSM9DS0::readBuffer(boolean, byte, byte, uint8_t*)':

        C:\Users\elbg\Arduino\libraries\arduino_373648\Adafruit_LSM9DS0.cpp:415:18: error: 'SPCR' was not declared in this scope

               SPCRback = SPCR;

                          ^

        C:\Users\elbg\Arduino\libraries\arduino_373648\Adafruit_LSM9DS0.cpp:426:7: error: 'SPCR' was not declared in this scope

               SPCR = SPCRback;

               ^

Any suggestions welcome !

body:
The Adafruit library for the LSM9DS0 is written to run on an 8-bit Arduino. The LinkitOne isn't - it's an ARM board.

Either get a different library that is written to work on ARM, write your own library to work on ARM, or don't use that combination of components.


message:
How to solve problem AT+INQ ERROR (1F), AT+INIT ERROR(17) on Bluetooth Module HC-05?

i have problem with accessing **at-command in module Bluetooh HC-05**.

i just follow all tutorial to activate at-command like this,
http://www.martyncurrey.com/arduino-with-hc-05-bluetooth-module-in-slave-mode/

or in this video
https://www.youtube.com/watch?v=Vr4cdpsoVEo&t=31s

and just read some explanation and implemented to my problem
https://electronics.stackexchange.com/questions/180962/hc-05-bluetooth-atinq-command-not-working

**but i just still get same error.
i cant use AT+INQ command, always get ERROR(1F).
AT+INIT get ERROR(17).**

i have module HC-05 with version 3.0-20170601

This is my code i use it.

    #include <SoftwareSerial.h>
    SoftwareSerial BTserial(8, 9); // RX | TX`

    const long baudRate = 38400;
    char c=' ';
    boolean NL = true;

    void setup()

    {
       Serial.begin(9600);
       Serial.print("Sketch:   ");   Serial.println(__FILE__);
       Serial.print("Uploaded: ");   Serial.println(__DATE__);
       Serial.println(" ");

    BTserial.begin(baudRate);
    Serial.print("BTserial started at "); Serial.println(baudRate);
    Serial.println(" ");
    }

    void loop()

    {

    // Read from the Bluetooth module and send to the Arduino Serial Monitor
    if (BTserial.available())
       {
           c = BTserial.read();
           Serial.write(c);
       }

       // Read from the Serial Monitor and send to the Bluetooth module
    if (Serial.available())
       {
           c = Serial.read();
           BTserial.write(c);

        // Echo the user input to the main window. The ">" character indicates
        the user entered text.
        if (NL) { Serial.print(">");  NL = false; }
        Serial.write(c);
        if (c==10) { NL = true; }
       }

    }

body:
I have two modules:

(A) HC-05 with firmware version 3.0-20170601

(B) HC-05 with firmware version 2.0-20100601 (ok)

I have the same problem: when the AT command "AT+INQ" is sent on (A) module, the response is always "ERROR:(1F)". This error code seems not be reported in any document or specification available on internet. This BT module have firmware version (AT+VERSION) 3.0-20170601. Also I have noticed that command AT+INIT on (A) module returns always ERROR:(17), this error normally can be ignored if the command has been sent already (Initiate SPP lib), but the first time should be return "OK" as on (B) module.

The (B) module with firmware version 2.0-20100601 works ok with the following commands (set PIN34 high at power-up, or press button on module and keep pressed during commands):

AT+RMAAD -> delete all paired devices list

AT+ROLE=1 -> Set master mode

AT+RESET -> reset module to enter into master mode

AT+CMODE=1 -> Permit connection with any device

AT+INQM=0,5,9 -> Set Search parameters(Query mode standard, 5 devices, 9secs)

AT+INIT  --> Init SPP profile mode (first time response: "OK")

AT+INQ  --> Start search devices (return device list after some seconds)

The differences between two modules are:

On AT+INIT the (A) module return always ERROR:(17), the (B) module return "OK" first time and ERROR:(17) if the command is sent twice.
On (A) module the command AT+INQ return always ERROR:(1F), the (B) module return the list of the BT devices.

Also the (A) and (B) modules are physically different. The (B) module have some components (resistors/capacitors) between the two big black chips, the (A) module no.

Also I noticed that on (A) module the AT+CLASS? return "1f00" value (default?). The correct value should be "0" as (B) module ? Anyway setting AT+CLASS=0 on (A) module the result is always the same.

In slave mode (AT+ROLE=0) both modules works fine.

With (A) module I'm unable to use it as "MASTER" and connect it to any other slave BT modules because did not perform devices search. (INQ fails).

I think that in 3.0 firmware is needed to set other(s) parameter(s) in order to start SPP profile correctly (INIT) and then avoid ERROR:(1F) in INQ command (search).

Someone already solved the problem ?


body:
I have a HC-05 with 3.0-20170601 that I managed to bind to a slave last night. It turns out that the v3 has two AT-modes.

The first is when you hold the button while you connect power. The led will blink slowly and you can connect at 38400 baud. But this is like a configuration mode, where AT+INQ is not available.

In this mode I did these commands:

    AT
    AT+UART
    AT+RMAAD
    AT+ROLE=1

(Press and hold the button)

    AT+RESET

(Release the button after device restarts and led is slowly blinking)

    AT+CMODE=1
    AT+INQM=0,5,5
    AT+PSWD="9999"

AT should give OK as answer to know connection is working

AT+UART will show configured baudrate. Default is 9600.

AT+RMAAD clears all saved connections

AT+ROLE=1 sets it as master

AT+RESET restarts the device to change to master

AT+CMODE=1 accepts all kinds of devices

AT+INQM=0,5,5 inquires in standard mode, with 5 max connections or 5 secs

AT+PSWD="9999" sets the pin code 9999, change to the pin you need

After this it is time to update the arudino code. In your case you should update line 4 from

    const long baudRate = 38400;

to

    const long baudRate = 9600;

...or what ever value you might have set the baud rate to. Then reflash your arduino.

Now enter the very irritating second AT command mode.

Power up without holding the button. You will get the fast blink speed. When its powered up, press and hold the button. The led will continue blinking fast, but while the button is pressed you can now connect to the device on the configured baud rate. So open the serial monitor and type AT to verify.
Remember that the mode is only active while the button is pressed. So keep it pressed. I had a small clamp I put on there.

Then I entered these commands:

    AT+STATE

AT+STATE will show current state, should be inquiring

Then power up the slave device and the adress should start popping up. It will be something like xyz:xy:xyzw,931F00,7FFF

The first part is the address you want (xyz:xy:xyzw)

Change : to , and get xyz,xy,xyzw

Check that you connecting to the correct device

    AT+RNAME?xyz,xy,xyzw

Then bind

    AT+PAIR=xyz,xy,xyzw,5
    AT+BIND=xyz,xy,xyzw
    AT+LINK=xyz,xy,xyzw

The AT+LINK command gave me FAIL as output. But it did not matter.
I restarted and did not press any button before or after. Just normal start.

After 5-10s serial data showed up in my serial monitor.

Modules are bound. And will automatically connect at power up. If not you might have the wrong pincode. Make sure to change 9999 above to 0000 or 1234 or what ever it may be. When I hade the wrong pin I still got OK from the AT+PAIR and AT+BIND commands... It didnt work for me until I entered the correct pin.

Sorry for long post, but I wanted to be thorough since info about HC-05 v3 is very scarce on the internet right now.

A reference to all commands can be found here:
http://www.electronicaestudio.com/docs/istd016A.pdf
(Link valid 2018-08-13)


body:
Extending the Presidenten's answer, the easiest way to program HC-05 is to sonnect a wire to EN on the chip and set the UART console to 9600.

Then pull the EN high, send commands, wait for OK (after each one), and drive EN down.

You now have a chip in data state.


body:
I have the same version module HC-05.
This mode (INQ) is enabled for default and it's impossible switch it off. Seems that manufacturer removed this command in that version.

Another point, that it works only on default 9600 bod/s regardless of settings AT+UART=... and only in standart AT mode (key pin pull high after power on device).

Once connected to other module only one way to return to "inquiring" that I found is full reset it by command ORGL, and reconfigure it class and role.

Don't touch IAC settings - that also causes improperty working.


message:
I'm trying to make a program which you choose an angle

, and it tells you it's respective Sin, Cos and Tan. But, I can't figure out why all of the angles I use have the same answer (Sin 0, Cos 1 and Tan 0. Can someone help me out?

    #include <math.h>
    double angulo;
    double seno;
    double cosseno;
    double tangente;
    double rad;
    void setup() {
      // put your setup code here, to run once:
    Serial.begin(9600);
    }

    void loop() {

     Serial.println("Programa para calcular sen, cos e tg");
     delay(1000);
     Serial.println("Digite o angulo");
     angulo = Serial.parseInt();
     rad = angulo*0,0174533;
     seno = sin(rad);
     Serial.println("Seno");
     Serial.println(seno);
     cosseno = cos(rad);
     Serial.println("Cosseno");
     Serial.println(cosseno);
     tangente = tan(rad);
     Serial.println("Tangente");
     Serial.println(tangente);

    }

body:
You have written

    rad = angulo*0,0174533;

But, C++ uses the american decimal notation:

    rad = angulo*0.0174533;

Thus, you have been multiplying `angulo` by zero every time.


message:
What is wrong with my code? Did you forget '()'?

#include <SimbleeBLE.h>

    // constants won't change. They're used here to set pin numbers:

    const int ButtonPlayPause = 15;
    const int ButtonNext = 12;
    const int ButtonPrevious = 11;
    const int OBled = 29;
           int Playp = 1;

    // variables will change:
    int buttonState = 0;         // variable for reading the pushbutton status

    void setup()
    {

      pinMode(ButtonPlayPause, INPUT);
      pinMode(ButtonNext, INPUT);
      pinMode(ButtonPrevious, INPUT);

      pinMode(OBled, INPUT);

      SimbleeBLE.deviceName = "GBAND";

      Serial.begin(115200);

      SimbleeBLE.begin();

      SimbleeBLE.txPowerLevel = +4;
    }

    void loop()
    {
      buttonState = digitalRead(ButtonPlayPause);
      if (buttonState == HIGH)
      {
        SimbleeBLE.begin();
        SimbleeBLE.deviceName = "GBAND";
        //More code here to establish connection with android
         SimbleeBLE.sendInt = (Playp);
        digitalWrite(OBled, HIGH);
        SimbleeBLE.end();
        digitalWrite(OBled, LOW);
      } else  {
                buttonState = digitalRead(ButtonNext);
                if (buttonState == HIGH)
                {
                  SimbleeBLE.begin();

                  //More code here to establish connection with android

                  digitalWrite(OBled, HIGH);
                  SimbleeBLE.end();
                  digitalWrite(OBled, LOW);
                } else  {
                          buttonState = digitalRead(ButtonPrevious);
                          if (buttonState == HIGH)
                          {
                            SimbleeBLE.begin();
                            //More code here to establish connection with android

                            digitalWrite(OBled, HIGH);
                            SimbleeBLE.end();
                            digitalWrite(OBled, LOW);
                          }
                        }
              }
        }

---

This is the error I keep getting:

    Arduino: 1.8.5 (Windows Store 1.8.10.0) (Windows 10), Board: "Simblee"

    C:\Users\Lestat\Desktop\SD PROJECR PAPERWORK\Sketch programs\sketch_mar20a\sketch_mar20a.ino: In function 'void loop()':

    sketch_mar20a:42: error: invalid use of member function (did you forget the '()' ?)

         SimbleeBLE.sendInt = (Playp);
                            ^
    exit status 1
    invalid use of member function (did you forget the '()' ?)

    This report would have more information with
    "Show verbose output during compilation"
    option enabled in File -> Preferences.

body:
You're trying to assign a value to a function. That is almost certainly wrong.

    SimbleeBLE.sendInt(Playp);


message:
Attiny85 appears to be drawing 0.2mA current but battery running down more quickly

I am trying to get a temperature sensor (tmp36) working with an Attiny and if possible I would like it to run for several weeks. I have tried to power down the Attiny and it appears to be drawing only 0.2mA current when asleep, and around 4mA when awake (using a multimeter). However the CR2032 battery went from 3.24V to 2.9V in about 1.5 days.  If it was really only using 0.2mA I would have thought it would go down much more slowly than this.

I wonder if it's using a lot of current every 8s when it turns on briefly and I'm not seeing this on the multimeter, or drawing a lot of current every hour when it reads the temperature or is there something else that I'm missing.

My circuit is an Attiny85 connected directly to a tmp36 temperature sensor.  I have a capacitor connected across the GND and Vcc of the tmp36.  Since I am using a surface mount tmp36 I also have the shutdown pin on the tmp36 pulled high (connected directly to Vcc). Otherwise there are no other connections, it's a very simple circuit and since the current normally appears to be 0.2mA I'm not sure why the battery voltage reading is going down so fast.

I am new to turning off the attiny(and still pretty new to arduino programming) and I copied most of the code for putting the arduino to sleep from here: https://folk.uio.no/jeanra/Microelectronics/ArduinoWatchdog.html
(and possibly other places).

The code I have is as follows:

    #include <stdlib.h>
    #include <EEPROM.h>
    #include <SoftwareSerial.h>

    #include <avr/sleep.h>    // Sleep Modes
    #include <avr/power.h>    // Power management
    #include <avr/wdt.h>      // Watchdog timer
    #include <avr/interrupt.h> // Interrupts handling

    // Definitions
    #define rxPin 3
    #define txPin 4

    // 0 1 0 Internal 1.1V Voltage Reference, calling INTERNAL should set the            reference voltage to 1.1

    SoftwareSerial mySerial(rxPin, txPin);

    int currentTime = 0;
    int timeLastSaveFullTemp = 0;

    int nbr_remaining;
    int sensorPin = 7; // This is the 7th pin on the ATtiny85,

                             // it is an analog input when reading as digital  call it 7? analogpintochannel function
                             // (On the HLT tutorial it is labelled as Pin2:  Analog input 1, SCK )

    float temperature = -500.00f;     // Create a new float called temperature and give it the value -500 to start with
    float prevTemp = -500.00f;
    float tempDiff = -500.00f;

    int tempAsInt = 0;
    int tempDiffAsInt = 0;  // create int to store temperature difference between samples

    signed char tempDiffAsChar; // create char to store temp difference between samples, hopefully this saves as a 1 byte no. between -128 and 127 (will store like this on EEPROM where difference is small enough since only 1 byte) (range around -128 to 128 so can't use for temp diff greater than 10 deg)
    signed char warningNextDataIsTwoBytes = 111;

    int eepromAddress = 0;       // initialize variable for position in eeprom to store data collected

    int decideWhatToSaveFlag = 1;    // Decide what to save,  if this = 0 then save the temp difference as a char (1 byte), otherwise save the entire temperature as an integer.

    // interrupt raised by the watchdog firing
    // when the watchdog fires during sleep, this function will be executed
    // remember that interrupts are disabled in ISR functions
    ISR(WDT_vect)
    {
            // not hanging, just waiting
            // reset the watchdog
            wdt_reset();
    }

    // function to configure the watchdog: let it sleep 8 seconds before firing
    // when firing, configure it for resuming program execution
    void configure_wdt(void)
    {

      cli();                           // disable interrupts for changing the registers

      MCUSR = 0;                       // reset status register flags

                                   // Put timer in interrupt-only mode:
      WDTCR |= 0b00011000;            // Set WDCE (5th from left) and WDE (4th from left) to enter config mode,
                                   // using bitwise OR assignment (leaves other bits unchanged).
      WDTCR =  0b01000000 | 0b100001; // set WDIE: interrupt enabled, 8 seconds
                                   // clr WDE: reset disabled
                                   // and set delay interval (right side of bar) to 8 seconds

      sei();                           // re-enable interrupts

    }

    // Put arduino to sleep.
    void sleep(int ncycles)
    {
     nbr_remaining = ncycles; // defines how many cycles should sleep

      // Set sleep to full power down.  Only external interrupts or
      // the watchdog timer can wake the CPU!
      set_sleep_mode(SLEEP_MODE_PWR_DOWN);

      // Turn off the ADC while asleep.
      power_adc_disable();

      while (nbr_remaining > 0){ // while some cycles left, sleep!

      // Enable sleep and enter sleep mode.
      sleep_mode();

      // CPU is now asleep and program execution completely halts!
      // Once awake, execution will resume at this point if the
      // watchdog is configured for resume rather than restart

      // When awake, disable sleep mode
      sleep_disable();

      // we have slept one time more
      nbr_remaining = nbr_remaining - 1;

      }

      // put everything on again
      power_all_enable();

     }

    // the setup routine runs once when you press reset:
    void setup() {
      analogReference(INTERNAL);    // This sets the internal ref to be 1.1V (or close to this), note that this makes 1.1V the highest voltage. The TMP36 gives 1.1V at around 55 or 60 deg so need to not put the chip in temperatures hotter than 55deg
      pinMode(sensorPin, INPUT);    // make pin 7 on the ATTiny an input pin

      delay(1000);

      configure_wdt();              // configure the watchdog

      mySerial.begin(9600);         // begin software serial at rate of 9600

    }

    // the loop routine runs over and over forever:
    void loop() {

      sleep(450);                                                 // sleep for a given number of cycles (here, 450 * 8 seconds = 60mins) in lowest power mode

      currentTime = currentTime + 60;                             // add 60 min to current time

      if((eepromAddress<=510))                                    //  the eeprom still has space
      {

    /***********Get temperature from sensor, then calculate difference since previous reading****************/

    //Earlier set the reference voltage for the analog to digital converter to 1.1V.  This means a value of 1.1V will be read as the maximum (not sure if 1023 or 1024, but anyway)
    //Note that this means an input greater than 1.1V from the temperature sensor (temperature about 55deg) is bad, not sure if it will damage the circuit or give bad readings but avoid.

    temperature = analogRead(sensorPin)*1100.0/1024.0;  // read value on pin 7, between 0 and 1023 where 1023 is max, convert result back to a voltage in millivolts.
    temperature = (temperature - 500)/ 10;              //Celcius temperature = [(analog voltage in mV) - 500] / 10
    tempDiff = temperature - prevTemp;

    /******* Change temperature diffence to integer and a signed char if it's between -2 and 2 deg ***********/
    tempAsInt = int(round(temperature*10));  // multiply temp. by 10 then round and change to an integer type, this should give temp. as a three digit integer scaled by x10, e.g. 335 = 33.5deg, 120 = 12.0deg etc.
    tempDiffAsInt = int (round(tempDiff*10));

    // work out whether want to save complete temperature or just temp difference
    if ((currentTime - timeLastSaveFullTemp) >=10)           // If the entire temperature hasn't been saved for more than 10 min, then want to save the entire temperature rather than just difference
    {
      decideWhatToSaveFlag = 1;                               // Set flag to 1, since want to save entire temperature
      }
    else
      decideWhatToSaveFlag = 0;                               // If the entire temperature has already been saved recently then set flag to zero since only want to save the difference.

    if ((tempDiffAsInt>-20 and tempDiffAsInt<20)and (decideWhatToSaveFlag == 0))    // if temp change is less than 2 degrees and if the decideWhatToSaveFlag hasn't been previously set to 1 for another reason.
      tempDiffAsChar = (char)(tempDiffAsInt);

    else decideWhatToSaveFlag = 1;                                                  // if the temp diff since prev sample is > 2 degrees or less than -2 degrees then set flag to 1 since want to save the entire temp. not just the difference

    if (decideWhatToSaveFlag == 0)
      {
      //mySerial.print(" Temp diff");
      EEPROM.put(eepromAddress, tempDiffAsChar);
      eepromAddress = eepromAddress + sizeof(tempDiffAsChar);
      }

    else
      {
      EEPROM.put(eepromAddress, warningNextDataIsTwoBytes);
      eepromAddress = eepromAddress + sizeof(warningNextDataIsTwoBytes);
      EEPROM.put(eepromAddress, tempAsInt);
      eepromAddress = eepromAddress + sizeof(tempAsInt);
      timeLastSaveFullTemp = currentTime;                       // Update time entire temperature was last saved to the current time.
      }

    prevTemp = temperature; // copy temp to prev temp for next time.

    }

    }

Please excuse my coding I'm still learning.  I deleted my comments at the start of the program which explain why I'm changing the temp. to char etc. as they weren't really relevant to this question but if anyone wants them let me know.

Here is the circuit, a 3V battery is connected between Vcc and GND.  The capacitor is 0.1uF ceramic.  I am using the SOIC (surfacemount) type package of the tmp36, the (not) shutdown pin in the SOIC version needs to be pulled high so I have connected it to Vcc as specified in the datasheet (this pin doesn't exist in the TO92 through-hole version of the tmp36).
[![schematic][1]][1]

All help is greatly appreciated,

I'm also interested in suggestions for reducing the current further.  (Or for how to store more temperatures in a 512 byte EEPROM but that's less important than the battery)

Thanks very much!!

p.s. I have tested this code and it did save one temperature per hour as expected. (The section of code that saves temperature differences rather than temperature doesn't run when there is a 60 min gap between temperatures so all temperatures were saved to the eeprom as integers).

  [1]: https://i.stack.imgur.com/TRrmg.png

body:
2.9V doesn't sound too bad. See [a datasheet for the CR2032](http://data.energizer.com/pdfs/cr2032.pdf) I found:

[![CR2032 datasheet][1]][1]

It looks like slightly more than 2.9V would be the expected voltage for up to 600 hours.

3.2V looks like it is fully charged, and won't stay at that level for long.

Having said that, 200 µA current sounds like a lot. You should be able to get it down to 6 µA. Perhaps post your schematic?

---

After a bit of experimenting I got the current draw down to the (expected) lower level of 4.25µA running at 3V, and 6.77µA running at 5V.

You had not in fact turned the ADC off. You need to change:

<!-- language: lang-c++ -->

     // Turn off the ADC while asleep.
      power_adc_disable();

To:

<!-- language: lang-c++ -->

      // Turn off the ADC while asleep.
      ADCSRA = 0;            // turn off ADC
      power_all_disable();

I can't comment on what extra draw, if any, your TMP36 will cause, however this should help get the overall current down.

---

Of course, you need to put the ADC back on afterwards, so this might be better:

<!-- language: lang-c++ -->

      // Turn off the ADC while asleep.
      byte saved_ADCSRA = ADCSRA;
      ADCSRA = 0;            // turn off ADC
      power_all_disable();

      ... sleep here

      power_all_enable();
      ADCSRA = saved_ADCSRA;

  [1]: https://i.stack.imgur.com/IDnQQ.png


body:
**THIS IS NOT AN ANSWER**; it's just a very long comment and I was not able to add all the formatting and ideas in the comment I was writing. Please don't consider it as a valid answer.

I leave all the low current topics to Nick, since he's doing a great work as usual. I wanted just to give you some ideas for the temperature acquisition and storing.

First of all, the `float`s. Forget them. `float`s are one of the worst things you can do to your poor microcontroller, unless you have an onboard FPU.

I haven't checked your sensor, so I assume that the calculations you performed were correct. (Note: voltages above 1.1V should not damage the board, but will not be detected - the value will cap at 1023)

So when you read number X (from 0 to 1023) you get the temperature by writing

    ((X * 1100 / 1024) - 500) / 10

You are using floats to do this. I don't like them at all, so let's switch to ints. Moreover you decided to store them with a 0.1°C precision, so that /10 is meaningless. So in the end

    <integral type> finalTempInTenthsOfDegree = ((X * 1100 / 1024) - 500);

Now, the types. The value of the final temperature is between +60°C (corresponding to 1.1V) and -50°C (0V - not sure about this, but let's stick with these value). This means an integral value going from +600 to -500; the proper type is therefore `int16_t` (signed 2-bytes value). During your calculations, the X (which is a `uint16_t`) is multiplied by 1100; this value can rise up to 1125300 (when X = 1023), which does not fit a 2-bytes variable. You can reduce 1100/1024 to 275/256, but this does not solve the problem.

**EDIT:** As Edgar Bonet pointed out in the comments, the problem of having a 4 bytes is not solved with this trick, but dividing by 1024 is more "time consuming" than dividing by 256 (because the 10-bit shift involves shifting bits through bytes, while a 8-bit shift is just moving the bytes. His tests (avr-gcc 4.9.2, optimization for size -Os) show that a shift by 10 bits (=division by 10) is converted in a routine to shift one bit through all the four bytes and then this is repeated 10 times. This lead to 72 clock cycles. A 8-bit shift, on the other hand, was converted to a byte movement for three out of four bytes and the zeroing of the uppermost. So 4 clock cycles. So... Yes, this does not solve the problem, but can optimize the code; I'll think of this trick in my future projects. Of course this can be done in a much more optimized way, and the number of cycles required can change according to the way the operation is written and the optimization level, but it is worth remembering that if you shift by a multiple of 8 bits (on an 8-bit machine) it is more optimized than another arbitrary value.

In any case, even with either of the two values, a 4-bytes int is required. In order to reduce unnecessary overhead, let's switch it back to a 2-bytes whenever possible. Something like

    int16_t finalTemp = ((int16_t)((((uint32_t)X) * 1100U) / 1024) - 500;

So the operation order is

 1. Take the X value
 2. Promote it to a unsigned 32 bit variable
 3. Multiplicate by 1100 (values from 1125300 to 0)
 4. Divide it by 1024 (values from 1098 to 0)
 5. Cast it back to a signed 16 bit value
 6. subtract 500 (values from 598 to -500)

Now, the storage. If you store the values as they are, you will get 256 measurements, which at one measurement per hour mean something like 10 days.

One easy way to increase this space is noticing that you are using only 11 bytes out of 16. So you can compact it and get 372 measurements (around 15 days)

The trick you used (ten measurements with just the difference) is ok only if you guarantee that in ten hours the value will not drift by more than +/- 12°C.  This is not guaranteed and probably also not optimal. I'd prefer another approach, which is based on the fact that you are using only 11 bytes out of 16. You can have two different data stored in the EEPROM, which are differences (1 byte) or whole temperatures (2 bytes). You will distinguish them with the first bits: a 0 denotes a difference, a 1 a whole temperature (followed by 0 is the low byte, by a 1 is a high byte). This means that for the difference you have seven bits, so it can range from +63 to -64. Whenever you reach a difference from the previous temperature within 6 degrees you don't save anymore the whole temperature. The code to do this is for instance the following one:

    // int16_t finalTemp calculated before
    // int16_t prevTemp initialised, at beginning, for instance to -32000, so the difference is greater and you force a full writing at the first round

    int16_t tempDiff = finalTemp - prevTemp;
    prevTemp = finalTemp; // update the temperature

    if ((tempDiff <= -63) || (tempDiff >= 63)
    {
     // In this case we want to save the whole integer
     EEPROM.update(eepromAddress++, (((uint8_t)finalTemp) & 0x3F) | 0x80); // Write the lowest 6 bits, and set the first two to 0b10
     EEPROM.update(eepromAddress++, (((uint8_t)(finalTemp >> 6)) & 0x3F)| 0xC0); // Write the highest 6 bits, and set the first two to 0b11
    }
    else
    {
     // In this case we save only the difference
     EEPROM.update(eepromAddress++, ((uint8_t)tempDiff) & 0x7F); // Just remove the highest bit, and store it
    }

In this case, provided that the temperature does not vary a lot, you will get 511 measurements, which is like 21 days. For each variation greater than 6°C/h you will lose one hour of measurement, down to 256 measurements. Please note that I wrote `EEPROM.update` instead of `write`, even if this is not necessary (just one of the things I do every time).

The last possibility is to switch to a 0.5°C resolution. If you use this resolution, you can map your values on a range 120/-100, thus being able to use only one byte for each measurement. Since the accuracy is +/- 2°C, you can also choose this without problems.

Apart from the storage, if you record only 256 bytes of information how do you know which are the correct values and which are the previous ones? My suggestion is to reserve one value (for instance if you have used my code you can get an impossible value such as 0x40 - which if I'm not wrong maps to DIFFERENCE -64, which is impossible since the difference is stored only when greater than -63) and fill the memory before starting to insert the values. beware that if you do it then turning on the board will reset the memory...

One last suggestion: you have a sensor which stores the data internally, but.. How do you get them out of it? My personal suggestion is to have a dedicated pin (for instance PB3) tied to a jumper. If it is open then you will proceed with the normal program, otherwise you wait for a download request. (don't do the opposite since the jumper inserted drains the battery). Consequently the code can be something like this:

    const uint8_t invalidEepromValue = 0x40;
    const int16_t maxAddress = 510; // Not equal to 512 to avoid a last reading of 2 bytes

    void dumpMemory()
    {
     int16_t prevTemp = 0;
     for (int16_t i = 0; i < maxAddress; i++)
     {
      int16_t value = EEPROM.read(i);
      if (value == invalidEepromValue)
       break; // Finished the reading

      if (value & 0x80)
      { // WholeData
       int16_t value2 = EEPROM.read(i+1);
       if (((((uint8_t)value) & 0xC0) != 0x80) || ((((uint8_t)value2) & 0xC0) != 0xC0))
       {
        mySerial.print("Error with memory cell ");
        mySerial.println(i);
        continue;
       }

       prevTemp = (value & 0x3F) | ((value2 & 0x3F) << 6);
       if (value2 & 0x40) prevTemp |= 0xF000; // Extend the sign

       mySerial.println(prevTemp);
       i++; // skip the next value (already analysed)
      }
      else
      { // Difference
       if (value & 0x40) value |= 0xFF80; // Extend the sign

       prevTemp += value;
       mySerial.println(prevTemp);
      }
     }
    }

    void setup() {
     pinMode(modePin, INPUT_PULLUP);
     mySerial.begin(9600);         // begin software serial at rate of 9600

     delay(1);
     if (digitalRead(modePin) == LOW)
     { // Enter read mode
      while (1) // loop forever
      {
       while (mySerial.available() == 0); // Wait for some chars

       dumpMemory();

       while (mySerial.available() > 0)
        mySerial.read(); // Flush receiving buffer
      }
     }

     // Clear the memory
     for (int16_t i = 0; i <= maxAddress; i++) // Equal to cover the last reading of 2 bytes
      EEPROM.update(i, invalidEepromValue); // Here update is almost mandatory

     // Go on with the initialization you already implemented
     ...
    }

I hope that the software serial works even without the main structure (so in a `while(1)` in the setup).

Please keep in mind that all the code written here has NOT been tested, so it may require some corrections


message:
How to externally power HC-05 module with Arduino Pro Mini?

guys, I am new to arduino. I am trying to power my HC-05 (5v with regulator to 3.3v) from Arduino Pro Mini 3.3v but I can't get it to power on.

**There is a problem: The site I bought HC-05 from says that it needs 3.3-6 volts to power on but the back of HC-05 shows only 5v pin. To confirm that it runs only on 5v I need to connect it to external 5v supply.**

But how do I make the connection? What do I connect to negative of the battery if I choose to externally power it?

Second Problem: If my HC-05 turns out to need only 3.3v input voltage, how many coins cells do I connect in series to power both pro mini and HC-05 module.

I am using a coin cell (3.3v) for powering the pro mini.

Thanks...

body:
The HC-05 (the PCB that is mounted on the PCB of the module) itself runs on 3.3V. Many microcontrollers run on 5V, so people are selling the HC-05 mounted on a PCB with extra components, for example a voltage regulator from 5V to 3.3V.

Voltage regulators have a minimum input voltage for which they can hold the output voltage at the specified value. Refer to [this question][1] for more information about this. So supplying the module with 3.3V instead of 5V will result in a supply voltage for the HC-05, that is significantly lower than 3.3V, so it most likely won't work correctly.

If you want to use the HC-05 module as it is, you have to provide 5V supply voltage from another source. In this case be sure to connect the grounds of both power supplies, so that they have a common ground.

If you don't want to use an extra power supply, than you may bridge the voltage regulator on your modules PCB and provide the 3.3V as supply voltage, that are used by the Arduino. Doing so would not be an easy task for a beginner, since you would have to solder small SMD components. Also the outlay of the modules PCBs are very different (depending on manufacturer). Note that in this case you should never ever put 5V on the Vcc pin of the module again, since it is then directly passed on to the HC-05 chip, which would be destroyed from the 5V supply.

  [1]: https://electronics.stackexchange.com/questions/41817/proper-use-of-a-voltage-regulator


message:
How to install several IDE version on my PC

How can i install old version of IDE, without uninstalling the other version?(How can i install several IDE version in same laptop).

body:
Arduino.cc have a guide :

https://www.arduino.cc/en/Guide/PortableIDE

The gist is:

 1. Download the desired version in ZIP format

 2. Unpack the content in the zip file to a folder

 3. Start the arduino.exe in that folder.

Remember that you have to place all libraries, board definitions in that folder.

The folder can be copied to another computer or a USB stick....