mirror of
https://github.com/RobTillaart/Arduino.git
synced 2024-09-19 16:46:11 -04:00
0.3.6 ACS712
This commit is contained in:
parent
ed5762da7b
commit
bb8c4a1d7b
@ -1,7 +1,7 @@
|
||||
//
|
||||
// FILE: ACS712.cpp
|
||||
// AUTHOR: Rob Tillaart, Pete Thompson
|
||||
// VERSION: 0.3.6
|
||||
// VERSION: 0.3.7
|
||||
// DATE: 2020-08-02
|
||||
// PURPOSE: ACS712 library - current measurement
|
||||
// URL: https://github.com/RobTillaart/ACS712
|
||||
@ -133,7 +133,7 @@ float ACS712::mA_AC_sampling(float frequency, uint16_t cycles)
|
||||
if (cycles == 0) cycles = 1;
|
||||
float sum = 0;
|
||||
|
||||
// float noiseLevel = _noisemV/_mVperStep;
|
||||
// float noiseLevel = _noisemV/_mVperStep;
|
||||
|
||||
for (uint16_t i = 0; i < cycles; i++)
|
||||
{
|
||||
@ -151,11 +151,11 @@ float ACS712::mA_AC_sampling(float frequency, uint16_t cycles)
|
||||
}
|
||||
float current = value - _midPoint;
|
||||
sumSquared += (current * current);
|
||||
// not adding noise squared might be more correct for small currents.
|
||||
// if (abs(current) > noiseLevel)
|
||||
// {
|
||||
// sumSquared += (current * current);
|
||||
// }
|
||||
// not adding noise squared might be more correct for small currents.
|
||||
// if (abs(current) > noiseLevel)
|
||||
// {
|
||||
// sumSquared += (current * current);
|
||||
// }
|
||||
}
|
||||
sum += sqrt(sumSquared / samples);
|
||||
}
|
||||
@ -416,7 +416,7 @@ uint16_t ACS712::getMaximum(uint16_t milliSeconds)
|
||||
{
|
||||
uint16_t maximum = _analogRead(_pin);
|
||||
|
||||
// find minimum
|
||||
// find maximum
|
||||
uint32_t start = millis();
|
||||
while (millis() - start < milliSeconds)
|
||||
{
|
||||
@ -444,11 +444,11 @@ void ACS712::setADC(uint16_t (* f)(uint8_t), float volts, uint16_t maxADC)
|
||||
//
|
||||
uint16_t ACS712::_analogRead(uint8_t pin)
|
||||
{
|
||||
// if extern ADC is defined use it.
|
||||
// if external ADC is defined use it.
|
||||
if (_readADC != NULL) return _readADC(pin);
|
||||
return analogRead(pin);
|
||||
}
|
||||
|
||||
|
||||
// -- END OF FILE --
|
||||
// -- END OF FILE --
|
||||
|
||||
|
@ -2,7 +2,7 @@
|
||||
//
|
||||
// FILE: ACS712.h
|
||||
// AUTHOR: Rob Tillaart, Pete Thompson
|
||||
// VERSION: 0.3.6
|
||||
// VERSION: 0.3.7
|
||||
// DATE: 2020-08-02
|
||||
// PURPOSE: ACS712 library - current measurement
|
||||
// URL: https://github.com/RobTillaart/ACS712
|
||||
@ -13,7 +13,7 @@
|
||||
|
||||
#include "Arduino.h"
|
||||
|
||||
#define ACS712_LIB_VERSION (F("0.3.6"))
|
||||
#define ACS712_LIB_VERSION (F("0.3.7"))
|
||||
|
||||
|
||||
// ACS712_FF_SINUS == 1.0/sqrt(2) == 0.5 * sqrt(2)
|
||||
@ -133,5 +133,5 @@ class ACS712
|
||||
};
|
||||
|
||||
|
||||
// -- END OF FILE --
|
||||
// -- END OF FILE --
|
||||
|
||||
|
@ -6,12 +6,17 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/)
|
||||
and this project adheres to [Semantic Versioning](http://semver.org/).
|
||||
|
||||
|
||||
## [0.3.7] - 2023-05-20
|
||||
- add example **estimateMidPointAC.ino** #37
|
||||
- update readme.md (sampling trick #38).
|
||||
- minor edits.
|
||||
|
||||
|
||||
## [0.3.6] - 2023-04-19
|
||||
- add **autoMidPointDC(cycles)** see issue #35
|
||||
- add rounding to **autoMidPoint()**
|
||||
- update README.md
|
||||
|
||||
|
||||
## [0.3.5] - 2023-01-18
|
||||
- fix #33 failing build => issue 345 created @ arduino-ci
|
||||
- redo **setADC()**
|
||||
|
@ -19,6 +19,9 @@ ACS712 ACS(A0, 5.0, 1023, 100);
|
||||
// ACS712 ACS(25, 3.3, 4095, 185);
|
||||
|
||||
|
||||
uint32_t start, stop;
|
||||
|
||||
|
||||
void setup()
|
||||
{
|
||||
Serial.begin(115200);
|
||||
@ -27,6 +30,10 @@ void setup()
|
||||
Serial.print("ACS712_LIB_VERSION: ");
|
||||
Serial.println(ACS712_LIB_VERSION);
|
||||
|
||||
|
||||
// use simulation
|
||||
ACS.setADC(signal, 5, 1024);
|
||||
|
||||
ACS.autoMidPoint();
|
||||
Serial.print("MidPoint: ");
|
||||
Serial.print(ACS.getMidPoint());
|
||||
@ -37,13 +44,27 @@ void setup()
|
||||
|
||||
void loop()
|
||||
{
|
||||
int mA = ACS.mA_AC();
|
||||
delay(100);
|
||||
start = micros();
|
||||
// int mA = ACS.mA_AC();
|
||||
int mA = ACS.mA_AC_sampling();
|
||||
stop = micros();
|
||||
Serial.print("mA: ");
|
||||
Serial.print(mA);
|
||||
Serial.print(". Form factor: ");
|
||||
Serial.println(ACS.getFormFactor());
|
||||
Serial.print(ACS.getFormFactor());
|
||||
Serial.print(" time: ");
|
||||
Serial.println(stop - start);
|
||||
delay(5000);
|
||||
}
|
||||
|
||||
|
||||
// -- END OF FILE --
|
||||
// simulated 50 Hz signal
|
||||
uint16_t signal(uint8_t p)
|
||||
{
|
||||
return 512 + 400 * sin((micros() % 1000000) * (TWO_PI * 50 / 1e6));
|
||||
}
|
||||
|
||||
|
||||
// -- END OF FILE --
|
||||
|
||||
|
@ -0,0 +1,66 @@
|
||||
//
|
||||
// FILE: ACS712_20_AC_simulation.ino
|
||||
// AUTHOR: Rob Tillaart
|
||||
// PURPOSE: demo AC measurement with point to point
|
||||
// URL: https://github.com/RobTillaart/ACS712
|
||||
|
||||
|
||||
#include "ACS712.h"
|
||||
|
||||
|
||||
// Arduino UNO has 5.0 volt with a max ADC value of 1023 steps
|
||||
// ACS712 5A uses 185 mV per A
|
||||
// ACS712 20A uses 100 mV per A
|
||||
// ACS712 30A uses 66 mV per A
|
||||
|
||||
|
||||
ACS712 ACS(A0, 5.0, 1023, 100);
|
||||
// ESP 32 example (might requires resistors to step down the logic voltage)
|
||||
// ACS712 ACS(25, 3.3, 4095, 185);
|
||||
|
||||
|
||||
uint32_t start, stop;
|
||||
|
||||
|
||||
void setup()
|
||||
{
|
||||
Serial.begin(115200);
|
||||
while (!Serial);
|
||||
Serial.println(__FILE__);
|
||||
Serial.print("ACS712_LIB_VERSION: ");
|
||||
Serial.println(ACS712_LIB_VERSION);
|
||||
|
||||
// select simulated signal
|
||||
ACS.setADC(signal, 5, 1024);
|
||||
|
||||
ACS.autoMidPoint();
|
||||
Serial.print("MidPoint: ");
|
||||
Serial.print(ACS.getMidPoint());
|
||||
Serial.print(". Noise mV: ");
|
||||
Serial.println(ACS.getNoisemV());
|
||||
}
|
||||
|
||||
|
||||
void loop()
|
||||
{
|
||||
delay(100);
|
||||
start = micros();
|
||||
// int mA = ACS.mA_AC();
|
||||
int mA = ACS.mA_AC_sampling(50);
|
||||
stop = micros();
|
||||
Serial.print("mA: ");
|
||||
Serial.print(mA);
|
||||
Serial.print(" time: ");
|
||||
Serial.println(stop - start);
|
||||
delay(5000);
|
||||
}
|
||||
|
||||
|
||||
// simulation.
|
||||
uint16_t signal(uint8_t p)
|
||||
{
|
||||
return round(512 + 400 * sin((micros() % 1000000) * (TWO_PI * 50 / 1e6)));
|
||||
}
|
||||
|
||||
|
||||
// -- END OF FILE --
|
@ -0,0 +1,89 @@
|
||||
// FILE: estimateMidPointAC.ino
|
||||
// AUTHOR: Rob Tillaart
|
||||
// PURPOSE: experimental
|
||||
// URL: https://github.com/RobTillaart/ACS712/issues/37
|
||||
//
|
||||
// Estimates the midpoint by taking many (short-blocking) samples
|
||||
// instead of many samples in a long blocking period.
|
||||
// The function adjusts the confidence (or quality) of the midpoint
|
||||
// depending on the value read.
|
||||
// This code is experimental and meant to investigate a non-blocking
|
||||
// way to find the midPoint for the ACS712 when measuring AC currents.
|
||||
//
|
||||
// It will not be included in the library
|
||||
//
|
||||
// Use with care.
|
||||
|
||||
|
||||
#include "Arduino.h"
|
||||
|
||||
|
||||
uint32_t start, stop;
|
||||
int _pin = A0;
|
||||
uint32_t count = 0;
|
||||
volatile uint16_t mp;
|
||||
float conf = 0;
|
||||
|
||||
|
||||
uint16_t estimateMidPointAC(float &confidence, bool reset = false)
|
||||
{
|
||||
static bool _firstCall = true;
|
||||
static float _minimum, _maximum, _confidence;
|
||||
|
||||
int value = analogRead(_pin);
|
||||
if (_firstCall || reset)
|
||||
{
|
||||
_firstCall = false;
|
||||
_minimum = _maximum = value;
|
||||
_confidence = 0;
|
||||
confidence = _confidence;
|
||||
return _minimum;
|
||||
}
|
||||
if (value > _maximum)
|
||||
{
|
||||
_maximum = value;
|
||||
_confidence /= 2;
|
||||
}
|
||||
else if (value < _minimum)
|
||||
{
|
||||
_minimum = value;
|
||||
_confidence /= 2;
|
||||
}
|
||||
else if (_confidence < 100)
|
||||
{
|
||||
_confidence += 1;
|
||||
}
|
||||
confidence = _confidence;
|
||||
return (_minimum + _maximum) / 2;
|
||||
}
|
||||
|
||||
|
||||
void setup()
|
||||
{
|
||||
Serial.begin(115200);
|
||||
while (!Serial);
|
||||
Serial.println(__FILE__);
|
||||
}
|
||||
|
||||
|
||||
void loop()
|
||||
{
|
||||
count++;
|
||||
start = micros();
|
||||
mp = estimateMidPointAC(conf, true);
|
||||
stop = micros();
|
||||
Serial.print(millis());
|
||||
Serial.print("\t");
|
||||
Serial.print(count);
|
||||
Serial.print("\t");
|
||||
Serial.print(conf);
|
||||
Serial.print("\t");
|
||||
Serial.print(mp);
|
||||
Serial.print("\t");
|
||||
Serial.print(stop - start);
|
||||
Serial.println();
|
||||
delay(random(100));
|
||||
}
|
||||
|
||||
|
||||
// -- END OF FILE --
|
@ -21,7 +21,7 @@
|
||||
"type": "git",
|
||||
"url": "https://github.com/RobTillaart/ACS712.git"
|
||||
},
|
||||
"version": "0.3.6",
|
||||
"version": "0.3.7",
|
||||
"license": "MIT",
|
||||
"frameworks": "arduino",
|
||||
"platforms": "*",
|
||||
|
@ -1,5 +1,5 @@
|
||||
name=ACS712
|
||||
version=0.3.6
|
||||
version=0.3.7
|
||||
author=Rob Tillaart <rob.tillaart@gmail.com>, Pete Thompson <pete.thompson@yahoo.com>
|
||||
maintainer=Rob Tillaart <rob.tillaart@gmail.com>
|
||||
sentence=ACS712 library for Arduino.
|
||||
|
@ -112,6 +112,11 @@ Not tested, but looks compatible - same formula as above
|
||||
|
||||
## Interface
|
||||
|
||||
```cpp
|
||||
#include ACS712.h
|
||||
```
|
||||
|
||||
|
||||
#### Base
|
||||
|
||||
- **ACS712(uint8_t analogPin, float volts = 5.0, uint16_t maxADC = 1023, float mVperAmpere = 100)** constructor.
|
||||
@ -141,6 +146,23 @@ A negative value indicates the current flows in the opposite direction.
|
||||
- 0.2.8 the parameter samples allow to average over a number of samples.
|
||||
|
||||
|
||||
#### mA_AC_sampling performance trick.
|
||||
|
||||
A trick to sample faster is to set the frequency to 2 times the actual frequency so to 100 or 120 Hz.
|
||||
This results in sampling only half a period and the same current will be measured.
|
||||
Advantage is that the function only blocks for ~10 ms @ 50Hz (8.5 @ 60Hz).
|
||||
The drawback is about 4x as many variation.
|
||||
So only use if the performance (or less blocking) is needed.
|
||||
|
||||
In a similar way one can increase the accuracy (reducing the variation)
|
||||
by setting the frequency a factor 2 lower (25 and 30 Hz).
|
||||
Drawback is a far longer blocking time.
|
||||
|
||||
Use with care!
|
||||
|
||||
See - https://github.com/RobTillaart/ACS712/issues/38
|
||||
|
||||
|
||||
#### Midpoint
|
||||
|
||||
The midpoint is the (raw) zero-reference for all current measurements.
|
||||
@ -153,7 +175,7 @@ Since 0.3.0 all midpoint functions return the actual midPoint.
|
||||
Parameter must be between 0 and maxADC/2, otherwise midpoint is not changed.
|
||||
- **uint16_t getMidPoint()** read the value set / determined.
|
||||
- **uint16_t incMidPoint()** manual increase midpoint, e.g. useful in an interactive application.
|
||||
Will not increase if midpoint equals macADC.
|
||||
Will not increase if midpoint equals maxADC.
|
||||
- **uint16_t decMidPoint()** manual decrease midpoint.
|
||||
Will not decrease if midpoint equals 0.
|
||||
- **uint16_t resetMidPoint()** resets the midpoint to the initial value of maxADC / 2 as in the constructor.
|
||||
|
Loading…
Reference in New Issue
Block a user