详解OpenCV中简单的鼠标事件处理
作者:代码骑士
谈及鼠标事件,就是在触发鼠标按钮后程序所做出相应的反应,但是不影响程序的整个线程。这有些像异步处理。鼠标事件响应不会一直等着我们去按而后续程序不执行,这样会造成阻塞,而是在我们不按鼠标的时候程序也会正常进行,按的时候会调用鼠标的事件响应,这个过程就像程序一边正常运行一边等待鼠标响应。
为了将鼠标响应和操作画面进行绑定,我们要创建一个回调函数:
cv2.setMouseCallback函数语法
cv2.setMouseCallback(img,onMouse)
cv2.setMouseCallback函数参数解释:
img
:要绑定画面的名字
onMouse
:响应函数,即当鼠标事件触发时调用的函数。
示例代码:
cv2.setMouseCallback('image',draw_circle)
举个例子:
当我们在画面内单击的时候,会回调draw_circle函数,而这个被调用的函数成为响应函数,它的作用是画一个圆。调用这个函数后,我们就实现了画面与回调函数的绑定。
011-2-鼠标事件
查看所有被支持的鼠标事件:
import cv2 events = [i for i in dir(cv2) if 'EVENT' in i] print(events)
程序显示的鼠标事件:
['EVENT_FLAG_ALTKEY', 'EVENT_FLAG_CTRLKEY', 'EVENT_FLAG_LBUTTON', 'EVENT_FLAG_MBUTTON', 'EVENT_FLAG_RBUTTON', 'EVENT_FLAG_SHIFTKEY', 'EVENT_LBUTTONDBLCLK', 'EVENT_LBUTTONDOWN', 'EVENT_LBUTTONUP', 'EVENT_MBUTTONDBLCLK', 'EVENT_MBUTTONDOWN', 'EVENT_MBUTTONUP', 'EVENT_MOUSEHWHEEL', 'EVENT_MOUSEMOVE', 'EVENT_MOUSEWHEEL', 'EVENT_RBUTTONDBLCLK', 'EVENT_RBUTTONDOWN', 'EVENT_RBUTTONUP']
回调函数
在OpenCV中没有特定的写好的回调函数供我们直接使用,这需要我们自己编写,回调函数的模板如下:
def draw_circle(event,x,y,flags,param): if event == cv2.EVENT_LBUTTONDBLCLK: cv2.circle(img,(x,y),100,(255,0,0),-1)
函数分析:
代码第一行:是我们设置的函数名draw_circle以及它的参数,第一个参数event表示在什么事件下调用这个函数,x ,y可以理解为图像中鼠标指针所在的像素点的坐标值,后面两个参数暂时不用理解。
代码第二行:是事件的判定,如果发出了该事件,那么执行第三行的代码。
下面我们来通过双击鼠标左键画一个圆:
import cv2 import numpy as np #设置回调函数 def draw_circle(event,x,y,flags,param): if event == cv2.EVENT_LBUTTONDBLCLK: cv2.circle(img,(x,y),100,(255,0,0),-1) #创建图像与窗口并将窗口与回调函数进行绑定 img = np.zeros((500,500,3),np.uint8) cv2.namedWindow('image') cv2.setMouseCallback('image',draw_circle) while(1): cv2.imshow('image',img) if cv2.waitKey(1)&0xFF == ord('q'): break cv2.destroyAllWindows()
结果:
在通过拖动鼠标画一个矩形:
import cv2 import numpy as np #按下鼠标时为True drawing = False #当mode为true时绘制矩形,按下m后mode变成false,用来绘制曲线 mode = True ix,iy=-1,-1 #设置回调函数 def draw_circle(event,x,y,flags,param): global ix,iy,drawing,mode #当单击时返回起始位置坐标 if event == cv2.EVENT_LBUTTONDOWN: drawing = True ix,iy=x,y #当移动鼠标时绘制图形,event可以查看移动效果,flag检测是否发生单击 elif event == cv2.EVENT_MOUSEMOVE and flags == cv2.EVENT_FLAG_LBUTTON: if drawing == True: if mode == True: cv2.rectangle(img,(ix,iy),(x,y),(0,255,0),-1) else: #绘制圆圈,圆点连成线,3代表笔的粗细 cv2.circle(img,(x,y),3,(0,255,0),-1) #当松开鼠标时停止绘制 elif event == cv2.EVENT_LBUTTONUP: drawing ==False #创建图像与窗口并将窗口与回调函数进行绑定 img = np.zeros((500,500,3),np.uint8) cv2.namedWindow('image') cv2.setMouseCallback('image',draw_circle) while(1): cv2.imshow('image',img) k = cv2.waitKey(1) if k == ord('m'): mode=not mode elif k == ord('q'): break elif k == ord('r'): img = np.zeros((500,500,3),np.uint8) cv2.namedWindow('image') cv2.setMouseCallback('image',draw_circle) cv2.destroyAllWindows()
结果:
到此这篇关于详解OpenCV中简单的鼠标事件处理的文章就介绍到这了,更多相关OpenCV鼠标事件处理内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!