Blog
OV7670 Camera Module with FIFO
OV7670 is a CMOS camera chip with FIFO, widely used in various embedded systems. It features low power consumption, high sensitivity and high image quality, making it suitable for image acquisition and processing applications.
The OV7670 with FIFO module is a type of module specifically designed for slow MCU to achieve image acquisition control, featuring a buffer storage space. This module incorporates a FIFO (First Input First Output) memory chip, along with a 300,000 pixels CMOS image sensor chip, a 3.6mm focal length lens and lens mount, and various different power supplies required by the onboard CMOS chip (power requirements are detailed in the chip’s data file). The board also has control pins and data pins, facilitating operation and use.
The module integrates the image sensor and the image buffer device AL422B, effectively resolving the speed bottleneck issue in image acquisition for low-end microcontrollers.
What is the OV7670 with FIFO, and why use FIFO?
To briefly explain, FIFO means “first in, first out”. It is similar to a data storage device that can only perform data reading and writing in sequence.
So why do we need a FIFO? The IO ports of the OV7670 camera itself have a very high speed, which is beyond the reach of ordinary microcontrollers. The GPIO ports of the development boards we usually use simply cannot meet the requirements of the camera. Therefore, it is impossible to directly perform data reading and writing. For example, the teacher is giving a lecture at 4G-like speed. You are a student with poor 2G performance. After the teacher says one sentence, you haven’t even had time to react, and the teacher starts the next sentence. In the end, you get nothing. So how should a student with poor grades learn? At this time, a FIFO is needed. You can think of it as a tape recorder. The teacher speaks at 4G speed, and the tape recorder records at 4G speed. When you want to listen, pause the (give the CLK clock signal) for one sentence, and then you will have heard all of it. The same is true for microcontrollers.
What is SCCB?
- SCCB is a bus developed by OmniVision, and it is widely used in the OV series image sensors. Therefore, image sensors using the OV technology generally cannot do without the SCCB bus protocol.
- The SCCB interface is similar to IIC. It has two working modes: master-slave mode and master-master mode. There are three lines (SCCB ENABLE/SCCB CLK/SCCB DATA), and we usually use the Clock and Data lines. The schematic diagram is as follows:
OV7670 Working Principle
The combination of OV7670 and FIFO requires attention to certain timing. A simple and effective combination is as follows: The field synchronization of OV is connected to the external interrupt of the MCU (triggered by the rising edge). When a field synchronization arrives (after a narrow high level, followed by the effective field synchronization [low level]), the write enable of FIFO is enabled. Thus, the data is written into FIFO in sequence under the control of the line synchronization and the MCU according to the pixel clock. When one frame of image data has entered the FIFO, it also indicates that the next frame of data is coming, that is, the rising edge of the next field synchronization is approaching. When the next rising edge triggers and enters the interrupt, the MCU should turn off the write enable of FIFO and then start reading the data from FIFO. After the data is read, the next data acquisition can begin. Therefore, the first step in debugging is a normally working external interrupt. It is important to clear the interrupt flag first when entering the external interrupt, otherwise the system may be in an interrupt nesting state.
Another point is the reset of the read and write pointers of FIFO. The reset of these two pointers of FIFO is very important for data synchronization. If they cannot be reset normally, the obtained image may be shifted or distorted. According to the FIFO datasheet, there are two ways to reset the pointers: Write Reset and Read Reset; RE RRST, WE WRST. When resetting for reading, Read Reset is used, requiring both RE and OE to be low, and then two or more read clocks are repeated when the read reset pin is low. Write Reset uses the code “WE WRST” . When WE is high, the write reset pin is pulled low. After a brief demonstration, raise the reset pin. The state of the WE pin does not need to be managed anymore and can be controlled normally by the interrupt program. Just remember that WE should be high before the write reset.
After one frame of data is buffered into FIFO, the MCU turns off the write enable of FIFO and starts reading the data from FIFO for processing. At this time, the processing can be writing the data to LCD for display or storing it in SD card to complete the photo-taking function. A relatively simple format for data storage is BMP. It only requires adding an appropriate BMP file header to each frame of data and then filling in the image data in sequence. The demonstration project has implemented the functions of image display and BMP storage, similar to a simple digital camera.
OV7670 Feature
- High sensitivity, low voltage, suitable for embedded applications
- Standard SCCB interface, compatible with IIC interface
- Supports RawRGB, RGB (GBR4:2:2, RGB565/RGB555/RGB444), YUV (4:2:2) and YCbCr (4:2:2) output formats
- Supports VGA, CIF, and various output sizes ranging from CIF to 40*30
- Supports automatic exposure control, automatic gain control, automatic white balance, automatic elimination of light stripes, automatic black level calibration, etc. Automatic control functions are also supported. Color saturation, hue, gamma, sharpness settings are also supported.
- Supports flash
- Supports image scaling
- Lens light loss compensation
- Automatic noise reduction adjustment
OV7670 Pin Functions
| PIN | Definition |
| 3V3 | input supply voltage (recommended 3.3,5 V can also be, but is not recommended) |
| GND | ground |
| SIOC | SCCB interface control clock (Note: some of the low-level microcontroller needs pull-up control, and the I2C interface similar) |
| SIOD | SCCB interface serial data input (output) end (Note: some of the low-level microcontroller needs pull-up control, and the I2C interface similar) |
| VSYNC | frame synchronizing signal (output signal) |
| HREF | line synchronizing signal (the output signal, can generally not applicable to use of special cases) |
| D0~D7 | data port (output signal) |
| RESET | reset port (normal use pulled) |
| PWDN | power selection mode (normal use pull down) |
| STROBE | photographed flash control port (normal use may not be required) |
| FIFO_RCK | FIFO memory read clock control terminal |
| FIFO_WR_CTR | FIFO write control terminal (1 allows the CMOS is written to the FIFO, to prohibit 0) |
| FIFO_OE | FIFO off control |
| FIFO_WRST | FIFO write pointer reset terminal |
| FIFO_RRST | FIFO read pointer reset terminal |
OV7670 Parameters
Optical Array | 640×480 |
Core Voltage | 1.8 V DV ±10 % |
I/O Voltage | 1.8 V – 3.0 V |
Active Power | 60 mW / 15 fps VGAYUV |
Sleep Current | < 20 µA |
Operating Temp | -30 °C – 70 °C |
Stable Operating Temp | 0 °C – 50 °C |
Output Formats (8-bit) | ?YUV/YCbCr 4:2:2 |
Optical Format | 1/6″ |
Field of View | 25° |
Max Frame Rate | 30 fps VGA |
Sensitivity | 1.3 V/(Lux-sec) |
SNR | 46 dB |
Dynamic Range | 52 dB |
Scan Mode | Progressive |
Electronic Exposure | 1 – 510 lines |
Pixel Size | 3.6 µm × 3.6 µm |
Dark Current | 12 mV/s at 60 °C |
Well Capacity | 17 Ke |
Image Area | 2.36 mm × 1.76 mm |
Package Dimensions | 3785 µm × 4235 µm |
If the internal LDO is used to power the core (1.8V), the I/O voltage should be 2.45V or higher. Otherwise, an external 1.8V power supply must be used for the core.
OV7670 VS OV2640
Key Specs | OV2640 | OV7670 |
Array Size | 1600 x 1200 (UXGA) | 640 x 480 (VGA) |
Power Supply | Core: 1.3V DC ± 5% | Core: 1.8V DC ± 10% |
Power Consumption | Free running: 125mW | Free running: 60mW |
Image Sensor Format | Type 1/4″ | Type 1/6″ |
Maximum Image Transfer Rate | 1600×1200/15fps, | VGA/30fps |
Sensitivity | 0.6V/Lux-sec | 1.3V/Lux-sec |
S/N ratio | 40dB | 46dB |
Dynamic Range | 50dB | 52dB |
Pixel Size | 2.2 x 2.2 μm | 3.6 x 3.6 μm |
Output Format | YUV/RGB/Raw RGB Data/MJPEG | YUV/RGB/GRB/Raw RGB Data |
How to use OV7670 camera module with Arduino
Simulated Wiring Diagram
Physical Wiring Diagram
OV7670 D0 ->Arduino 3
OV7670 D1 ->Arduino 4
OV7670 D2 ->Arduino 5
OV7670 D3 ->Arduino 6
OV7670 D4 ->Arduino 7
OV7670 D5 ->Arduino 8
OV7670 D6 ->Arduino 9
OV7670 D7 ->Arduino 10
OV7670 FIFIO_RCK -> Arduino A0
OV7670 FIFIO_OE -> Arduino A1
OV7670 FIFIO_WR -> Arduino A2
OV7670 FIFIO_RRST -> Arduino A3
OV7670 SIO_C -> Arduino A5 (The pins cannot be adjusted to any other pins.)
OV7670 SIO_D -> Arduino A4 (The pins cannot be adjusted to any other pins.)
OV7670 FIFIO_WRST -> Arduino 11
OV7670 VSYNC -> Arduino 2 (The pins cannot be adjusted to any other pins.)
OV7670 RESET -> Arduino 12
OV7670 3.3V -> Arduino 3.3V
OV7670 GND -> Arduino GND
The pins of the other cameras do not need to be connected (Floating).
Sample Code
#include // I2C Essential libraries for the protocol
#define OV7670_ADDRESS 0x21
#define VSYNC 2
#define D0 3
#define D1 4
#define D2 5
#define D3 6
#define D4 7
#define D5 8
#define D6 9
#define D7 10
#define RESET 12
#define FIFO_WRST 11
#define FIFO_WR A2
#define FIFO_RRST A3
#define FIFO_RCK A0
#define FIFO_OE A1
unsigned char WrCmos7670(unsigned char regID, unsigned char regDat);
unsigned char rdCmos7670Reg(unsigned char regID);
unsigned char Cmos7670_init(void);
void set_Cmos7670reg(void);
unsigned char ov7670_data(void);
void IO_Init(void);
/****Variable********/
unsigned char tmp;
uint16_t Vsync_Flag,i,j;
unsigned char t1,t2;
void setup() {
// put your setup code here, to run once:
Serial.begin(9600);
Wire.begin();//I2C Begin
IO_Init();
digitalWrite(RESET, LOW);
delay(20);
digitalWrite(RESET, HIGH);
while(1!=Cmos7670_init()); //CMOS initialize
tmp = rdCmos7670Reg(0x3A);
if(tmp == 0x04)
{
}
else
{
while(1);
}
attachInterrupt(digitalPinToInterrupt(VSYNC), OV7670, FALLING);//Set the port for triggering interrupts, the program to run after the interrupt, and the triggering mode
}
void loop() {
// put your main code here, to run repeatedly:
}
void IO_Init(void)
{
pinMode(D0, INPUT);
pinMode(D1, INPUT);
pinMode(D2, INPUT);
pinMode(D3, INPUT);
pinMode(D4, INPUT);
pinMode(D5, INPUT);
pinMode(D6, INPUT);
pinMode(D7, INPUT);
pinMode(RESET, OUTPUT);
pinMode(FIFO_WRST, OUTPUT);
pinMode(FIFO_WR, OUTPUT);
pinMode(FIFO_RRST, OUTPUT);
pinMode(FIFO_RCK, OUTPUT);
pinMode(FIFO_OE, OUTPUT);
pinMode(VSYNC, INPUT_PULLUP);
}
unsigned char WrCmos7670(unsigned char regID, unsigned char regDat)
{
Wire.beginTransmission(OV7670_ADDRESS); // The device address is 0x21
Wire.write(regID);
Wire.write(regDat);
Wire.endTransmission(); //End communication
return(1);
}
unsigned char rdCmos7670Reg(unsigned char regID)
{
unsigned char regDat;
Wire.beginTransmission(OV7670_ADDRESS); // The device address is 0x21
Wire.write(regID);
Wire.endTransmission(); //End communication
Wire.requestFrom(OV7670_ADDRESS, 1);
regDat = Wire.read();
return regDat;
}
unsigned char Cmos7670_init(void)
{
unsigned char mmm;
mmm=0x80;
if(0==WrCmos7670(0x12, mmm))
{
return 0 ;
}
delay(10);
set_Cmos7670reg();
return 1;
}
void set_Cmos7670reg(void) //OV7670 Register configuration, without any logical meaning. The specific meanings need to be understood according to the manufacturer's chip manual.
{
WrCmos7670(0x3a, 0x04);
WrCmos7670(0x40, 0xd0);
WrCmos7670(0x12, 0x14);
WrCmos7670(0x32, 0x80);
WrCmos7670(0x17, 0x16);
WrCmos7670(0x18, 0x04);
WrCmos7670(0x19, 0x02);
WrCmos7670(0x1a, 0x7b);
WrCmos7670(0x03, 0x06);
WrCmos7670(0x0c, 0x00);
WrCmos7670(0x3e, 0x00);
WrCmos7670(0x70, 0x3a);
WrCmos7670(0x71, 0x35); //If it is set to WrCmos7670 (0x71, 0x80); it will display eight colored vertical bars, for debugging purposes.
WrCmos7670(0x72, 0x11);
WrCmos7670(0x73, 0x00);
WrCmos7670(0xa2, 0x02);
WrCmos7670(0x11, 0x81);
WrCmos7670(0x7a, 0x20);
WrCmos7670(0x7b, 0x1c);
WrCmos7670(0x7c, 0x28);
WrCmos7670(0x7d, 0x3c);
WrCmos7670(0x7e, 0x55);
WrCmos7670(0x7f, 0x68);
WrCmos7670(0x80, 0x76);
WrCmos7670(0x81, 0x80);
WrCmos7670(0x82, 0x88);
WrCmos7670(0x83, 0x8f);
WrCmos7670(0x84, 0x96);
WrCmos7670(0x85, 0xa3);
WrCmos7670(0x86, 0xaf);
WrCmos7670(0x87, 0xc4);
WrCmos7670(0x88, 0xd7);
WrCmos7670(0x89, 0xe8);
WrCmos7670(0x13, 0xe0);
WrCmos7670(0x00, 0x00);
WrCmos7670(0x10, 0x00);
WrCmos7670(0x0d, 0x00);
WrCmos7670(0x14, 0x28);
WrCmos7670(0xa5, 0x05);
WrCmos7670(0xab, 0x07);
WrCmos7670(0x24, 0x75);
WrCmos7670(0x25, 0x63);
WrCmos7670(0x26, 0xA5);
WrCmos7670(0x9f, 0x78);
WrCmos7670(0xa0, 0x68);
WrCmos7670(0xa1, 0x03);
WrCmos7670(0xa6, 0xdf);
WrCmos7670(0xa7, 0xdf);
WrCmos7670(0xa8, 0xf0);
WrCmos7670(0xa9, 0x90);
WrCmos7670(0xaa, 0x94);
WrCmos7670(0x13, 0xe5);
WrCmos7670(0x0e, 0x61);
WrCmos7670(0x0f, 0x4b);
WrCmos7670(0x16, 0x02);
WrCmos7670(0x1e, 0x37);
WrCmos7670(0x21, 0x02);
WrCmos7670(0x22, 0x91);
WrCmos7670(0x29, 0x07);
WrCmos7670(0x33, 0x0b);
WrCmos7670(0x35, 0x0b);
WrCmos7670(0x37, 0x1d);
WrCmos7670(0x38, 0x71);
WrCmos7670(0x39, 0x2a);
WrCmos7670(0x3c, 0x78);
WrCmos7670(0x4d, 0x40);
WrCmos7670(0x4e, 0x20);
WrCmos7670(0x69, 0x00);
WrCmos7670(0x6b, 0x60);
WrCmos7670(0x74, 0x19);
WrCmos7670(0x8d, 0x4f);
WrCmos7670(0x8e, 0x00);
WrCmos7670(0x8f, 0x00);
WrCmos7670(0x90, 0x00);
WrCmos7670(0x91, 0x00);
WrCmos7670(0x92, 0x00);
WrCmos7670(0x96, 0x00);
WrCmos7670(0x9a, 0x80);
WrCmos7670(0xb0, 0x84);
WrCmos7670(0xb1, 0x0c);
WrCmos7670(0xb2, 0x0e);
WrCmos7670(0xb3, 0x82);
WrCmos7670(0xb8, 0x0a);
WrCmos7670(0x43, 0x14);
WrCmos7670(0x44, 0xf0);
WrCmos7670(0x45, 0x34);
WrCmos7670(0x46, 0x58);
WrCmos7670(0x47, 0x28);
WrCmos7670(0x48, 0x3a);
WrCmos7670(0x59, 0x88);
WrCmos7670(0x5a, 0x88);
WrCmos7670(0x5b, 0x44);
WrCmos7670(0x5c, 0x67);
WrCmos7670(0x5d, 0x49);
WrCmos7670(0x5e, 0x0e);
WrCmos7670(0x64, 0x04);
WrCmos7670(0x65, 0x20);
WrCmos7670(0x66, 0x05);
WrCmos7670(0x94, 0x04);
WrCmos7670(0x95, 0x08);
WrCmos7670(0x6c, 0x0a);
WrCmos7670(0x6d, 0x55);
WrCmos7670(0x6e, 0x11);
WrCmos7670(0x6f, 0x9f);
WrCmos7670(0x6a, 0x40);
WrCmos7670(0x01, 0x40);
WrCmos7670(0x02, 0x40);
WrCmos7670(0x13, 0xe7);
WrCmos7670(0x15, 0x00);
WrCmos7670(0x4f, 0x80);
WrCmos7670(0x50, 0x80);
WrCmos7670(0x51, 0x00);
WrCmos7670(0x52, 0x22);
WrCmos7670(0x53, 0x5e);
WrCmos7670(0x54, 0x80);
WrCmos7670(0x58, 0x9e);
WrCmos7670(0x41, 0x08);
WrCmos7670(0x3f, 0x00);
WrCmos7670(0x75, 0x05);
WrCmos7670(0x76, 0xe1);
WrCmos7670(0x4c, 0x00);
WrCmos7670(0x77, 0x01);
WrCmos7670(0x3d, 0xc2);
WrCmos7670(0x4b, 0x09);
WrCmos7670(0xc9, 0x60);
WrCmos7670(0x41, 0x38);
WrCmos7670(0x56, 0x40);
WrCmos7670(0x34, 0x11);
WrCmos7670(0x3b, 0x02);
WrCmos7670(0xa4, 0x89);
WrCmos7670(0x96, 0x00);
WrCmos7670(0x97, 0x30);
WrCmos7670(0x98, 0x20);
WrCmos7670(0x99, 0x30);
WrCmos7670(0x9a, 0x84);
WrCmos7670(0x9b, 0x29);
WrCmos7670(0x9c, 0x03);
WrCmos7670(0x9d, 0x4c);
WrCmos7670(0x9e, 0x3f);
WrCmos7670(0x78, 0x04);
WrCmos7670(0x79, 0x01);
WrCmos7670(0xc8, 0xf0);
WrCmos7670(0x79, 0x0f);
WrCmos7670(0xc8, 0x00);
WrCmos7670(0x79, 0x10);
WrCmos7670(0xc8, 0x7e);
WrCmos7670(0x79, 0x0a);
WrCmos7670(0xc8, 0x80);
WrCmos7670(0x79, 0x0b);
WrCmos7670(0xc8, 0x01);
WrCmos7670(0x79, 0x0c);
WrCmos7670(0xc8, 0x0f);
WrCmos7670(0x79, 0x0d);
WrCmos7670(0xc8, 0x20);
WrCmos7670(0x79, 0x09);
WrCmos7670(0xc8, 0x80);
WrCmos7670(0x79, 0x02);
WrCmos7670(0xc8, 0xc0);
WrCmos7670(0x79, 0x03);
WrCmos7670(0xc8, 0x40);
WrCmos7670(0x79, 0x05);
WrCmos7670(0xc8, 0x30);
WrCmos7670(0x79, 0x26);
WrCmos7670(0x09, 0x00);
}
void OV7670(void)
{
uint16_t cnt;
detachInterrupt(digitalPinToInterrupt(VSYNC));
Vsync_Flag++;
if(Vsync_Flag==1)
{
digitalWrite(FIFO_WRST, HIGH);
digitalWrite(FIFO_WRST, LOW);
for(i=0;i<100;i++);
digitalWrite(FIFO_WRST, HIGH);
digitalWrite(FIFO_WR, HIGH);
}
if(Vsync_Flag==2)
{
digitalWrite(FIFO_WR, LOW);
detachInterrupt(digitalPinToInterrupt(VSYNC));
//EXTI->EMR&=~(1<<4);
//GPIOA->ODR ^= (1 << 3);
digitalWrite(FIFO_RRST, LOW);
digitalWrite(FIFO_RCK, LOW);
digitalWrite(FIFO_RCK, HIGH);
digitalWrite(FIFO_RCK, LOW);
digitalWrite(FIFO_RCK, HIGH);
digitalWrite(FIFO_RRST, HIGH);
digitalWrite(FIFO_OE, LOW);
Serial.write(0x01);
Serial.write(0xFE);
for(i = 0; i < 9600; i ++)
{
for(j = 0; j < 8; j ++)
{
digitalWrite(FIFO_RCK, LOW);
digitalWrite(FIFO_RCK, HIGH);
t1 = ov7670_data();
digitalWrite(FIFO_RCK, LOW);
digitalWrite(FIFO_RCK, HIGH);
t2 = ov7670_data();
Serial.write(t2);
Serial.write(t1);
}
}
digitalWrite(FIFO_OE, HIGH);
}
if(Vsync_Flag >= 2)
{
Serial.write(0xFE);
Serial.write(0x01);
pinMode(VSYNC, INPUT_PULLUP);
detachInterrupt(digitalPinToInterrupt(VSYNC));
}
else
{
pinMode(VSYNC, INPUT_PULLUP);
attachInterrupt(digitalPinToInterrupt(VSYNC), OV7670, FALLING);//Set the port for triggering interrupts, the program to run after the interrupt, and the triggering mode
}
}
unsigned char ov7670_data(void)
{
unsigned char tmp;
unsigned char DATA7 = 0;
unsigned char DATA6 = 0;
unsigned char DATA5 = 0;
unsigned char DATA4 = 0;
unsigned char DATA3 = 0;
unsigned char DATA2 = 0;
unsigned char DATA1 = 0;
unsigned char DATA0 = 0;
tmp = 0;
DATA7 = (unsigned char)digitalRead(D7);
DATA6 = (unsigned char)digitalRead(D6);
DATA5 = (unsigned char)digitalRead(D5);
DATA4 = (unsigned char)digitalRead(D4);
DATA3 = (unsigned char)digitalRead(D3);
DATA2 = (unsigned char)digitalRead(D2);
DATA1 = (unsigned char)digitalRead(D1);
DATA0 = (unsigned char)digitalRead(D0);
tmp = (DATA7 << 7) | (DATA6 << 6) | (DATA5 << 5) | (DATA4 << 4)\
|(DATA3 << 3) | (DATA2 << 2) | (DATA1 << 1) | (DATA0 << 0);
return tmp;
}
Effect Demonstration
We observe the effect on the software interface. After the program is burned into the board, Arduino will start to automatically upload data. Wait for about 10 seconds, and the image will appear on the right side of the software.
If you want to refresh the picture again, click the “Close Serial Port” button in the software. Then click “Open Serial Port”. Wait for about 10 seconds, and the new picture will overwrite the old one.
OV7670 Usage Instructions
- Image quality problem: If you find the image quality is poor, you can try adjusting the camera parameters, such as increasing brightness and contrast, or using image post-processing algorithms for image enhancement.
- Frame rate problem: If you need to increase the frame rate, you can reduce the resolution or decrease the image processing operations to achieve this.
- Data transmission problem: If there are errors or losses in data transmission, you can check if the hardware connection is correct, if the clock frequency is appropriate, or add data verification measures to improve the reliability of data transmission.
- If the picture is unclear, please rotate the small lens, and you can adjust the focal length.
OV7670 Application Scenarios
The OV7670 camera module can effectively alleviate the data processing pressure of the MCU, enabling smooth image acquisition and transmission. It can be applied in various fields such as small experiments, product development, production needs, instrument and metering, and intelligent manufacturing, and is particularly suitable for embedded development scenarios with limited resources.
Relative Information
OV7670 Camera Module Purchase Link
FAQ
1、How to determine which type of camera to use?
If you just want to display the image, 8 bits will be sufficient. A camera without FIFO is enough. Just add a TFT display! If your chip is an advanced MCU, ARM9 or above, or DSP, then you can choose to not use the FIFO module because the speed of high-end chips is very fast and the storage space is large, which is sufficient for directly collecting image data.
If you also want to do some very simple processing on the acquired image data (note that it is very simple), choose the FIFO camera. Since the FIFO does not have an address function, it does not have the function of locating (site selection) and reading data, so there can be no real data processing capability! Remember this!!
2、What is the difference between a camera without FIFO and a camera with FIFO?
Cameras with FIFO have 3 Megabytes more cache capacity than those without. They can temporarily store the collected data in this cache. When using them, the image data in the cache can be read directly. Therefore, the speed requirement of the MCU for collecting image data can be reduced.
(Note: Compared to other sensors, CMOS cameras are more challenging as they involve a lot of knowledge. Please do more evaluation and research before purchasing and using them, and make a decision accordingly!)