你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

全网首发,用STM32F429实现的网页摄像头mjpeg-stream  

[复制链接]
shanji 发布时间:2019-4-1 17:58
本帖最后由 shanji 于 2019-4-27 09:03 编辑
5 R3 v( I/ u7 G/ X
& t$ J7 d% a) ^, x* j7 ?) }1 @https://www.stmcu.org.cn/module/forum/thread-609701-1-1.html
9 b! [/ }% F1 `" F  r# ~4 d- i距上次分享了个网络摄像头的示例也有一段时间了,用的裸TCP协议,这次来玩玩不同的花样,网页摄像头mjpeg-stream传输,用HTTP协议。网上搜了下,清一色的在Linux下实现的,在单片机上实现的还真没找到,为了玩起来,只能琢磨linux下的代码。' l$ ~- G- h% {% c. B
        一、先把网页做出来
  o! w3 C* H3 v4 e0 E      网页端的实现比较简单,用img标签,例:' r4 n! F$ W8 [% y
<html>9 h* N, @8 D& |$ C7 I# u
      <head>/ P2 V+ P( o, x5 l* m& B" v
      </head>
: ]* u4 y& d. F6 |0 v      <body>
1 b' H( N8 _) o1 c" m      <img src="http://192.168.1.199:80/?stm32=mjpeg">,此处的ip指的是服务器的ip。
- @# Z$ `1 s% u      </body>
1 J) @( v; V1 C0 Q4 x* F: f; J</html># f8 K! }$ C( Z' L8 K2 F
      二、 服务端的代码实现0 o2 b# j* V* y0 Q
      要在网页上看到不断刷新的图片,服务端需要发送如下的相应包1 G9 O, i4 N, b' R' H( Q: j& E
     HTTP/1.1 200 OK\r\n8 f) d. w0 Q" y7 k- ?, A

# f# p9 L; Y  W* g; g
     Content-Type: multipart/x-mixed-replace;boundary=xxxxxxxx\r\n\r\n   //boundary后面的字段自行定义
     关于multipart/x-mixed-replaceboundary网上有很多专业解释,我就不copy了,知道怎么用它就对了。
    要发送图片时的数据包格式是
  --xxxxxxxx\r\n
   Content-Type: img/jpeg\r\n
   Content-Length: 2048\r\n\r\n  //此帧图片的大小
   循环发送这样的数据包给网页,网页上就能看到不断刷新的画面了      
   有了上面的基础,就可以开始码代码。
    关键代码:
     程序中使用了RT-Therad RTOS,用socket编程。
  1. **7 t$ o8 ?2 h- h5 u9 ^* n+ P
  2.   * @brief 开始发送流$ H$ r& Q) u6 I6 N( t
  3.   * @param  client,count2 \9 f! R  U1 o) G. l- E* e
  4.   * @retval None
    % D0 U- a4 s7 u  z4 I
  5.   */0 e5 b7 y' ^! S. H" `3 w+ z
  6. HTTP_STA HTTP_Streamer_Start(int client,u8 count)
    1 d0 ?2 g: M3 e# F
  7. {        
    ; d: e0 i% [3 h" Z, j# C
  8.     int frame_size=0;, k2 g! G/ }3 g8 w8 h0 Q
  9.    uint16_t haed_len=0;
    / d1 z9 w' ^; ~8 d! x
  10.    sprintf(buffer, "HTTP/1.1 200 OK\r\n"\
    ( ~. `, M: J6 T* P" V) v
  11.    "Connection: Keep-Alive\r\n"\
    " e! O6 i1 P/ Q! F6 {2 d1 P
  12.    "Server: MJPG-Streamer/0.2\r\n"\
    4 K# T, Z$ S7 `/ l3 q
  13.    "Cache-Control:no-store, no-cache, must-revalidate, pre-check=0, post-check=0, max-age=0\r\n"\  i& t1 p9 w8 X7 K1 r6 L1 E3 M
  14.    "Pragma:no-cache\r\n"\, M; C* i" g' e
  15.    "Expires:WED, 23 Jan 2019 01:00:00 GMT\r\n"\: m: p1 ?4 d& i5 m! u
  16.    "Content-Type: multipart/x-mixed-replace;boundary=openmcu\r\n\r\n"\5 u, R& C: J" X7 b/ q* q* I
  17.    "--openmcu\r\n");
    5 f3 q- b4 `* N  ^6 Z7 ]
  18.                               
    * Z2 |8 Q* Z1 m  h& I+ y
  19.     haed_len=strlen(buffer);' a' y: a; r+ S
  20.    //printf("\r\n%s\r\n",buffer);+ {% s! d8 ~9 R
  21.    if(send(client, buffer,haed_len, 0)==-1)
    1 L. q" H- _( Q) q7 D
  22.    {
    : n( l4 ~. E% c5 n. f: K
  23.       return HTTP_FAIL;
    ; k) x2 D, A. a# C8 O3 A
  24.    }
    $ Z9 o! s% p! V  t$ j0 J2 M
  25.   #if USE_CAMERA/ D! J  I( K2 s; f, K9 D
  26.   frame_size=jpeg_data_len(); % r: W8 `/ X: C
  27.   if(frame_size==0) return HTTP_FAIL;2 l; u& x% w5 i0 D/ H+ c
  28.   #else
    4 f% J0 C2 p4 }" |
  29.   if(count==0)
    2 T+ B* M' u* d5 Y3 Z
  30.   frame_size=sizeof(cam_data);
    + t# W. k1 f. g  O' G8 o
  31.   else if(count==1)
    6 N! o! n- E1 Z$ a6 G$ D6 c
  32.   frame_size=sizeof(cam_data2);- T6 i5 _' B' q
  33.   #endif         
    ; u2 @9 Q( V) _) A) _4 U
  34.   haed_len=strlen(buffer);
    & U3 X5 b" |3 V* e
  35. # O5 W. b% n( R# Q( P( t; S5 W  N
  36.   sprintf(buffer, "Content-Type: image/jpeg\r\n"\
    ' z6 o& }+ c: o, ?* e
  37.   "Content-Length: %d\r\n\r\n", frame_size);2 E9 G9 M6 g$ m6 Z
  38.   printf("\r\n%s\r\n",buffer);
    - o4 g* e9 {9 E. p' m
  39.   haed_len=strlen(buffer);6 R3 Q8 d* \  [9 @; w! K
  40.   if(send(client, buffer,haed_len, 0)==-1)
    0 w$ r2 m6 L0 Q
  41.   {
    0 D* [; G% [% b; _
  42.      return HTTP_FAIL;4 F0 ~( {8 Q% ~4 I+ |9 G8 P" l
  43.    }
    - ~& |4 ]  V& T) l0 O
  44.   #if USE_CAMERA0 N( S& y8 T* g; q" |. L; k
  45.   memcpy(&buffer[haed_len],(char*)ptr,frame_size);/ k: w' I6 c: a  |, u9 c2 ^5 T" T' \
  46.   #else" s% C2 A6 f7 y* o5 P
  47.   if(count==0)
    ! ^. ?/ ^2 t3 X4 @# T% n
  48.   memcpy(&buffer[haed_len],(char*)cam_data,frame_size);8 g* I4 O  Z* N5 e! y: b. X# ?
  49.   else if(count==1)2 q2 L4 ]8 c* d% P4 O7 a
  50.   memcpy(&buffer[haed_len],(char*)cam_data2,frame_size);  C4 B  t. Y* W& d
  51.   #endif                 
    7 T  R0 F2 r. W) A  I; v/ C
  52.   if(send(client, &buffer[haed_len],frame_size, 0)==-1)6 l$ f" e0 S; T3 U" x
  53.   {
    9 J3 w4 r: x' ~6 ]
  54.      return HTTP_FAIL;
    7 Y$ t3 L- ^9 W- ~' i
  55.   }
    ( ^$ p  S+ g6 {# V# \' X+ j7 B
  56.   #if USE_CAMERA+ N: O/ c. i+ X! Z: u2 R
  57.        newframe=0;  
    7 U4 J6 h6 {  S# `. d) \: d2 b) Z
  58.        cam_start();         + f: ^6 V, }8 Y  E2 q; c' y- t
  59.   #endif
    9 s/ w( Q1 _  a% V1 k, M  y
  60.       //lwip_close(client);               
    # B$ K2 z4 c8 n3 Z* V% l/ W
  61.   return HTTP_OK;, O8 Z& e# L/ o  |( R" E. Q
  62. }
复制代码

; s' J0 D/ d* ?  @" t
发送完第一帧图片后,循环发送前面介绍的图片数据格式,就能看到摄像头的实时画面了。
GIF2.gif
/ O( s: [1 H7 O& f/ j% @& G* L
测试源码
【】STM32F429_网络摄像头(网页版)V1.1.rar (1.74 MB, 下载次数: 354)

评分

参与人数 2 ST金币 +13 收起 理由
你若安好_清风徐来 + 5 很给力!
g921002 + 8 很给力!

查看全部评分

1 收藏 19 评论202 发布时间:2019-4-1 17:58

举报

202个回答
昱枫 回答时间:2019-12-19 10:06:22
学习了,
0 c' q. c, ~; s* j* I, K  K7 f下次可以和楼主的整合一起3 U% p( Z! H3 T
将视频实时显示在屏幕上,
& q) \8 v# g0 l& g; ^. T! i4 y7 ehttps://www.stmcu.org.cn/module/forum/forum.php?mod=viewthread&tid=622494&page=1#pid2473242) T% m* g1 i) g3 Y$ ]6 ?6 L

% e3 ~6 V# ~) [/ g) f感谢支持下
8 o' `) k2 E8 b* q
shanji 回答时间:2019-4-3 10:34:11
yklstudent-1794 发表于 2019-4-3 10:16& }2 V8 b% ^$ w( s" i0 H
楼主请教下,发送数据后就立即关闭连接,之前发送的数据还能发送出去吗? ...
7 ?( X  p# }* A. `7 c
关闭连接后发不出去了,需要重新等待客户端的连接。
yklstudent 回答时间:2019-4-3 10:43:01
shanji 发表于 2019-4-3 10:34
1 Y. d& `+ F% j* k. w& s# w关闭连接后发不出去了,需要重新等待客户端的连接。
. y; F0 ?$ w7 }# a) t( w/ P; X0 S
那为什么send后面要close呢,这样之前的send数据也发不出去啊
海迹天涯 回答时间:2019-4-2 09:30:25
厉害了我的哥
3111272 回答时间:2019-4-2 09:31:44
膜拜大佬
Wature 回答时间:2019-4-2 09:58:24
真的是厉害了我的哥
神奇小芭比 回答时间:2019-4-2 09:59:41
厉害了我的歌
Kevin_G 回答时间:2019-4-2 10:11:11
点赞,超级牛
xiaobai.. 回答时间:2019-4-2 10:41:30
不错
网络孤客 回答时间:2019-4-2 10:54:27
厉害,学习学习!
Bowen 回答时间:2019-4-2 10:54:58
厉害了,学习下
STMWoodData 回答时间:2019-4-2 11:29:19
提示: 作者被禁止或删除 内容自动屏蔽
与我非 回答时间:2019-4-2 11:35:29
厉害厉害
yklstudent 回答时间:2019-4-2 12:32:20
MARK,厉害了我的哥
STMCU-管管 回答时间:2019-4-2 13:00:43
支持支持
七哥 回答时间:2019-4-2 13:04:33
膜拜
老牛洋车 回答时间:2019-4-2 13:20:00
佩服!拜楼主为师。
关于意法半导体
我们是谁
投资者关系
意法半导体可持续发展举措
创新和工艺
招聘信息
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
关注我们
st-img 微信公众号
st-img 手机版