So I need to output a varying voltage off an Arduino Mega in a range of 17 to 32 millivolts, which I've attempted to do by sending a PWM signal off the board into a low-pass filter which steps down the voltage.

This works, but the problem is that Arduino's analogWrite function accepts a value of 0 - 255 to represent the duty cycle of the PWM which isn't precise enough. A value of 1 yields around 20 millivolts and a value of 2 yields around 40 millivolts. Is there some way to have a duty cycle that is more precise than the 0 - 255 range like 0 - 1023 (I think even this isn't really precise enough)? Or is there a better way to get precise voltage output?

The mega is running on and outputting a max voltage of 5 volts, and the low pass filter contains an 11 kiloohm resistor and a 1 microfarad capacitor.

  • 1
    $\begingroup$ why not also drop the voltage when you filter it? then you'd have more of the 255 range to use rather than just 1 and 2. a simple voltage divider could do the trick. $\endgroup$
    – Octopus
    Commented May 7, 2014 at 22:46

1 Answer 1


analogWrite() does not support a higher range of duty cycle.

However the timers on the AVR chip do support higher precision/resolution, so you can bang the registers directly, especially if you don't need to use the rest of the Arduino libraries. I recommend using avr-gcc with avr-libc and avrdude for programming, and let go of Arduino IDE/libraries entirely.

You have up to 16 bit timers, where the duty cycle can be up to 0-65535. However, at 16 MHz, a 16 bit timer only ticks over 244 times a second, so the filter has to be very low-frequency and thus the lag in the output will be long (although the default PWM frequency for 8-bit timers is only 490 Hz or so, so only twice as good.)

The second thing you can do is output to a resistor divider. If you output to a 9.9k:100ohm divider, the voltage at the 1ohm resistor will vary from 0 to 50 mV even though the voltage across the top will vary from 0 to 5V. Note that the source impedance is kind-of high here, so you might want to re-buffer with an opamp if the load is low-impedance.


Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.