Named interrupt routines and simplified

Named interrupt routines and simplified

#include <SPI.h>
#include <Elcano_Serial.h>
#define LOOP_TIME_MS 200
#define ERROR_HISTORY 20

// New section    TCF 9/17/15
#define VEHICLE_NUMBER 1
#define RC_SPEKTRUM
#undef  RC_HITEC

#if (VEHICLE_NUMBER == 1)
//OUTPUT values -  0 to 255
#define MIN_ACC_OUT 40
#define MAX_ACC_OUT 227
#define MIN_BRAKE_OUT 180
#define MAX_BRAKE_OUT 250
#define RIGHT_TURN_OUT 146
#define LEFT_TURN_OUT 230
#define STRAIGHT_TURN_OUT 180
#define DAC_CHANNEL 0
#define STEER_OUT_PIN 7 // Output to steer actuator
#define BRAKE_OUT_PIN 6  // output to brake actuator

/*================ReadTurnAngle 1================*/
// Value measured at analog input A3 from right steering column when wheels pointed straight ahead.
// An analog voltage can be 0 to 5V, which correspond to angles from 0 to 360 degrees.
// Analog input reads this as a value form 0 to 1024.
// We may want to mount the sensors so that straight is close to 500.
// This number is not critical, since actual wheel turn range is much less than 360
#define RIGHT_STRAIGHT_A3 181
// Value measured at analog input A2 from left steering column when wheels pointed straight ahead.
#define LEFT_STRAIGHT_A2  181
// Calibration constants
// Aangle (degrees) = (Value - RIGHT_STRAIGHT_A3) * RIGHT_DEGx1000pCOUNT / 1000
#define RIGHT_DEGx1000pCOUNT  3333
#define LEFT_DEGx1000pCOUNT  3333
// A correct sensor will produce a reading between these values
#define RIGHT_MIN_COUNT  80
#define RIGHT_MAX_COUNT 284
#define LEFT_MIN_COUNT   80
#define LEFT_MAX_COUNT  284

#endif

#if (VEHICLE_NUMBER == 2)

//OUTPUT values -  0 to 255
#define MIN_ACC_OUT 40
#define MAX_ACC_OUT 227
#define MIN_BRAKE_OUT 180
#define MAX_BRAKE_OUT 250
#define RIGHT_TURN_OUT 146 // Original value 146
#define LEFT_TURN_OUT 223 // Original value 230
#define STRAIGHT_TURN_OUT 182 // Original value 187

#define DAC_CHANNEL 3
#define STEER_OUT_PIN 7 // Output to steer actuator
#define BRAKE_OUT_PIN 9  // output to brake actuator

/*================ReadTurnAngle 2================*/
#define RIGHT_STRAIGHT_A3 515 // Original value 181
#define LEFT_STRAIGHT_A2  522 // Original value 181
#define RIGHT_DEGx1000pCOUNT  3333
#define LEFT_DEGx1000pCOUNT  3333
#define RIGHT_MIN_COUNT 466 // Original value 80
#define RIGHT_MAX_COUNT 557 // Original value 284
#define LEFT_MIN_COUNT 465  // Original value 80
#define LEFT_MAX_COUNT 559  // Original value 284

#endif
// End new section

// Channel order differs for differernt vehicles
// Indices for information stored in array RC_results
// Right joystick left/right to D21
#define RC_TURN 1
#define RC_AUTO 2
// Right joystick up/down to D19
#define RC_GO   3
// Red (Gear) Switch to D18
#define RC_ESTP 4
// Left joystick left/right to D20
#define RC_RDR  5
// Left joystick up/down to D2
#define RC_RVS  6
// There are six channels, but we are limited to five interrupts
#define NUMBER_CHANNELS 6

#define ProcessFallOfINT(Index)  RC_results[Index]=(micros()-RC_results[Index])
#define ProcessRiseOfINT(Index) RC_results[Index]=micros()

// TO DO: Throttle and brake values should be in a header file and depend on vehicle number.
// Values to send over DAC
const int FullThrottle =  227;   // 3.63 V
const int MinimumThrottle = 70;  // Throttle has no effect until 1.2 V
// Values to send on PWM to get response of actuators
const int FullBrake = 167;  // start with a conservative value; could go as high as 255;
const int NoBrake = 207; // start with a conservative value; could go as low as 127;

//RC input values - pulse widths in microseconds
const int LONG_DEADZONE_THRESHOLD = 10000; // used for syncing to determine if the last down time was the long down zone
const int DEAD_ZONE = 75;
const int MIDDLE = 1500;  // was 1322; new stable value = 1510
// extremes of RC pulse width
const int MIN_RC = 1090;  // was 911;
const int MAX_RC = 1930; // was 1730;
const int CYCLE_MAX = 25000;  // Pulses come at 42.27 Hz, every 21155 us
const int MAX_PULSE = 4000; // Next pulse should be no longer than this time from last.

const int SelectCD = 49; // Select IC 3 DAC (channels C and D)
const int SelectAB = 53; // Select IC 2 DAC (channels A and B)

const unsigned long INVALID_DATA = 0;
volatile int rc_index = 0;
volatile  unsigned long RC_results[7];
volatile boolean synced = false;
volatile unsigned long last_fallingedge_time = 4294967295; // max long
volatile int RC_Done[7] = {0,0,0,0,0,0,0};

// interrupt number handling a function depends on the RC controller.

#ifdef RC_SPEKTRUM
const int IRPT_RVS = 0;   // D2  = Int 0
const int IRPT_TURN = 2;  // D21 = Int 2
const int IRPT_GO = 3;   //  D20 = Int 3
const int IRPT_RDR = 4;   // D19 = Int 4
const int IRPT_ESTOP = 5; // D18 = Int 5
#endif

#ifdef RC_HITEC
const int IRPT_RVS = 0;   // D2  = Int 0
const int IRPT_TURN = 2;  // D21 = Int 2
const int IRPT_GO = 3;   //  D20 = Int 3
const int IRPT_RDR = 4;   // D19 = Int 4
const int IRPT_ESTOP = 5; // D18 = Int 5
#endif
//  D3 = Int 1  Wheel Click

// globals
long sensor_speed_mmPs = 0;
long drive_speed_mmPs = 0;
char IncomingMessage[BUFFER_SIZE];
int  InIndex=0;
int  throttle_control = MinimumThrottle;
int  brake_control = FullBrake;
// int  steer_control = Straight;
long speed_errors[ERROR_HISTORY];
/*================Read Turn Angle=================*/
long old_turn_degx1000, older_turn_degx1000;
long expected_turn_degx1000;

void ISR_TURN_rise() {
  noInterrupts();
  ProcessRiseOfINT(RC_TURN);
  attachInterrupt(IRPT_TURN, ISR_TURN_fall, FALLING);
  interrupts();
}

void ISR_RDR_rise() {
  noInterrupts();
  ProcessRiseOfINT(RC_RDR);
  attachInterrupt(IRPT_RDR, ISR_RDR_fall, FALLING);
  interrupts();
}

void ISR_GO_rise() {
  noInterrupts();
  ProcessRiseOfINT(RC_GO);
  attachInterrupt(IRPT_GO, ISR_GO_fall, FALLING);
  interrupts();
}

void ISR_ESTOP_rise() {
  noInterrupts();
  ProcessRiseOfINT(RC_ESTP);
  attachInterrupt(IRPT_ESTOP, ISR_ESTOP_fall, FALLING);
  interrupts();
}

void ISR_RVS_rise() {
  noInterrupts();
  ProcessRiseOfINT(RC_RVS);
  attachInterrupt(IRPT_RVS, ISR_RVS_fall, FALLING);
  interrupts();
}

void ISR_TURN_fall() {
  noInterrupts();
  ProcessFallOfINT(RC_TURN);
  RC_Done[RC_TURN] = 1;
  attachInterrupt(IRPT_TURN, ISR_TURN_rise, RISING);
  interrupts();
}

void ISR_RDR_fall() {
  noInterrupts();
  ProcessFallOfINT(RC_RDR);
  RC_Done[RC_RDR] = 1;
  attachInterrupt(IRPT_RDR, ISR_RDR_rise, RISING);
  interrupts();
}

void ISR_GO_fall() {
  noInterrupts();
  ProcessFallOfINT(RC_GO);
  RC_Done[RC_GO] = 1;
  attachInterrupt(IRPT_GO, ISR_GO_rise, RISING);
  interrupts();
}
void ISR_ESTOP_fall() {
  noInterrupts();
  ProcessFallOfINT(RC_ESTP);
  RC_Done[RC_ESTP] = 1;
  attachInterrupt(IRPT_ESTOP, ISR_ESTOP_rise, RISING);
  interrupts();
}

void ISR_RVS_fall() {
  noInterrupts();
  ProcessFallOfINT(RC_RVS);
  RC_Done[RC_RVS] = 1;
  attachInterrupt(IRPT_RVS, ISR_RVS_rise, RISING);
  interrupts();
}

void initialize()
{
  for (int i = 0; i < ERROR_HISTORY; i++)
  {
      speed_errors[i] = 0;
  }

}
void setup()
{ //Set up pins
      pinMode(BRAKE_OUT_PIN, OUTPUT);
      pinMode(STEER_OUT_PIN, OUTPUT);
      // SPI: set the slaveSelectPin as an output:
      pinMode (SelectAB, OUTPUT);
      pinMode (SelectCD, OUTPUT);
      pinMode (10, OUTPUT);
      SPI.setDataMode( SPI_MODE0);
      SPI.setBitOrder( MSBFIRST);
      // initialize SPI:
      // The following line should not be neccessary. It uses a system library.
      PRR0 &= ~4; // turn off PRR0.PRSPI bit so power isn't off
      SPI.begin();
      for (int channel = 0; channel < 4; channel++)
      DAC_Write (channel, 0); // reset did not clear previous states
      Serial.begin(9600);
      rc_index = 0;
      for (int i = 0; i < 8; i++)
          RC_results[i] = INVALID_DATA;
      initialize();

      setupWheelRev(); // WheelRev4 addition

    attachInterrupt(IRPT_TURN,  ISR_TURN_rise,  RISING);
    attachInterrupt(IRPT_RDR,   ISR_RDR_rise,   RISING);
    attachInterrupt(IRPT_GO,    ISR_GO_rise,    RISING);
    attachInterrupt(IRPT_ESTOP, ISR_ESTOP_rise, RISING);
    attachInterrupt(IRPT_RVS,   ISR_RVS_rise,   RISING);

    old_turn_degx1000 = older_turn_degx1000 = expected_turn_degx1000 = 0; // ReadTurnAngle addition
}
void loop() {
    SerialData Results;
    unsigned long Start_us = micros();
    unsigned long time, endTime;
    time = millis();
    endTime = time + LOOP_TIME_MS ;

    startCapturingRCState();

    unsigned long local_results[7];
/*    delay (10);
    for (int j = 2; j < 7; j++)
    {
         Serial.print(RC_Done[j]);    Serial.print("\t");
    }
 */
    while (!(RC_Done[RC_ESTP] == 1 && RC_Done[RC_GO] == 1 && RC_Done[RC_TURN] == 1 &&
            RC_Done[RC_RVS] == 1 && RC_Done[RC_RDR] == 1))
    ;
    // got data;
    for (int i = 0; i < 8; i++)
        local_results[i] = RC_results[i];
    unsigned long Elapsed_us = micros() - Start_us;
    Serial.print(Start_us);      Serial.print("\t");
    Serial.print(Elapsed_us);    Serial.print("\t");
    Serial.print(local_results[0]);  Serial.print("\t");
    Serial.print(local_results[1]); Serial.print("\t");
    Serial.print(local_results[2]); Serial.print("\t");
    Serial.print(local_results[3]); Serial.print("\t");
    Serial.print(local_results[4]); Serial.print("\t");
    Serial.print(local_results[5]); Serial.print("\t");
    Serial.println(local_results[6]);

    processRC(local_results);
    Results.Clear();
    Results.kind = MSG_SENSOR;
    Results.angle_deg = TurnAngle_degx10() / 10;
    show_speed (&Results);
    delay(500);
/*    while (time < endTime)
    {
        time = millis();
    }
*/
}

void startCapturingRCState()
{
  for (int i = 1; i < 7; i++) {
    RC_Done[i] = 0;
  }
}

// processRC modified by TCF  9/17/15
void processRC (unsigned long *RC_results)
{
    // 1st pulse is aileron (position 5 on receiver; controlled by Right left/right joystick on transmitter)
    //     used for Steering
    int aileron = RC_results[RC_TURN];
    RC_results[RC_TURN] = convertTurn(aileron);

    /* 2nd pulse is aux (position 1 on receiver; controlled by flap/gyro toggle on transmitter)
       will be used for selecting remote control or autonomous control. */
    if (NUMBER_CHANNELS > 5)
        RC_results[RC_AUTO] = (RC_results[RC_AUTO] > MIDDLE? HIGH: LOW);

    /* 4th pulse is gear (position 2 on receiver; controlled by gear/mode toggle on transmitter)
    will be used for emergency stop. D38 */
    RC_results[RC_ESTP] = (RC_results[RC_ESTP] > MIDDLE? HIGH: LOW);

    if (RC_results[RC_ESTP] == HIGH)
    {
        E_Stop();
        if (RC_results[RC_AUTO] == HIGH  && NUMBER_CHANNELS > 5) // under RC control
            steer(RC_results[RC_TURN]);
        return;
    }
    if ( RC_results[RC_AUTO] == LOW  && NUMBER_CHANNELS > 5)
        return;  // not under RC control

    /*  6th pulse is marked throttle (position 6 on receiver; controlled by Left up/down joystick on transmitter).
    It will be used for shifting from Drive to Reverse . D40
    */
    RC_results[RC_RVS] = (RC_results[RC_RVS] > MIDDLE? HIGH: LOW);

// TO DO: Select Forward / reverse based on RC_results[RC_RVS]

    /*   3rd pulse is elevator (position 4 on receiver; controlled by Right up/down.
       will be used for throttle/brake: RC_Throttle
    */
    // Braking or Throttle
    if (liveBrake(RC_results[RC_GO]))
        brake(convertBrake(RC_results[RC_GO]));
    else
        brake(MIN_BRAKE_OUT);
    //Accelerating
    if(liveThrottle(RC_results[RC_GO]))
        moveVehicle(convertThrottle(RC_results[RC_GO]));
    else
        moveVehicle(MIN_ACC_OUT);

    steer(RC_results[RC_TURN]);

    /* 5th pulse is rudder (position 3 on receiver; controlled by Left left/right joystick on transmitter)
    Not used */
    RC_results[RC_RDR] = (RC_results[RC_RDR] > MIDDLE? HIGH: LOW);  // could be analog

}
//Converts RC values to corresponding values for the PWM output
int convertTurn(int input)
{
     long int steerRange, rcRange;
     long output;
     int trueOut;
//  Check if Input is in steer dead zone
      if (input <= MIDDLE + DEAD_ZONE && input >= MIDDLE - DEAD_ZONE)
       return STRAIGHT_TURN_OUT;
       // MIN_RC = 1 msec = right; MAX_RC = 2 msec = left
      // LEFT_TURN_OUT > RIGHT_TURN_OUT

      if (input > MIDDLE + DEAD_ZONE)
      {  // left turn
         steerRange = LEFT_TURN_OUT - STRAIGHT_TURN_OUT;
         rcRange = MAX_RC - (MIDDLE + DEAD_ZONE);
        input = input - MIDDLE - DEAD_ZONE; // originally input = middle + dead_zone
        output = STRAIGHT_TURN_OUT + input * steerRange / rcRange;
        //set max and min values if out of range
        trueOut = (int)output;
        if(trueOut > LEFT_TURN_OUT)
            trueOut = LEFT_TURN_OUT;
        if(trueOut < STRAIGHT_TURN_OUT)
            trueOut = STRAIGHT_TURN_OUT;
        return trueOut;
    }
      if (input < MIDDLE - DEAD_ZONE)
      {  // right turn
         steerRange = STRAIGHT_TURN_OUT - RIGHT_TURN_OUT;
         rcRange = MIDDLE - DEAD_ZONE - MIN_RC;
        input = input - DEAD_ZONE - MIDDLE;  // input is negative
        output = STRAIGHT_TURN_OUT + input * steerRange / rcRange;
        //set max and min values if out of range
        trueOut = (int)output;
        if(trueOut < RIGHT_TURN_OUT)
            trueOut = RIGHT_TURN_OUT;
        if(trueOut > STRAIGHT_TURN_OUT)
            trueOut = STRAIGHT_TURN_OUT;
        return trueOut;
    }
}
int convertBrake(int input)
{
      if (input < (MIDDLE + MIN_RC)/2)
           return MAX_BRAKE_OUT;
      else
           return MIN_BRAKE_OUT;
}
int convertThrottle(int input)
{
      //full throttle = 227, min = 40
      const int dacRange = MAX_ACC_OUT - MIN_ACC_OUT;
      const int rcRange = MAX_RC - (MIDDLE + DEAD_ZONE);
      input -= (MIDDLE + DEAD_ZONE);
      double output = (double)input /(double)rcRange;
      output *= dacRange;
      output += MIN_ACC_OUT;
      //set max values if out of range
      int trueOut = (int)output;
      if(trueOut > MAX_ACC_OUT)
          trueOut = MAX_ACC_OUT;
      return trueOut;
}
//Tests for inputs
// Input not in throttle dead zone
boolean liveThrottle(int acc)
{
      return (acc > MIDDLE + DEAD_ZONE);
}
// Input is not in brake dead zone
boolean liveBrake(int brake)
{
      return (brake < MIDDLE - DEAD_ZONE);
}
// Emergency stop
void E_Stop()
{
    brake(MAX_BRAKE_OUT);
    moveVehicle(MIN_ACC_OUT);
    // TO DO: disable 36V power
}
//Send values to output pin
void steer(int pos)
{
      analogWrite(STEER_OUT_PIN, pos);
}
void brake(int amount)
{
      analogWrite(BRAKE_OUT_PIN, amount);
      Serial.println(amount);
}
/*---------------------------------------------------------------------------------------*/
/* DAC_Write applies value to address, producing an analog voltage.
// address: 0 for chan A; 1 for chan B; 2 for chan C; 3 for chan D
// value: digital value converted to analog voltage
// Output goes to mcp 4802 Digital-Analog Converter Chip via SPI
// There is no input back from the chip.
*/
void DAC_Write(int address, int value)
/*
REGISTER 5-3: WRITE COMMAND REGISTER FOR MCP4802 (8-BIT DAC)
A/B — GA SHDN D7 D6 D5 D4 D3 D2 D1 D0 x x x x
bit 15 bit 0
bit 15 A/B: DACA or DACB Selection bit
1 = Write to DACB
0 = Write to DACA
bit 14 — Don’t Care
bit 13 GA: Output Gain Selection bit
1 = 1x (VOUT = VREF * D/4096)
0 = 2x (VOUT = 2 * VREF * D/4096), where internal VREF = 2.048V.
bit 12 SHDN: Output Shutdown Control bit
1 = Active mode operation. VOUT is available.
0 = Shutdown the selected DAC channel. Analog output is not available at the channel that was shut down.
VOUT pin is connected to 500 k (typical)
bit 11-0 D11:D0: DAC Input Data bits. Bit x is ignored.
With 4.95 V on Vcc, observed output for 255 is 4.08V.
This is as documented; with gain of 2, maximum output is 2 * Vref
*/
{
      int byte1 = ((value & 0xF0)>>4) | 0x10; // acitve mode, bits D7-D4
      int byte2 = (value & 0x0F)<<4; // D3-D0
      if (address < 2)
      {
          // take the SS pin low to select the chip:
          digitalWrite(SelectAB,LOW);
          if (address >= 0)
          {
              if (address == 1)
                  byte1 |= 0x80; // second channnel
              SPI.transfer(byte1);
              SPI.transfer(byte2);
          }
          // take the SS pin high to de-select the chip:
          digitalWrite(SelectAB,HIGH);
      }
      else
      {
          // take the SS pin low to select the chip:
          digitalWrite(SelectCD,LOW);
          if (address <= 3)
          {
              if (address == 3)
                  byte1 |= 0x80; // second channnel
              SPI.transfer(byte1);
              SPI.transfer(byte2);
          }
          // take the SS pin high to de-select the chip:
          digitalWrite(SelectCD,HIGH);
      }
}
void moveVehicle(int acc)
{
      /* Observed behavior on ElCano #1 E-bike no load (May 10, 2013, TCF)
      0.831 V at rest 52 counts
      1.20 V: nothing 75
      1.27 V: just starting 79
      1.40 V: slow, steady 87
      1.50 V: brisker 94
      3.63 V: max 227 counts
      255 counts = 4.08 V
      */
      DAC_Write(DAC_CHANNEL, acc);
}

/*========================================================================/
 *============================WheelRev4 code==============================/
 *=======================================================================*/

/* Wheel Revolution Interrupt routine
   Ben Spencer 10/21/13
   Modified by Tyler Folsom 3/16/14

   A cyclometer gives a click once per revolution.
   This routine computes the speed.
*/
// CLICK_IN defined: use interrupt; not defined: simulate with timer
#define CLICK_IN 1
#define LOOP_TIME_MS 1000
#define CLICK_TIME_MS 1000
#define SerialOdoOut  Serial3
#define SerialMonitor Serial

#define WHEEL_DIAMETER_MM 397
#define MEG 1000000
#define MAX_SPEED_KPH 50
#define MAX_SPEED_mmPs   ((MAX_SPEED_KPH * MEG) / 3600)
// MAX_SPEED_mmPs = 13,888 mm/s = 13.888 m/s
unsigned long MinTickTime_ms;
// ((WHEEL_DIAMETER_MM * 3142) / MAX_SPEED_mmPs)
// MinTickTime_ms = 89 ms
#define MIN_SPEED_mPh 500
// A speed of less than 0.5 KPH is zero.
unsigned long MaxTickTime_ms;
// ((WHEEL_DIAMETER_MM * 3142) / MIN_SPEED_mmPs)
// MinTickTime_ms = 9239 ms = 9 sec

float Odometer_m = 0;
long SpeedCyclometer_mmPs = 0;
// Speed in revolutions per second is independent of wheel size.
float SpeedCyclometer_revPs = 0.0;//revolutions per sec
volatile unsigned long TickTime = 0;
long WheelRev_ms = 0;
unsigned long OldTick = 0;
#define IRQ_NONE 0
#define IRQ_FIRST 1
#define IRQ_RUNNING 2
volatile int InterruptState = IRQ_NONE;
unsigned long ShowTime_ms;

/*---------------------------------------------------------------------------------------*/
// WheelRev is called by an interrupt.
void WheelRev()
{
    static int flip = 0;
    unsigned long tick;
    noInterrupts();
    tick = millis();
    if (InterruptState != IRQ_RUNNING)
    // Need to process 1st two interrupts before results are meaningful.
        InterruptState++;

    if (tick - TickTime > MinTickTime_ms)
    {
        OldTick = TickTime;
        TickTime = tick;
    }
    if (flip)
        digitalWrite(13, LOW);
    else
        digitalWrite(13, HIGH);
    flip =!flip;

    interrupts();
}
/*---------------------------------------------------------------------------------------*/

void setupWheelRev()
{

    SerialOdoOut.begin(115200); // C6 to C4
    pinMode(13, OUTPUT); //led
    digitalWrite(13, LOW);//turn LED off

    pinMode(2, INPUT);//pulls input HIGH
    float MinTick = WHEEL_DIAMETER_MM * PI;
//    SerialMonitor.print (" MinTick = ");
//    SerialMonitor.println (MinTick);
    MinTick *= 1000.0;
    MinTick /= MAX_SPEED_mmPs;
//    SerialMonitor.print (MinTick);
    MinTickTime_ms = MinTick;
    SerialMonitor.print (" MinTickTime_ms = ");
    SerialMonitor.println (MinTickTime_ms);

//    SerialMonitor.print (" MIN_SPEED_mPh = ");
//    SerialMonitor.print (MIN_SPEED_mPh);
    float MIN_SPEED_mmPs =  ((MIN_SPEED_mPh * 1000.0) / 3600.0);
    // MIN_SPEED_mmPs = 135 mm/s
//    SerialMonitor.print (" MIN_SPEED_mmPs = ");
//    SerialMonitor.print (MIN_SPEED_mmPs);
    float MaxTick = (WHEEL_DIAMETER_MM * PI * 1000.0) / MIN_SPEED_mmPs;
//    SerialMonitor.print (" MaxTick = ");
//    SerialMonitor.print (MaxTick);
    MaxTickTime_ms = MaxTick;
//    SerialMonitor.print (" MaxTickTime = ");
//    SerialMonitor.println (MaxTickTime_ms);
    TickTime = millis();
    // OldTick will normally be less than TickTime.
    // When it is greater, TickTime - OldTick is a large positive number,
    // indicating that we have not moved.
    // TickTime would overflow after days of continuous operation, causing a glitch of
    // a display of zero speed.  It is unlikely that we have enough battery power to ever see this.
    OldTick = TickTime;
    ShowTime_ms = TickTime;
    InterruptState = IRQ_NONE;

    attachInterrupt (0, WheelRev, RISING);//pin 2 on Mega
    SerialMonitor.print("TickTime: ");
    SerialMonitor.print(TickTime);
    SerialMonitor.print(" OldTick: ");
    SerialMonitor.println(OldTick);

    SerialMonitor.println("setup complete");

}
/*---------------------------------------------------------------------------------------*/

void show_speed(SerialData *Results)
{

   ShowTime_ms = millis();
   if (InterruptState == IRQ_NONE || InterruptState == IRQ_FIRST)  // no OR 1 interrupts
   {
       SpeedCyclometer_mmPs = 0;
       SpeedCyclometer_revPs = 0;
   }

  //check if velocity has gone to zero
  else
  {
    if(ShowTime_ms - TickTime > MaxTickTime_ms)
    {  // stopped
/*        SerialMonitor.print("Stop. Showtime: ");
        SerialMonitor.print(ShowTime_ms);
        SerialMonitor.print(" Tick: ");
        SerialMonitor.println(TickTime); */
        SpeedCyclometer_mmPs = 0;
        SpeedCyclometer_revPs = 0;
    }
    else
    {  // moving
        WheelRev_ms = max(TickTime - OldTick, ShowTime_ms - TickTime);
        if (InterruptState == IRQ_RUNNING)
        {  // have new data

            float Circum_mm = (WHEEL_DIAMETER_MM * PI);
            if (WheelRev_ms > 0)
            {
                SpeedCyclometer_revPs = 1000.0 / WheelRev_ms;
                SpeedCyclometer_mmPs  = Circum_mm * SpeedCyclometer_revPs;
            }
            else
            {
                SpeedCyclometer_mmPs = 0;
                SpeedCyclometer_revPs = 0;
            }
        }

      }
    }
    Odometer_m += (float)(LOOP_TIME_MS * SpeedCyclometer_mmPs) / MEG;
    Results->speed_cmPs = SpeedCyclometer_mmPs / 10;
    writeSerial(&Serial3, Results);

    // Show on monitor
/*    SerialMonitor.print("\nWheelRev (ms): ");
    SerialMonitor.print(WheelRev_ms);
    SerialMonitor.print(" SENSOR ");
    SerialMonitor.print("{Speed ");
    SerialMonitor.print(SpeedCyclometer_revPs);
    SerialMonitor.println("}\0");
 */
}

/*======================ReadTurnAngle======================*/
int TurnAngle_degx10()
{
    long new_turn_degx1000;
    int new_turn_degx10;
    long min_ang, max_ang;
    bool OK_right = false;
    bool OK_left = false;
    int right = analogRead(A3);
    int left = analogRead(A2);
    Serial.print("Left"); Serial.print("\t"); Serial.println(left);
    Serial.print("Right"); Serial.print("\t"); Serial.println(right);
    if (RIGHT_MIN_COUNT <= right && right <= RIGHT_MAX_COUNT)
       OK_right = true;
    if (LEFT_MIN_COUNT <= left && left <= LEFT_MAX_COUNT)
       OK_left = true;
    long right_degx1000 = (right - RIGHT_STRAIGHT_A3) * RIGHT_DEGx1000pCOUNT;
    long left_degx1000  = (left -  LEFT_STRAIGHT_A2) *  LEFT_DEGx1000pCOUNT;

    expected_turn_degx1000 = 2 * old_turn_degx1000 - (older_turn_degx1000);
    if (OK_left && OK_right)
    {  // use the median
        if (right_degx1000 < left_degx1000)
        {
            min_ang = right_degx1000;
            max_ang = left_degx1000;
        }
        else
        {
            min_ang = left_degx1000;
            max_ang = right_degx1000;
        }
        if (expected_turn_degx1000 < min_ang)
            new_turn_degx1000 = min_ang;
        else if (expected_turn_degx1000 > max_ang)
            new_turn_degx1000 = max_ang;
        else  // TO DO; limit this value to keep it bounded when both sensors fail
            new_turn_degx1000 = expected_turn_degx1000;
    }
    else if (OK_left)
    {
        new_turn_degx1000 = left_degx1000;
    }
    else if (OK_right)
    {
        new_turn_degx1000 = right_degx1000;
    }
    else
    {
        new_turn_degx1000 = expected_turn_degx1000;
    }
    new_turn_degx10 = (int) (new_turn_degx1000 / 100);
    older_turn_degx1000 = old_turn_degx1000;
    old_turn_degx1000 = new_turn_degx1000;
    return new_turn_degx10;
}
/*---------------------------------------------------------------------------------------*/
void Throttle_PID(long error_speed_mmPs)

/* Use throttle and brakes to keep vehicle at a desired speed.
   A PID controller uses the error in the set point to increase or decrease the juice.
   P = proportional; change based on present error
   I = integra;  change based on recent sum of errors
   D = derivative: change based on how error is changing.
   The controller needs to avoid problems of being too sluggish or too skittery.
   A sluggish control (overdamped) takes too long to reach the set-point.
   A skitterish control (underdamped) can overshoot, then undershoot, producing
   oscillations and jerky motion.
   Getting the right control is a matter of tuning right parts of P, I, and D,
   which is something of a black art.
   For more information, search for:
   VanDoren Proportional Integral Derivative Control
*/
{
  static long speed_errors[ERROR_HISTORY];
  static int error_index = 0;
  int i;
  static long error_sum = 0;
  long mean_speed_error = 0;
  long extrapolated_error = 0;
  long PID_error;
  const float P_tune = 0.4;
  const float I_tune = 0.5;
  const float D_tune = 0.1;
  const long speed_tolerance_mmPs = 75;  // about 0.2 mph
  // setting the max_error affacts control: anything bigger gets maximum response
  const long max_error_mmPs = 2500; // about 5.6 mph

  error_sum -= speed_errors[error_index];
  speed_errors[error_index] = error_speed_mmPs;
  error_sum += error_speed_mmPs;
  mean_speed_error = error_sum / ERROR_HISTORY;
  i = (error_index-1) % ERROR_HISTORY;
  extrapolated_error = 2 * error_speed_mmPs - speed_errors[i];

  PID_error = P_tune * error_speed_mmPs
            + I_tune * mean_speed_error
            + D_tune * extrapolated_error;
  if (PID_error > speed_tolerance_mmPs)
  {  // too fast
    long throttle_decrease = (FullThrottle - MinimumThrottle) * PID_error / max_error_mmPs;
    throttle_control -= throttle_decrease;
    if (throttle_control < MinimumThrottle)
        throttle_control = MinimumThrottle;
    moveVehicle(throttle_control);

    long brake_increase = (NoBrake - FullBrake) * PID_error / max_error_mmPs;
    // NoBrake = 207; FullBrake = 167;
    brake_control -= brake_increase;
    if (brake_control < FullBrake)
        brake_control = FullBrake;
    brake(brake_control);
  }
  else if (PID_error < speed_tolerance_mmPs)
  {  // too slow
    long throttle_increase = (FullThrottle - MinimumThrottle) * PID_error / max_error_mmPs;
    throttle_control += throttle_increase;
    if (throttle_control > FullThrottle)
        throttle_control = FullThrottle;
    moveVehicle(throttle_control);

    // release brakes
    long brake_decrease = (NoBrake - FullBrake) * PID_error / max_error_mmPs;
    // NoBrake = 207; FullBrake = 167;
    brake_control += brake_decrease;
    if (brake_control > NoBrake)
        brake_control = NoBrake;
    brake(brake_control);
  }
  // else maintain current speed
  //Serial.print("Thottle Brake,");  // csv for spreadsheet
  Serial.print(throttle_control);
  Serial.print(",");
  Serial.print(brake_control);
  Serial.print(",");
  Serial.print(drive_speed_mmPs);  Serial.print(",");
  Serial.println(sensor_speed_mmPs);
}

/*---------------------------------------------------------------------------------------*/

error: pathspec 'Elcano_C2_LowLevel/Elcano_C2_LowLevel/Elcano_C2_LowLevel.ino' did not match any file(s) known to git


Current code for the device

Current code for the device

//Version 1.0 - Tyler Sisk - 1/2/15
//Use with arduino, place in folder named RevA_Code, also must have the Rtc_Pcf8563 library (look for it on github)
//Open in arduino and go to file, upload using programmer
//Make sure that your programmer is selected under tools.

#include <Wire.h>
#include <Rtc_Pcf8563.h>
#include <SPI.h>
#include <avr/sleep.h>

int led = 9;
const int cs = 10;
int ocon = 8;
Rtc_Pcf8563 rtc;
volatile int alarm_flag=0;

void isr(){ //interrupt service routine
  alarm_flag=1;
}

void setup(){
  pinMode(led,OUTPUT);
  pinMode (cs, OUTPUT);
  pinMode (ocon, OUTPUT);
  pinMode(3, INPUT);
  SPI.begin();
  rtc.initClock();
  delay(1000);
  attachInterrupt(0, isr, FALLING);

  digitalWrite(cs,HIGH);
  digitalWrite(ocon,LOW);
  digitalWrite(led,LOW);

  //This part is not yet used but will be in the final version
  //const char time[] = __TIME__; //Get current time from PC when compiling
  //int myhour = 10*(time[0] - '0') + (time[1] - '0');
  //int mymin = 10*(time[3] - '0') + (time[4] - '0');
  //int mysec = 10*(time[6] - '0') + (time[7] - '0');

  rtc.setTime(23,22,52);

  //////////////////////////////////set time to wake up///////////////////////////////////////////////
  int wakemin = 23;
  int wakehour = 23;
  rtc.setAlarm(wakemin, wakehour, 99, 99); //min,hour,day,weekday, 99 = no alarm value to be set
  ////////////////////////////////////////////////////////////////////////////////////////////////////
}

void digitalPotWrite(int value)
{
  digitalWrite(cs, LOW);
  SPI.transfer(0x11);
  SPI.transfer(value);
  digitalWrite(cs, HIGH);
}

void clr_alarm()
{
  detachInterrupt(0);
  rtc.clearAlarm();
  delay(1000);
  alarm_flag=0;
  attachInterrupt(0, isr, FALLING);
}

void loop(){

  if(alarm_flag == 0){
    sleep_enable();
    set_sleep_mode(SLEEP_MODE_STANDBY);
    sleep_mode();  //go to sleep
    sleep_disable();
  }

  if(alarm_flag == 1){
    clr_alarm();
    digitalWrite(ocon,HIGH);
    int i = 255;
    digitalWrite(led,HIGH);

    while(i >= 0){  //Ramp Up approximately 10 seconds
      delay(40);
      digitalPotWrite(i);
      i--;
    }

    delay(120000); //Sustain for 2 minutes

    while(i <= 255){  //Ramp Down approximately 10 seconds
      delay(40);
      digitalPotWrite(i);
      i++;
    }
    digitalWrite(led,LOW);
  }
}

error: pathspec 'RevA_Code.ino' did not match any file(s) known to git


Aumentata robustezza comunicazione Xbee e loop

#include <SPI.h>
#include <SD.h>
#include <IcarusXbee.h>
#include <IcarusCelle.h>
#include <IcarusIO.h>

#define myDebugSerial Serial
#define SerialXbee Serial3
#define PIN_BUZZER 12
#define LED_CHARGE 9
#define LED_FIRE 10
#define LED_TEST 11
#define RELE_CHARGE 5
#define RELE_FIRE 6
#define RELE_SAFE 7
#define BUTTON_DISCHARGE 8
#define T_SAFE_DISCHARGE 10000
#define T_CHARGE 30000
#define T_FIRE 3000
#define T_TOLL 2000
#define T_LAMP 1000

typedef enum {
	Charge,
	safeDischarge,
	Fire,
	countDown,
	testMode,
	Idle
} mode;

IcarusIO IO(&myDebugSerial);
IcarusXbee myXbee(&IO,crocodile,&SerialXbee);
File dataFile;
typeCmdFire CmdFireReceived;
mode Fase;
bool fireEnabled;
bool countdownStarted;
uint16_t t_countdown;

unsigned long t_lastDataSent,t_startCmdFire, t_lastLamp;

void setup() {
  myDebugSerial.begin(115200);
  setupSDCard();
  setupXbee();
  setupPinIO();
  IO.Time = millis();
  t_lastDataSent = IO.Time;
  t_startCmdFire = IO.Time;
  t_lastLamp= IO.Time;
  Fase = Idle;
  fireEnabled = false;
}

void loop() {

	IO.Time = millis();

	// make a string for assembling the data to log:
	String dataString = "";
	// read three sensors and append to the string:
	if (digitalRead(BUTTON_DISCHARGE) == HIGH) {
		digitalWrite(RELE_CHARGE, LOW);
		digitalWrite(RELE_FIRE, LOW);
		digitalWrite(RELE_SAFE, HIGH);
		digitalWrite(LED_FIRE, LOW);
		digitalWrite(LED_TEST, LOW);
		digitalWrite(LED_CHARGE, LOW);
		Fase = safeDischarge;
		t_startCmdFire = IO.Time;
		myXbee.SendCmdFire(scaricaSicura);
		dataFile.println(String(String(IO.Time)+" - Safe Discharge button pressed"));
		dataFile.flush();
	}
	myXbee.Read();
	if (IO.cmdFireAvailable) {
		CmdFireReceived=myXbee.readCmdFire();
		if (CmdFireReceived == stopEmergenza || CmdFireReceived == Fuoco)
		{
			if (CmdFireReceived == stopEmergenza) {
				digitalWrite(RELE_SAFE, LOW);
				digitalWrite(LED_TEST, LOW);
				digitalWrite(RELE_FIRE, LOW);
				digitalWrite(LED_FIRE, LOW);
				digitalWrite(RELE_CHARGE, LOW);
				digitalWrite(LED_CHARGE, LOW);
				Fase = Idle;
				t_startCmdFire = IO.Time;
				myXbee.SendCmdFire(stopEmergenza);
				dataFile.println(String(String(IO.Time) + " - Emergency stop command received"));
				myDebugSerial.println("Emergency stop command received");
			}
			else if (CmdFireReceived == Fuoco) {
				if (((IO.Time - t_startCmdFire) >= (t_countdown - T_TOLL)) &&
					((IO.Time - t_startCmdFire) <= (t_countdown + T_TOLL))) {
					Fase = Fire;
					fireEnabled = true;
					myXbee.SendCmdFire(Fuoco);
					dataFile.println(String(String(IO.Time) + " - Fire command received"));
					myDebugSerial.println("Fire command received");
				}
				else
				{
					Fase = Idle;
					myXbee.SendCmdFire(Timeout);
					dataFile.println(String(String(IO.Time) + " - Fire command not received on time"));
					myDebugSerial.println("Fire command not received on time");
				}
			}
		}
		else if (Fase==Idle)
		{
			switch (CmdFireReceived)
			{
			case Carica:
				digitalWrite(RELE_SAFE, LOW);
				digitalWrite(RELE_FIRE, LOW);
				digitalWrite(RELE_CHARGE, HIGH);
				digitalWrite(LED_TEST, LOW);
				digitalWrite(LED_FIRE, LOW);
				digitalWrite(LED_CHARGE, HIGH);
				Fase = Charge;
				t_startCmdFire = IO.Time;
				myXbee.SendCmdFire(Carica);
				dataFile.println(String(String(IO.Time) + " - Charge command received"));
				myDebugSerial.println("Charge command received");
				break;
			case scaricaSicura:
				digitalWrite(RELE_CHARGE, LOW);
				digitalWrite(RELE_FIRE, LOW);
				digitalWrite(RELE_SAFE, HIGH);
				digitalWrite(LED_CHARGE, LOW);
				digitalWrite(LED_FIRE, LOW);
				digitalWrite(LED_TEST, LOW);
				Fase = safeDischarge;
				t_startCmdFire = IO.Time;
				myXbee.SendCmdFire(scaricaSicura);
				dataFile.println(String(String(IO.Time) + " - Safe Discharge command received"));
				myDebugSerial.println("Safe Discharge command received");
				break;
			case avviaCountdown:
				digitalWrite(RELE_SAFE, LOW);
				digitalWrite(LED_TEST, LOW);
				digitalWrite(RELE_FIRE, LOW);
				digitalWrite(LED_FIRE, LOW);
				digitalWrite(RELE_CHARGE, LOW);
				digitalWrite(LED_CHARGE, LOW);
				Fase = countDown;
				t_startCmdFire = IO.Time;
				myXbee.SendCmdFire(avviaCountdown);
				dataFile.println(String(String(IO.Time) + " - Start countdown command received"));
				myDebugSerial.println("Start countdown command received");
				break;
			case testConnessione:
				digitalWrite(RELE_SAFE, LOW);
				digitalWrite(LED_TEST, HIGH);
				digitalWrite(RELE_FIRE, LOW);
				digitalWrite(LED_FIRE, LOW);
				digitalWrite(RELE_CHARGE, LOW);
				digitalWrite(LED_CHARGE, LOW);
				Fase = testMode;
				t_startCmdFire = IO.Time;
				myXbee.SendCmdFire(testConnessione);
				dataFile.println(String(String(IO.Time) + " - Test command received"));
				myDebugSerial.println("Test command received");
				break;
			default: break;
			}
		}
		dataFile.flush();
	}
	switch (Fase) {
	case Charge:
		if (IO.Time - t_startCmdFire >= T_CHARGE)
		{
			Fase = Idle;
			digitalWrite(RELE_CHARGE, LOW);
			digitalWrite(LED_CHARGE, LOW);
			myXbee.SendCmdFire(Carica);
			myDebugSerial.println("Carica completata");
		}
		break;
	case safeDischarge:
		if (IO.Time - t_startCmdFire >= T_SAFE_DISCHARGE)
		{
			Fase = Idle;
			digitalWrite(RELE_SAFE, LOW);
			myXbee.SendCmdFire(scaricaSicura);
			myDebugSerial.println("Scarica sicura completata");
		}
		break;
	case Fire:
		if (IO.Time - t_startCmdFire >= T_FIRE)
		{
			digitalWrite(RELE_FIRE, LOW);
			digitalWrite(LED_FIRE, LOW);
			Fase = Idle;
			t_startCmdFire = IO.Time;
			fireEnabled = false;
			countdownStarted = false;
			myXbee.SendCmdFire(Fuoco);
			myDebugSerial.println("Fuoco completato");
		}
		break;
	case countDown:
		if (IO.cmdAvailable)
		{
			t_countdown = myXbee.getCmd();
			myXbee.addToPayload(Comando);
			myXbee.Send();
			countdownStarted = true;
			myDebugSerial.println("Tempo di countdown ricevuto");
		}
		if (IO.Time - t_startCmdFire >= t_countdown * 1000)
		{
			if (fireEnabled) {
				digitalWrite(RELE_FIRE, HIGH);
				digitalWrite(LED_FIRE, HIGH);
				Fase = Fire;
				t_startCmdFire = IO.Time;
				myXbee.SendCmdFire(avviaCountdown);
				myDebugSerial.println("Countdown avviato");
			}
			else
			{
				Fase = Idle;
				myXbee.SendCmdFire(MissingCountdown);

			}
		}
		break;
	case testMode:
		if (IO.Time - t_startCmdFire >= T_LAMP) {
			Fase = Idle;
			digitalWrite(LED_TEST, LOW);
			myDebugSerial.println("Stop Led");
			break;
		}
		if (IO.Time - t_lastLamp > 200)
		{
			digitalWrite(LED_TEST, !digitalRead(LED_TEST));
			t_lastLamp = IO.Time;
			myDebugSerial.println("Switch");
		}
		break;
	case Idle:
	default: break;
	}
	}

void setupSDCard() {
	const int chipSelect = 4;
	myDebugSerial.print("Initializing SD card...");
	// see if the card is present and can be initialized:
	if (!SD.begin(chipSelect)) {
		myDebugSerial.println("Card failed, or not present");
		// don't do anything more:
		return;
	}
	myDebugSerial.println("SDcard initialized.");

	int numfile = 0;
	String nomefile = "RHINO_" + String(numfile) + ".txt";
	while (SD.exists(nomefile)) {
		numfile++;
		nomefile = "RHINO_" + String(numfile) + ".txt";
	}
	dataFile = SD.open(nomefile, FILE_WRITE);
	delay(100);
	myDebugSerial.print("Opened ");
	myDebugSerial.println(nomefile);
	delay(1000);

}

void setupXbee() {
	SerialXbee.begin(115200);
	if (!SerialXbee)
	{
		myDebugSerial.println("Xbee not ready!");
	}
	if (SerialXbee) myDebugSerial.println("Communications initialized");
}

void setupPinIO() {
	pinMode(LED_CHARGE, OUTPUT);
	pinMode(LED_FIRE, OUTPUT);
	pinMode(LED_TEST, OUTPUT);
	pinMode(RELE_CHARGE, OUTPUT);
	pinMode(RELE_FIRE, OUTPUT);
	pinMode(RELE_SAFE, OUTPUT);
	pinMode(PIN_BUZZER, OUTPUT);
	pinMode(BUTTON_DISCHARGE, INPUT);
	digitalWrite(LED_CHARGE, LOW);
	digitalWrite(LED_FIRE, LOW);
	digitalWrite(LED_TEST, LOW);
	digitalWrite(RELE_CHARGE, LOW);
	digitalWrite(RELE_FIRE, LOW);
	digitalWrite(RELE_SAFE, LOW);
	digitalWrite(PIN_BUZZER, LOW);
}

error: pathspec 'Rhino.ino' did not match any file(s) known to git


Diff pins for LED, old ones are in use by network.

remote: Support for password authentication was removed on August 13, 2021.
remote: Please see https://docs.github.com/en/get-started/getting-started-with-git/about-remote-repositories#cloning-with-https-urls for information on currently recommended modes of authentication.
fatal: Authentication failed for 'https://github.com/lgramatikov/celeste.git/'


Receiver should now adhere to the iteration delay sent by the transmitter

remote: Support for password authentication was removed on August 13, 2021.
remote: Please see https://docs.github.com/en/get-started/getting-started-with-git/about-remote-repositories#cloning-with-https-urls for information on currently recommended modes of authentication.
fatal: Authentication failed for 'https://github.com/hooroo/moteino_build_lights.git/'


checking for opmode changes in pvcloud works. reading distances work too

remote: Support for password authentication was removed on August 13, 2021.
remote: Please see https://docs.github.com/en/get-started/getting-started-with-git/about-remote-repositories#cloning-with-https-urls for information on currently recommended modes of authentication.
fatal: Authentication failed for 'https://github.com/JulioOrdonezV/pvcloud.git/'


Optimise data types

Optimise data types

fatal: remote error: upload-pack: not our ref 8c88cce633886344d5fe15450473c4fe63b52cfa
fatal: the remote end hung up unexpectedly


Create bumperexample.ino

Create bumperexample.ino

Here's the example file we created at the workshop today. None of the libraries are included... and this code doesn't work perfectly--there's some issue with the line following where it starts to hug the curve.

This is related somehow to its sensor readings. I would put some sort of additional check in the sensor booleans, like "sensor_values[0] < QTR_THRESHOLD && currentDelay == 0" maybe. It's something to check out.

Make sure the threshold is okay.

#include <ZumoBuzzer.h>
#include <ZumoMotors.h>
#include <Pushbutton.h>
#include <QTRSensors.h>
#include <ZumoReflectanceSensorArray.h>
#define LED 13 // this might need to be tuned for different lighting conditions, surfaces, etc.
#define QTR_THRESHOLD 0 // microseconds

// these might need to be tuned for different motor types
#define REVERSE_SPEED 200 // 0 is stopped, 400 is full speed
#define TURN_SPEED 200
#define FORWARD_SPEED 400
#define REVERSE_DURATION 100 // ms
#define TURN_DURATION 300 // ms

// POKêMON CHAMPION MUSIC
#define MELODY_LENGTH 95
unsigned char note[MELODY_LENGTH] = { NOTE_E(5), SILENT_NOTE, NOTE_E(5), SILENT_NOTE, NOTE_E(5), SILENT_NOTE, NOTE_C(5), NOTE_E(5), NOTE_G(5), SILENT_NOTE, NOTE_G(4), SILENT_NOTE, NOTE_C(5), NOTE_G(4), SILENT_NOTE, NOTE_E(4), NOTE_A(4), NOTE_B(4), NOTE_B_FLAT(4), NOTE_A(4), NOTE_G(4), NOTE_E(5), NOTE_G(5), NOTE_A(5), NOTE_F(5), NOTE_G(5), SILENT_NOTE, NOTE_E(5), NOTE_C(5), NOTE_D(5), NOTE_B(4), NOTE_C(5), NOTE_G(4), SILENT_NOTE, NOTE_E(4), NOTE_A(4), NOTE_B(4), NOTE_B_FLAT(4), NOTE_A(4), NOTE_G(4), NOTE_E(5), NOTE_G(5), NOTE_A(5), NOTE_F(5), NOTE_G(5), SILENT_NOTE, NOTE_E(5), NOTE_C(5), NOTE_D(5), NOTE_B(4), SILENT_NOTE, NOTE_G(5), NOTE_F_SHARP(5), NOTE_F(5), NOTE_D_SHARP(5), NOTE_E(5), SILENT_NOTE, NOTE_G_SHARP(4), NOTE_A(4), NOTE_C(5), SILENT_NOTE, NOTE_A(4), NOTE_C(5), NOTE_D(5), SILENT_NOTE, NOTE_G(5), NOTE_F_SHARP(5), NOTE_F(5), NOTE_D_SHARP(5), NOTE_E(5), SILENT_NOTE, NOTE_C(6), SILENT_NOTE, NOTE_C(6), SILENT_NOTE, NOTE_C(6), SILENT_NOTE, NOTE_G(5), NOTE_F_SHARP(5), NOTE_F(5), NOTE_D_SHARP(5), NOTE_E(5), SILENT_NOTE, NOTE_G_SHARP(4), NOTE_A(4), NOTE_C(5), SILENT_NOTE, NOTE_A(4), NOTE_C(5), NOTE_D(5), SILENT_NOTE, NOTE_E_FLAT(5), SILENT_NOTE, NOTE_D(5), NOTE_C(5) }; // Measured in MS
/* This is the Mario Theme song. Using official sheet music, we can convert bpm and ms to note lengths, then reverse the process */

unsigned int duration[MELODY_LENGTH] = { 100, 25, 125, 125, 125, 125, 125, 250, 250, 250, 250, 250, 375, 125, 250, 375, 250, 250, 125, 250, 167, 167, 167, 250, 125, 125, 125, 250, 125, 125, 375, 375, 125, 250, 375, 250, 250, 125, 250, 167, 167, 167, 250, 125, 125, 125, 250, 125, 125, 375, 250, 125, 125, 125, 250, 125, 125, 125, 125, 125, 125, 125, 125, 125, 250, 125, 125, 125, 250, 125, 125, 200, 50, 100, 25, 500, 250, 125, 125, 125, 250, 125, 125, 125, 125, 125, 125, 125, 125, 125, 250, 250, 125, 375, 500 };
ZumoBuzzer buzzer;
ZumoMotors motors;
Pushbutton button(ZUMO_BUTTON); // pushbutton on pin 12
unsigned int currentNote;
unsigned int currentDelay;
char currentDir;
#define NUM_SENSORS 6
unsigned int sensor_values[NUM_SENSORS];
ZumoReflectanceSensorArray sensors(QTR_NO_EMITTER_PIN);
void waitForButtonAndCountDown() {
  digitalWrite(LED, HIGH);
  button.waitForButton();
  digitalWrite(LED, LOW); // play audible countdown
  for (int i = 0; i < 3; i++) {
    buzzer.playNote(NOTE_G(3), 200, 10+i);
    delay(1000);
  }
    delay(1000);
    buzzer.playNote(NOTE_G(4), 500, 15);
    delay(1000);
}

void setup() {
  // uncomment if necessary to correct motor directions
  //motors.flipLeftMotor(true);
  //motors.flipRightMotor(true);
  pinMode(LED, HIGH);
  currentNote = 0;
  currentDelay = 0;
  currentDir = 'F';
  waitForButtonAndCountDown();
}

void loop() {
  if (button.isPressed()) {
    // if button is pressed, stop and wait for another press to go again
    motors.setSpeeds(0, 0);
    button.waitForRelease();
    waitForButtonAndCountDown();
  }
  sensors.read(sensor_values);
  if (currentNote < MELODY_LENGTH && !buzzer.isPlaying()) {
    // play note at max volume
    // VOLUME ON A SCALE OF 0-15
    buzzer.playNote(note[currentNote], duration[currentNote], 15);
    currentNote++;
  } else if(currentNote >= MELODY_LENGTH) {
    currentNote = 0;
  }

  if (sensor_values[0] < QTR_THRESHOLD) {
    // if leftmost sensor detects line, reverse and turn to the right
    currentDir = 'R';
    currentDelay = 0;
  } else if (sensor_values[5] < QTR_THRESHOLD) {
    // if rightmost sensor detects line, reverse and turn to the left
    currentDir = 'L';
    currentDelay = 0;
  } else {
    // otherwise, go straight
    motors.setSpeeds(FORWARD_SPEED, FORWARD_SPEED);
    currentDir = 'F';
 }

  if(currentDir == 'R') {
    if(currentDelay < REVERSE_DURATION) {
      motors.setSpeeds(-REVERSE_SPEED, -REVERSE_SPEED);
    } else if(currentDelay < REVERSE_DURATION + TURN_DURATION) {
      motors.setSpeeds(TURN_SPEED, -TURN_SPEED);
    } else {
      motors.setSpeeds(FORWARD_SPEED, FORWARD_SPEED);
      currentDir = 'F';
      currentDelay = 0;
    }
    currentDelay++;
    } else if(currentDir == 'L') {
      if(currentDelay < REVERSE_DURATION) {
        motors.setSpeeds(-REVERSE_SPEED, -REVERSE_SPEED);
      } else if(currentDelay < REVERSE_DURATION + TURN_DURATION) {
        motors.setSpeeds(-TURN_SPEED, TURN_SPEED);
      } else {
        motors.setSpeeds(FORWARD_SPEED, FORWARD_SPEED);
        currentDir = 'F';
        currentDelay = 0;
      } currentDelay++;
    }
}

error: pathspec 'bumperexample.ino' did not match any file(s) known to git


Script using two lidars on one side to get both distance form the center of the vehicle and the heading relative to the wall.

// Two LIDARs on one side

#include <Wire.h>
#include <math.h>

#define    LIDARLite_ADDRESS   0x62          // Default I2C Address of LIDAR-Lite.
#define    RegisterMeasure     0x00          // Register to write to initiate ranging.
#define    MeasureValue        0x04          // Value to initiate ranging.
#define    RegisterHighLowB    0x8f          // Register to get both High and Low bytes in 1 call.

void getDist(double (&distArray)[4]);
// Variables to store last state
double lastDist0;
double lastDist1;
// Variables to store current distances
double dist0;
double dist1;

//Spacing between LIDARs on vehicle
double LIDARspacing = 20;

// Power enable switches
const int switch0 = 12;
const int switch1 = 13;

// # of LIDAR samples
int samples = 5;

// Set pi
const float pi = 3.142;

void setup() {
  // Initialize power enable pins
  pinMode(switch0, OUTPUT);
  pinMode(switch1, OUTPUT);
  // Initialize LIDAR0 on and LIDAR1 off
  digitalWrite(switch0, HIGH);
  digitalWrite(switch1, LOW);

  // Begin serial
  Serial.begin(9600);
  // Open and join irc bus as master
  Wire.begin();
  delay(100);

}

void loop() {
  double distArr[4];
  getDist(distArr);
  for (int k = 0; k < 4 ; k++) {
    Serial.println(distArr[k]);
    delay(10);
  }
  Serial.println("end");
  delay(10);
}

void getDist(double (&distArray)[4]) {

  for (int i = 0; i < 2; i++) {
    switch (i) {
      // case 0 is LIDAR0, case 1 is LIDAR1
      case 0:
        digitalWrite(switch0, LOW);
        digitalWrite(switch1, LOW);
        delay(5);
        digitalWrite(switch0, HIGH);
        delay(5);
        break;
      case 1:
        digitalWrite(switch0, LOW);
        digitalWrite(switch1, LOW);
        delay(5);
        digitalWrite(switch1, HIGH);
        delay(5);
        break;
    }
    //Error checking
    //    Serial.print("case: ");
    //    Serial.println(i);
    //--

    // sum distances so that we can average multiple samples
    int distSum = 0;
    int distance;

    for (int j = 0; j < samples; j++) {
      distance = 0;
      // This section from LIDAR Lite Wire example
      //-----------------//
      Wire.beginTransmission((int)LIDARLite_ADDRESS); // transmit to LIDAR-Lite
      Wire.write((int)RegisterMeasure); // sets register pointer to  (0x00)
      Wire.write((int)MeasureValue); // sets register pointer to  (0x00)
      Wire.endTransmission(); // stop transmitting

      delay(20); // Wait 20ms for transmit

      Wire.beginTransmission((int)LIDARLite_ADDRESS); // transmit to LIDAR-Lite
      Wire.write((int)RegisterHighLowB); // sets register pointer to (0x8f)
      Wire.endTransmission(); // stop transmitting

      delay(20); // Wait 20ms for transmit

      Wire.requestFrom((int)LIDARLite_ADDRESS, 2); // request 2 bytes from LIDAR-Lite

      if (2 <= Wire.available()) // if two bytes were received
      {
        distance = Wire.read(); // receive high byte (overwrites previous reading)
        distance = distance << 8; // shift high byte to be high 8 bits
        distance |= Wire.read(); // receive low byte as lower 8 bits
      }
      //-----------------//
      //low pass filter
      switch (i) {
        case 0:
          if (distance < 0 || distance > 400) {
            distance = lastDist0;
          }
          distance = 0.7 * distance + 0.3 * lastDist0;
          lastDist0 = distance;
          break;
        case 1:
          if (distance < 0 || distance > 400) {
            distance = lastDist1;
          }
          distance = 0.7 * distance + 0.3 * lastDist1;
          lastDist1 = distance;
          break;
      }
      distSum = distSum + distance;
      delay(10);
    }
    if (i == 0) {
      dist0 = distSum / samples;
      //Error checking
      //      Serial.print("dist0: ");
      //      Serial.println(dist0);
      //--
      //      distArray[0] = dist0 * 1.0;
    } else if (i == 1) {
      dist1 = distSum / samples;
      // Distance calibration for sensor 2
      //      dist1 = 46 + ((88 - 46) / (82 - 39)) * (dist1 - 39);
      dist1 = 6.5 + dist1 * (0.98);
      //Error checking
      //      Serial.print("dist1: ");
      //      Serial.println(dist1);
      //--
      //      distArray[1] = dist1 * 1.0;
    }
    double angle = atan((dist0 - dist1) / LIDARspacing);
    //Error checking
    //    Serial.print("angle: ");
    //    Serial.println(angle);
    //--
    distArray[2] = angle;
    double perpDist0 = dist0 * cos(angle);
    distArray[0] = perpDist0;
    double perpDist1 = dist1 * cos(angle);
    distArray[1] = perpDist1;
    double centerDist = (perpDist0 + perpDist1) / 2;
    //Error checking
    //    Serial.print("centerDist: ");
    //    Serial.println(centerDist);
    //--
    distArray[3] = centerDist;
    delay(10);
  }
}

error: pathspec 'LIDAR_DistAndAngle/LIDAR_DistAndAngle.ino' did not match any file(s) known to git


arduino: Added sketch which uses the tlc59xx driver and message interfaces to set variety of colors on the Maki LED mouth

#include <arduino.h>

#include "bit_utils.h"
#include "tlc59xx_driver.h"
#include "tlc59xx_packet.h"

typedef tlc59xx::Driver _Driver;
typedef tlc59xx::Packet _Packet;
typedef tlc59xx::FunctionControlMessage _FunctionControlMsg;

// use pin 4 for data and pin 6 for clock
_Driver led_driver( 4, 6 );

void setup()
{
//	Serial.begin( 115200 );
	// keep inputs from floating and declare pin use case
	led_driver.initialize();

	_Packet packet;

	// reset function flags
	packet.function_control_msg_.setGrayscaleClockSource( _FunctionControlMsg::GrayscaleClockSource::INTERNAL_CLOCK );
	packet.function_control_msg_.setOutputTiming( _FunctionControlMsg::OutputTiming::RISING_EDGE );
	packet.function_control_msg_.setTimingResetMode( _FunctionControlMsg::TimingResetMode::RESET_DISABLED );
	packet.function_control_msg_.setDisplayRepeatMode( _FunctionControlMsg::DisplayRepeatMode::REPEAT_DISABLED );
	packet.function_control_msg_.setBlankMode( _FunctionControlMsg::BlankMode::OUTPUTS_DISABLED );

	// zero-out brightness
	packet.global_brightness_control_msg_.setValues( 0, 0, 0 );

	// sero-out colors
	packet.grayscale_control_msg_array_[0].setValues( 0, 0, 0 );
	packet.grayscale_control_msg_array_[1].setValues( 0, 0, 0 );
	packet.grayscale_control_msg_array_[2].setValues( 0, 0, 0 );
	packet.grayscale_control_msg_array_[3].setValues( 0, 0, 0 );

	// send a copy of the packet for each IC (last IC is addressed first)
	for( uint8_t chip_idx = 0; chip_idx < 5; ++chip_idx )
	{
		packet.send( led_driver );
	}

	// delay to trigger latch pulse
	delay( 1 );
}

void loop()
{
//	Serial.println( ">>>>>>>>>>" );
	_Packet packet;

	// set function flags
	// use internal clock for duty cycle
	packet.function_control_msg_.setGrayscaleClockSource( _FunctionControlMsg::GrayscaleClockSource::INTERNAL_CLOCK );
	// turn LEDs on at rising edge of duty cycle clock
	packet.function_control_msg_.setOutputTiming( _FunctionControlMsg::OutputTiming::RISING_EDGE );
	// automatically reset the internal PWM counter (used to simulate analog duty cycle) during a latch pulse
	packet.function_control_msg_.setTimingResetMode( _FunctionControlMsg::TimingResetMode::RESET_ENABLED );
	// automatically repeat the latched data if no updates were made in a given display cycle
	packet.function_control_msg_.setDisplayRepeatMode( _FunctionControlMsg::DisplayRepeatMode::REPEAT_ENABLED );
	// enable current-sinking outputs
	packet.function_control_msg_.setBlankMode( _FunctionControlMsg::BlankMode::OUTPUTS_ENABLED );

	// set current limit for each channel (R, G, B)
	// the values here were selected to ensure the overall current would remain below 900 mA when all LEDs are at 25% duty cycle
	packet.global_brightness_control_msg_.setValues( 75, 75, 75 );

	// for each IC
	// display a color pallete
	// keep in mind that the 0th chip is the nth chip in the data path (farthest from the data/clock source)
	// and the nth chip is the first chip in the data path
	for( uint8_t chip_idx = 0; chip_idx < 5; ++chip_idx )
	{
		if( chip_idx == 4 )
		{
			// set the RGB values for each output group [0-4] on the current IC
			packet.grayscale_control_msg_array_[0].setValuesPercent( 0.25f, 0.25f, 0.25f );
			packet.grayscale_control_msg_array_[1].setValuesPercent( 0.25f, 0.0f, 0.0f );
			packet.grayscale_control_msg_array_[2].setValuesPercent( 0.0f, 0.25f, 0.0f );
			packet.grayscale_control_msg_array_[3].setValuesPercent( 0.0f, 0.0f, 0.25f );
		}
		else if( chip_idx == 3 )
		{
			// set the RGB values for each output group [0-4] on the current IC
			packet.grayscale_control_msg_array_[0].setValuesPercent( 0.25f, 0.25f, 0.0f );
			packet.grayscale_control_msg_array_[1].setValuesPercent( 0.0f, 0.0, 0.0 );
			packet.grayscale_control_msg_array_[2].setValuesPercent( 0.0f, 0.25f, 0.25f );
			packet.grayscale_control_msg_array_[3].setValuesPercent( 0.25f, 0.0f, 0.25f );
		}
		else if( chip_idx == 2 )
		{
			// set the RGB values for each output group [0-4] on the current IC
			packet.grayscale_control_msg_array_[0].setValuesPercent( 0.25f, 0.125f, 0.0f );
			packet.grayscale_control_msg_array_[1].setValuesPercent( 0.125f, 0.25f, 0.0f );
			packet.grayscale_control_msg_array_[2].setValuesPercent( 0.0f, 0.25f, 0.125f );
			packet.grayscale_control_msg_array_[3].setValuesPercent( 0.0f, 0.125f, 0.25f );
		}
		else if( chip_idx == 1 )
		{
			// set the RGB values for each output group [0-4] on the current IC
			packet.grayscale_control_msg_array_[0].setValuesPercent( 0.25f, 0.0f, 0.125f );
			packet.grayscale_control_msg_array_[1].setValuesPercent( 0.125f, 0.0f, 0.25f );
			packet.grayscale_control_msg_array_[2].setValuesPercent( 0.9f, 0.9f, 0.9f );
			packet.grayscale_control_msg_array_[3].setValuesPercent( 0.7f, 0.7f, 0.7f );
		}
		else // chip_idx == 0
		{
			// set the RGB values for each output group [0-4] on the current IC
			packet.grayscale_control_msg_array_[0].setValuesPercent( 0.5f, 0.5f, 0.5f );
			packet.grayscale_control_msg_array_[1].setValuesPercent( 0.3f, 0.3f, 0.3f );
			packet.grayscale_control_msg_array_[2].setValuesPercent( 0.0f, 0.0, 0.0 );
			packet.grayscale_control_msg_array_[3].setValuesPercent( 0.1f, 0.1f, 0.1f );
		}

		// toggle the OutputTiming bit on every other IC to avoid noise from nearby ICs
		if( chip_idx % 2 == 0 ) packet.function_control_msg_.setOutputTiming( _FunctionControlMsg::OutputTiming::RISING_EDGE );
		else packet.function_control_msg_.setOutputTiming( _FunctionControlMsg::OutputTiming::FALLING_EDGE );

		// write out the entire packet (need to do this once for each IC)
		packet.send( led_driver );
	}

	// delay to trigger latch pulse
	delay( 1 );
}

error: pathspec 'arduino/maki_led_mouth/maki_led_mouth.ino' did not match any file(s) known to git


copy gps sketch to 20140808_kayak_depth

copy gps sketch to 20140808_kayak_depth

#include <stdlib.h>
#include <SPI.h>
#include <Adafruit_GPS.h>
#include <SoftwareSerial.h>
#include <SD.h>
#include <avr/sleep.h>

// Ladyada's logger modified by Bill Greiman to use the SdFat library
//
// 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 Ultimate GPS Shield
// using MTK33x9 chipset
//    ------> http://www.adafruit.com/products/
// Pick one up today at the Adafruit electronics shop
// and help support open source hardware & software! -ada

// ref: https://github.com/adafruit/Adafruit-GPS-Library/blob/master/examples/due_shield_sdlog/due_shield_sdlog.ino

SoftwareSerial mySerial(8, 7);
Adafruit_GPS GPS(&mySerial);

// 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
/* set to true to only log to SD when GPS has a fix, for debugging, keep it false */
#define LOG_FIXONLY false

// this keeps track of whether we're using the interrupt
// off by default!
boolean usingInterrupt = false;
void useInterrupt(boolean); // Func prototype keeps Arduino 0023 happy

// Set the pins used
#define chipSelect 10
#define ledPin 13

File logfile;

// read a Hex value and return the decimal equivalent
uint8_t parseHex(char c) {
  if (c < '0')
    return 0;
  if (c <= '9')
    return c - '0';
  if (c < 'A')
    return 0;
  if (c <= 'F')
    return (c - 'A')+10;
}

// blink out an error code
void error(uint8_t errno) {
/*
  if (SD.errorCode()) {
    putstring("SD error: ");
    Serial.print(card.errorCode(), HEX);
    Serial.print(',');
    Serial.println(card.errorData(), HEX);
  }
  */
  while(1) {
    uint8_t i;
    for (i=0; i<errno; i++) {
      digitalWrite(ledPin, HIGH);
      delay(100);
      digitalWrite(ledPin, LOW);
      delay(100);
    }
    for (i=errno; i<10; i++) {
      delay(200);
    }
  }
}

void setup() {
  // for Leonardos, if you want to debug SD issues, uncomment this line
  // to see serial output
  //while (!Serial);

  // connect at 115200 so we can read the GPS fast enough and echo without dropping chars
  // also spit it out
  Serial.begin(115200);
  Serial.println("\r\nUltimate GPSlogger Shield - CSV");
  pinMode(ledPin, OUTPUT);

  // make sure that the default chip select pin is set to
  // output, even if you don't use it:
  pinMode(10, OUTPUT);

  // see if the card is present and can be initialized:
  // if (!SD.begin(chipSelect, 11, 12, 13)) {
  if (!SD.begin(chipSelect)) {      // if you're using an UNO, you can use this line instead
    Serial.println("Card init. failed!");
    error(2);
  }
  char filename[15];
  strcpy(filename, "GPSLOG00.CSV");
  for (uint8_t i = 0; i < 100; i++) {
    filename[6] = '0' + i/10;
    filename[7] = '0' + i%10;
    // create if does not exist, do not open existing, write, sync after write
    if (! SD.exists(filename)) {
      break;
    }
  }

  logfile = SD.open(filename, FILE_WRITE);
  if( ! logfile ) {
    Serial.print("Couldnt create "); Serial.println(filename);
    error(3);
  }
  Serial.print("Writing to "); Serial.println(filename);

  // connect to the GPS at the desired rate
  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 logging data, we don't suggest using anything but either RMC only or RMC+GGA
  // to keep the log files at a reasonable size
  // Set the update rate
  GPS.sendCommand(PMTK_SET_NMEA_UPDATE_1HZ);   // 1 or 5 Hz update rate

  // Turn off updates on antenna status, if the firmware permits it
  // GPS.sendCommand(PGCMD_NOANTENNA);

  // Request updates on antenna status, comment out to keep quiet
  GPS.sendCommand(PGCMD_ANTENNA);

  // the nice thing about this code is you can have a timer0 interrupt go off
  // every 1 millisecond, and read data from the GPS for you. that makes the
  // loop code a heck of a lot easier!
  useInterrupt(true);

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

  Serial.println("Ready!");

  // adding the headers seems to break the sd card
//  logfile.println("DATETIME_UTC,FIX,FIX_QUALITY,LATITUDE,LONGITUDE,SPEED,ANGLE,ALTITUDE,NUM_SATELLITES");
//  Serial.println("DATETIME_UTC,FIX,FIX_QUALITY,LATITUDE,LONGITUDE,SPEED,ANGLE,ALTITUDE,NUM_SATELLITES");

}

// Interrupt is called once a millisecond, looks for any new GPS data, and stores it
SIGNAL(TIMER0_COMPA_vect) {
  char c = GPS.read();
  // if you want to debug, this is a good time to do it!
#ifdef UDR0
  if (GPSECHO)
    if (c) UDR0 = c;
    // writing direct to UDR0 is much much faster than Serial.print
    // but only one character can be written at a time.
#endif
}

void useInterrupt(boolean v) {
  if (v) {
    // Timer0 is already used for millis() - we'll just interrupt somewhere
    // in the middle and call the "Compare A" function above
    OCR0A = 0xAF;
    TIMSK0 |= _BV(OCIE0A);
    usingInterrupt = true;
  } else {
    // do not call the interrupt function COMPA anymore
    TIMSK0 &= ~_BV(OCIE0A);
    usingInterrupt = false;
  }
}

uint32_t timer = millis();
void loop() {
  // make a string for assembling the data to log:
  String dataString = "";

  // in case you are not using the interrupt above, you'll
  // need to 'hand query' the GPS, not suggested :(
  if (! usingInterrupt) {
    // 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 trying 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 millis() or timer wraps around, we'll just reset it
    if (timer > millis())  timer = millis();

    // approximately every 2 seconds or so, print out the current stats
    if (millis() - timer > 2000) {
      timer = millis(); // reset the timer

      logfile.print("20");
      logfile.print(GPS.year, DEC);
      logfile.print("-");
      logfile.print(GPS.month, DEC);
      logfile.print("-");
      logfile.print(GPS.day, DEC);
      logfile.print(" ");
      logfile.print(GPS.hour, DEC);
      logfile.print(":");
      logfile.print(GPS.minute, DEC);
      logfile.print(":");
      logfile.print(GPS.seconds, DEC);
      logfile.print(".");
      logfile.print(GPS.milliseconds);
      logfile.print(",");
      logfile.print((int)GPS.fix);
      logfile.print(",");
      logfile.print((int)GPS.fixquality);
      logfile.print(",");
      logfile.print(GPS.latitude, 4);
      logfile.print(",");
      logfile.print(GPS.longitude, 4);
      logfile.print(",");
      logfile.print(GPS.speed);
      logfile.print(",");
      logfile.print(GPS.angle);
      logfile.print(",");
      logfile.print(GPS.altitude);
      logfile.print(",");
      logfile.println((int)GPS.satellites);
      logfile.flush();

      Serial.print("20");
      Serial.print(GPS.year);
      Serial.print("-");
      Serial.print(GPS.month, DEC);
      Serial.print("-");
      Serial.print(GPS.day, DEC);
      Serial.print(" ");
      Serial.print(GPS.hour, DEC);
      Serial.print(":");
      Serial.print(GPS.minute, DEC);
      Serial.print(":");
      Serial.print(GPS.seconds, DEC);
      Serial.print(".");
      Serial.print(GPS.milliseconds);
      Serial.print(",");
      Serial.print((int)GPS.fix);
      Serial.print(",");
      Serial.print((int)GPS.fixquality);
      Serial.print(",");
      Serial.print(GPS.latitude, 4);
      Serial.print(",");
      Serial.print(GPS.longitude, 4);
      Serial.print(",");
      Serial.print(GPS.speed);
      Serial.print(",");
      Serial.print(GPS.angle);
      Serial.print(",");
      Serial.print(GPS.altitude);
      Serial.print(",");
      Serial.println((int)GPS.satellites);
    }
  }
}

error: pathspec 'analyses/20140808_kayak_depth/ino/uno_gps/uno_gps.ino' did not match any file(s) known to git


add example

add example

#include "colour.h"
#include "ws2812b.h"

#define DATA_PIN 13

#define COLS 6
#define ROWS 5
#define COUNT (COLS*ROWS)

WS2812B driver;
Colour matrix[COLS*ROWS];

void setup()
{
  Serial.begin(9600);
  pinMode(DATA_PIN, OUTPUT);

  if (WS2812B_init(&driver, DATA_PIN, matrix, WS2812B_ZIGZAG_EVEN|WS2812B_GRB, COLS, ROWS)) {
    Serial.println("Error intiailising driver");
    /* Error handling goes here. */
  } else {
    Serial.println("WS2812B Driver loaded");
  }

  // Set all LEDs to black (off)
  WS2812B_set_all(&driver, {0,0,0});
  WS2812B_sync(&driver);
}

void loop()
{
  WS2812B_set_all(&driver, {0,0,0});
  WS2812B_sync(&driver);

  for (size_t i = 0; i < COUNT; ++i) {
    WS2812B_set_pixel_at_offset(&driver, i, colour_hsl(i*10, 100, 50));
    WS2812B_sync(&driver);
    delay(30);
  }
}

error: pathspec 'examples/rainbow.ino' did not match any file(s) known to git


increase baudrate when using h/w serial

increase baudrate when using h/w serial

// Initialise an STM32F103 with a boot loader, embedded in this code.
// MIT license, see https://github.com/jeelabs/embello -jcw, 2015-11-10

#include <Arduino.h>

#ifdef __AVR_ATmega328P__ // use a modified SoftwareSerial implementation
#define USE_SOFT_PARITY 1
#endif

#if USE_SOFT_PARITY

#include "ParitySerial.h"

#define RX_PIN      4   // Arduino Digital.4, ATmega portD.4, ATMega328 pin.6
#define TX_PIN      14  // Arduino Analog.0, ATmega portC.0, ATMega328 pin.23
ParitySerial Target (RX_PIN, TX_PIN); // defaults to even parity

#define TIMEOUT 200000

#else // assume an STM32F103 running at 72 MHz, with hardware serial

#define Target  Serial1
#define TIMEOUT 800000

#endif

// only uncomment one of the boot loaders mentioned below (or add your own)
//#define BOOT_LOADER "boot-maplemini-v20.h"
#define BOOT_LOADER "boot-usbSerial-v01.h"
//#define BOOT_LOADER "boot-bmp-jc66-v01.h"

const uint8_t data[] PROGMEM = {
#include BOOT_LOADER
};

uint8_t check;  // this checksum will get updated on each call to sendByte()

enum { ACK = 0x79, NAK = 0x1F };

// boot request codes sent to the target, based on STM's USART protocol
enum {
    GET_CMD = 0x00,
    GETID_CMD = 0x02,
    WRITE_CMD = 0x31,
    ERASE_CMD = 0x43,
    EXTERA_CMD = 0x44,
    RDUNP_CMD = 0x92,
};

// get the specific data byte to send to the target
static uint8_t getData (uint16_t index) {
    // this is equivalent to data[index] on ARM chips
    return pgm_read_byte(data + index);
}

// read a reply from the target, or return 0 after a certain amount of time
static uint8_t getReply () {
    for (long i = 0; i < TIMEOUT; ++i)
        if (Target.available())
            return Target.read();
    return 0;
}

// wait for an ACK reply, else print an error message and halt
static void wantAck () {
    uint8_t b = 0;
    // wait a bit longer than normal getReply() timeouts, if needed
    for (int i = 0; i < 5; ++i) {
        b = getReply();
        if (b == 0) {
            Serial.print('.'); // each retry prints a dot
            continue;
        }
        if (b != ACK)
            break;
        check = 0; // the global checksum is always cleared after an ACK
        return;
    }
    Serial.print(" FAILED - got 0x");
    Serial.println(b, HEX);
    while (true) ; // halt
}

// send a byte to the target and update the global checkum value
static void sendByte (uint8_t b) {
    check ^= b;
    Target.write(b);
}

// send a command and wait for the corresponding ACK
static void sendCmd (uint8_t cmd) {
    Serial.flush();
    sendByte(cmd);
    sendByte(~cmd);
    wantAck();
}

// special infinite loop to trigger target autobaud and wait for ACK or NAK
static void connectToTarget () {
#ifdef USE_SOFT_PARITY
    Target.begin(9600);
#else // use serial port hardware, can run much faster
    Target.begin(115200, SERIAL_8E1);
#endif

    uint8_t b = 0;
    do {
        Serial.print(".");
        Target.write(0x7F);
        b = getReply();
    } while (b != ACK && b != NAK); // NAK is fine, it's still a response
}

// boot loader request for the boot version, ignoring the rest
static uint8_t getBootVersion () {
    sendCmd(GET_CMD);
    uint8_t n = getReply();
    uint8_t bootRev = getReply();
    for (int i = 0; i < n; ++i)
        getReply();
    wantAck();
    return bootRev;
}

// boot loader request for the chip type, as 16-bit int
static uint16_t getChipType () {
    sendCmd(GETID_CMD);
    getReply(); // should be 1
    uint16_t chipType = getReply() << 8;
    chipType |= getReply();
    wantAck();
    return chipType;
}

// boot loader request for a mass erase of flash memory
static void massErase () {
#if 1
    sendCmd(ERASE_CMD);
    sendByte((uint8_t) 0xFF);
    sendByte((uint8_t) 0x00);
    wantAck();
#else
    sendCmd(EXTERA_CMD);
    sendByte((uint8_t) 0xFF);
    sendByte((uint8_t) 0xFF);
    sendByte((uint8_t) 0xFF);
    wantAck();
#endif
}

// main sketch logic
void setup () {
    Serial.begin(115200);
    Serial.print("[stm32f1init] ");
    Serial.println(BOOT_LOADER);
    Serial.println();
    Serial.println("(When you see a question mark: RESET your TARGET board!)");
    Serial.println();

    Serial.print("  Connecting? ");
    connectToTarget();
    Serial.println(" OK");

    uint8_t bootRev = getBootVersion();
    Serial.print("Boot version: 0x");
    Serial.println(bootRev, HEX);

    uint16_t chipType = getChipType();
    Serial.print("   Chip type: 0x");
    Serial.println(chipType, HEX);

    Serial.print("Unprotecting: ");
    sendCmd(RDUNP_CMD);
    wantAck();
    Serial.println("OK");

    Serial.print("    Resuming? ");
    connectToTarget();
    Serial.println(" OK");

    Serial.print("     Erasing: ");
    massErase();
    Serial.println("OK");

    Serial.print("     Writing: ");
    for (uint16_t offset = 0; offset < sizeof data; offset += 256) {
        Serial.print('+');
        sendCmd(WRITE_CMD);
        uint32_t addr = 0x08000000 + offset;
        sendByte(addr >> 24);
        sendByte(addr >> 16);
        sendByte(addr >> 8);
        sendByte(addr);
        sendByte(check);
        wantAck();
        sendByte(256-1);
        for (int i = 0; i < 256; ++i)
            sendByte(getData(i));
        sendByte(check);
        wantAck();
    }
    Serial.println(" OK");

    Serial.print("        Done: ");
    Serial.print(sizeof data);
    Serial.println(" bytes uploaded.");
}

void loop () {}

// Initialise an STM32F103 with a boot loader, embedded in this code.
// MIT license, see https://github.com/jeelabs/embello -jcw, 2015-11-10

#include <Arduino.h>

#ifdef __AVR_ATmega328P__ // use a modified SoftwareSerial implementation

#include "ParitySerial.h"

#define RX_PIN      4   // Arduino Digital.4, ATmega portD.4, ATMega328 pin.6
#define TX_PIN      14  // Arduino Analog.0, ATmega portC.0, ATMega328 pin.23
ParitySerial Target (RX_PIN, TX_PIN); // defaults to even parity

#define TIMEOUT 200000

#else // assume an STM32F103 running at 72 MHz, with hardware serial

#define Target  Serial1
#define TIMEOUT 800000

#endif

// only uncomment one of the boot loaders mentioned below (or add your own)
//#define BOOT_LOADER "boot-maplemini-v20.h"
#define BOOT_LOADER "boot-usbSerial-v01.h"
//#define BOOT_LOADER "boot-bmp-jc66-v01.h"

const uint8_t data[] PROGMEM = {
#include BOOT_LOADER
};

uint8_t check;  // this checksum will get updated on each call to sendByte()

enum { ACK = 0x79, NAK = 0x1F };

// boot request codes sent to the target, based on STM's USART protocol
enum {
    GET_CMD = 0x00,
    GETID_CMD = 0x02,
    WRITE_CMD = 0x31,
    ERASE_CMD = 0x43,
    EXTERA_CMD = 0x44,
    RDUNP_CMD = 0x92,
};

// get the specific data byte to send to the target
static uint8_t getData (uint16_t index) {
    // this is equivalent to data[index] on ARM chips
    return pgm_read_byte(data + index);
}

// read a reply from the target, or return 0 after a certain amount of time
static uint8_t getReply () {
    for (long i = 0; i < TIMEOUT; ++i)
        if (Target.available())
            return Target.read();
    return 0;
}

// wait for an ACK reply, else print an error message and halt
static void wantAck () {
    uint8_t b = 0;
    // wait a bit longer than normal getReply() timeouts, if needed
    for (int i = 0; i < 5; ++i) {
        b = getReply();
        if (b == 0) {
            Serial.print('.'); // each retry prints a dot
            continue;
        }
        if (b != ACK)
            break;
        check = 0; // the global checksum is always cleared after an ACK
        return;
    }
    Serial.print(" FAILED - got 0x");
    Serial.println(b, HEX);
    while (true) ; // halt
}

// send a byte to the target and update the global checkum value
static void sendByte (uint8_t b) {
    check ^= b;
    Target.write(b);
}

// send a command and wait for the coorresponding ACK
static void sendCmd (uint8_t cmd) {
    Serial.flush();
    sendByte(cmd);
    sendByte(~cmd);
    wantAck();
}

// special infinite loop to trigger target autobaud and wait for ACK or NAK
static void connectToTarget () {
#ifdef __AVR_ATmega328P__   // use a modified SoftwareSerial implementation
    Target.begin(9600);
#else                       // use serial port hardware, set to even parity
    Target.begin(9600, SERIAL_8E1);
#endif

    uint8_t b = 0;
    do {
        Serial.print(".");
        Target.write(0x7F);
        b = getReply();
        //Serial.print(b, HEX);
    } while (b != ACK && b != NAK); // NAK is fine, it's still a response
}

// boot loader request for the boot version, ignoring the rest
static uint8_t getBootVersion () {
    sendCmd(GET_CMD);
    uint8_t n = getReply();
    uint8_t bootRev = getReply();
    for (int i = 0; i < n; ++i)
        getReply();
    wantAck();
    return bootRev;
}

// boot loader request for the chip type, as 16-bit int
static uint16_t getChipType () {
    sendCmd(GETID_CMD);
    getReply(); // should be 1
    uint16_t chipType = getReply() << 8;
    chipType |= getReply();
    wantAck();
    return chipType;
}

// boot loader request for a mass erase of flash memory
static void massErase () {
#if 1
    sendCmd(ERASE_CMD);
    sendByte((uint8_t) 0xFF);
    sendByte((uint8_t) 0x00);
    wantAck();
#else
    sendCmd(EXTERA_CMD);
    sendByte((uint8_t) 0xFF);
    sendByte((uint8_t) 0xFF);
    sendByte((uint8_t) 0xFF);
    wantAck();
#endif
}

// main sketch logic
void setup () {
    Serial.begin(115200);
    Serial.print("[stm32f1init] ");
    Serial.println(BOOT_LOADER);
    Serial.println();
    Serial.println("(When you see a question mark: RESET your TARGET board!)");
    Serial.println();

    Serial.print("  Connecting? ");
    connectToTarget();
    Serial.println(" OK");

    uint8_t bootRev = getBootVersion();
    Serial.print("Boot version: 0x");
    Serial.println(bootRev, HEX);

    uint16_t chipType = getChipType();
    Serial.print("   Chip type: 0x");
    Serial.println(chipType, HEX);

    Serial.print("Unprotecting: ");
    sendCmd(RDUNP_CMD);
    wantAck();
    Serial.println("OK");

    Serial.print("    Resuming? ");
    connectToTarget();
    Serial.println(" OK");

    Serial.print("     Erasing: ");
    massErase();
    Serial.println("OK");

    Serial.print("     Writing: ");
    for (uint16_t offset = 0; offset < sizeof data; offset += 256) {
        Serial.print('+');
        sendCmd(WRITE_CMD);
        uint32_t addr = 0x08000000 + offset;
        sendByte(addr >> 24);
        sendByte(addr >> 16);
        sendByte(addr >> 8);
        sendByte(addr);
        sendByte(check);
        wantAck();
        sendByte(256-1);
        for (int i = 0; i < 256; ++i)
            sendByte(getData(i));
        sendByte(check);
        wantAck();
    }
    Serial.println(" OK");

    Serial.print("        Done: ");
    Serial.print(sizeof data);
    Serial.println(" bytes uploaded.");
}

void loop () {}


Create custom_groups.ino

Create custom_groups.ino

//***************************************************************
// custom_groups.ino
// Example of making custom groups for specific sets of LEDs.
//***************************************************************

#include "FastLED.h"
#define LED_TYPE NEOPIXEL  // ***Update to your strip type.  NEOPIXEL, APA102, LPD8806, etc.
#define DATA_PIN 6  // ***Set this to your data pin number.
#define NUM_LEDS 12  // ***Remember to set this to your strip length.
#define MASTER_BRIGHTNESS 255  // Master brightness range is 0-255.
CRGB leds[NUM_LEDS];

// Specify the number of pixels and which pixels are in each custom group.
// Rename these as needed to make sense for your project!
#define NUM_GROUP_A 2  // The number of pixels in this custom group.
#define NUM_GROUP_B 4  // The number of pixels in this custom group.
uint8_t groupA[NUM_GROUP_A] = {0,5};  // The pixels in this custom group.
uint8_t groupB[NUM_GROUP_B] = {1,2,3,4};  // The pixels in this custom group.

//---------------------------------------------------------------
void setup() {
  delay(1000);  // Startup delay
  Serial.begin(115200);  // Allows serial monitor output (check baud rate)
  FastLED.addLeds<LED_TYPE,DATA_PIN>(leds, NUM_LEDS);  // ***For Clock-less strips.
  FastLED.setBrightness(MASTER_BRIGHTNESS);
}

//---------------------------------------------------------------
void loop () {
  // Initially set all pixels to a color.
  for (int i = 0; i < NUM_LEDS; i++) {
    leds[i] = CHSV(80,255,255);
  }
  FastLED.show();
  delay(1200);

  // Set the custom groups to some other colors.
  for (int i = 0; i < NUM_GROUP_A; i++) {
    leds[groupA[i]] = CRGB::Red;
  }

  for (int i = 0; i < NUM_GROUP_B; i++) {
    leds[groupB[i]] = CRGB::Yellow;
  }
  FastLED.show();
  delay(800);

}//end main loop

error: pathspec 'custom_groups.ino' did not match any file(s) known to git


Fucking github I lost my original single led server code !!!!

Will have to start at new RGB version

#include <ESP8266WiFi.h>
#include <DNSServer.h>
#include <ESP8266WebServer.h>
#include <WiFiManager.h>
#include <ESP8266HTTPClient.h>
#include <Ticker.h>
#include <ESP8266mDNS.h>
#include <OneWire.h>
#include <DallasTemperature.h>
#define ONE_WIRE_BUS D4
String resetpass = "YourResetPassword"; // password to reset wifimanager when allready connected
const String thingkey = "YOURTHINGSPEKKEY"; //your thingspeak API key
String dernadd = "Fraichement booté"; //variable for ip logging (you can put your fresh boot mesage here in text/html)
int pinRouge = D1; // pin for red leds
int pinVerte = D7; // pin for green leds
int pinBleu = D5; // pin for blue leds
const long interval = 60000; // interval in ms for sending temperature data to thingspeak
const String liens = "Acceuil - Température - Version - Reset - Temp stats\n"; // html/links shown at bottom of pages
ESP8266WebServer server(80);
String derncoul;
long r;
long g;
long b;
int rouge = 0;
int vert = 0;
int bleu = 0;
unsigned long previousMillis = 0;
OneWire oneWire(ONE_WIRE_BUS);
DallasTemperature sensors(&oneWire);
int roulepastusuite = 0;
Ticker tiqueFade;

const String css = "\n";

void fadeRGB() {
  if (r == rouge && g == vert && b == bleu) {
    tiqueFade.detach();
//    Serial.println("Stopping");
  }
  for (int i = 0; i <= 2; i++) {
    int couleur;
    int tc;
    int pinouche;
    switch (i) {
      case 0:
        pinouche = pinRouge;
        tc = r;
        couleur = rouge;
        break;
      case 1:
        pinouche = pinVerte;
        tc = g;
        couleur = vert;
        break;
      case 2:
        pinouche = pinBleu;
        tc = b;
        couleur = bleu;
        break;
    }
    if (couleur < tc) {
      couleur++;
      analogWrite(pinouche, couleur);
    } else if (couleur > tc) {
      couleur--;
      analogWrite(pinouche, couleur);
    }
    switch (i) {
      case 0:
        rouge = couleur;
        break;
      case 1:
        vert = couleur;
        break;
      case 2:
        bleu = couleur;
        break;
    }
  }
}

void handleRoot() {
  String addy = server.client().remoteIP().toString();
  //  Serial.println("");
  //  Serial.println(addy);
  String testteu = server.arg("COULEUR");
  //  Serial.println(testteu);
  if (testteu != 0) {
    derncoul = testteu;
    long number = strtol( &testteu[1], NULL, 16);
    // Split them up into r, g, b values
    r = number >> 16;
    g = number >> 8 & 0xFF;
    b = number & 0xFF;
    if (r != rouge) {
      //      Serial.print("Rouge = ");
      //      Serial.println(r);
      tiqueFade.attach_ms(40, fadeRGB);
      dernadd = addy;
      delay(5);
    }
    if (g != vert) {
      //      Serial.print("Vert = ");
      //      Serial.println(g);
      tiqueFade.attach_ms(40, fadeRGB);
      dernadd = addy;
      delay(5);
    }
    if (b != bleu) {
      //      Serial.print("Bleu = ");
      //      Serial.println(b);
      tiqueFade.attach_ms(40, fadeRGB);
      dernadd = addy;
    }
  }
  String contenu = "<!DOCTYPE html>\n\n\n";
  if (server.args()) { // recharge la page / pour permetre d'appuyer refresh sans re-poster la form
    contenu += "<meta http-equiv=\"refresh\" content=\"0;url=/\" />\n";
  }
  contenu += "<meta charset=\"UTF-8\" />\n<title>Que la lumiere soit</title>\n"
             "<meta name=\"viewport\" content=\"width=device-width, initial-scale=1\">\n";
  contenu += css;
  contenu += "\n\n"
             "
\n"
             "<form action=\"/\" method=\"post\">\n"
             "
Change la couleur de mon bureau:
"
             "<input type=\"color\" name=\"COULEUR\" value=\"" + derncoul + "\">
\n"
             "<input type=\"submit\" class=\"button1\" value=\"Changer\">\n"
             "</form>\n
Dernier IP à avoir changé la couleur : ";
  contenu += dernadd;
  contenu += "
\n";
  contenu += liens;
  contenu += "
\n";
  server.send(200, "text/html", contenu);
}

void handleReset() {
  int ouireset = 0;
  String addy = server.client().remoteIP().toString();
  //  Serial.println("");
  //  Serial.println(addy);
  //  Serial.println("!!! RESET PAGE !!!");
  String testteu = server.arg("RESET");
  String passme = server.arg("PASSME");
  if (testteu == "OUI") {
    if (passme == resetpass) {
      ouireset = 1;
    } else {
      ouireset = 2;
    }
  }
  String contenu = "<!DOCTYPE html>\n\n\n";
  contenu += "<meta charset=\"UTF-8\" />\n<title>Que la lumiere se RESET</title>\n"
             "<meta name=\"viewport\" content=\"width=device-width, initial-scale=1\">\n";
  contenu += css;
  contenu += "\n\n"
             "
\n";
  if (!ouireset) {
    contenu += "<form action=\"/reset\" method=\"post\">\n"
               "
Tu veux resetter le wifi network pour reconfigurer ?
"
               "<input type=\"hidden\" name=\"RESET\" value=\"OUI\">
\n"
               "<input type=\"password\" name=\"PASSME\" value=\"password\">
\n"
               "<input type=\"submit\" class=\"button1\" value=\"Reset Wifi Network\">\n"
               "</form>\n";
  } else if (ouireset != 1) {
    contenu += "<form action=\"/reset\" method=\"post\">\n"
               "
Tu veux resetter le wifi network pour reconfigurer ?
"
               "<input type=\"hidden\" name=\"RESET\" value=\"OUI\">
\n"
               "<input type=\"password\" name=\"PASSME\" value=\"password\">
\n"
               "
!!! MAUVAIS PASSWORD !!!

\n"
               "<input type=\"submit\" class=\"button1\" value=\"Reset Wifi Network\">\n"
               "</form>\n";
    //    Serial.print("BAD PASSWORD : ");
    //    Serial.println(passme);
  } else if (ouireset == 1) {
    contenu += "
Reset Dans 10 Secondes
\n";
  }
  contenu += "
Dernier IP à avoir changé la couleur :";
  contenu += dernadd;
  contenu += "\n
";
  contenu += liens;
  contenu += "\n

\n";
  server.send(200, "text/html", contenu);
  if (ouireset == 1) {
    //    Serial.println("Reset dans 10 secondes");
    delay(10000);
    WiFiManager wifiManager;
    wifiManager.resetSettings();
    ESP.restart();
  }
}

void handleNotFound() {
  String addy = server.client().remoteIP().toString();
  //  Serial.println("");
  //  Serial.println(addy);
  String htmlmessage = "<!DOCTYPE html>\n\n\n";
  htmlmessage += "<meta charset=\"UTF-8\" />\n<title>404 Not found</title>\n"
                 "<meta name=\"viewport\" content=\"width=device-width, initial-scale=1\">\n";
  htmlmessage += css;
  htmlmessage += "\n\n"
                 "
\n";
  htmlmessage += "
404 File Not Found

\n";
  htmlmessage += "URI: ";
  htmlmessage += server.uri();
  htmlmessage += "
\nMethod: ";
  htmlmessage += (server.method() == HTTP_GET) ? "GET" : "POST";
  htmlmessage += "
\nArguments: ";
  htmlmessage += server.args();
  htmlmessage += "
\n";
  for (uint8_t i = 0; i < server.args(); i++) {
    htmlmessage += " " + server.argName(i) + ": " + server.arg(i) + "
\n";
  }
  htmlmessage += "
\n";
  htmlmessage += liens;
  htmlmessage += "
\n
\n";
  server.send(404, "text/html", htmlmessage);
  String message = "404 File Not Found\n";
  message += "URI: ";
  message += server.uri();
  message += "\nMethod: ";
  message += (server.method() == HTTP_GET) ? "GET" : "POST";
  message += "\nArguments: ";
  message += server.args();
  message += "\n";
  for (uint8_t i = 0; i < server.args(); i++) {
    message += " " + server.argName(i) + ": " + server.arg(i) + "\n";
  }
  //  Serial.print(message);
}

void updateTemp(String tempe) {
  if (tempe != "-127.00") {
    //    Serial.print("Sending temp : ");
    //    Serial.println(tempe);
    HTTPClient http;
    String webadd = "http://api.thingspeak.com/update?key=";
    webadd += thingkey;
    webadd += "&field1=";
    webadd += tempe;
    http.begin(webadd);
    int httpCode = http.GET();//Send the request
    if (httpCode > 0) { //Check the returning code
      String payload = http.getString();   //Get the request response payload
      //      Serial.println(payload);                     //Print the response payload
    }
    http.end();   //Close connection
  }
}

void latemp() {
  sensors.requestTemperatures();
  float thetemp = sensors.getTempCByIndex(0);// Why "byIndex"? You can have more than one IC on the same bus. 0 refers to the first IC on the wire
  char buffer[10];
  String tempF = dtostrf(thetemp, 5, 2, buffer);
  updateTemp(tempF);
}

void handleTemp() {
  sensors.requestTemperatures();
  float latemp = sensors.getTempCByIndex(0);
  while (latemp == -127.00) {
    sensors.requestTemperatures();
    latemp = sensors.getTempCByIndex(0);
  }
  String addy = server.client().remoteIP().toString();
  //  Serial.println("");
  //  Serial.println(addy);
  //  Serial.print("Temperature : ");
  //  Serial.println(latemp);
  String contenu = "<!DOCTYPE html>\n\n\n";
  contenu += "<meta charset=\"UTF-8\" />\n<title>Quel chaleur</title>\n"
             "<meta name=\"viewport\" content=\"width=device-width, initial-scale=1\">\n";
  contenu += css;
  contenu += "\n\n"
             "
\n";
  contenu += "<form action=\"/\" method=\"get\">\n"
             "
Voici la temperature
"
             "
";
  contenu += latemp;
  contenu += "°C

\n<input type=\"submit\" class=\"button1\" value=\"Go Home\">\n"
             "</form>\n"
             "
Dernier IP à avoir changé la couleur :";
  contenu += dernadd;
  contenu += "\n
";
  contenu += liens;
  contenu += "\n

\n";
  server.send(200, "text/html", contenu);
}

void setup() {
  analogWriteRange(255);
  //  analogWriteFreq(500);
  //  Serial.begin(9600);
  pinMode(pinRouge, OUTPUT);
  pinMode(pinVerte, OUTPUT);
  pinMode(pinBleu, OUTPUT);
  digitalWrite(pinRouge, LOW);
  digitalWrite(pinBleu, LOW);
  digitalWrite(pinVerte, LOW);
  WiFiManager wifiManager;
  wifiManager.autoConnect();
  delay(500);
  if (!MDNS.begin("esp8266")) {
    //Serial.println("Error setting up MDNS responder!");
    while (1) {
      delay(1000);
    }
  }
  server.on("/", handleRoot);
  server.on("/reset", handleReset);
  server.on("/temp", handleTemp);
  server.on("/version", []() {
    String addy = server.client().remoteIP().toString();
    //Serial.println("");
    //Serial.println(addy);
    //Serial.println("Version request");
    server.send(200, "text/html", "V1.7, Steve Olmstead sansillusion@gmail.com\n\n

"
                "Added fader function\nRemoved connection watchdog (better have good signal)\n
"
                "Removed mDns (did not work anyway)\n\n

"
                "Added smoother fading\n\n

"
                "Added AutoConect WifiManager !\n\n

"
                "Added basic last IP logging\n
"
                "Added /reset page to reset wifiManager connection settings\n\n

"
                "Added /temp (temperature sensor read of ky-001)\n\n

"
                "Added thingspeak support to send temperature each minute
\n\n
"
                "Major rewrite for RGB led trip usin mosfet
\n"
                "Removed serial to free resources for software pwm (still flikers but less than before)
\n" + liens);
  });
  server.onNotFound(handleNotFound);
  server.begin();
  //Serial.println("HTTP server started");
  MDNS.addService("http", "tcp", 80);
  sensors.begin();
}

void loop() {
  server.handleClient();
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    previousMillis = currentMillis;
    latemp();
  }
}

error: pathspec 'espLightServerRGB.ino' did not match any file(s) known to git


Create desk_help.ino

Create desk_help.ino

controls the robot arm on my workbench with potentiometers

#include <Servo.h>

Servo claw, tilt, pan;

char cmd_byte;
int potpin1 (A0);
int potpin2 (A1);
int potpin3 (A2);

void setup(){
  Serial.begin(9600);
  claw.attach(8);
  tilt.attach(7);
  pan.attach(6);
}

void loop(){
  int val1 = analogRead(potpin1);
  int val2 = analogRead(potpin2);
  int val3 = analogRead(potpin3);

  val1 = map(val1, 0, 1023, 0, 179);

  claw.write(val1);
  delay(50);
  val2 = map(val2, 0, 1023, 0, 179);
  tilt.write(val2);
  delay(50);
  val3 = map(val3, 0, 1023, 0, 179);
  pan.write(val3);
  delay(50);
}

error: pathspec 'desk_help.ino' did not match any file(s) known to git