Hey everyone, I’m working on a project using an ESP32 with the Mega 5MP SPI Camera Module (the one with autofocus). It’s deployed outdoors inside a scarecrow product (scarow.com) so it’s exposed to all kinds of lighting — blazing sun, overcast days, early dawn, you name it.
Here’s the problem: the image exposure is all over the place depending on the time of day and weather. On sunny days the picture looks fine with whatever the default settings are. But as soon as it gets cloudy or it’s early morning, the image is way too dark — almost unusable.
I haven’t explicitly called any exposure-related functions in my code yet. Everything’s basically at factory defaults. Is this a known issue with this camera module outdoors? Anyone else dealt with this?
Thanks for the details. That’s a pretty challenging environment for any camera module, especially one using auto-exposure outdoors across such a wide range of lighting conditions.
Before we dig deeper, can you clarify a couple things?
Have you tried calling setAutoExposure() at all yet, or is the camera completely running on whatever the sensor’s default power-on state is?
What firmware / library are you using to interface with the camera? (e.g., the ArduCAM library, or something custom?)
If you’re able to grab any sample images from the dark vs bright scenarios, that would help — but even just confirming the behavior is enough for now.
Good questions. So I hadn’t touched any exposure settings initially — just default state after power-up. That’s what gave me decent sunny-day images but terrible low-light performance.
Then I tried explicitly calling:
camera.setAutoExposure(0);
And that flipped the problem completely. Now when it’s early morning the image looks genuinely good, but for most of the day — basically any time there’s decent sunlight — the image is totally overexposed, like washed-out white.
So I’ve got two bad options:
Default AE: fails when it’s dark/cloudy
setAutoExposure(0): fails when it’s bright
I’m kind of stuck. I’m using the standard ArduCAM SPI library for this module. What I don’t understand is what setAutoExposure(0) is actually doing under the hood — is it disabling AE or setting it to some manual mode? The naming is confusing.
That’s really helpful context, and I think I see what’s going on.
Here’s the situation: the internal auto-exposure algorithm on this sensor isn’t really built to handle the extreme variance you’re getting outdoors — going from dark early-morning light all the way to bright noon sun. It’s a fixed algorithm with a limited adjustment range, and outdoor lighting swings can easily exceed what it can compensate for dynamically.
So what you’re seeing makes sense:
Default AE (on): The algorithm tries to brighten the scene but bottoms out in low light — it can’t push the exposure far enough for cloudy or dawn conditions, so you get dark images.
setAutoExposure(0) (off): It stops trying to adjust entirely and the sensor operates at some fixed internal exposure level. In low light that fixed level happens to look okay, but as soon as the sun comes out, it’s way too much light for that fixed setting — hence overexposure.
Neither mode is going to handle the full range of outdoor lighting reliably on its own.
Okay, that explains the “why” — appreciate the breakdown. So what’s the right path forward here? I can’t be swapping exposure modes based on time of day, that’s way too hacky for a product that needs to run unattended.
Is there a way to find some middle ground? Like some kind of manual exposure compromise that works across most conditions?
Yeah, that’s exactly the direction I’d recommend: ditch auto-exposure entirely and go with a calibrated manual exposure.
The idea is to find a single fixed exposure time that’s a compromise — bright enough that you still get usable detail during darker morning hours, but not so bright that noon sunlight blows everything out.
Here’s the approach I’d take:
Disable AE with setAutoExposure(0) so the sensor stops trying to adjust on its own.
Set manual exposure — you’ll want to look at the register-level controls or any manual exposure APIs your library exposes. Depending on the ArduCAM library version, you may need to write to the sensor registers directly for exposure time / gain.
Test incrementally — start with a moderate exposure value, capture images at different times of day (early morning, noon, cloudy afternoon) and see where you land.
Find the sweet spot — you’re looking for the exposure value where sunny images aren’t clipping highlights and morning images aren’t crushed into black. It won’t be perfect at either extreme, but it should be consistently usable.
Lock it in — once you find that value, hardcode it so the camera always starts with that calibrated setting.
This avoids both the random overexposure from setAutoExposure(0) and the low-light failures of default AE. You’re trading dynamic range for consistency, which sounds like what you need for an unattended outdoor deployment.
Give that a shot and let us know how the test images turn out at different times of day.