A Digital-to-Analog Converter (DAC) translates discrete binary numbers from a microcontroller into a continuous, proportional analog voltage or current that physical components like speakers, amplifiers, or motor drivers can use. In a real circuit, a DAC changes a rigid digital logic environment—where signals are strictly locked to 0V or 3.3V—into a smooth, variable output capable of driving real-world analog equipment. Most basic Arduinos (like the Uno) have zero true DACs, while the ESP32 features built-in 8-bit DACs, and dedicated I2C chips like the MCP4725 offer 12-bit precision.
The Core Mechanism: Binary to Voltage
At the silicon level, a DAC takes a parallel or serial string of bits (e.g., 10110010) and uses an internal network of precision resistors or switched capacitors to generate a specific voltage. The most common architecture you will encounter in hobbyist and industrial breakout boards is the R-2R resistor ladder or the Sigma-Delta modulator. The microcontroller sends a digital command, and the DAC's internal circuitry connects a precise reference voltage ($V_{REF}$) to the output pin in a weighted proportion.
The output voltage is strictly bound by the DAC's reference voltage. If your DAC is powered by a 3.3V $V_{REF}$, it is physically impossible for it to output 5.0V without an external operational amplifier (op-amp) gain stage. According to All About Circuits' DAC fundamentals, the accuracy of this translation relies entirely on the stability of that reference voltage and the precision of the internal resistor network.
True DAC vs. PWM: The Most Common Confusion
If you ask a beginner how to get analog output from an Arduino, they will almost always point to the analogWrite() function. This is the single most common confusion in embedded electronics: PWM (Pulse Width Modulation) is not a DAC.
When you call analogWrite(pin, 128) on an Arduino Uno, the microcontroller does not output 2.5V. Instead, it outputs a 5V square wave that switches on and off thousands of times per second, spending exactly 50% of its time at 5V and 50% at 0V. The average voltage is 2.5V, but the actual signal is a harsh digital square wave.
As noted in the official Arduino analogWrite documentation, this PWM signal works fine for dimming an LED or controlling a DC motor's speed because the physical inertia of the filament or the motor's inductance naturally averages out the pulses. However, if you feed that raw PWM signal into an audio amplifier, you will hear a harsh, high-frequency whine. If you feed it into a sensitive analog-to-digital converter (ADC) for data logging, the reading will fluctuate wildly.
A true DAC outputs a steady, quiet DC voltage or a clean waveform without high-frequency switching noise. If you absolutely must use PWM as a pseudo-DAC, you have to build a hardware RC (resistor-capacitor) low-pass filter to smooth the square wave into a DC level, which introduces severe trade-offs in settling time and output ripple.
Worked Example: Calculating Resolution and Step Size
To understand how resolution impacts your circuit, let's run the math on two common scenarios: the internal DAC of an ESP32 versus a dedicated external I2C DAC chip.
The fundamental formula for a DAC's step size (also known as 1 LSB, or Least Significant Bit) is:
Step Size = $V_{REF}$ / ($2^{Resolution}$ - 1)
Scenario A: ESP32 Internal DAC (8-bit)
- Resolution: 8 bits ($2^8 = 256$ steps)
- $V_{REF}$: 3.3V
- Step Size: 3.3V / 255 = 12.94 mV per step
If you are trying to generate an audio sine wave, a 12.94 mV jump between every single sample introduces noticeable quantization noise (hiss) and distortion. It is entirely inadequate for precision DC voltage control.
Scenario B: MCP4725 External DAC (12-bit)
- Resolution: 12 bits ($2^{12} = 4096$ steps)
- $V_{REF}$: 3.3V
- Step Size: 3.3V / 4095 = 0.805 mV per step
If you need to output exactly 1.65V to bias a transistor or set a threshold on a comparator, you calculate the required binary value: 1.65V / 0.000805V = 2049. You send the integer 2049 over I2C, and the DAC outputs 1.650V with less than a millivolt of error. This is the difference between a blinking LED project and a functional piece of test equipment.
Where You Meet DACs in Practice
You will reach for a true DAC whenever a physical system requires a continuous, noise-free control signal. Common bench and jobsite applications include:
- Industrial 0-10V Control: Variable Frequency Drives (VFDs) and commercial dimmers use a 0-10V DC signal to set motor speed or light levels. A DAC paired with an op-amp gain circuit generates this exact control voltage.
- Audio Synthesis: Generating sine, triangle, or complex arbitrary waveforms for synthesizers or function generators requires the high sample rates and clean output of a true DAC.
- Programmable Power Supplies: Bench power supplies use a DAC to feed a reference voltage into an error amplifier, which then regulates the main power transistors to hold the output at the exact voltage you dialed in.
- Sensor Simulation: When testing an ADC or a microcontroller's data-logging code, a DAC is used to inject highly precise, known voltages to verify the system's accuracy.
Decision Tree: Which DAC Should You Actually Use?
Selecting the right DAC depends entirely on your required speed, resolution, and interface. Use this decision matrix to pick the right silicon for your board.
| Application Need | Required Specs | Concrete Part Pick | Interface / Notes |
|---|---|---|---|
| Basic DC Voltage / Sensor Sim | 12-bit, Low Speed, Non-Volatile | Microchip MCP4725 | I2C. Includes EEPROM to save state on power loss. |
| Audio / Basic Waveforms | 8-bit, Medium Speed, Free | ESP32 Internal DAC | Native GPIO (Pins 25/26). No extra parts needed. |
| Precision Lab Equipment | 16-bit, Ultra-Low Noise, Multi-Channel | TI DAC8568 | SPI. 8 channels, internal precision voltage reference. |
| High-Frequency RF / Sine Waves | 28-bit DDS, 25MHz Clock | Analog Devices AD9833 | SPI. Dedicated waveform generator, not for DC control. |
If you are building a custom programmable power supply, a motor controller, or a sensor simulator and need a reliable, easy-to-code DC voltage, buy the MCP4725 breakout board (typically priced between $3 and $6). It requires only two I2C wires, operates natively at 3.3V or 5V, and works flawlessly with the standard Adafruit_MCP4725 library in the Arduino IDE. For 90% of embedded hobbyist and prototyping tasks that require true analog output, the MCP4725 is the definitive default choice.






