Skip to content
  • MySensors
  • OpenHardware.io
  • Categories
  • Recent
  • Tags
  • Popular
Skins
  • Light
  • Brite
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Brand Logo
  1. Home
  2. Troubleshooting
  3. insufficient accuracy for internal Vcc measurement

insufficient accuracy for internal Vcc measurement

Scheduled Pinned Locked Moved Troubleshooting
1 Posts 1 Posters 908 Views 2 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • M Offline
    M Offline
    MikaelK
    wrote on last edited by
    #1

    Hi,

    I'm working on a battery operated node doing motion + temp, and I use Yveaux's Arduino_Vcc library to measure battery voltage.

    I've tested the voltage from the 2 AAs and it's 2.99v, but the internal measurement gives 2.22v. I have a 25% difference where we should expect max 10%, shouldn't we ?

    I'll try to debug that tomorrow with a dedicated sketch, but maybe someone can easily spot the error in the following code ?

    /**
     * DESCRIPTION
     * Motion Sensor (HC-SR501) + Temp sensor (MCP9700 analog sensor)
     * inspired by :
     * mysensors PIR example created by Henrik Ekblad : http://www.mysensors.org/build/motion
     * Slim Node as a Mini 2AA Battery PIR Motion Sensor : http://forum.mysensors.org/topic/2715/slim-node-as-a-mini-2aa-battery-pir-motion-sensor
     * Kevin Kessler's blog for reading MCP9700 temperature sensor : http://blog.kkessler.com/2012/06/20/mcp9700/
     */
    
    #include <MySensor.h>  
    #include <SPI.h>
    #include <Vcc.h>
    
    #define NODE_ID 30
    #define MOTION_INPUT_PIN 3   // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define CHILD_ID_MOTION 1
    #define CHILD_ID_TEMP 2  
    #define CHILD_ID_BATT 3
    #define DOMOTICZ_OFF_DELAY 10000
    #define MINIMUM_SEND_INTERVAL 86400000 // once a day
    #define TEMP_SEND_FREQ 300000 // every 5min
    #define TEMP_SEND_THRESHOLD 0.3 // do not send temp if variation is below delta
    #define VCC_MIN 1.9
    #define VCC_MAX 3.3
    
    float lastTemperature = 0;;
    float lastVoltage = 0;
    
    int loopCounter = 0;
    
    bool interruptReturn = false; // "false" will make the first loop disregard high output from HC-SR501 (from start-up) and make a battery+temp report instead.
     
    Vcc vcc(1.34); // 2.98/2.22=1.3423 . Can this be ok ???
    
    MySensor gw;
    MyMessage msgMotion(CHILD_ID_MOTION, V_TRIPPED);
    MyMessage msgTemp(CHILD_ID_TEMP,V_TEMP);
    MyMessage msgBattery(CHILD_ID_BATT, V_VOLTAGE);
    
    
    void setup()  
    {  
      delay(100); // to settle power for radio
      
      gw.begin(NULL, NODE_ID);
    
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Motion & Temp Sensor", "1.0");
    
      pinMode(MOTION_INPUT_PIN, INPUT);      // sets the motion sensor digital pin as input
    
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_MOTION, S_MOTION);
      gw.present(CHILD_ID_TEMP, S_TEMP);
      gw.present(CHILD_ID_BATT, S_MULTIMETER);
      
      gw.sleep(20000); // Wait until motion sensor warmed-up and output returned low.    
    }
    
    void loop()     
    {     
      int sleeptime = 0;
      
      if (interruptReturn) {    // Woke up by rising pin
        gw.send(msgMotion.set("1"));  // Domoticz will take care of setting the node off after some delay
        sleeptime = DOMOTICZ_OFF_DELAY;  // sleep until domoticz sets the sensor off on its side    
      } 
      else 
      {
        float voltage = vcc.Read_Volts();    
        float temperature = readMCP9700(4,0);
    
        // send if variation is enough or if delay was reached       
        if (abs(temperature - lastTemperature) >= TEMP_SEND_THRESHOLD) {
          lastTemperature = temperature;
          sleeptime = 3000;
          loopCounter = 0;
          gw.send(msgTemp.set(temperature, 1));
        } 
    
        // send on first iteration, then if variation is enough  or if delay was reached
        if (abs(voltage - lastVoltage) >= 0.1) {
          sendBatteryReport(voltage);
          sleeptime = 3000;
          loopCounter = 0;
          lastVoltage = voltage;      
        }
    
        if (loopCounter++ * TEMP_SEND_FREQ >= MINIMUM_SEND_INTERVAL) {
          loopCounter = 0;
          sleeptime = 3000;      
          gw.send(msgTemp.set(temperature, 1));
          sendBatteryReport(voltage);        
        }
      }  
    
      if (sleeptime) {
        gw.sleep(sleeptime); // Make sure everything is stable before start to sleep with interrupts. (don't use "gw.wait()" here). Tests shows false trip ~2s after battery report otherwise.
      }
      interruptReturn = gw.sleep(MOTION_INPUT_PIN-2, RISING, TEMP_SEND_FREQ);  
    }
    
    void sendBatteryReport(float voltage) {
      float perc = 100.0 * (voltage-VCC_MIN) / (VCC_MAX-VCC_MIN);
      gw.send(msgBattery.set(voltage, 2));          
      gw.sendBatteryLevel(static_cast<int>(perc));
    }
    
    // this function comes from Kevin Kessler's blog : http://blog.kkessler.com/2012/06/20/mcp9700/
    float readMCP9700(int pin,float offset)
    {
      analogReference(INTERNAL);
      for (int n=0;n<5;n++)
        analogRead(pin);
    
      int adc=analogRead(pin);
      float tSensor=((adc*(1.1/1024.0))-0.5+offset)*100;
      float error=244e-6*(125-tSensor)*(tSensor - -40.0) + 2E-12*(tSensor - -40.0)-2.0;
      float temp=tSensor-error;
    
      return temp;
    }
    

    Regards
    Mikael

    1 Reply Last reply
    0

    Hello! It looks like you're interested in this conversation, but you don't have an account yet.

    Getting fed up of having to scroll through the same posts each visit? When you register for an account, you'll always come back to exactly where you were before, and choose to be notified of new replies (either via email, or push notification). You'll also be able to save bookmarks and upvote posts to show your appreciation to other community members.

    With your input, this post could be even better 💗

    Register Login
    Reply
    • Reply as topic
    Log in to reply
    • Oldest to Newest
    • Newest to Oldest
    • Most Votes


    21

    Online

    12.0k

    Users

    11.2k

    Topics

    113.4k

    Posts


    Copyright 2025 TBD   |   Forum Guidelines   |   Privacy Policy   |   Terms of Service
    • Login

    • Don't have an account? Register

    • Login or register to search.
    • First post
      Last post
    0
    • MySensors
    • OpenHardware.io
    • Categories
    • Recent
    • Tags
    • Popular