Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5

Peet Bros Anemometer > WeatherDuino converter
#2

I need some help Huh 


I now have a working converter for direction (pulses to analog 0-5V)  BUT the output of the speed is in MPH!

For the WD we need pulses as input but Peet Bros has THREE calibration calculations (see previous post)
which must then be done in th WD software?!

what's the best way to move forward here...?

Thanks!


Idea I bought a MCP4725 DAC to convert the direction from degrees into analog output but this is not yet incorporated in the sketch below...
Code:
// Peet Bros wind sensor convertor #define windSpeedPin 2 #define windDirPin 3 #define windSpeedINT 0 // INT0 #define windDirINT 1   // INT1 #define windSpeedOutPin 8 #define windDirOutPin   9 // Pin 13 has an LED connected on most Arduino boards. int LED = 13; const unsigned long DEBOUNCE = 10000ul;      // Minimum switch time in microseconds const unsigned long DIRECTION_OFFSET = 0ul;  // Manual direction offset in degrees, if required const unsigned long TIMEOUT = 1500000ul;       // Maximum time allowed between speed pulses in microseconds const unsigned long UPDATE_RATE = 500ul;     // How often to send out NMEA data in milliseconds volatile unsigned long speedPulse = 0ul;    // Time capture of speed pulse volatile unsigned long dirPulse = 0ul;      // Time capture of direction pulse volatile unsigned long speedTime = 0ul;     // Time between speed pulses (microseconds) volatile unsigned long directionTime = 0ul; // Time between direction pulses (microseconds) volatile boolean newData = false;           // New speed pulse received volatile unsigned long lastUpdate = 0ul;    // Time of last serial output int windDirection = 0; volatile boolean ignoreNextReading = false; boolean debug = true; void setup() {  pinMode(LED, OUTPUT);  pinMode(windSpeedOutPin, OUTPUT);  pinMode(windDirOutPin, OUTPUT);  Serial.begin(115200, SERIAL_8N1);  pinMode(windSpeedPin, INPUT_PULLUP);  attachInterrupt(windSpeedINT, readWindSpeed, FALLING);  pinMode(windDirPin, INPUT_PULLUP);  attachInterrupt(windDirINT, readWindDir, FALLING);  interrupts(); } void readWindSpeed() {  // Despite the interrupt being set to FALLING edge, double check the pin is now LOW  if (((micros() - speedPulse) > DEBOUNCE) && (digitalRead(windSpeedPin) == LOW))  {    // Work out time difference between last pulse and now    speedTime = micros() - speedPulse;    // Direction pulse should have occured after the last speed pulse    if (dirPulse - speedPulse >= 0) directionTime = dirPulse - speedPulse;    newData = true;    speedPulse = micros();    // Capture time of the new speed pulse  } } void readWindDir() {  if (((micros() - dirPulse) > DEBOUNCE) && (digitalRead(windDirPin) == LOW))  {    dirPulse = micros();        // Capture time of direction pulse  } } void calcWindSpeedAndDir() {  unsigned long dirPulse_, speedPulse_;  unsigned long speedTime_;  unsigned long directionTime_;  unsigned long windDirection = 0l, rps = 0l, mph = 0l; // Peet Bros wind sensor convertor #define windSpeedPin 2 #define windDirPin 3 #define windSpeedINT 0 // INT0 #define windDirINT 1   // INT1 #define windSpeedOutPin 8 #define windDirOutPin   9 // Pin 13 has an LED connected on most Arduino boards. int LED = 13; const unsigned long DEBOUNCE = 10000ul;      // Minimum switch time in microseconds const unsigned long DIRECTION_OFFSET = 0ul;  // Manual direction offset in degrees, if required const unsigned long TIMEOUT = 1500000ul;       // Maximum time allowed between speed pulses in microseconds const unsigned long UPDATE_RATE = 500ul;     // How often to send out NMEA data in milliseconds volatile unsigned long speedPulse = 0ul;    // Time capture of speed pulse volatile unsigned long dirPulse = 0ul;      // Time capture of direction pulse volatile unsigned long speedTime = 0ul;     // Time between speed pulses (microseconds) volatile unsigned long directionTime = 0ul; // Time between direction pulses (microseconds) volatile boolean newData = false;           // New speed pulse received volatile unsigned long lastUpdate = 0ul;    // Time of last serial output int windDirection = 0; volatile boolean ignoreNextReading = false; boolean debug = true; void setup() {   pinMode(LED, OUTPUT);   pinMode(windSpeedOutPin, OUTPUT);   pinMode(windDirOutPin, OUTPUT);   Serial.begin(115200, SERIAL_8N1);   pinMode(windSpeedPin, INPUT_PULLUP);   attachInterrupt(windSpeedINT, readWindSpeed, FALLING);   pinMode(windDirPin, INPUT_PULLUP);   attachInterrupt(windDirINT, readWindDir, FALLING);   interrupts(); } void readWindSpeed() {   // Despite the interrupt being set to FALLING edge, double check the pin is now LOW   if (((micros() - speedPulse) > DEBOUNCE) && (digitalRead(windSpeedPin) == LOW))   {     // Work out time difference between last pulse and now     speedTime = micros() - speedPulse;     // Direction pulse should have occured after the last speed pulse     if (dirPulse - speedPulse >= 0) directionTime = dirPulse - speedPulse;     newData = true;     speedPulse = micros();    // Capture time of the new speed pulse   } } void readWindDir() {   if (((micros() - dirPulse) > DEBOUNCE) && (digitalRead(windDirPin) == LOW))   {     dirPulse = micros();        // Capture time of direction pulse   } } void calcWindSpeedAndDir() {   unsigned long dirPulse_, speedPulse_;   unsigned long speedTime_;   unsigned long directionTime_;   unsigned long windDirection = 0l, rps = 0l, mph = 0l;   // Get snapshot of data into local variables. Note: an interrupt could trigger here   noInterrupts();   dirPulse_ = dirPulse;   speedPulse_ = speedPulse;   speedTime_ = speedTime;   directionTime_ = directionTime;   interrupts();   // Make speed zero, if the pulse delay is too long   if (micros() - speedPulse_ > TIMEOUT) speedTime_ = 0ul;   // The following converts revolutions per 100 seconds (rps) to mph x 100   // This calculation follows the Peet Bros. piecemeal calibration data   if (speedTime_ > 0)   {     // to prevent calculation errors with float numbers, make them larger     rps = 100000000 / speedTime_;     if (1 < rps && rps < 323)     {       //      float mph = (-0.1095 * (rps * rps)) + (2.9318 * rps) - 0.1412;       mph = (-1095 * rps * rps + 29318 * rps * 100 - 14120000) / 1000000;     }     else if (323 <= rps && rps < 5436)     {       //            mph = 0.0052 * (rps * rps) + 2.1980 * rps + 1.1091;       mph = (52 * rps * rps + 21980 * rps * 100 + 110910000) / 1000000;     }     else if (5436 <= rps && rps < 6633)     {       //            mph = 0.1104 * (rps * rps) - 9.5685 * rps + 329.87;       mph = (1104 * rps * rps - 95685 * rps * 100 + 32987000000) / 1000000;     }          // Remove the possibility of negative speed     if (mph < 0l) mph = 0l;          // only calculate direction if we have wind     if (mph >= 0)     {       // Calculate direction from captured pulse times       windDirection = ( ( (directionTime_ * 360) / speedTime_) + DIRECTION_OFFSET) % 360;     }     else     {       mph = 0;     }     //============================================     // output to Weatherduino     //int degrees2analog = map(dirOut, 0, 360, 0, 255);     analogWrite(windDirOutPin, map(windDirection, 0, 360, 0, 255));     //============================================     if (debug)     {       Serial.print("speedTime_: "); Serial.println(speedTime_);       Serial.print("rps: "); Serial.println(rps);       Serial.print("dir: "); Serial.println(windDirection);       Serial.print("mph: "); Serial.println(mph);       Serial.println("");     }   } } void loop() {   int i;   const unsigned int LOOP_DELAY = 50;   const unsigned int LOOP_TIME = TIMEOUT / LOOP_DELAY;   digitalWrite(LED, !digitalRead(LED));    // Toggle LED   i = 0;   // If there is new data, process // Peet Bros wind sensor convertor #define windSpeedPin 2 #define windDirPin 3 #define windSpeedINT 0 // INT0 #define windDirINT 1   // INT1 #define windSpeedOutPin 8 #define windDirOutPin   9 // Pin 13 has an LED connected on most Arduino boards. int LED = 13; const unsigned long DEBOUNCE = 10000ul;      // Minimum switch time in microseconds const unsigned long DIRECTION_OFFSET = 0ul;  // Manual direction offset in degrees, if required const unsigned long TIMEOUT = 1500000ul;       // Maximum time allowed between speed pulses in microseconds const unsigned long UPDATE_RATE = 500ul;     // How often to send out NMEA data in milliseconds volatile unsigned long speedPulse = 0ul;    // Time capture of speed pulse volatile unsigned long dirPulse = 0ul;      // Time capture of direction pulse volatile unsigned long speedTime = 0ul;     // Time between speed pulses (microseconds) volatile unsigned long directionTime = 0ul; // Time between direction pulses (microseconds) volatile boolean newData = false;           // New speed pulse received volatile unsigned long lastUpdate = 0ul;    // Time of last serial output int windDirection = 0; volatile boolean ignoreNextReading = false; boolean debug = true; void setup() {   pinMode(LED, OUTPUT);   pinMode(windSpeedOutPin, OUTPUT);   pinMode(windDirOutPin, OUTPUT);   Serial.begin(115200, SERIAL_8N1);   pinMode(windSpeedPin, INPUT_PULLUP);   attachInterrupt(windSpeedINT, readWindSpeed, FALLING);   pinMode(windDirPin, INPUT_PULLUP);   attachInterrupt(windDirINT, readWindDir, FALLING);   interrupts(); } void readWindSpeed() {   // Despite the interrupt being set to FALLING edge, double check the pin is now LOW   if (((micros() - speedPulse) > DEBOUNCE) && (digitalRead(windSpeedPin) == LOW))   {     // Work out time difference between last pulse and now     speedTime = micros() - speedPulse;     // Direction pulse should have occured after the last speed pulse     if (dirPulse - speedPulse >= 0) directionTime = dirPulse - speedPulse;     newData = true;     speedPulse = micros();    // Capture time of the new speed pulse   } } void readWindDir() {   if (((micros() - dirPulse) > DEBOUNCE) && (digitalRead(windDirPin) == LOW))   {     dirPulse = micros();        // Capture time of direction pulse   } } void calcWindSpeedAndDir() {   unsigned long dirPulse_, speedPulse_;   unsigned long speedTime_;   unsigned long directionTime_;   unsigned long windDirection = 0l, rps = 0l, mph = 0l;   // Get snapshot of data into local variables. Note: an interrupt could trigger here   noInterrupts();   dirPulse_ = dirPulse;   speedPulse_ = speedPulse;   speedTime_ = speedTime;   directionTime_ = directionTime;   interrupts();   // Make speed zero, if the pulse delay is too long   if (micros() - speedPulse_ > TIMEOUT) speedTime_ = 0ul;   // The following converts revolutions per 100 seconds (rps) to mph x 100   // This calculation follows the Peet Bros. piecemeal calibration data   if (speedTime_ > 0)   {     // to prevent calculation errors with float numbers, make them larger     rps = 100000000 / speedTime_;     if (1 < rps && rps < 323)     {       //      float mph = (-0.1095 * (rps * rps)) + (2.9318 * rps) - 0.1412;       mph = (-1095 * rps * rps + 29318 * rps * 100 - 14120000) / 1000000;     }     else if (323 <= rps && rps < 5436)     {       //            mph = 0.0052 * (rps * rps) + 2.1980 * rps + 1.1091;       mph = (52 * rps * rps + 21980 * rps * 100 + 110910000) / 1000000;     }     else if (5436 <= rps && rps < 6633)     {       //            mph = 0.1104 * (rps * rps) - 9.5685 * rps + 329.87;       mph = (1104 * rps * rps - 95685 * rps * 100 + 32987000000) / 1000000;     }          // Remove the possibility of negative speed     if (mph < 0l) mph = 0l;          // only calculate direction if we have wind     if (mph >= 0)     {       // Calculate direction from captured pulse times       windDirection = ( ( (directionTime_ * 360) / speedTime_) + DIRECTION_OFFSET) % 360;     }     else     {       mph = 0;     }     //============================================     // output to Weatherduino     //int degrees2analog = map(dirOut, 0, 360, 0, 255);     analogWrite(windDirOutPin, map(windDirection, 0, 360, 0, 255));     //============================================     if (debug)     {       Serial.print("speedTime_: "); Serial.println(speedTime_);       Serial.print("rps: "); Serial.println(rps);       Serial.print("dir: "); Serial.println(windDirection);       Serial.print("mph: "); Serial.println(mph);       Serial.println("");     }   } } void loop() {   int i;   const unsigned int LOOP_DELAY = 50;   const unsigned int LOOP_TIME = TIMEOUT / LOOP_DELAY;   digitalWrite(LED, !digitalRead(LED));    // Toggle LED   i = 0;   // If there is new data, process it, otherwise wait for LOOP_TIME to pass   while ((newData != true) && (i < LOOP_TIME))   {     i++;     delayMicroseconds(LOOP_DELAY);   }   calcWindSpeedAndDir();    // Process new data   newData = false; }it, otherwise wait for LOOP_TIME to pass   while ((newData != true) && (i < LOOP_TIME))   {     i++;     delayMicroseconds(LOOP_DELAY);   }   calcWindSpeedAndDir();    // Process new data   newData = false; }  // Get snapshot of data into local variables. Note: an interrupt could trigger here  noInterrupts();  dirPulse_ = dirPulse;  speedPulse_ = speedPulse;  speedTime_ = speedTime;  directionTime_ = directionTime;  interrupts();  // Make speed zero, if the pulse delay is too long  if (micros() - speedPulse_ > TIMEOUT) speedTime_ = 0ul;  // The following converts revolutions per 100 seconds (rps) to mph x 100  // This calculation follows the Peet Bros. piecemeal calibration data  if (speedTime_ > 0)  {    // to prevent calculation errors with float numbers, make them larger    rps = 100000000 / speedTime_;    if (1 < rps && rps < 323)    {      //      float mph = (-0.1095 * (rps * rps)) + (2.9318 * rps) - 0.1412;      mph = (-1095 * rps * rps + 29318 * rps * 100 - 14120000) / 1000000;    }    else if (323 <= rps && rps < 5436)    {      //            mph = 0.0052 * (rps * rps) + 2.1980 * rps + 1.1091;      mph = (52 * rps * rps + 21980 * rps * 100 + 110910000) / 1000000;    }    else if (5436 <= rps && rps < 6633)    {      //            mph = 0.1104 * (rps * rps) - 9.5685 * rps + 329.87;      mph = (1104 * rps * rps - 95685 * rps * 100 + 32987000000) / 1000000;    }        // Remove the possibility of negative speed    if (mph < 0l) mph = 0l;        // only calculate direction if we have wind    if (mph >= 0)    {      // Calculate direction from captured pulse times      windDirection = ( ( (directionTime_ * 360) / speedTime_) + DIRECTION_OFFSET) % 360;    }    else    {      mph = 0;    }    //============================================    // output to Weatherduino    //int degrees2analog = map(dirOut, 0, 360, 0, 255);    analogWrite(windDirOutPin, map(windDirection, 0, 360, 0, 255));    //============================================    if (debug)    {      Serial.print("speedTime_: "); Serial.println(speedTime_);      Serial.print("rps: "); Serial.println(rps);      Serial.print("dir: "); Serial.println(windDirection);      Serial.print("mph: "); Serial.println(mph);      Serial.println("");    }  } } void loop() {  int i;  const unsigned int LOOP_DELAY = 50;  const unsigned int LOOP_TIME = TIMEOUT / LOOP_DELAY;  digitalWrite(LED, !digitalRead(LED));    // Toggle LED  i = 0;  // If there is new data, process it, otherwise wait for LOOP_TIME to pass  while ((newData != true) && (i < LOOP_TIME))  {    i++;    delayMicroseconds(LOOP_DELAY);  }  calcWindSpeedAndDir();    // Process new data  newData = false; }
Reply


Messages In This Thread
Peet Bros Anemometer > WeatherDuino converter - by edr1924 - 11-05-2019, 20:48
RE: Advice needed... Peet Bros Anemometer > WeatherDuino converter - by edr1924 - 14-05-2019, 17:45
RE: Peet Bros Anemometer > WeatherDuino converter - by engolling - 14-05-2019, 22:04
RE: Peet Bros Anemometer > WeatherDuino converter - by edr1924 - 15-05-2019, 11:43
RE: Peet Bros Anemometer > WeatherDuino converter - by engolling - 15-05-2019, 12:29
RE: Peet Bros Anemometer > WeatherDuino converter - by edr1924 - 15-05-2019, 13:03



Users browsing this thread: 1 Guest(s)