【翻譯:OpenCV-Python教程】把鼠標當做一個畫筆

⚠️這個系列是自己瞎翻的,文法很醜,跳着跳着撿重要的部分翻,翻錯了不負責,就這樣。

⚠️基於3.4.3,Mouse as a Paint-Brush,原文

目標 

簡單示例 

現在,我們創建一個簡單的應用,在我們鼠標雙擊的地方畫一個圓圈。

首先我們創建一個由鼠標事件觸發的鼠標回調方法。鼠標事件可以是任何與鼠標相關的操作,比如按下鼠標左鍵,彈起鼠標左鍵,雙擊鼠標左鍵等等。它返回給我們鼠標事件發生的座標點 (x,y) 。有了這些事件類型和發生事件的位置點,我們可以做出任何我們喜歡的操作。要列出所有被允許的鼠標事件,在python控制檯上運行下面的代碼。 

import cv2 as cv

events = [i for i in dir(cv) if 'EVENT' in i]

print( events )

創建鼠標回調方法,有一個走到哪都一樣的固定格式。唯一不同的點在於方法本身做什麼。因此我們的鼠標回調方法只幹一個事情,它畫一個圓圈在我們雙擊的地方。然後看下面的代碼,代碼自帶註釋:

import numpy as np
import cv2 as cv
# mouse callback function
def draw_circle(event,x,y,flags,param):
    if event == cv.EVENT_LBUTTONDBLCLK:
        cv.circle(img,(x,y),100,(255,0,0),-1)
# Create a black image, a window and bind the function to window
img = np.zeros((512,512,3), np.uint8)
cv.namedWindow('image')
cv.setMouseCallback('image',draw_circle)
while(1):
    cv.imshow('image',img)
    if cv.waitKey(20) & 0xFF == 27:
        break
cv.destroyAllWindows()

更復雜的示例 

現在我們要來一個更好玩的應用。在這個應用裏,我們使用好像畫圖軟件中那種拖動鼠標的方式,要麼畫框框要麼畫圓圈(取決於我們選擇的模式)。因此我們的鼠標回調方法分爲兩部分,一部分畫一個方框,另一部分畫一個圓圈。這個特殊的示例會真的幫助到我們創建和理解一些有趣的應用比如object tracking、image segmentation等等。i

import numpy as np
import cv2 as cv
drawing = False # true if mouse is pressed
mode = True # if True, draw rectangle. Press 'm' to toggle to curve
ix,iy = -1,-1
# mouse callback function
def draw_circle(event,x,y,flags,param):
    global ix,iy,drawing,mode
    if event == cv.EVENT_LBUTTONDOWN:
        drawing = True
        ix,iy = x,y
    elif event == cv.EVENT_MOUSEMOVE:
        if drawing == True:
            if mode == True:
                cv.rectangle(img,(ix,iy),(x,y),(0,255,0),-1)
            else:
                cv.circle(img,(x,y),5,(0,0,255),-1)
    elif event == cv.EVENT_LBUTTONUP:
        drawing = False
        if mode == True:
            cv.rectangle(img,(ix,iy),(x,y),(0,255,0),-1)
        else:
            cv.circle(img,(x,y),5,(0,0,255),-1)

然後咱們必須要綁定這個鼠標回調方法到一個Opencv的窗口上,在主循環下,我們得爲m鍵設置一個鍵盤綁定,用來在畫方框和畫圓圈之間切換。

img = np.zeros((512,512,3), np.uint8)
cv.namedWindow('image')
cv.setMouseCallback('image',draw_circle)
while(1):
    cv.imshow('image',img)
    k = cv.waitKey(1) & 0xFF
    if k == ord('m'):
        mode = not mode
    elif k == 27:
        break
cv.destroyAllWindows()

額外資源 

練習 

  • 在我們的示例中,我們畫了一個被填滿的矩形。 自行修改代碼畫一個沒有被填滿的。

上篇:【翻譯:OpenCV-Python教程】OpenCV裏的畫圖方法

下篇:【翻譯:OpenCV-Python教程】把拖動條當做調色板

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章