描述
问候。
所以这里有一些引人注目的东西,Vader Cam 。
Vader Cam 是一个基于 ESP32 CAM 的设备,它是一个实时视频源流设备,我们可以通过网络应用程序访问源并查看发生了什么。
这就像一个以达斯维德为主题的保姆摄像头或监控设备。
Darth Vader 一直在关注事物,我制作这个设备是为了用它来监控在另一个房间里进行的 3D 打印作业,但我们可以使用这个设备来监控各种各样的东西,从保姆到孩子甚至宠物。
这篇文章是关于这个 Vader Cam 的整个构建过程,所以让我们开始吧。
所需材料
这些是这个内置的东西 -
Seeed Studio 的定制 PCB
ESP32 凸轮
M7 二极管 SMA
UART 编程器
USB 微型端口
ESP32 板的排针
电源 - 智能手机适配器
关于 ESP32 CAM
ESP32 CAM 是一款非常实用的开发板,它在板的底部配备了一个 2MP OV2640 摄像头模块和一个 SD 读卡器。
此外,它的价格约为 10 美元,对于这种功能强大的微控制器来说,这是一个相当不错的价格标签。
本版本使用的WIFI模块为ESP-32S,内置32Mbit Flash和512KB Internal plus外置4M PSRAM。
它可以承受 5 伏电压,这意味着我们可以使用低于 5V 的电压为 ESP32 Cam 供电,如果您提供的电压高于 5V,它就会被损坏。
为 Arduino IDE 安装 ESP32 开发板
为了在 Arduino IDE 上安装第三方开发板,我们必须复制他们的 JSON URL,
复制此 URL 并将其粘贴到 Arduino IDE 首选项中的附加板管理器 URL 中。
(如果您在附加板管理器中已经有其他开发板 URL,则可以在两个 URL 之间放置一个逗号)
放好网址后,打开板子管理器,在里面搜索ESP32,然后下载ESP32 Board包。
完成所有这些后,您需要重新启动 Arduino IDE,新的 ESP32 板将出现在板管理器菜单中。
面包板设置
在开始这个项目之前,我们首先准备一个面包板设置,该设置由一个 ESP32 Cam 和一个 FTDI 板根据下面的示意图连接。
ESP32 CAM 没有板载编程芯片,这很糟糕,因此我们必须在串行编程模块中添加一个外部 USB。
为此,我将使用这个 USB 转串口模块。该模块基于 FTDI FT232 芯片。您也可以使用其他串行转换器,它们的接线将保持不变,因为我们只需将 TX 和 RX 与 ESP32 连接。
将 FTDI 输出设置为 5V
将 FTDI 的 VCC(即 5V)连接到 ESP32 CAM 的 5V
地到地
RX 到 U0T
TX 转 U0R
GPIO0 是 IO0 到 GND(这将使 ESP32 CAM 进入 Flash 模式)
主要代码
#include "esp_camera.h" #include#include "esp_timer.h" #include "img_converters.h" #include "Arduino.h" #include "fb_gfx.h" #include "soc/soc.h" //disable brownout problems #include "soc/rtc_cntl_reg.h" //disable brownout problems #include "esp_http_server.h" //Replace with your network credentials const char *ssid = "JioFiber-nCDgC"; const char *password = "jiexaifieXai5chu"; #define PART_BOUNDARY "123456789000000000000987654321" // This project was tested with the AI Thinker Model, M5STACK PSRAM Model and M5STACK WITHOUT PSRAM #define CAMERA_MODEL_AI_THINKER //#define CAMERA_MODEL_M5STACK_PSRAM //#define CAMERA_MODEL_M5STACK_WITHOUT_PSRAM // Not tested with this model //#define CAMERA_MODEL_WROVER_KIT #if defined(CAMERA_MODEL_WROVER_KIT) #define PWDN_GPIO_NUM -1 #define RESET_GPIO_NUM -1 #define XCLK_GPIO_NUM 21 #define SIOD_GPIO_NUM 26 #define SIOC_GPIO_NUM 27 #define Y9_GPIO_NUM 35 #define Y8_GPIO_NUM 34 #define Y7_GPIO_NUM 39 #define Y6_GPIO_NUM 36 #define Y5_GPIO_NUM 19 #define Y4_GPIO_NUM 18 #define Y3_GPIO_NUM 5 #define Y2_GPIO_NUM 4 #define VSYNC_GPIO_NUM 25 #define HREF_GPIO_NUM 23 #define PCLK_GPIO_NUM 22 #elif defined(CAMERA_MODEL_M5STACK_PSRAM) #define PWDN_GPIO_NUM -1 #define RESET_GPIO_NUM 15 #define XCLK_GPIO_NUM 27 #define SIOD_GPIO_NUM 25 #define SIOC_GPIO_NUM 23 #define Y9_GPIO_NUM 19 #define Y8_GPIO_NUM 36 #define Y7_GPIO_NUM 18 #define Y6_GPIO_NUM 39 #define Y5_GPIO_NUM 5 #define Y4_GPIO_NUM 34 #define Y3_GPIO_NUM 35 #define Y2_GPIO_NUM 32 #define VSYNC_GPIO_NUM 22 #define HREF_GPIO_NUM 26 #define PCLK_GPIO_NUM 21 #elif defined(CAMERA_MODEL_M5STACK_WITHOUT_PSRAM) #define PWDN_GPIO_NUM -1 #define RESET_GPIO_NUM 15 #define XCLK_GPIO_NUM 27 #define SIOD_GPIO_NUM 25 #define SIOC_GPIO_NUM 23 #define Y9_GPIO_NUM 19 #define Y8_GPIO_NUM 36 #define Y7_GPIO_NUM 18 #define Y6_GPIO_NUM 39 #define Y5_GPIO_NUM 5 #define Y4_GPIO_NUM 34 #define Y3_GPIO_NUM 35 #define Y2_GPIO_NUM 17 #define VSYNC_GPIO_NUM 22 #define HREF_GPIO_NUM 26 #define PCLK_GPIO_NUM 21 #elif defined(CAMERA_MODEL_AI_THINKER) #define PWDN_GPIO_NUM 32 #define RESET_GPIO_NUM -1 #define XCLK_GPIO_NUM 0 #define SIOD_GPIO_NUM 26 #define SIOC_GPIO_NUM 27 #define Y9_GPIO_NUM 35 #define Y8_GPIO_NUM 34 #define Y7_GPIO_NUM 39 #define Y6_GPIO_NUM 36 #define Y5_GPIO_NUM 21 #define Y4_GPIO_NUM 19 #define Y3_GPIO_NUM 18 #define Y2_GPIO_NUM 5 #define VSYNC_GPIO_NUM 25 #define HREF_GPIO_NUM 23 #define PCLK_GPIO_NUM 22 #else #error "Camera model not selected" #endif static const char* _STREAM_CONTENT_TYPE = "multipart/x-mixed-replace;boundary=" PART_BOUNDARY; static const char* _STREAM_BOUNDARY = "\r\n--" PART_BOUNDARY "\r\n"; static const char* _STREAM_PART = "Content-Type: image/jpeg\r\nContent-Length: %u\r\n\r\n"; httpd_handle_t stream_httpd = NULL; static esp_err_t stream_handler(httpd_req_t *req){ camera_fb_t * fb = NULL; esp_err_t res = ESP_OK; size_t _jpg_buf_len = 0; uint8_t * _jpg_buf = NULL; char * part_buf[64]; res = httpd_resp_set_type(req, _STREAM_CONTENT_TYPE); if(res != ESP_OK){ return res; } while(true){ fb = esp_camera_fb_get(); if (!fb) { Serial.println("Camera capture failed"); res = ESP_FAIL; } else { if(fb->width > 400){ if(fb->format != PIXFORMAT_JPEG){ bool jpeg_converted = frame2jpg(fb, 80, &_jpg_buf, &_jpg_buf_len); esp_camera_fb_return(fb); fb = NULL; if(!jpeg_converted){ Serial.println("JPEG compression failed"); res = ESP_FAIL; } } else { _jpg_buf_len = fb->len; _jpg_buf = fb->buf; } } } if(res == ESP_OK){ size_t hlen = snprintf((char *)part_buf, 64, _STREAM_PART, _jpg_buf_len); res = httpd_resp_send_chunk(req, (const char *)part_buf, hlen); } if(res == ESP_OK){ res = httpd_resp_send_chunk(req, (const char *)_jpg_buf, _jpg_buf_len); } if(res == ESP_OK){ res = httpd_resp_send_chunk(req, _STREAM_BOUNDARY, strlen(_STREAM_BOUNDARY)); } if(fb){ esp_camera_fb_return(fb); fb = NULL; _jpg_buf = NULL; } else if(_jpg_buf){ free(_jpg_buf); _jpg_buf = NULL; } if(res != ESP_OK){ break; } //Serial.printf("MJPG: %uB\n",(uint32_t)(_jpg_buf_len)); } return res; } void startCameraServer(){ httpd_config_t config = HTTPD_DEFAULT_CONFIG(); config.server_port = 80; httpd_uri_t index_uri = { .uri = "/", .method = HTTP_GET, .handler = stream_handler, .user_ctx = NULL }; //Serial.printf("Starting web server on port: '%d'\n", config.server_port); if (httpd_start(&stream_httpd, &config) == ESP_OK) { httpd_register_uri_handler(stream_httpd, &index_uri); } } void setup() { WRITE_PERI_REG(RTC_CNTL_BROWN_OUT_REG, 0); //disable brownout detector Serial.begin(115200); Serial.setDebugOutput(false); 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(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; } // 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; } // Wi-Fi connection WiFi.begin(ssid, password); while (WiFi.status() != WL_CONNECTED) { delay(500); Serial.print("."); } Serial.println(""); Serial.println("WiFi connected"); Serial.print("Camera Stream Ready! Go to: http://"); Serial.print(WiFi.localIP()); // Start streaming web server startCameraServer(); } void loop() { delay(1); }
闪烁板步骤
在闪烁过程之前,您需要更改示例草图中的一些内容。
转到示例> ESP32> 相机并打开CameraWebServer草图
输入您的 SSID 和密码
将相机模块从#define CAMERA_MODEL_WROVER_KIT更改为#define CAMERA_MODEL_AI_THINKER
现在,转到工具并选择正确的板,在我们的例子中是 AI-Thinker ESP32-CAM。
选择正确的端口并点击上传。
现在,当 ESP32 开始上传过程时,您将看到带有点和破折号的连接消息。按下板底部的重置按钮,点和划线开始。
如果您在此设置过程中遇到无法连接的错误,这意味着您的时机不对,请重试,当第一个点出现在调试菜单中时,长按重置按钮至少 1 秒钟。
几秒钟后,您的草图将被上传。
现在从 FTDI 模块中拔出 USB 并移除 GPIO0 和 GND 之间的跳线。
插入 USB 并打开串行监视器。
ESP32 将与 WIFI 连接(需要 1 分钟),您将看到 ESP32 CAM 的 IP 地址。
结果到目前为止...
我们复制 ESP32 Cam 的 IP 地址并在 Web 浏览器中打开它,它将显示 ESP32 Cam 的实时信息。接下来,我们开始为此设置准备 PCB。
PCB设计
1 / 2
完成面包板设置后,我们准备了一个简单的 PCB 设计,其中包括一个 USB 微型端口和一个二极管,用于为 ESP32 Cam 供电。
至于让这个电路板更美观和更酷,我下载了一张黑白 Darth Vader 图像并将其转换为 BMP 图像,这样我就可以将它添加到 PCB 设计中。
我将 ESP32 Cam 放在 Darth Vader 脸的一侧,这样看起来 Vader 正在通过 ESP32 Cam 看着我们。
从 Seeed Fusion 获取 PCB
1 / 2
在完成 PCB 并生成其 Gerber 数据后,我将其发送到 SEEED STUDIO 以获取样本。
订购了带有白色丝印的 RED 阻焊层的 PCB。
我在一周内收到了多氯联苯,考虑到价格也很低,它们的质量非常好。
Seeed Fusion PCB 服务为 PCB 制造和 PCB 组装提供一站式原型设计,因此,他们在 7 个工作日内生产出优质 PCB 和快速交钥匙 PCBA。
Seeed Studio Fusion PCB 组装服务负责从PCB 制造、零件采购、组装和测试服务的整个制造过程,因此您可以确保他们获得优质产品。
在评估市场兴趣并验证工作原型后,Seeed Propagate Service 可以通过专业指导和强大的联系网络帮助您将产品推向市场。
PCB组装
PCB组装包括两个步骤,
添加焊膏和二极管
添加头针和 USB 端口
焊膏和添加二极管
我们首先将焊膏添加到电路板底部的每个组件焊盘,然后将二极管放置在其位置。
接下来,我们小心地提起整个 PCB 并将其放在热板上。我正在使用我不久前制作的老式DIY 电炉。
热板将表面加热到焊膏熔化温度,然后慢慢熔化。几分钟后焊膏完全融化,我们取下PCB并让它冷却片刻。
这是最终设置,我们使用烙铁放置两个插头引脚连接器。
结果
我们将 ESP32 放在 VaderCam 板上并插入 5V 充电器。
等待几秒钟后,我们在浏览器中打开 Web 应用程序,我们可以看到来自 esp32 cam 的实时提要。
这就是今天的人们,如果您需要有关此项目的任何帮助,请发表评论。
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
全部0条评论
快来发表一下你的评论吧 !