HOW ESP32-CAM ADC, analogRead

Hi,
after many hours,
how can I use the ADC pins to read analog values with the ESP32-CAM Board?

Best regards

What have you tried ?

Post a pinout of your ESP32 CAM board. I bet you may find that the A:D pins are not exposed.

If you remember this part of the code:

 config.ledc_channel = LEDC_CHANNEL_0;
  config.ledc_timer   = LEDC_TIMER_0;
  config.pin_d0       = GPIO_NUM_5; //Y2
  config.pin_d1       = GPIO_NUM_18; //Y3
  config.pin_d2       = GPIO_NUM_19; //Y4
  config.pin_d3       = GPIO_NUM_21; //Y5
  config.pin_d4       = GPIO_NUM_36; //Y6
  config.pin_d5       = GPIO_NUM_39; //Y7
  config.pin_d6       = GPIO_NUM_34; //Y8
  config.pin_d7       = GPIO_NUM_35; // Y9
  config.pin_xclk     = GPIO_NUM_0; //XCLK
  config.pin_pclk     = GPIO_NUM_22; //PCLK
  config.pin_vsync    = GPIO_NUM_25; //VSSYNC
  config.pin_href     = GPIO_NUM_23; // HREF
  config.pin_sscb_sda = GPIO_NUM_26; //SIOD
  config.pin_sscb_scl = GPIO_NUM_27; //SIOC
  config.pin_pwdn     = GPIO_NUM_32; //PWDN

It eats up the ADC1 pins.

If you are not using WiFi you may get ADC2 working. Here are the deets on ADC2. Analog to Digital Converter (ADC) - ESP32 - — ESP-IDF Programming Guide latest documentation (espressif.com).

Almost forgot, you can program the ULP to do A:D reads. The ULP is the 2nd processer. The deets are in the link from the previous post.

Hi,
yes correct.
I don´t want to use the SD Card.
Also the pins GPIO12 - GPIO15 for ADC2 must be free, or not?
The ADC2 must not work when I stream video over WiFi.

I´m not an expert in programming, has somebody example code for ULP?

  //...
  #define POTI_PIN 12
  pinMode(POTI_PIN,INPUT);
  adcAttachPin(POTI_PIN);
  analogReadResolution(11); // from an example, normally 12?
  analogSetAttenuation(ADC_6db);  // Filtering?
} // SETUP END

void loop() {  
  PotiValue = analogRead(POTI_PIN); // is global
  Serial.print("0-4095 PotiValue: "); Serial.println(PotiValue);  
} // PROGRAMM ENDE !

In the normal way;

ADvalue = analogRead(GPIOpin);

All the exposed GPIO pins on the ESP32CAM are Analog pins apart from GPI016.

But the exposed pins are also used by the SD card, so there is likely a conflict if the SD card is in use.

Hi,
ADvalue = analogRead(GPIOpin); do not work! ADvalue = 0 constant.
I don't use the SD card and I don't have any active librarys.

If someone has the chance, give it a try.
For the ESP32 without the CAM, no problem.

Humm, a code snippet does not show how the analog pin was setup.

Analog pins on the ESP32's ADC1 can be found here, Analog to Digital Converter (ADC) - ESP32 - — ESP-IDF Programming Guide latest documentation (espressif.com). One will see GPIO_NUM_12 is NOT an analog pin of ADC1.

That defination is made in setup(), fracking code snippets, how does

the loop() function know which analog pin is the potty pin?

GPIO_NUM_12 is ADC2_5 !

Cool! DId you initialze ADC2?

here is the code, I am of the opinion that analogRead does not work with ESP32-CAM.

#include "esp_camera.h"
#include <WiFi.h>
#include <Arduino.h>

//
// WARNING!!! PSRAM IC required for UXGA resolution and high JPEG quality
//            Ensure ESP32 Wrover Module or other board with PSRAM is selected
//            Partial images will be transmitted if image exceeds buffer size
//

// Select camera model
#define CAMERA_MODEL_AI_THINKER // Has PSRAM

#include "camera_pins.h"

// print the received signal strength:

const char* ssid = "XXXXXXXXXXXXXXXXXXX"; 
const char* password = "XXXXXXXXXXXXXXXXXXXX"; 

// Set web server port number to 80
//WiFiServer server(555);

void startCameraServer();

// Set your Static IP address
IPAddress local_IP(192, 168, 2, 120); // local_IP(192, 168, 178, 210); 
// Set your Gateway IP address
IPAddress gateway(192, 168, 2, 1); // gateway(192, 168, 178, 1); 
IPAddress subnet(255, 255, 255, 0);
///IPAddress primaryDNS(8, 8, 8, 8); //optional
///IPAddress secondaryDNS(8, 8, 4, 4); //optional

void setup() {
  Serial.begin(115200);
  Serial.setDebugOutput(true);
  Serial.println();

  camera_config_t config;
  config.ledc_channel = LEDC_CHANNEL_0;
  config.ledc_timer = LEDC_TIMER_0;
  config.pin_d0 = Y2_GPIO_NUM;
  config.pin_d1 = Y3_GPIO_NUM;
  config.pin_d2 = Y4_GPIO_NUM;
  config.pin_d3 = Y5_GPIO_NUM;
  config.pin_d4 = Y6_GPIO_NUM;
  config.pin_d5 = Y7_GPIO_NUM;
  config.pin_d6 = Y8_GPIO_NUM;
  config.pin_d7 = Y9_GPIO_NUM;
  config.pin_xclk = XCLK_GPIO_NUM;
  config.pin_pclk = PCLK_GPIO_NUM;
  config.pin_vsync = VSYNC_GPIO_NUM;
  config.pin_href = HREF_GPIO_NUM;
  config.pin_sscb_sda = SIOD_GPIO_NUM;
  config.pin_sscb_scl = SIOC_GPIO_NUM;
  config.pin_pwdn = PWDN_GPIO_NUM;
  config.pin_reset = RESET_GPIO_NUM;
  config.xclk_freq_hz = 20000000;
  config.pixel_format = PIXFORMAT_JPEG;
  
  // if PSRAM IC present, init with UXGA resolution and higher JPEG quality
  //                      for larger pre-allocated frame buffer.
  if(psramFound()){
    config.frame_size = FRAMESIZE_UXGA;
    config.jpeg_quality = 10;
    config.fb_count = 2;
  } else {
    config.frame_size = FRAMESIZE_SVGA;
    config.jpeg_quality = 12;
    config.fb_count = 1;
  }

//#if defined(CAMERA_MODEL_ESP_EYE)
 // pinMode(13, INPUT_PULLUP);
 // pinMode(14, INPUT_PULLUP);
//#endif

  // camera init
  esp_err_t err = esp_camera_init(&config);
  if (err != ESP_OK) {
    Serial.printf("Camera init failed with error 0x%x", err);
    return;
  }

  sensor_t * s = esp_camera_sensor_get();
  // initial sensors are flipped vertically and colors are a bit saturated
  if (s->id.PID == OV3660_PID) {
  //  s->set_vflip(s, 1); // flip it back
    s->set_brightness(s, 1); // up the brightness just a bit
    s->set_saturation(s, -2); // lower the saturation
  }
  
  // drop down frame size for higher initial frame rate
  s->set_framesize(s, FRAMESIZE_XGA); //FRAMESIZE_QVGA <- HIER standard Auflösung ändern !!!
  s->set_vflip(s, 1);
  s->set_hmirror(s, 1);
 // s->set_quality(s, 30); 

//#if defined(CAMERA_MODEL_M5STACK_WIDE) || defined(CAMERA_MODEL_M5STACK_ESP32CAM)
//  s->set_vflip(s, 1);
//  s->set_hmirror(s, 1);
//#endif

// Configures static IP address
  if (!WiFi.config(local_IP, gateway, subnet)) { // , primaryDNS, secondaryDNS
    Serial.println("STA Failed to configure");
  }
  
  WiFi.begin(ssid, password);

  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.println("WiFi connected");

  startCameraServer();

  Serial.print("Camera Ready! Use 'http://");
  Serial.print(WiFi.localIP());
  Serial.println("' to connect");

 // #define POTI_PIN 12 // ADC2_5 !!!
  pinMode(12,INPUT);
  adcAttachPin(12);
 // analogReadResolution(11);
  //analogSetAttenuation(ADC_6db);
  
} // SETUP END

void loop() {
  
  Serial.print("0-4095 Potivalue: ");Serial.println(analogRead(12));  
   delay(500*1);
  
} // PROGRAMM ENDE !

I dont know how...
google only find examples for esp32 without cam

Clue4U Analog to Digital Converter (ADC) - ESP32 - — ESP-IDF Programming Guide latest documentation (espressif.com). i will not write the code for you but i will help with debugging.

An example of using ADC1 under the Arduio iDE using the A:D ESP32 API

#include <driver/adc.h>

void setup ()
{
 // set up A:D channels, refer: https://dl.espressif.com/doc/esp-idf/latest/api-reference/peripherals/adc.html
  adc1_config_width(ADC_WIDTH_12Bit);
  adc1_config_channel_atten(ADC1_CHANNEL_0, ADC_ATTEN_DB_11);// using GPIO 36
}

void fDoParticleDetector( void * parameter )
{
  /*
    ug/m3     AQI                 Lvl AQ (Air Quality)
    (air Quality Index)
    0-35     0-50                1   Excellent
    35-75    51-100              2   Average
    75-115   101-150             3   Light pollution
    115-150  151-200             4   moderate
    150-250  201-300             5   heavy
    250-500  >=300               6   serious
  */
  float ADbits = 4095.0f;
  float uPvolts = 3.3f;
  float adcValue = 0.0f;
  float dustDensity = 0.0f;
  float Voc = 0.6f; // Set the typical output voltage, when there is zero dust.
  const float K = 0.5f; // Use the typical sensitivity in units of V per 100ug/m3.
  xEventGroupWaitBits (eg, evtWaitForBME, pdTRUE, pdTRUE, portMAX_DELAY );
  TickType_t xLastWakeTime = xTaskGetTickCount();
  const TickType_t xFrequency = 100; //delay for mS
  for (;;)
  {
    //enable sensor led
    gpio_set_level( GPIO_NUM_4, HIGH ); // set gpio 4 to high to turn on sensor internal led for measurement
    esp_timer_start_once( oneshot_timer, 280 ); // trigger one shot timer for a 280uS timeout, warm up time.
    xEventGroupWaitBits (eg, evtDoParticleRead, pdTRUE, pdTRUE, portMAX_DELAY ); // event will be triggered by the timer expiring, wait here for the 280uS
    adcValue = float( adc1_get_raw(ADC1_CHANNEL_0) ); //take a raw ADC reading from the dust sensor
    gpio_set_level( GPIO_NUM_4, LOW );//Shut off the sensor LED
    adcValue = ( adcValue * uPvolts ) / ADbits; //calculate voltage
    dustDensity = (adcValue / K) * 100.0; //convert volts to dust density
    if ( dustDensity < 0.0f )
    {
      dustDensity = 0.00f; // make negative values a 0
    }
    if ( xSemaphoreTake( sema_PublishPM, 0 ) == pdTRUE )  // don't wait for semaphore to be available
    {
      xSemaphoreTake( sema_MQTT_KeepAlive, portMAX_DELAY );
      //log_i( "ADC volts %f Dust Density = %ug / m3 ", adcValue, dustDensity ); // print the calculated voltage and dustdensity
      MQTTclient.publish( topicInsidePM, String(dustDensity).c_str() );
      xSemaphoreGive( sema_MQTT_KeepAlive );
      x_eData.PM2 = dustDensity;
    }
    xLastWakeTime = xTaskGetTickCount();
    vTaskDelayUntil( &xLastWakeTime, xFrequency );
    //log_i( " high watermark % d",  uxTaskGetStackHighWaterMark( NULL ) );
  }
  vTaskDelete( NULL );
}// end fDoParticleDetector()

In the APi you'll see things like ADC2_CHANNEL_5 ADC2 channel 5 is GPIO12 (ESP32), GPIO16 (ESP32-S2) that you'd want to pay attention to.

ClueU:
You CANNOT use ADC2 with WiFi.

ClueU:
You CANNOT use ADC2 with WiFi.

ClueU:
You CANNOT use ADC2 with WiFi.

ClueU:
You CANNOT use ADC2 with WiFi.

ClueU:
You CANNOT use ADC2 with WiFi.

ClueU:
You CANNOT use ADC2 with WiFi.

Got it?

Why is a board developed without ADC pins to use?
Only access to ADC2 Pins, without Wifi, useless... :frowning:
https://www.mischianti.org/2021/09/02/esp32-cam-high-resolution-pinout-and-specs/

Have you considered the implication of post#8?

yep