您的位置:首页 > 脚本大全 > > 正文

python监控系统界面(Python远程视频监控程序的实例代码)

更多 时间:2021-10-08 00:48:16 类别:脚本大全 浏览量:2746

python监控系统界面

Python远程视频监控程序的实例代码

老板由于事务繁忙无法经常亲临教研室,于是让我搞个监控系统,让他在办公室就能看到教研室来了多少人。o(>﹏<)o|||

最初我的想法是直接去网上下个软件,可是找来找去不是有毒就是收费,无奈技术不到家无法破解,只得另寻他法。

正当没有办法的时候,我看到一篇博文 一个基于python的高速视频传输程序 ,看完茅塞顿开,觉得完全可以自己写一个,在此感谢作者詹姆斯。

这个程序包括一个服务器和一个客户端。需要的库有 videocapture 和 pygame,一个用来得到摄像头的视频,一个用来显示。python库可以点这里下载:python extension packages。进去后ctrl+f找到相应的库,然后选择相应的版本即可,这里还有很多其他的库可提供下载。

我想到的解决方案是,在教研室开一台电脑,接一个usb摄像头,然后开启一个服务器程序,等待着老板使用客户端连接,由于是实时视频传输,使用udp协议。(主要传输部分采用詹姆斯的代码)。

服务器端代码如下:

  • ?
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • # -*- coding: utf-8 -*-
  • import socket
  • import time
  • import traceback
  • from videocapture import device
  • import threading
  • # 全局变量
  • is_sending = false
  • cli_address = ('', 0)
  • # 主机地址和端口
  • host = ''
  • port = 10218
  • # 初始化udp socket
  • ser_socket = socket.socket(socket.af_inet, socket.sock_dgram)
  • ser_socket.setsockopt(socket.sol_socket, socket.so_reuseaddr, 1)
  • ser_socket.bind((host, port))
  • # 接收线程类,用于接收客户端发送的消息
  • class udpreceiver(threading.thread):
  •  def __init__(self):
  •   threading.thread.__init__(self)
  •   self.thread_stop = false
  •  def run(self):
  •   while not self.thread_stop:
  •    # 声明全局变量,接收消息后更改
  •    global cli_address
  •    global is_sending
  •    try:
  •     message, address = ser_socket.recvfrom(2048)
  •    except:
  •     traceback.print_exc()
  •     continue
  •   #  print message,cli_address
  •    cli_address = address
  •    if message == 'startcam':
  •     print 'start camera',
  •     is_sending = true
  •     ser_socket.sendto('startrcv', cli_address)   
  •    if message == 'quitcam':
  •     is_sending = false
  •     print 'quit camera',
  •  def stop(self):
  •   self.thread_stop = true
  • # 创建接收线程
  • receivethread = udpreceiver()
  • receivethread.setdaemon(true)   # 该选项设置后使得主线程退出后子线程同时退出
  • receivethread.start()
  • # 初始化摄像头
  • cam = device()
  • cam.setresolution(320,240)
  • # 主线程循环,发送视频数据
  • while 1:
  •  if is_sending: 
  •   img = cam.getimage().resize((160,120))
  •   data = img.tostring()
  •   ser_socket.sendto(data, cli_address)
  •   time.sleep(0.05)
  •  else:
  •   time.sleep(1)
  • receivethread.stop()
  • ser_socket.close()
  • 服务器启动一个子线程,来监听客户端发送的消息。当有消息时,将is_sending改为true,则服务器向该客户端发送视频数据。具体信息可以看代码注释。

    客户端代码如下:

  • ?
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • # -*- coding: utf-8 -*-
  • import socket, time
  • import pygame
  • from pygame.locals import *
  • from sys import exit
  • # 服务器地址,初始化socket
  • ser_address = ('localhost', 10218)
  • cli_socket = socket.socket(socket.af_inet, socket.sock_dgram)
  • # 设置超时
  • cli_socket.settimeout(5)
  • # 向服务器发送消息,并判断接收时是否超时,若超时则重发
  • while 1:
  •  cli_socket.sendto('startcam', ser_address)
  •  try:
  •   message, address = cli_socket.recvfrom(2048)
  •   if message == 'startrcv':
  •    print message
  •    break
  •  except socket.timeout:
  •   continue
  • # 此句无用。。防止窗口初始化后等待数据
  • cli_socket.recvfrom(65536)
  • # 初始化视频窗口
  • pygame.init()
  • screen = pygame.display.set_mode((640,480))
  • pygame.display.set_caption('web camera')
  • pygame.display.flip()
  • # 设置时间,可以用来控制帧率
  • clock = pygame.time.clock()
  • # 主循环,显示视频信息
  • while 1:
  •  try:
  •   data, address = cli_socket.recvfrom(65536)
  •  except socket.timeout:
  •   continue
  •  camshot = pygame.image.frombuffer(data, (160,120), 'rgb')
  •  camshot = pygame.transform.scale(camshot, (640, 480))
  •  for event in pygame.event.get():
  •   if event.type == pygame.quit:
  •    cli_socket.sendto('quitcam', ser_address)
  •    cli_socket.close()
  •    pygame.quit()
  •    exit()
  •  screen.blit(camshot, (0,0))
  •  pygame.display.update()
  •  clock.tick(20)
  • 客户端就是简单地向服务器发送启动消息,接收到回复后开始进入主循环开始接收视频数据并显示。

    由于udp协议不保证信息是否成功到达,因此前面设置了个重发机制,只有当客户端收到服务器的回复后,才停止发送开启消息并进入主循环。具体见注释。

    使用时将localhost改成服务器ip即可,目前测试仅适用于局域网,校园网。外网暂未测试,熟悉网络编程的同学可以自行实验。

    经验

    调试的时候出现过服务器怎么都收不到客户端消息,结果调试一下午都找不到原因。晚上回来把防火墙、安全软件全关了,顺利通过。

    服务器开启新线程后,由于python奇怪的设定,主线程退出后子线程得完成后才会退出,而这里子线程又是一个死循环,因此需要对子线程调用setdaemon(true),这样主线程退出时子线程也会自动退出。若没有调用该方法,调试一次后第二次可能失败,因为后台还有个子线程在运行。

    原文链接:https://www.cnblogs.com/Leo_wl/p/3335877.html#_label0

    标签:视频 Python 监控
    您可能感兴趣