1. 程式人生 > >【Opencv-Python 官方教程】3.Opencv畫圖函式

【Opencv-Python 官方教程】3.Opencv畫圖函式

本節目標

  • 學會用Opencv畫不同的幾何形狀
  • 將會學到以下幾個函式:cv2.line()、cv2.circle()、cv2.rectangle()、cv2.ellipse()、cv2.putText()

所有上述函式,你將用到一些共同的引數如下

  • img,你畫圖的畫板,或者說背景圖。
  • color,當前繪畫的顏色。如在BGR模式下,傳遞(255,0,0)表示藍色畫筆。灰度圖下,只需要傳遞亮度值即可。
  • thickness,畫筆的粗細,線寬。若是-1表示畫封閉影象,如填充的圓。預設值是1.
  • lineType,線條的型別,如8-connected型別、anti-aliased線條(反鋸齒),預設情況下是8-connected樣式ide,cv2.LINE_AA
    表示反鋸齒線條,在曲線的時候視覺效果更佳。

畫直線

畫一條線,只需要傳遞起始點和終點座標即可,下面的程式碼建立一個黑色的畫板,然後在坐上到右下對角線上畫一個藍色的線條。

line(img, pt1, pt2, color, thickness=None, lineType=None, shift=None) ,pt1、pt2,起止點座標

import numpy as np
import cv2

# 建立一個影象作為背景圖,size:512*512,channel:3
img = np.zeros((512, 512, 3), np.uint8)

# 1.畫藍色對角線
img = cv2.line(img, (0, 0), (511, 511), (255, 0, 0), 5) # 顯示並回收資源 cv2.imshow('draw',img) cv2.waitKey(0) cv2.destroyAllWindows()

畫矩形

需要傳遞矩形的左上角和右下角兩個點座標,比如,如下程式碼在畫板的右上角畫一個綠色的矩形

# 2.畫矩形
img = cv2.rectangle(img,(384,0),(510,128),(0,255,0),3)

畫圓

需要給出中心座標和半徑。下面程式碼在上述畫出的矩形中畫一個紅色的圓,通過thickness=-1設定為填充。

# 3.畫圓
img = cv2.circle(img, (447, 63), 63, (0, 0, 255), -1)

畫橢圓

畫橢圓需要多傳遞幾個引數。首先是中心點座標,然後是長短軸的長度,之後是橢圓逆時針旋轉的角度angle,然後是startAngle和endAngle分別代表橢圓開始和結束的角度(該角度是沿長軸順時針旋轉的角度,這裡給兩個角度因為它可以畫橢圓弧,而不僅僅是滿的橢圓),比如當給引數stratAngle和endAngle分別傳遞0和360,表示畫一個滿的橢圓。更多細節,可檢視cv2.ellipse()的函式文件。下面我們畫一個半橢圓在畫布的中心。

注意,angle是整個橢圓的旋轉角度(逆時針)。startAngle和endAngle是畫筆畫過的角度(順時針)

# 4.畫橢圓
img = cv2.ellipse(img, (256, 256), (100, 50), 0, 0, 180, 255, -1)

畫多邊形(Polygon)

畫多邊形,首先需要給出一組(陣列)頂點的座標,形式是ROWSx1x2,rows表示頂點的數量,它的型別是int32.這裡我們用黃色畫一個小的4邊形。

# 5.畫多邊形
pts = np.array([[10, 5], [20, 30], [70, 20], [50, 10]], np.int32)
pts = pts.reshape((-1,1,2))
img = cv2.polylines(img, [pts], True, (0, 255, 255))

事實上,pts = pts.reshape((-1,1,2))注掉並不影響效果。

如果第三個引數設為False,只會得到頂點依次相連的圖形(首尾不連),而不會得到所有頂點封閉連線的圖形

tips:cv2.polylines()可以被用來同時畫多條線,只需要同時建立多個線段,傳入函式中,它將獨立的畫出所有線,這比重複為每條線呼叫cv2.line()更快更好。

# 6.polylines同時畫多條線
line1 = np.array([[100, 50], [200, 300]], np.int32)
line2 = np.array([[120, 60], [250, 350]], np.int32)
line3 = np.array([[180, 80], [100, 380]], np.int32)
img = cv2.polylines(img, [line1, line2, line3], False, (0, 255, 255))

新增文字

在畫布中新增文字,需要指定以下個引數:

  • Text,想要輸出到影象上的的文字
  • Position,輸出位置的座標
  • Font type,字型,可以用cv2.putText()函式文件檢視支援的字型
  • Font Scale,指定字型大小
  • 其他,如顏色,線寬,線型等,推薦使用lineType = cv2.LINE_AA
# 7.輸出文字
font = cv2.FONT_HERSHEY_SIMPLEX
cv2.putText(img,'OpenCV',(10,500), font, 4,(255,255,255),2,cv2.LINE_AA)

完整程式碼及結果如下

# -*- coding: utf-8 -*-
# @File    : 3_draw.py
# @Time    : 2018/5/23 17:41
# @Author  : hyfine
# @Contact : [email protected]
# @Desc    : draw functions

import numpy as np
import cv2

# 建立一個影象作為背景圖,size:512*512,channel:3
img = np.zeros((512, 512, 3), np.uint8)

# 1.畫藍色對角線
img = cv2.line(img, (0, 0), (511, 511), (255, 0, 0), 5)
# 2.畫矩形
img = cv2.rectangle(img, (384, 0), (510, 128), (0, 255, 0), 3)
# 3.畫圓
img = cv2.circle(img, (447, 63), 63, (0, 0, 255), -1)
# 4.畫橢圓
img = cv2.ellipse(img, (256, 256), (100, 50), 0, 0, 180, 255, -1)
# 5.畫多邊形
pts = np.array([[10, 5], [20, 30], [70, 20], [50, 10]], np.int32)
# pts = pts.reshape((-1,1,2))
# print(pts.shape)
img = cv2.polylines(img, [pts], False, (0, 255, 255))

# 6.polylines同時畫多條線
line1 = np.array([[100, 50], [200, 300]], np.int32)
line2 = np.array([[120, 60], [250, 350]], np.int32)
line3 = np.array([[180, 80], [100, 380]], np.int32)
img = cv2.polylines(img, [line1, line2, line3], False, (0, 255, 255))

# 7.輸出文字
font = cv2.FONT_HERSHEY_SIMPLEX
cv2.putText(img,'OpenCV',(10,500), font, 4,(255,255,255),2,cv2.LINE_AA)

# 顯示並回收資源
cv2.imshow('draw', img)
cv2.waitKey(0)
cv2.destroyAllWindows()

這裡寫圖片描述

練習

利用所學函式,畫opencv logo

# -*- coding: utf-8 -*-
# @File    : 3_draw_exercise.py
# @Time    : 2018/5/23 21:24
# @Author  : hyfine
# @Contact : [email protected]
# @Desc    : draw function exercise:畫opencv logo

import numpy as np
import cv2

# 1.建立一個藍色背景
img = np.zeros((512, 512, 3), np.uint8)
# 三個通道分別賦值,天藍色的rgb值是(0, 204, 255),opencv通道順序是BGR
img[:, :, 0] = np.ones([512, 512], np.uint8) * 255
img[:, :, 1] = np.ones([512, 512], np.uint8) * 204
img[:, :, 2] = np.ones([512, 512], np.uint8) * 0

# 2.畫三個帶缺口的圓,座標隨便計算,半徑為30,缺口角度為60
# 最上面的紅圈
img = cv2.ellipse(img, (256, 100), (30, 30), 120, 0, 300, (0, 0, 255), -1, cv2.LINE_AA)
# img = cv2.ellipse(img, (256, 100), (10, 10), 120, 0, 300, (255, 204, 0), -1, cv2.LINE_AA)
img = cv2.circle(img, (256, 100), 10, (255, 204, 0), -1, cv2.LINE_AA)

# 畫左下的綠色
img = cv2.ellipse(img, (226, 160), (30, 30), 0, 0, 300, (0, 255, 0), -1, cv2.LINE_AA)
img = cv2.circle(img, (226, 160), 10, (255, 204, 0), -1, cv2.LINE_AA)

# 畫右下的藍色
img = cv2.ellipse(img, (290, 160), (30, 30), -60, 0, 300, (255, 0, 0), -1, cv2.LINE_AA)
img = cv2.circle(img, (290, 160), 10, (255, 204, 0), -1, cv2.LINE_AA)

# 3.畫文字
font = cv2.FONT_HERSHEY_SIMPLEX
cv2.putText(img, 'OpenCV', (160, 240), font, 2, (255, 255, 255), 8, cv2.LINE_AA)

# 顯示並回收資源
cv2.imshow('draw', img)
cv2.waitKey(0)
cv2.destroyAllWindows()

注:此處

img = cv2.ellipse(img, (256, 100), (30, 30), 120, 0, 300, (0, 0, 255), -1, cv2.LINE_AA)
#img = cv2.ellipse(img, (256, 100), (10, 10), 120, 0, 300, (255, 204, 0), -1, cv2.LINE_AA)
img = cv2.circle(img, (256, 100), 10, (255, 204, 0), -1)

一開始畫圓形的思路時,畫兩個長短軸相等的橢圓,且開口相同(startAngle、endAngle流出60度),都使用填充畫筆,內部填充成背景顏色即可。但是這樣處理有個問題,內部會出現一個輪廓線,因為這個輪廓線是屬於外層的,且外層和背景色不同,針對這種情況,內部改用整圓畫背景色就可以了。

logo中的座標是粗略估計然後試出來的,所有logo並不精細

這裡寫圖片描述