Python运动检测编程实战演练(上)

上一篇 / 下一篇  2022-08-25 10:32:23

  概述
  由于Python编程语言面临多个开源库可用;因此,选择Python语言进行运动检测开发是很容易的。目前,运动检测已经有许多的商业应用。例如,它可以用于在线考试的监考,也可以用于商店、银行等领域的安全目的。
  Python编程语言是一种开源的且支持库极其丰富的语言,如今基于此语言已经为用户开发了大量的应用程序,并拥有大量用户。正因为如此,Python语言在市场上快速增长。Python语言的优点不胜枚举,不仅是因为它的语法简单、易于发现错误,而且其非常迅速的调试过程使其对用户更加友好。
  为什么建议您学习Python呢?我们可以使用下图来简单说明:
  Python于1991年设计,由Python软件基金会开发。如今已经发布了许多版本。其中,Python2和Python3最为著名。目前,Python3已经被广泛使用,用户数量也在快速增长。在本文这个项目中,我们将使用Python3作为开发语言。
  什么是运动检测?
  根据物理学原理,当一个物体静止不动且没有速度时,它就被认为处于静止状态;而恰恰相反的是,当一物体没有完全静止且在某个方向(无论是左右、前后或上下)上有一定的运动或速度时,它都被认为处于运动状态。在本文中,我们将尝试检测出物体的运行情况。
  目前,运动检测在现实生活中已经存在大量实现或应用,这充分证明其巨大的应用价值。其中,使用网络摄像头(我们将在本文中实现)作为安全警卫进行在线考试监考等是最典型的应用。
  在本文中,我们将尝试实现一个脚本。通过该脚本,我们将使用台式机或笔记本电脑上安装的网络摄像头实现对物体运动的检测。我们的想法是,我们将拍摄两帧视频,并试图找出它们之间的差异。如果两帧之间存在某种差异,那么很明显,相机前面的物体存在某种移动,这就产生了差异。
  主要的参考库
  在着手实现代码之前,让我们先看看我们将在代码中使用的一些模块或库,这些模块或库用于操作网络摄像头进行运动检测。正如我们所讨论的,这些开源库对于Python声誉的传播起着重要作用。让我们看看本文示例项目中需要的开源库:
  ·OpenCV
  · Pandas
  上述两个库OpenCV和Pandas都是纯粹基于Python的免费开源库,我们将通过Python语言的Python3版本来使用它们。
  1.OpenCV
  OpenCV是一个非常著名的开源库,可以与许多编程语言(如C++、Python等)一起使用,专门应用于处理图像和视频程序开发。通过与Python的开源库Pandas或者NumPy库集成应用,我们可以充分挖掘出OpenCV的功能。
  2.Pandas
  Pandas是一个开放源码的Python库,为数据分析提供了丰富的内置工具;因此,在数据科学和数据分析领域得到了广泛的应用。在Pandas中提供了数据结构形式DataFrame数据帧,这种结构对于将表格数据操作和存储到二维数据结构中提供了极方便的支持。
  上述两个模块都不是Python内置的,我们必须在使用前先安装它们。除此之外,我们还将在项目中使用另外两个模块。
  · Python日期时间(DateTime)模块
  · Python时间(Time)模块
  这两个模块都内置在Python中,以后无需安装。这些模块分别用来处理与日期和时间相关的功能。
  代码实现
  到目前为止,我们已经看到了我们将在代码中使用的库。接下来,让我们从视频只是许多静态图像或帧的组合这一假定开始,然后使用所有这些帧的组合来创建一个视频。
  导入所需的库
  在本节中,我们将首先导入所有库,如Pandas和OpenCV。然后,我们从DateTime模块导入time和DateTime函数。
  #导入Pandas库
  import Pandas as panda  
  # 导入OpenCV库
  import cv2  
  #导入时间模块
  import time  
  #从datetime 模块导入datetime 函数 
  from datetime import datetime 
  初始化数据变量
  在本节中,我们要初始化一些变量,并将在代码中进一步使用这些变量。首先,我们将初始状态定义为“None”,然后通过另一个变量motionTrackList来存储跟踪的运动。
  此外,我们还定义了一个列表“motionTime”,用于存储发现运动的时间,并使用Panda的模块初始化数据帧列表。
  # 对于初始帧,以变量initialState的形式将初始状态指定为None  
  initialState = None  
  # 帧中检测到任何运动时存储所有轨迹的列表 
  motionTrackList= [ None, None ]  
  # 一个新的“时间”列表,用于存储检测到移动时的时间  
  motionTime = []  
  # 使用带有初始列和最终列的Panda库初始化数据帧变量“DataFrame” 
  dataFrame = panda.DataFrame(columns = ["Initial", "Final"])  
  关键帧捕获过程
  在本节中,我们将实现本文示例项目中最关键的运动检测步骤。下面,让我们分步骤进行解说:
  首先,我们将开始使用cv2模块捕获视频,并将其存储在视频变量中。
  然后,我们将使用无限while循环从视频中捕获每一帧。
  接下来,将使用read()方法读取每个帧,并将它们存储到各自的变量中。
  我们定义了一个变量var_motion,并将其初始化为零。
  我们使用cv2函数cvtColor和GaussianBlur创建另外两个变量grayImage和grayFrame,以找到运动中的变化。
  如果我们的initialState为None,则我们将当前grayFrame指定为initialState;否则,使用“continue”关键字跳过后面代码的执行。
  在后面代码中,我们计算在当前迭代中创建的初始帧和灰度帧grayscale之间的差异。
  然后,我们将使用cv2阈值和dilate函数突出显示初始帧和当前帧之间的变化。
  我们将从当前图像或帧中的运动对象中找到轮廓,并通过使用rectangle函数在其周围创建绿色边界来指示运动对象。
  在此之后,我们将把当前检测到的元素添加到列表变量motionTrackList。
  到目前为止,我们已经通过使用imshow方法显示出如灰度和原始帧等所有的关键帧。
  此外,我们还使用cv2模块的witkey()方法来结束进程。程序中,我们选择使用按下键盘上的'm'键来结束我们的进程。
  # 使用cv2模块启动网络摄像头以捕获视频 
  video = cv2.VideoCapture(0)  
  # 使用无限循环从视频中捕获帧
  while True:  
     # 使用read功能从视频中读取每个图像或帧
     check, cur_frame = video.read()  
     
     #将'motion'变量定义为等于零的初始帧
     var_motion = 0  
     
     # 从彩色图像创建灰色帧 
     gray_image = cv2.cvtColor(cur_frame, cv2.COLOR_BGR2GRAY)  
     
     # 从灰度图像中使用GaussianBlur函数找到变化部分
     gray_frame = cv2.GaussianBlur(gray_image, (21, 21), 0)  
     
     # 在第一次迭代时进行条件检查
     # 如果为None,则把grayFrame赋值给变量initalState  
     if initialState is None:  
         initialState = gray_frame  
         continue  
         
     # 计算静态(或初始)帧与我们创建的灰色帧之间的差异  
     differ_frame = cv2.absdiff(initialState, gray_frame)  
     
     # 静态或初始背景与当前灰色帧之间的变化将突出显示 
     
     thresh_frame = cv2.threshold(differ_frame, 30, 255, cv2.THRESH_BINARY)[1]  
     thresh_frame = cv2.dilate(thresh_frame, None, iterations = 2)  
     
     #对于帧中的移动对象,查找轮廓
     cont,_ = cv2.findContours(thresh_frame.copy(),   
                        cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)  
     
     for cur in cont:  
         if cv2.contourArea(cur) < 10000:  
             continue  
         var_motion = 1  
         (cur_x, cur_y,cur_w, cur_h) = cv2.boundingRect(cur)  
         
         # 在移动对象周围创建一个绿色矩形
         cv2.rectangle(cur_frame, (cur_x, cur_y), (cur_x + cur_w, cur_y + cur_h), (0, 255, 0), 3)  
         
    # 从帧中添加运动状态 
     motionTrackList.append(var_motion)  
     motionTrackList = motionTrackList[-2:]  
     
     # 添加运动的开始时间 
     if motionTrackList[-1] == 1 and motionTrackList[-2] == 0:  
         motionTime.append(datetime.now())  
         
    # 添加运动的结束时间 
     if motionTrackList[-1] == 0 and motionTrackList[-2] == 1:  
         motionTime.append(datetime.now())  
         
    # 在显示捕获图像的灰度级中 
     cv2.imshow("The image captured in the Gray Frame is shown below: ", gray_frame)  
     
     # 显示初始静态帧和当前帧之间的差异 
     cv2.imshow("Difference between the  inital static frame and the current frame: ", differ_frame)  
     
     # 在框架屏幕上显示视频中的黑白图像 
     cv2.imshow("Threshold Frame created from the PC or Laptop Webcam is: ", thresh_frame)  
     
     #通过彩色框显示物体的轮廓
     cv2.imshow("From the PC or Laptop webcam, this is one example of the Colour Frame:", cur_frame)  
     
     # 创建处于等待状态的键盘按键 
     wait_key = cv2.waitKey(1)  
     
     # 按下'm'键时,结束整个进程执行
     if wait_key == ord('m'):  
         # 当屏幕上有东西移动时,将运动变量值添加到motiontime列表中 
         if var_motion == 1:  
             motionTime.append(datetime.now())  
         break 

TAG: 软件开发 Python

 

评分:0

我来说两句

Open Toolbar