When investigating the working of sensors for AC and DC current measurement, the ACS712 Hall-effect module remains a ubiquitous bench staple. The direct answer to how it operates is straightforward: it outputs a ratiometric analog voltage centered at half the supply voltage, which shifts proportionally as current flows through its internal copper conduction path. For the popular ACS712ELCTR-20A-T variant, the sensitivity is exactly 100 mV/A, meaning a 10A load shifts the output by 1.0V from its baseline.
The Hall Effect: Working of Sensors Explained
The fundamental sensing principle relies on the Hall effect. When current flows through the primary conduction path (pins 1-2 to pins 3-4), it generates a localized magnetic field. A Hall element inside the IC measures this flux density and converts it into a proportional voltage. Because the magnetic coupling is internal to the IC package, the sensor provides 2.1 kV of galvanic isolation between the high-current path and the low-voltage signal pins, allowing you to measure load current without breaking the circuit or inserting a shunt resistor.
Critically, the ACS712 output is ratiometric. This means the zero-current offset voltage and the sensitivity scale directly with the supply voltage (VCC). If VCC sags from 5.00V to 4.80V, both the 2.5V baseline offset and the 100 mV/A sensitivity drop by 4%. Understanding this ratiometric behavior is the difference between a stable measurement system and one that drifts wildly when powered from a noisy USB bus.
ACS712 Variants and Electrical Specifications
The ACS712 family is manufactured in three primary current ranges, each with a distinct sensitivity and internal trace resistance. Selecting the wrong variant forces your microcontroller's ADC to resolve tiny voltage changes, amplifying noise. Always choose the lowest range that safely encompasses your maximum expected load.
| Part Number | Range | Sensitivity | Offset (at 5V) | Trace Resistance | Bandwidth |
|---|---|---|---|---|---|
| ACS712ELCTR-05B | ±5A | 185 mV/A | 2.50V | 1.2 mΩ | 80 kHz |
| ACS712ELCTR-20A | ±20A | 100 mV/A | 2.50V | 1.5 mΩ | 80 kHz |
| ACS712ELCTR-30A | ±30A | 66 mV/A | 2.50V | 1.2 mΩ | 80 kHz |
| ACS723LLCTR-10AB* | ±10A | 400 mV/A | 1.65V | 1.0 mΩ | 80 kHz |
*Note: The ACS723 is included as a modern, 3.3V-native alternative. Unlike the 5V-only ACS712, the ACS723 operates natively at 3.3V, eliminating the need for voltage dividers when wiring to ESP32 or Raspberry Pi Pico analog inputs.
Wiring to 5V and 3.3V Microcontrollers
A frequent point of failure in embedded projects is conflating 5V analog outputs with 3.3V microcontroller ADC limits. The ACS712 requires a 4.5V to 5.5V supply to operate correctly. If you power it with 5V, the output swings from 0V to 5V. Feeding a 5V signal into an ESP32 GPIO will permanently damage the pin.
| ACS712 Pin | Arduino Uno (5V) | ESP32 (3.3V ADC) | Notes |
|---|---|---|---|
| VCC | 5V | 5V (External or USB) | Supply range: 4.5V - 5.5V |
| GND | GND | GND | Must share common ground |
| OUT | A0 (Direct) | GPIO 34 (via Divider) | ESP32 requires 10kΩ/10kΩ divider |
The ESP32 Voltage Divider Fix: To safely interface the 0-5V output to the ESP32's 0-3.3V ADC, use two 10kΩ resistors in series from the OUT pin to GND, and tap the middle junction to GPIO 34. This halves the voltage. You must account for this 0.5 scaling factor in your software math.
Output Signal Math: Converting Raw ADC to Amps
The output of the ACS712 is strictly an analog voltage. To convert the raw ADC integer into a physical Amperage value, you must reverse the sensor's transfer function. The governing equation is:
I = (V_out - V_offset) / Sensitivity
Let's work through a concrete numeric example using an Arduino Uno (10-bit ADC, 0-1023) and the 20A sensor (100 mV/A sensitivity). Assume VCC is exactly 5.00V.
- Determine V_offset: 5.00V / 2 = 2.50V.
- Calculate ADC Resolution: 5.00V / 1024 steps = 0.00488V per step (4.88 mV/step).
- Read Raw ADC: Suppose the microcontroller reads
614. - Convert to Voltage: 614 * 0.00488V = 2.996V.
- Apply Transfer Function: (2.996V - 2.50V) / 0.100 V/A = 4.96 Amps.
For AC current measurement, the output voltage oscillates above and below the 2.5V offset. You must sample the ADC at a high rate (e.g., 1 kHz), calculate the RMS (Root Mean Square) of the voltage deltas over one full AC cycle (20ms for 50Hz, 16.6ms for 60Hz), and then apply the sensitivity divisor.
Calibration and Interference Mitigation
The working of sensors based on magnetic fields makes them inherently susceptible to environmental noise. If your readings are jittery or drifting, you are likely encountering one of three common interference sources:
- External Magnetic Fields: Permanent magnets, transformers, or adjacent high-current DC traces will bias the Hall element. Keep the sensor at least 2 cm away from AC transformers and stepper motors.
- VCC Ripple: Because the sensor is ratiometric, any noise on the 5V supply line injects directly into the OUT pin. If powering from a switching buck converter, add a 100µF electrolytic and a 0.1µF ceramic capacitor across the VCC and GND pins on the breakout board.
- ADC Non-Linearity: The ESP32's SAR ADC is notoriously non-linear near the 0V and 3.3V rails. By using the voltage divider to center the zero-current offset at ~1.25V (mid-scale for the ESP32), you keep the operating point in the ADC's most linear region.
Software Zero-Offset Calibration
Never hardcode the 2.5V offset in your firmware. Component tolerances and resistor divider variances mean the actual zero-current voltage might be 2.48V or 2.53V. Implement a startup calibration routine that samples the sensor with zero load to establish the true baseline.
// ESP32 Zero-Current Calibration Snippet
const int ADC_PIN = 34;
const int SAMPLES = 1000;
const float VCC = 5.0;
const float DIVIDER_RATIO = 0.5; // 10k/10k divider
const float SENSITIVITY = 0.100; // 100mV/A for 20A variant
float zeroOffsetVoltage = 0;
void calibrateSensor() {
long sum = 0;
for (int i = 0; i < SAMPLES; i++) {
sum += analogRead(ADC_PIN);
delayMicroseconds(500);
}
float avgADC = (float)sum / SAMPLES;
// Convert 12-bit ADC to voltage, accounting for divider
zeroOffsetVoltage = (avgADC / 4095.0) * 3.3 / DIVIDER_RATIO;
Serial.printf("Calibrated Offset: %.3f V\n", zeroOffsetVoltage);
}
float readCurrentDC() {
int raw = analogRead(ADC_PIN);
float vOut = (raw / 4095.0) * 3.3 / DIVIDER_RATIO;
return (vOut - zeroOffsetVoltage) / SENSITIVITY;
}
By anchoring your math to a dynamically sampled offset and respecting the ratiometric nature of the Hall effect, you transform a jittery, $3 breakout board into a reliable measurement instrument capable of tracking DC motor stalls or AC compressor loads with sub-amp precision.






