create time:2019年7月8日
我在网上找了好多,现在基本实现了传输视频的功能,其思路是:首先得先了解如何使用openCV采集摄像头数据,
其次得了解python socket网络编程。因为socket不能直接传输openCV采集的数据,所以还需要转码操作。在该版本我实现最基
本的功能,客户端采集,服务端接收(也可以倒过来,看个人需求),使用类实现。
服务端
#!usr/bin/python
# coding=utf-8
import
socket
import
cv2
import
numpy
class
VideoServer
:
def
__init__
(
self
)
:
try
:
self
.
s_sock
=
socket
.
socket
(
socket
.
AF_INET
,
socket
.
SOCK_STREAM
)
self
.
s_sock
.
setsockopt
(
socket
.
SOL_SOCKET
,
socket
.
SO_REUSEADDR
,
1
)
self
.
s_sock
.
bind
(
(
'10.0.0.30'
,
9999
)
)
self
.
s_sock
.
listen
(
5
)
except
Exception
,
err
:
print
err
exit
(
0
)
def
recv_all
(
self
,
sock
,
count
)
:
buf
=
''
while
count
:
newbuf
=
sock
.
recv
(
count
)
if
not
newbuf
:
return
None
buf
+=
newbuf
count
-=
len
(
newbuf
)
return
buf
def
recvImgAndShow
(
self
)
:
c_sock
,
c_addr
=
self
.
s_sock
.
accept
(
)
while
True
:
tempdata_len
=
self
.
recv_all
(
c_sock
,
16
)
if
len
(
tempdata_len
)
==
16
:
stringData
=
self
.
recv_all
(
c_sock
,
int
(
tempdata_len
)
)
data
=
numpy
.
fromstring
(
stringData
,
dtype
=
'uint8'
)
tmp
=
cv2
.
imdecode
(
data
,
1
)
# 解码处理,返回mat图片
img
=
cv2
.
resize
(
tmp
,
(
640
,
480
)
)
cv2
.
imshow
(
'SERVER'
,
img
)
if
cv2
.
waitKey
(
1
)
==
27
:
break
self
.
s_sock
.
close
(
)
cv2
.
destroyAllWindows
(
)
if
__name__
==
'__main__'
:
videoS
=
VideoServer
(
)
videoS
.
recvImgAndShow
(
)
客户端
#!usr/bin/python
# coding=utf-8
import
socket
import
cv2
import
numpy
class
CaptureCam
:
def
__init__
(
self
)
:
# 连接服务器(初始化)
self
.
sock
=
socket
.
socket
(
socket
.
AF_INET
,
socket
.
SOCK_STREAM
)
self
.
sock
.
connect
(
(
'10.0.0.30'
,
9999
)
)
# 采集视频(参数)
self
.
resolution
=
(
640
,
480
)
# 分辨率
self
.
img_fps
=
95
# each second send pictures
self
.
img
=
''
self
.
img_data
=
''
def
sendfun
(
self
)
:
camera
=
cv2
.
VideoCapture
(
0
)
img_param
=
[
int
(
cv2
.
IMWRITE_JPEG_QUALITY
)
,
self
.
img_fps
]
while
True
:
_
,
self
.
img
=
camera
.
read
(
)
self
.
img
=
cv2
.
resize
(
self
.
img
,
self
.
resolution
)
_
,
img_encode
=
cv2
.
imencode
(
'.jpg'
,
self
.
img
,
img_param
)
img_code
=
numpy
.
array
(
img_encode
)
self
.
img_data
=
img_code
.
tostring
(
)
try
:
self
.
sock
.
send
(
str
(
len
(
self
.
img_data
)
)
.
ljust
(
16
)
)
self
.
sock
.
send
(
self
.
img_data
)
except
Exception
,
err
:
print
err
camera
.
release
(
)
self
.
sock
.
close
(
)
exit
(
0
)
if
__name__
==
'__main__'
:
cam
=
CaptureCam
(
)
cam
.
sendfun
(
)
点
- python opencv imencode跟imdecode函数用法
经典用法
_
,
img_encode
=
cv2
.
imencode
(
'.jpg'
,
img
,
img_param
)
- img 是一张图片文件(在openCV中就是一个numpy的多维矩阵)
- img_param 是压缩参数
img_param
=
[
int
(
cv2
.
IMWRITE_JPEG_QUALITY
)
,
img_fps
]
- cv2.IMWRITE_JPEG_QUALITY 是openCV中的一个参数(类型是long这里需要做int转换)
- 对于jpg来说,imf_fps这个地方的数字可以是0到100,默认95。数字越大图片质量越好
参考:
https://blog.csdn.net/a19990412/article/details/80940310
https://blog.csdn.net/li_dongxuan/article/details/73135364
https://blog.csdn.net/a19990412/article/details/80930725
https://www.jianshu.com/p/4aed39710676
https://blog.csdn.net/hackjames/article/details/6943426
https://www.cnblogs.com/Leo_wl/p/3335877.html
python socket模块详解