电子产业一站式赋能平台

PCB联盟网

搜索
查看: 109|回复: 0
收起左侧

ESP32-S3搭建外网可访问的网络摄像头(内网穿透)

[复制链接]

840

主题

840

帖子

6491

积分

高级会员

Rank: 5Rank: 5

积分
6491
发表于 2023-9-6 12:00:00 | 显示全部楼层 |阅读模式

rfaefhoaoi064011337440.gif

rfaefhoaoi064011337440.gif
, Z5 V$ Y1 G! X" B! s7 F+ D
点击上方蓝色字体,关注我们* x  \/ w8 Z( W. t0 v! P8 G
本篇博文使用ESP32-S3搭建网络摄像头,相比较局域网摄像头,本篇博文将分享如何搭建外网可以访问的网络摄像头。, `3 s1 J8 i" i6 Z/ O
这主要是使用内网穿透技术,内网穿透是为了使具有某一个特定源 IP 地址和源端口号的数据包(这里指局域网摄像头)不被网络地址转换设备屏蔽而正确路由到内网主机。
! j8 f  ^0 b; d8 Z. _主要流程分为两步:. M' x0 t  r3 ?; a; o8 D
1、先实现局域网访问网络摄像头;
7 Q# f# o- }  f' m2、在此基础,使用内网穿透的方式,搭建外网可访问的网络摄像头。
# U, ^  C: W% c7 d$ p1 H  r! c1( L1 t+ G; K6 H) G
局域网摄像头
1 h, v) @6 W. kESP32实现局域网摄像头的方式比较简单,驱动代码如下:
* ], ?8 X: b; U$ L$ w( r! @! t. o' A: D$ z9 {% @+ v3 g7 @8 |
  • #include "esp_camera.h"#include
    3 e0 ^3 \8 {/ ~0 C//// 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////            You must select partition scheme from the board menu that has at least 3MB APP space.//            Face Recognition is DISABLED for ESP32 and ESP32-S2, because it takes up from 15 //            seconds to process single frame. Face Detection is ENABLED if PSRAM is enabled as well$ v; L7 j2 K% P) Q
    // ===================// Select camera model// ===================//#define CAMERA_MODEL_WROVER_KIT // Has PSRAM// #define CAMERA_MODEL_ESP_EYE // Has PSRAM//#define CAMERA_MODEL_ESP32S3_EYE // Has PSRAM//#define CAMERA_MODEL_M5STACK_PSRAM // Has PSRAM//#define CAMERA_MODEL_M5STACK_V2_PSRAM // M5Camera version B Has PSRAM//#define CAMERA_MODEL_M5STACK_WIDE // Has PSRAM//#define CAMERA_MODEL_M5STACK_ESP32CAM // No PSRAM//#define CAMERA_MODEL_M5STACK_UNITCAM // No PSRAM//#define CAMERA_MODEL_AI_THINKER // Has PSRAM//#define CAMERA_MODEL_TTGO_T_JOURNAL // No PSRAM//#define CAMERA_MODEL_XIAO_ESP32S3 // Has PSRAM// ** Espressif Internal Boards **//#define CAMERA_MODEL_ESP32_CAM_BOARD//#define CAMERA_MODEL_ESP32S2_CAM_BOARD//#define CAMERA_MODEL_ESP32S3_CAM_LCD#define CAMERA_MODEL_DFRobot_FireBeetle2_ESP32S3 // Has PSRAM//#define CAMERA_MODEL_DFRobot_Romeo_ESP32S3 // Has PSRAM
    1 U+ c- Y# E2 {, a#include "camera_pins.h"#include "DFRobot_AXP313A.h"
    / [6 \2 A  o" d$ Z8 [) [DFRobot_AXP313A axp;
    4 z* W4 Z# ]& n8 g( Q- j// ===========================// Enter your WiFi credentials// ===========================const char* ssid = "";const char* password = "";1 w% p+ G5 m' G0 K% `2 C: m, j
    void startCameraServer();void setupLedFlash(int pin);
    : h% S; M% M4 a: `' bvoid setup() {  Serial.begin(115200);  Serial.setDebugOutput(true);  Serial.println();
    1 X% V( P( X* d9 O" Q  while(axp.begin() != 0){    Serial.println("init error");    delay(1000);  }/ e; S( y- L8 O; ~
      axp.enableCameraPower(axp.eOV2640);  // 给摄像头供电
    # F  ?$ B5 k! \% b) D2 X7 v  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_sccb_sda = SIOD_GPIO_NUM;  config.pin_sccb_scl = SIOC_GPIO_NUM;  config.pin_pwdn = PWDN_GPIO_NUM;  config.pin_reset = RESET_GPIO_NUM;  config.xclk_freq_hz = 20000000;  config.frame_size = FRAMESIZE_UXGA;  config.pixel_format = PIXFORMAT_JPEG; // for streaming  //config.pixel_format = PIXFORMAT_RGB565; // for face detection/recognition  config.grab_mode = CAMERA_GRAB_WHEN_EMPTY;  config.fb_location = CAMERA_FB_IN_PSRAM;  config.jpeg_quality = 12;  config.fb_count = 1;. p, A# [! |- k1 B
      // if PSRAM IC present, init with UXGA resolution and higher JPEG quality  //                      for larger pre-allocated frame buffer.  if(config.pixel_format == PIXFORMAT_JPEG){    if(psramFound()){      config.jpeg_quality = 10;      config.fb_count = 2;      config.grab_mode = CAMERA_GRAB_LATEST;    } else {      // Limit the frame size when PSRAM is not available      config.frame_size = FRAMESIZE_SVGA;      config.fb_location = CAMERA_FB_IN_DRAM;    }  } else {    // Best option for face detection/recognition    config.frame_size = FRAMESIZE_240X240;#if CONFIG_IDF_TARGET_ESP32S3    config.fb_count = 2;#endif  }
    % p8 ~- M: }8 T" K! c6 s" Z#if defined(CAMERA_MODEL_ESP_EYE)  pinMode(13, INPUT_PULLUP);  pinMode(14, INPUT_PULLUP);#endif
    & H, ~0 l- c) x0 u/ l  // 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;  }
    + L. N. @& i! @9 a3 \% r  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  if(config.pixel_format == PIXFORMAT_JPEG){    s->set_framesize(s, FRAMESIZE_QVGA);  }
    & X/ X4 ]. r4 V) G# q#if defined(CAMERA_MODEL_M5STACK_WIDE) || defined(CAMERA_MODEL_M5STACK_ESP32CAM)  s->set_vflip(s, 1);  s->set_hmirror(s, 1);#endif
    ) Z+ m: I) y. A9 ]5 D: c  f) ?#if defined(CAMERA_MODEL_ESP32S3_EYE)  s->set_vflip(s, 1);#endif0 k, |9 F& ?. E4 j  O  j$ I9 \
    // Setup LED FLash if LED pin is defined in camera_pins.h#if defined(LED_GPIO_NUM)  setupLedFlash(LED_GPIO_NUM);#endif' v4 J' S! ^1 m3 F9 Q3 |
      WiFi.begin(ssid, password);  WiFi.setSleep(false);4 _! N9 Z2 h7 ]. @' K+ e
      while (WiFi.status() != WL_CONNECTED) {    delay(500);    Serial.print(".");  }  Serial.println("");  Serial.println("WiFi connected");
    $ t" g2 I; X0 a1 A" {* J# D* L2 Y  startCameraServer();
    9 J6 M4 [3 s7 i% X  o0 e' l4 E. S  Serial.print("Camera Ready! Use 'http://");  Serial.print(WiFi.localIP());  Serial.println("' to connect");}
    ! u; `7 K: v3 s- ^void loop() {  // Do nothing. Everything is done in another task by the web server  delay(10000);}
    $ X! E' c/ |2 K5 s. E% N9 X" W* D代码中有几点需要注意:
    ) l0 C# Q9 J6 D( u5 S. T& ]4 a* z; H6 D+ l1 p  b5 I
    1、宏定义选择适配的摄像头模式。1 t, c$ F4 v6 }3 b3 [; o

    7 v8 X& B% n' n8 \
  • // ===================// Select camera model// ===================//#define CAMERA_MODEL_WROVER_KIT // Has PSRAM// #define CAMERA_MODEL_ESP_EYE // Has PSRAM//#define CAMERA_MODEL_ESP32S3_EYE // Has PSRAM//#define CAMERA_MODEL_M5STACK_PSRAM // Has PSRAM//#define CAMERA_MODEL_M5STACK_V2_PSRAM // M5Camera version B Has PSRAM//#define CAMERA_MODEL_M5STACK_WIDE // Has PSRAM//#define CAMERA_MODEL_M5STACK_ESP32CAM // No PSRAM//#define CAMERA_MODEL_M5STACK_UNITCAM // No PSRAM//#define CAMERA_MODEL_AI_THINKER // Has PSRAM//#define CAMERA_MODEL_TTGO_T_JOURNAL // No PSRAM//#define CAMERA_MODEL_XIAO_ESP32S3 // Has PSRAM// ** Espressif Internal Boards **//#define CAMERA_MODEL_ESP32_CAM_BOARD//#define CAMERA_MODEL_ESP32S2_CAM_BOARD//#define CAMERA_MODEL_ESP32S3_CAM_LCD#define CAMERA_MODEL_DFRobot_FireBeetle2_ESP32S3 // Has PSRAM//#define CAMERA_MODEL_DFRobot_Romeo_ESP32S3 // Has PSRAM
    ; P0 N# b! o$ v' U8 S2、无线路由器SSID和密码要填写正确。
    : J8 q" B' |' q! i( Z
    - Z" O2 o0 b+ w' v; B0 L7 s% u
  • // ===========================// Enter your WiFi credentials// ===========================const char* ssid = "";const char* password = "";3 K, u% e* M. X8 [1 A# Y& Z
    3、给摄像头供电' a0 |3 O) ^) `# _  q

    ; j& K1 @5 {8 `7 r# o9 p. N
  • axp.enableCameraPower(axp.eOV2640);  // 给摄像头供电9 X7 `1 b# k6 y! a: U6 X
    4、板卡需要外接天线,否则可能无法连接路由器。
    + q6 V4 A# G* C+ R: l7 d: l0 p
    # v% ]. v4 R( K0 `4 b编译下载程序到板卡中,确保局域网访问网络摄像头可正常使用。; g) ~* J# t# W0 q
    2
    : u) g0 c7 O1 n# N2 w3 Y; P. a# B6 ^内网穿透网络摄像头
    6 G7 M9 R, b0 {+ l: \内网穿透我们使用花生壳这款软件提供的内网穿透服务。" t$ Z% [6 J% O
    ; v/ {! P- B9 T: Y, n" q$ K

    3lfxtyznlrd64011337540.png

    3lfxtyznlrd64011337540.png

    4 Z1 S8 d% |( k6 h$ T) e# L1 A$ C! m+ c3 ~7 N% M8 g! V3 s
    在官网下载APP:https://hsk.oray.com// D5 y: G7 |! f1 a! V+ \
    * ?, r/ h+ n/ w) Y7 U" l( x
    下载安装完成后,在内网穿透服务点击新建映射,如下图所示:
    7 U5 T- t# v/ [0 d/ u% l6 H1 p4 c" ^& G& I+ @  t

    rpgbgw2g41b64011337641.png

    rpgbgw2g41b64011337641.png
    * V9 L- W( \) q! K
    . S- ^( q. D$ n( H$ _; h
    填写新建映射的基本信息,请注意内网主机和内网端口是局域网摄像头的主机和端口(端口默认为80) ,如下图所示:" J5 l6 w, t) s
    3 l* _* N. J$ Q1 g- `5 J

    q0c3b1hvwqd64011337741.png

    q0c3b1hvwqd64011337741.png
    0 A) c. {+ t, t5 X3 ^, ~5 Z6 A; b

    * p/ z! e6 i5 \) T! j7 M新建映射完成后,可以在APP看到新增的设备列表,如下图所示:
    $ W5 @+ a- j! K  l8 f( B
    1 ^: |- L1 Q+ }! _( {* o

    jpntetpardb64011337841.png

    jpntetpardb64011337841.png
    / k, ?, i( L: p2 j+ ^
    ; w; h9 z7 ^+ o, {- b9 T  u) Q
    复制访问网址,在浏览器中打开:http://2j90962r69.goho.co:47918/
    6 w* C' o+ q6 {7 X$ a4 x
    ' M; O' u  q2 w& S/ R9 v即使不在同一个局域网内也可以正常访问摄像头啦。) f2 L$ [: [8 b, E4 v
    " r0 k: b9 _/ O

    seuqxikv5et64011337941.png

    seuqxikv5et64011337941.png
    % D) I# I3 z0 Q( b2 {

    ' Z: g3 E$ M9 L' c2 l5 A. E! i+ b( m$ `. Q' v1 l& i7 ?7 ]

    15dszar1me464011338041.png

    15dszar1me464011338041.png

    / d" w  n* o. [- t4 d往期推荐HarmonyOS学习路之开发篇—Java UI框架(Position和AdaptiveBox layout)9 D4 `+ [/ U" m
    Python数据可视化:如何选择合适的图表可视化?
    & @) W# H# H6 f* K- ?" X- H0 g磁耦合共振无线供电装置" j% {+ {' h* C, M
    Python Qt GUI设计:表格和树类(提升篇—1)) @0 J9 G; K+ N
    7 h) O. b' m$ L* _6 r

    41rkstvxwvl64011338141.jpg

    41rkstvxwvl64011338141.jpg
    ' s) X; O5 H. h

    g0bwzytg1q564011338241.gif

    g0bwzytg1q564011338241.gif
    / A5 C6 p$ B* T* K5 @* T' b1 I2 Z
    点击阅读原文,更精彩~
  • 回复

    使用道具 举报

    发表回复

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则


    联系客服 关注微信 下载APP 返回顶部 返回列表