电子产业一站式赋能平台

PCB联盟网

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

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

[复制链接]

1001

主题

1001

帖子

8805

积分

高级会员

Rank: 5Rank: 5

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

xn004lltngs64024997850.gif

xn004lltngs64024997850.gif
+ s- k* ]: k. L0 q3 j5 A
点击上方蓝色字体,关注我们7 O; d+ C: Y, m+ T) F5 D
本篇博文使用ESP32-S3搭建网络摄像头,相比较局域网摄像头,本篇博文将分享如何搭建外网可以访问的网络摄像头。. j7 V$ _; X5 H! r
这主要是使用内网穿透技术,内网穿透是为了使具有某一个特定源 IP 地址和源端口号的数据包(这里指局域网摄像头)不被网络地址转换设备屏蔽而正确路由到内网主机。
: w' {: }% G& u; X主要流程分为两步:
& C5 A/ r/ L& x  E5 g1、先实现局域网访问网络摄像头;6 i: ~9 Q! b& i7 f2 \2 L- g5 i  h
2、在此基础,使用内网穿透的方式,搭建外网可访问的网络摄像头。
1 f' d5 ?2 S( g; E' o1+ u2 Q, E% a0 L; n8 a. J6 j) [# b0 v5 i
局域网摄像头
+ n: R1 ?0 h, P/ C( T! qESP32实现局域网摄像头的方式比较简单,驱动代码如下:
+ H( X7 V9 M' {# z( M
; p! h  i$ K  `7 D9 Q
  • #include "esp_camera.h"#include
    % l3 A* }# ^8 Q9 a//// 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
    " N. U9 d! T5 v// ===================// 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& v! h7 r# u7 _( C6 f; w
    #include "camera_pins.h"#include "DFRobot_AXP313A.h"
      {. f; q1 A5 ^4 ]. vDFRobot_AXP313A axp;
    - D# z/ t. j$ k3 O  w// ===========================// Enter your WiFi credentials// ===========================const char* ssid = "";const char* password = "";
    # n  j6 `* o( S. `% Nvoid startCameraServer();void setupLedFlash(int pin);
    2 ]$ v. b$ a' \1 A6 Gvoid setup() {  Serial.begin(115200);  Serial.setDebugOutput(true);  Serial.println();' m9 P% h0 Q/ }* B1 y. \1 x/ m! U% F
      while(axp.begin() != 0){    Serial.println("init error");    delay(1000);  }% U, o$ h5 U4 J
      axp.enableCameraPower(axp.eOV2640);  // 给摄像头供电) u/ b4 C; W4 I! B3 |- O6 N
      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;$ X+ P; S4 I4 X; B) q
      // 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  }# i/ L' T5 W3 |/ d+ V: i; ^% A3 v4 P
    #if defined(CAMERA_MODEL_ESP_EYE)  pinMode(13, INPUT_PULLUP);  pinMode(14, INPUT_PULLUP);#endif1 G1 O# `+ n8 ?
      // 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;  }, J/ E( l2 d( ]6 @$ M3 i8 v( k
      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);  }" l0 a: \# R' X1 q, g4 O+ Q# e, I
    #if defined(CAMERA_MODEL_M5STACK_WIDE) || defined(CAMERA_MODEL_M5STACK_ESP32CAM)  s->set_vflip(s, 1);  s->set_hmirror(s, 1);#endif) f4 ]1 \5 m) D8 E; J. u  A: {
    #if defined(CAMERA_MODEL_ESP32S3_EYE)  s->set_vflip(s, 1);#endif
    8 H8 m8 r; X' L7 A* u3 A% q// Setup LED FLash if LED pin is defined in camera_pins.h#if defined(LED_GPIO_NUM)  setupLedFlash(LED_GPIO_NUM);#endif+ H. k0 B8 Y+ y- I( T$ e
      WiFi.begin(ssid, password);  WiFi.setSleep(false);: o* D' X: X7 @; V- i9 g0 ^- W; d9 ^
      while (WiFi.status() != WL_CONNECTED) {    delay(500);    Serial.print(".");  }  Serial.println("");  Serial.println("WiFi connected");
    # f6 S, m# K3 q( f$ P: F' r2 Y+ V  startCameraServer();, K: @4 l4 y2 g; A  \
      Serial.print("Camera Ready! Use 'http://");  Serial.print(WiFi.localIP());  Serial.println("' to connect");}* l& B, n& N# c3 Q
    void loop() {  // Do nothing. Everything is done in another task by the web server  delay(10000);}. t% C6 Q: k* U0 x9 {
    代码中有几点需要注意:4 w$ j) A2 ~. o7 a& ^/ h

    3 r/ r1 p& U: f2 W1、宏定义选择适配的摄像头模式。- g) W" \" x( \8 a7 \$ u
    # ]% ~8 [) r+ k; s
  • // ===================// 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) _6 i& O# |4 i" W  `& T; V
    2、无线路由器SSID和密码要填写正确。; o: H! |; K3 w; [" N

    " D* L0 ?6 |" k& {" U3 t
  • // ===========================// Enter your WiFi credentials// ===========================const char* ssid = "";const char* password = "";
    + c9 X# B# M8 H! o& X$ Y1 u2 ~3、给摄像头供电
    " J' W. x9 h* y/ N$ `% T5 I) t/ k6 H* w7 R- l7 W9 _2 `% t  g
  • axp.enableCameraPower(axp.eOV2640);  // 给摄像头供电: L0 D: d& b' a) p5 \0 N
    4、板卡需要外接天线,否则可能无法连接路由器。+ V* i0 e/ c0 N( z1 H% ?
    / G# ]) N2 i8 a& j) O5 M# z  Q
    编译下载程序到板卡中,确保局域网访问网络摄像头可正常使用。- O1 P4 H/ b# x+ X9 ?
    2
    , F' q* Y3 `8 J1 t: O内网穿透网络摄像头3 q" k7 f& ?" R4 w8 \3 R8 l
    内网穿透我们使用花生壳这款软件提供的内网穿透服务。
    5 e# e6 O0 r) C* g6 U3 j; H
    2 z8 \1 o9 X2 l: m

    0jnk2h53pao64024997950.png

    0jnk2h53pao64024997950.png
    . P0 `$ |1 ~1 ~
    . @- |, D( L& H
    在官网下载APP:https://hsk.oray.com/0 G1 h8 d4 W+ n6 k( S
    9 v+ U" ?: r. m, Y) S$ t8 f8 b
    下载安装完成后,在内网穿透服务点击新建映射,如下图所示:
    4 _& E. `; n: m  w4 v' B; x: e
    6 v0 O! @8 t7 W( i9 V, N* x; R

    2ihowi4eyk164024998050.png

    2ihowi4eyk164024998050.png

    ! x# H' O: ^% ?, r( V& o5 W! x; k8 V2 F1 A8 p
    填写新建映射的基本信息,请注意内网主机和内网端口是局域网摄像头的主机和端口(端口默认为80) ,如下图所示:
    $ r6 n) Q1 P1 n( ?; J4 A, I
    ; q; U; U) R) B5 ^1 Q

    uwg2bilylxy64024998150.png

    uwg2bilylxy64024998150.png
    + J1 r( a6 G( e
    3 t* S. X! Z2 E* G
    新建映射完成后,可以在APP看到新增的设备列表,如下图所示:
    ) n4 h1 ^, Z% E9 O3 Q& ^6 z# R! I$ `* P0 `

    1ep4jr0jimd64024998250.png

    1ep4jr0jimd64024998250.png
    : R1 `. p! G- S" F' d% O5 Q
    * T+ {+ i7 k/ V' U7 l/ E" U% g$ k; E
    复制访问网址,在浏览器中打开:http://2j90962r69.goho.co:47918/, |: v5 [( w3 Y
    ! F* b4 Y8 Q! A  k0 M/ R
    即使不在同一个局域网内也可以正常访问摄像头啦。' e5 f3 `: p# @, J3 F

    ; @; W: r9 W+ `9 s6 Y1 _

    ihll0o153jn64024998350.png

    ihll0o153jn64024998350.png
    3 @8 m- r' R/ Q5 ~) ]( _( R
    6 j* Z2 {, E2 i* K2 w& L2 R* ^

    # @9 q& {  D- S3 X6 M; t& @

    cacav3gtzet64024998450.png

    cacav3gtzet64024998450.png

    ; \, E$ F, S7 R1 f往期推荐HarmonyOS学习路之开发篇—Java UI框架(Position和AdaptiveBox layout)6 M1 \: e$ k+ N% ~0 ]: i% u' Z
    Python数据可视化:如何选择合适的图表可视化?. T: ~7 P1 S* G+ g- ]( O) X7 e
    磁耦合共振无线供电装置
    ) Q! i' Z5 |5 w, C6 |* V2 s: sPython Qt GUI设计:表格和树类(提升篇—1)
    9 g! G. b. p. N. D$ d9 v: d
    * I! |) L7 Z7 _" w" @

    aeltjeee3ob64024998551.jpg

    aeltjeee3ob64024998551.jpg

    " G( h0 k( a& }  ]9 D$ }  G" M

    tze3hq3ggik64024998651.gif

    tze3hq3ggik64024998651.gif
      E  T7 b  j0 K$ K( [0 r, R
    点击阅读原文,更精彩~
  • 回复

    使用道具 举报

    发表回复

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

    本版积分规则


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