opencv模塊學習

1、簡介

''' 分辨率(resolution,港臺稱之爲解析度)就是屏幕圖像的精密度,是指顯示器所能顯示的像素的多少。因爲屏幕上的點、線和麪都是由像素組成的,顯示器可顯示的像素越多,畫面就越精細,一樣的屏幕區域內能顯示的信息也越多,因此分辨率是個很是重要的性能指標之一。能夠把整個圖像想象成是一個大型的棋盤,而分辨率的表示方式就是全部經線和緯線交叉點的數目。 一、圖象分辨率(PPI) 圖像分辨率(ImageResolution):指圖像中存儲的信息量。這種分辨率有多種衡量方法,典型的是以每英寸的像素數(PPI,pixelperinch)來衡量;固然也有以每釐米的像素數(PPC,pixelpercentimeter)來衡量的。圖像分辨率決定了圖像輸出的質量,而圖像分辨率和圖象尺寸(高寬)的值一塊兒決定文件的大小,且該值越大圖形文件所佔用的磁盤空間也就越多。圖像分辨率以比例關係影響着文件的大小,即文件大小與其圖像分辨率的平方成正比。若是保持圖像尺寸不變,將圖像分辨率提升一倍,則其文件大小增大爲原來的四倍。 二、掃描分辨率(SPI) 掃描分辨率:指在掃描一幅圖像以前所設定的分辨率,它將影響所生成的圖像文件的質量和使用性能,它決定圖像將以何種方式顯示或打印。若是掃描圖像用於640×480像素的屏幕顯示,則掃描分辨率沒必要大於通常顯示器屏幕的設備分辨率,即通常不超過120DPI。但大多數狀況下,掃描圖像是爲了在高分辨率的設備中輸出。若是圖像掃描分辨率太低,會致使輸出的效果很是粗糙。反之,若是掃描分辨率太高,則數字圖像中會產生超過打印所須要的信息,不但減慢打印速度,並且在打印輸出時會使圖像色調的細微過渡丟失。通常狀況下,圖像分辨率應該是網屏分辨率的2倍,這是目前中國大多數輸出中心和印刷廠都採用的標準。然而實際上,圖像分辨率應該是網幕頻率的1.5倍,關於這個問題,恐怕會有爭議,而具體到不一樣的圖像自己,狀況也確實各不相同。要了解詳細內容,請看《網屏角度及輸出分辨率》。可能有不少朋友沒有明白這其中是如何計算的,下面筆者就簡單的講解一下PPI的計算方法。首先,咱們先了解一下什麼叫PPI,PPI是英文Pixelsperinch的縮寫,意思就是每英寸所擁有的像素(Pixel)數目,搞清楚了PPI是什麼意思,咱們就能很容易理解PPI的計算方式了,咱們須要首先算出手機屏幕的對角線等效像素,而後除以對角線(咱們日常所說的手機屏幕尺寸就是說的手機屏幕對角線的長度),就能夠獲得PPI了。準確的計算公示你們能夠參照下圖。比較有意思的是,根據公式計算出來的iPhone4的PPI爲330,要比蘋果官方公佈的326要高一點點。 三、網屏分辨率(LPI) 網屏分辨率(ScreenResolution):又稱網幕頻率(是印刷術語),指的是印刷圖像所用的網屏的每英寸的網線數(即掛網網線數),以(LPI)來表示。例如,150LPI是指每英寸加有150條網線。 四、設備分辨率 設備分辨率(DeviceResolution):又稱輸出分辨率,指的是各種輸出設備每英寸上可產生的點數,如顯示器、噴墨打印機、激光打印機、繪圖儀的分辨率。這種分辨率經過DPI來衡量,目前,PC顯示器的設備分辨率在60至120DPI之間。而打印設備的分辨率則在360至2400DPI之間。 五、圖像的位分辨率 圖像的位分辨率(BitResolution):又稱位深,是用來衡量每一個像素儲存信息的位數。這種分辨率決定能夠標記爲多少種色彩等級的可能性。通常常見的有8位、16位、24位或32位色彩。有時咱們也將位分辨率稱爲顏色深度。所謂「位」,其實是指「2」的平方次數,8位便是2的八次方,也就是8個2相乘,等於256。因此,一幅8位色彩深度的圖像,所能表現的色彩等級是256級。 六、打印機的分辨率 某臺爲360DPI,是指在用該打印機輸出圖像時,在每英寸打印紙上能夠打印出360個表徵圖像輸出效果的色點。表示打印機分辨率的這個數越大,代表圖像輸出的色點就越小,輸出的圖像效果就越精細。打印機色點的大小隻同打印機的硬件工藝有關,而與要輸出圖像的分辨率無關。 七、掃描儀的分辨率 要從三個方面來肯定:光學部分、硬件部分和軟件部分。也就是說,掃描儀的分辨率等於其光學部件的分辨率加上其自身經過硬件及軟件進行處理分析所獲得的分辨率。光學分辨率是掃描儀的光學部件在每平方英寸面積內所能捕捉到的實際的光點數,是指掃描儀CCD的物理分辨率,也是掃描儀的真實分辨率,它的數值是由CCD的像素點除以掃描儀水平最大可掃尺寸獲得的數值。分辨率爲1200DPI的掃描儀,其光學部分的分辨率只佔400~600DPI。擴充部分的分辨率,是經過計算機對圖像進行分析,對空白部分進行科學填充所產生的(由硬件和軟件所生成,這一過程也叫「插值」處理)。光學掃描與輸出是一對一的,掃描到什麼,輸出的就是什麼。通過計算機軟硬件處理以後,輸出的圖像就會變得更逼真,分辨率會更高。目前市面上出售的掃描儀大都具備對分辨率的軟、硬件擴充功能。有的掃描儀廣告上寫9600×9600DPI,這只是經過軟件"插值"所獲得的最大分辨率,並非掃描儀真正光學分辨率。因此對掃描儀來說,其分辨率有光學分辨率(或稱光學解析度)和最大分辨率之說。咱們說某臺掃描儀的分辨率高達4800DPI(這個4800DPI是光學分辨率和軟件差值處理的總和),是指用掃描儀輸入圖像時,在1平方英寸的掃描幅面上,可採集到4800×4800個像素點(Pixel)。1英寸見方的掃描區域,用4800DPI的分辨率掃描後生成的圖像大小是4800Pixel×4800Pixel。在掃描圖像時,掃描分辨率設得越高,生成的圖像的效果就越精細,生成的圖像文件也就越大,但插值成分也越多。關於掃描儀、打印機、顯示器的分辨率對掃描儀、打印機及顯示器等硬件設備來講,其分辨率用每英寸上可產生的點數即DPI(DotsPerInch)來度量。 八、顯示器的分辨率 顯示裝置能有效辨別的最小的示值差。顯示器的分辨率爲80DPI,是指在顯示器的有效顯示範圍內,顯示器的顯像設備能夠在每英寸熒光屏上產生80個光點。舉個例子來講,一臺14英寸的顯示器(熒光屏對角線長度爲14英寸),其點距爲0.28mm,那麼:顯示器分辨率=25.39956mm/inch÷0.28mm/Dot≈90DPI(1inch=2.539999918cm)。顯示器出廠時通常並不標出表徵顯示器分辨率的DPI值,只給出點距,咱們根據上述公式便可算出顯示器的分辨率。根據咱們算出的DPI值,咱們進而能夠推算出顯示器可支持的最高顯示模式。假設該14英寸顯示器熒光屏有效顯示範圍的對角線長度爲11.5英寸,因顯示器的水平方向和垂直方向的顯示比例爲4:3,故可設有效顯示範圍水平寬度爲4x英寸,垂直高度爲3x英寸,根據數學上的勾股定理,可得x=11.5÷5=2.3英寸。因此有效顯示範圍寬度爲2.3×4=9.2英寸,垂直高度爲2.3×3=6.8英寸。最高顯示模式約爲:800(9.2×90)×600(6.8×90),這時是用一個點(Dot)表示一個像素(pixel)。上面主要講述了掃描儀、打印機和顯示器的設備分辨率。特別提醒:設備分辨率與用該設備處理的圖像的分辨率是兩個既有聯繫又有區別的概念。測量儀器方面的分辨率。 九、數碼相機的分辨率 數碼相機分辨率的高低決定了所拍攝的影像最終可以打印出高質量畫面的大小,或在計算機顯示器上所可以顯示畫面的大小。數碼相機分辨率的高低,取決於相機中CCD(ChargeCoupledDevice:電荷耦合器件)芯片上像素的多少,像素越多,分辨率越高。因而可知,數碼相機的最大分辨率也是由其生產工藝決定的,但用戶能夠調整到更低分辨率以減小照片佔用的空間。就同類數碼相機而言,最大分辨率越高,相機檔次越高。但高分辨率的相機生成的數據文件很大,對加工、處理的計算機的速度、內存和硬盤的容量以及相應軟件都有較高的要求。數碼相機像素水平的高低與最終所能打印必定分辨率照片的尺寸,可用如下方法簡單計算:假如彩色打印機的分辨率爲NDPI,數碼相機水平像素爲M,最大可打印出的照片爲M÷N英寸。好比,打印機的分辨率爲300DPI,那麼水平像素爲3600的數碼相機,其所攝的影像文件不做插值處理可以打印出的最大照片尺寸爲12英寸(3600÷300)。很顯然,要打印出尺寸越大的數碼照片,就須要越高像素水平的數碼相機。計算顯示尺寸的方法與打印尺寸的方法相同。 十、投影機的分辨率 投影機的分辨率有兩種常見的表示方式,一種是以電視線(TV線)的方式表示,另外一種是以像素的方式表示。以電視線表示時,其分辨率的含義與電視類似,這種分辨率表示方式主要是爲了匹配接入投影機的電視信號而提供的。以像素方式表示時一般表示爲1024×768等形式,從某種意義上講這種分辨率的限制是對輸入投影機的VGA信號的行頻及場頻做必定要求。當VGA信號的行頻或場頻超過這個限制後,投影機就不能正常投顯了。 十一、商業印刷領域的分辨率 在商業印刷領域,分辨率以每英寸上等距離排列多少條網線即LPI(LinesPerInch)表示。在傳統商業印刷製版過程當中,製版時要在原始圖像前加一個網屏,這一網屏由呈方格狀的透明與不透明部分相等的網線構成。這些網線也就是光柵,其做用是切割光線解剖圖像。因爲光線具備衍射的物理特性,所以光線經過網線後,造成了反映原始圖像影像變化的大小不一樣的點,這些點就是半色調點。一個半色調點最大不會超過一個網格的面積,網線越多,表現圖像的層次越多,圖像質量也就越好。所以商業印刷行業中採用了LPI表示分辨率。 十二、電視的分辨率 在電視工業中,分辨率指的是在熒光屏等於像高的距離內人眼所能分辨的黑白條紋數,單位是電視線(TV線)。咱們國家採用的電視標準是PAL制式,它規定每秒25幀,每幀625掃描行。因爲採用了隔行掃描方式,625行掃描線分爲奇數行和偶數行,這分別構成了每一幀的奇、偶兩場,因爲在每一幀中電子束都要從上面開始掃描,所以存在着電子束從終點回到起點的掃描逆程期,在這期間被消隱的掃描行是不可能分解圖像的。掃描逆程期約佔整個掃描時間的8%,所以625行中用於掃描圖像的有效行數只有576行,由此推導出圖像在垂直方向上的分辨率爲576點。按現行4∶3寬高比的電視標準,圖像在水平方向上的分辨率應爲576×4/3=768點,這就獲得了768×576這一常見的圖像大小。另外,在計算機視頻捕捉時,咱們還會遇到遵循CCIR601標準的PAL制式圖像尺寸,其大小爲720×576。對於咱們還能接觸到的NTSC制式來說,它規定每秒30幀,每幀525行,一樣採用了隔行掃描方式,每一幀由兩場組成,其圖像大小是720×486。日本的D端子,採用了相似計算機的多針D型插接頭,用來直接傳輸數字圖像信號,根據傳輸數字信號的規格不一樣,D端子已經造成了一個系列的型號。目前有D一、D二、D三、D四、D5,系列序號越高,傳輸數據的規格越高。 1三、鼠標的分辨率 鼠標的分辨率是指每移動一英寸能檢測出的點數,分辨率越高,質量也就越高。之前鼠標的分辨率一般爲100DPI,如今的鼠標分辨率從200DPI到1000DPI不等。高分辨率的鼠標一般用於製圖和精確計算機繪圖等。 1四、觸摸屏的分辨率 觸摸屏的分辨率是指將屏幕分割成可識別的觸點數目。一般用水平和垂直方向上的觸點數目來表示,如32×32。有的人認爲觸摸屏的分辨率越高越好,其實並不是如此,在選用觸摸屏時應根據具體用途加以考慮。採用模擬量技術的觸摸屏分辨率很高,可達到1024×1024,能勝任一些相似屏幕繪畫和寫字(手寫識別)的工做。而在多數場合下,觸摸技術的應用只是讓人們用手觸摸來選擇軟件設計的「按鈕」,沒有必要使用很是高的分辨率。例如在14英寸顯示器上使用觸摸屏時,顯示區域的實際大小通常是25cm×18.5cm,一個分辨率爲32×32的觸摸屏就能把屏幕分割成1024個0.78cm×0.58cm(比一支香菸還細小)的觸點。人的手指按壓觸摸屏的觸點比香菸的直徑大多了,因此這樣一個觸點就已經足夠了。 1五、望遠鏡分辨率 望遠鏡的分辨率,也能夠說是光學透鏡的分辨率。光具備波動性和粒子性,因此經過透鏡匯聚的光線投射到感光元件上,若是兩個像點距離很小,就會發生干涉,如右圖。角度這個參數就是望遠鏡或者透鏡的理論分辨率,通常用弧度表示。 這個數值越小,也就是能夠分辨的物體越細小,那麼透鏡的分辨率越高,這個角度與透鏡的口徑和所使用波長有關,理論計算可得最小分辨角:r=1.22λ/D,其中λ爲觀測波長,D爲望遠鏡的口徑,兩者取同一單位時r的單位爲弧度。對於目視觀測,一般取λ爲肉眼最敏感的550nm。這個數值是一個理論結果,實際上地面觀測,受到氣流,污染物,雜光等的影響也就達不到這個最好的效果,也就是分辨率要降低。對於人眼來說,平均瞳孔直徑7mm,有60角秒的分辨率,而對於口徑116mm口徑的小型望遠鏡,具備1角秒的分辨率。 1六、顯微物鏡的分辨率 顯微物鏡的分辨率即物面上能分開的最短距離,由如下公式計算σ=0.61λ/NA其中σ爲顯微物鏡分辨率,λ爲光源波長,NA爲顯微物鏡的數值孔徑。 1七、顯示器分辨率設置與疾病預防 有研究顯示,在800×600分辨率環境下工做的人,更有機會患上一些疾病,這與用手機打一天電話的效果是同樣的。所以,有專家提示人們應將顯示器分辨率設置爲1024×768以上,這樣能夠擋住更多輻射。 '''
分辨率

OpenCV安裝
pip install --upgrade setuptools
pip install numpy Matplotlib
pip install opencv-pythonphp

2、定義
3、結構分析

和Python同樣,當前的OpenCV也有兩個大版本,OpenCV2和OpenCV3。相比OpenCV2,OpenCV3提供了更強的功能和更多方便的特性。不過考慮到和深度學習框架的兼容性,以及上手安裝的難度,這部分先以2爲主進行介紹。python

根據功能和需求的不一樣,OpenCV中的函數接口大致能夠分爲以下部分:算法

''' 一、core:核心模塊,主要包含了OpenCV中最基本的結構(矩陣,點線和形狀等),以及相關的基礎運算/操做。 二、imgproc:圖像處理模塊,包含和圖像相關的基礎功能(濾波,梯度,改變大小等),以及一些衍生的高級功能(圖像分割,直方圖,形態分析和邊緣/直線提取等)。 三、highgui:提供了用戶界面和文件讀取的基本函數,好比圖像顯示窗口的生成和控制,圖像/視頻文件的IO等。 '''
View Code

若是不考慮視頻應用,以上三個就是最核心和經常使用的模塊了。針對視頻和一些特別的視覺應用,OpenCV也提供了強勁的支持:canvas

''' 一、video:用於視頻分析的經常使用功能,好比光流法(Optical Flow)和目標跟蹤等。 二、calib3d:三維重建,立體視覺和相機標定等的相關功能。 三、features2d:二維特徵相關的功能,主要是一些不受專利保護的,商業友好的特徵點檢測和匹配等功能,好比ORB特徵。 四、object:目標檢測模塊,包含級聯分類和Latent SVM 五、ml:機器學習算法模塊,包含一些視覺中最經常使用的傳統機器學習算法。 六、flann:最近鄰算法庫,Fast Library for Approximate Nearest Neighbors,用於在多維空間進行聚類和檢索,常常和關鍵點匹配搭配使用。 七、gpu:包含了一些gpu加速的接口,底層的加速是CUDA實現。 八、photo:計算攝像學(Computational Photography)相關的接口,固然這只是個名字,其實只有圖像修復和降噪而已。 九、stitching:圖像拼接模塊,有了它能夠本身生成全景照片。 十、nonfree:受到專利保護的一些算法,其實就是SIFT和SURF。 十一、contrib:一些實驗性質的算法,考慮在將來版本中加入的。 十二、legacy:字面是遺產,意思就是廢棄的一些接口,保留是考慮到向下兼容。 1三、ocl:利用OpenCL並行加速的一些接口。 1四、superres:超分辨率模塊,其實就是BTV-L1(Biliteral Total Variation – L1 regularization)算法 1五、viz:基礎的3D渲染模塊,其實底層就是著名的3D工具包VTK(Visualization Toolkit)。 '''
View Code

4、範例分析

一、存取圖像:主要包含圖像的讀取、存儲、圖片模式的轉換、格式的轉換。框架

#導入cv模塊
import cv2 as cv # 讀取一張487x650分辨率的圖像
color_img1 = cv.imread('D:\\picture\\timg.jpg') print(color_img1.shape)            #(487, 650, 3)
print(type(color_img))    #<type 'numpy.ndarray'>

# 直接讀取單通道灰度圖
color_img2 = cv.imread('D:\\picture\\timg.jpg',cv.IMREAD_GRAYSCALE) print(color_img2.shape)        #(487, 650)

# 把單通道圖片保存後,再讀取,仍然是3通道,至關於把單通道值複製到3個通道保存
cv.imwrite('D:\\picture\\stimg.jpg', color_img2) color_img3 = cv.imread('D:\\picture\\stimg.jpg') print(color_img3.shape)        #(487, 650, 3);stimg.jpg是灰色圖。

# cv2.IMWRITE_JPEG_QUALITY指定jpg質量,範圍0到100,默認95,越高畫質越好,文件越大
cv.imwrite('D:\\picture\\sgtimg.jpg', color_img1, (cv.IMWRITE_JPEG_QUALITY, 80)) # cv2.IMWRITE_PNG_COMPRESSION指定png質量,範圍0到9,默認3,越高文件越小,畫質越差
cv.imwrite('D:\\picture\\sg.png', color_img1, (cv.IMWRITE_PNG_COMPRESSION, 5))
View Code

二、縮放,裁剪和補邊:主要包括圖片大小縮放(比例縮放、按指定值縮放)、局部裁剪、周邊補色less

#導入cv模塊
import cv2 as cv # 讀取一張原始圖片
img = cv.imread('D:\\picture\\timg.jpg') # 縮放成200x200的方形圖像
img_200x200 = cv.resize(img, (200, 200)) # 不直接指定縮放後大小,經過fx和fy指定縮放比例,0.5則長寬都爲原來一半 # 等效於img_100x100 = cv2.resize(img, (100, 100)),注意指定大小的格式是(寬度,高度) # 插值方法默認是cv2.INTER_LINEAR,這裏指定爲最近鄰插值
img_100x100 = cv.resize(img_200x200, (0, 0), fx=0.5, fy=0.5,interpolation=cv.INTER_NEAREST) # 在上張圖片的基礎上,上下各貼50像素的黑邊,生成300x300的圖像
img_200x100 = cv.copyMakeBorder(img_100x100, 50, 50, 0, 0,cv.BORDER_CONSTANT,value=(0, 0, 0)) # 對照片中局部進行剪裁
patch_img = img[220:550, -180:-50] cv.imwrite('img/cropped_img.jpg', patch_img) cv.imwrite('img/resized_200x200.jpg', img_200x200) cv.imwrite('img/resized_100x100.jpg', img_100x100) cv.imwrite('img/bordered_200x100.jpg', img_200x100)
View Code

三、色調,明暗,直方圖和Gamma曲線:主要包含色度、飽和度、明暗的條件。dom

import cv2 as cv
img = cv.imread('D:\\picture\\timg.jpg')

# 經過cv2.cvtColor把圖像從BGR轉換到HSV
img_hsv = cv.cvtColor(img, cv.COLOR_BGR2HSV)

# H空間中,綠色比黃色的值高一點,因此給每一個像素+15,黃色的樹葉就會變綠
turn_green_hsv = img_hsv.copy()
turn_green_hsv[:, :, 0] = (turn_green_hsv[:, :, 0]+15) % 180
turn_green_img = cv.cvtColor(turn_green_hsv, cv.COLOR_HSV2BGR)
cv.imwrite('D:\\picture\\img\\turn_green.jpg', turn_green_img)

# 減少飽和度會讓圖像損失鮮豔,變得更灰
colorless_hsv = img_hsv.copy()
colorless_hsv[:, :, 1] = 0.5 * colorless_hsv[:, :, 1]
colorless_img = cv.cvtColor(colorless_hsv, cv.COLOR_HSV2BGR)
cv.imwrite('D:\\picture\\img\\colorless.jpg', colorless_img)

# 減少明度爲原來一半
darker_hsv = img_hsv.copy()
darker_hsv[:, :, 2] = 0.5 * darker_hsv[:, :, 2]
darker_img = cv.cvtColor(darker_hsv, cv.COLOR_HSV2BGR)
cv.imwrite('D:\\picture\\img\\darker.jpg', darker_img)
View Code

四、圖像的仿射變換:主要包括縮放、旋轉、剪切、翻轉、平移,以及他們之間的組合機器學習

#導入cv模塊
import cv2 as cv
import numpy as np
# =====================圖像的仿射變換===============================
# 仿射變換具體到圖像中的應用,主要是對圖像的縮放,旋轉,剪切,翻轉和平移的組合。

# 讀取一張原始照片
img = cv.imread('D:\\picture\\src_400x600.jpg')

# 沿着橫縱軸放大1.6倍,而後平移(-150,-240),最後沿原圖大小截取,等效於裁剪並放大
M_crop_elephant = np.array([
[1.6, 0, -150],
[0, 1.6, -240]
], dtype=np.float32)

img_elephant = cv.warpAffine(img, M_crop_elephant, (400, 600))
cv.imwrite('D:\\picture\\img\\lanka_elephant.jpg', img_elephant)

# x軸的剪切變換,角度15°
theta = 15 * np.pi / 180
M_shear = np.array([
[1, np.tan(theta), 0],
[0, 1, 0]
], dtype=np.float32)

img_sheared = cv.warpAffine(img, M_shear, (400, 600))
cv.imwrite('D:\\picture\\img\\lanka_safari_sheared.jpg', img_sheared)

# 順時針旋轉,角度15°
M_rotate = np.array([
[np.cos(theta), -np.sin(theta), 0],
[np.sin(theta), np.cos(theta), 0]
], dtype=np.float32)

img_rotated = cv.warpAffine(img, M_rotate, (400, 600))
cv.imwrite('D:\\picture\\img\\lanka_safari_rotated.jpg', img_rotated)

# 某種變換,具體旋轉+縮放+旋轉組合能夠經過SVD分解理解
M = np.array([
[1, 1.5, -400],
[0.5, 2, -100]
], dtype=np.float32)

img_transformed = cv.warpAffine(img, M, (400, 600))
cv.imwrite('D:\\picture\\img\\lanka_safari_transformed.jpg', img_transformed)
View Code

 五、基本繪圖:能夠在畫面上繪製線段,圓,矩形和多邊形等,還能夠在圖像上指定位置打印文字ide

#coding=utf-8
import cv2 as cv import numpy as np # 定義一塊寬600,高400的畫布,初始化爲白色
canvas = np.zeros((400, 600, 3), dtype=np.uint8) + 255

# 畫一條縱向的正中央的黑色分界線
cv.line(canvas, (300, 0), (300, 399), (0, 0, 0), 2) # 畫一條右半部份畫面以150爲界的橫向分界線
cv.line(canvas, (300, 149), (599, 149), (0, 0, 0), 2) # 左半部分的右下角畫個紅色的圓
cv.circle(canvas, (200, 300), 75, (0, 0, 255), 5) # 左半部分的左下角畫個藍色的矩形
cv.rectangle(canvas, (20, 240), (100, 360), (255, 0, 0), thickness=3) # 定義兩個三角形,並執行內部綠色填充
triangles = np.array([ [(200, 240), (145, 333), (255, 333)], [(60, 180), (20, 237), (100, 237)]]) cv.fillPoly(canvas, triangles, (0, 255, 0)) # 畫一個黃色五角星 # 第一步經過旋轉角度的辦法求出五個頂點
phi = 4 * np.pi / 5 rotations = [[[np.cos(i * phi), -np.sin(i * phi)], [i * np.sin(phi), np.cos(i * phi)]] for i in range(1, 5)] pentagram = np.array([[[[0, -1]] + [np.dot(m, (0, -1)) for m in rotations]]], dtype=np.float) # 定義縮放倍數和平移向量把五角星畫在左半部分畫面的上方
pentagram = np.round(pentagram * 80 + np.array([160, 120])).astype(np.int) # 將5個頂點做爲多邊形頂點連線,獲得五角星
cv.polylines(canvas, pentagram, True, (0, 255, 255), 9) # 按像素爲間隔從左至右在畫面右半部份的上方畫出HSV空間的色調連續變化
for x in range(302, 600): color_pixel = np.array([[[round(180*float(x-302)/298), 255, 255]]], dtype=np.uint8) line_color = [int(c) for c in cv.cvtColor(color_pixel, cv.COLOR_HSV2BGR)[0][0]] cv.line(canvas, (x, 0), (x, 147), line_color) # 若是定義圓的線寬大於半斤,則等效於畫圓點,隨機在畫面右下角的框內生成座標
np.random.seed(42) n_pts = 30 pts_x = np.random.randint(310, 590, n_pts) pts_y = np.random.randint(160, 390, n_pts) pts = zip(pts_x, pts_y) # 畫出每一個點,顏色隨機
for pt in pts: pt_color = [int(c) for c in np.random.randint(0, 255, 3)] cv.circle(canvas, pt, 3, pt_color, 5) # 在左半部分最上方打印文字
cv.putText(canvas, 'hostname just english', (5, 15), cv.FONT_HERSHEY_SIMPLEX, 0.5, (0, 0, 0), 1) cv.imshow('new', canvas) cv.waitKey()
View Code

六、相機功能:一個是VideoCapture,用於獲取相機設備並捕獲圖像和視頻,或是從文件中捕獲。還有一個VideoWriter,用於生成視頻。函數

  下面的代碼會根據電腦攝像頭捕捉到的信息,在img文件夾下生成一個save.avi的視頻文件。

#coding=utf-8 #導入cv模塊
import time import cv2 as cv import os import sys interval = 1 # 捕獲圖像的間隔,單位:秒
num_frames = 50 # 捕獲圖像的總幀數
out_fps = 24 # 輸出文件的幀 # VideoCapture(0)表示打開默認的相機
cap = cv.VideoCapture(0) # 獲取捕獲的分辨率
size = (int(cap.get(cv.CAP_PROP_FRAME_WIDTH)), int(cap.get(cv.CAP_PROP_FRAME_HEIGHT))) # 設置要保存視頻的編碼,分辨率和幀率
video = cv.VideoWriter("D:\\picture\\img\\save.avi", cv.VideoWriter_fourcc('M', 'P', '4', '2'), # 視頻編碼格式參考 http://www.fourcc.org/codecs.php
 out_fps, size ) # 對於一些低畫質的攝像頭,前面的幀可能不穩定,略過
for i in range(42): cap.read() # 開始捕獲,經過read()函數獲取捕獲的幀
try: for i in range(num_frames): _, frame = cap.read() video.write(frame) # 若是但願把每一幀也存成文件,好比製做GIF,則容許下面的代碼運行 # filename = '{:0>6d}.png'.format(i) # cv.imwrite(filename, frame)
        print('Frame {} is captured.'.format(i)) time.sleep(interval) except KeyboardInterrupt: # 捕獲提早中止。方便後面使已經捕獲好的部分視頻能夠順利生成
    print('Stopped! {}/{} frames captured!'.format(i, num_frames)) # 釋放資源並寫入視頻文件
video.release() cap.release()
View Code

七、視頻文件功能:間隔讀取視頻文件中的每幀的圖片。

#coding=utf-8 #導入cv模塊
import time,os,sys import cv2 as cv frame_path="D:\\picture\\img\\frames"  # 存放視頻截圖的文件夾路徑

# 第二個輸入參數是設定每隔多少幀截取一幀
frame_interval = 1

if not os.path.exists(frame_path): os.mkdir(frame_path) # 初始化一個VideoCapture對象
cap = cv.VideoCapture() filepath = "D:\\picture\\img\\save.avi"

# VideoCapture::open函數能夠從文件獲取視頻
cap.open(filepath) # 獲取視頻幀數
n_frames = int(cap.get(cv.CAP_PROP_FRAME_COUNT)) print(n_frames) # 一樣爲了不視頻頭幾幀質量低下,黑屏或者無關等
for i in range(2): cap.read() for i in range(2,n_frames):  # 讀取後面的幀數據
    ret, frame = cap.read() # 每隔frame_interval幀進行一次截屏操做
    if i % frame_interval == 0: imagepath = frame_path+'/video_test'+ str(i)+".jpg"
        print('導出 {}!'.format(imagepath)) cv.imwrite(imagepath, frame) # 執行結束釋放資源
cap.release()
View Code

八、交互——播放圖片:窗口播放圖片、循環播放圖片

#coding=utf-8
#導入cv模塊
import time,os,sys
import cv2 as cv
from itertools import cycle
# =====================OpenCV窗口顯示===============================
img = cv.imread('D:\\picture\\img\\test.jpg')
cv.imshow('Window Title', img)
cv.waitKey()
# =====================OpenCV窗口循環===============================
frame_path="D:\\picture\\img\\frames"  # 圖片的文件夾路徑
# 列出frames文件夾下的全部圖片
filenames = os.listdir(frame_path)

# 經過itertools.cycle生成一個無限循環的迭代器,每次迭代都輸出下一張圖像對象
img_iter = cycle([cv.imread(os.sep.join([frame_path, x])) for x in filenames])

key = 0
while key & 0xFF != 27:
    cv.imshow('window title', next(img_iter))
    key = cv.waitKey(500)  # cv.waitKey()參數不爲零的時候則能夠和循環結合產生動態畫面
View Code

九、交互——鼠標事件:主要包括爲窗口綁定鼠標事件的處理。

#coding=utf-8
#導入cv模塊
import time,os,sys
import cv2
from itertools import cycle

# 定義鼠標事件回調函數
def on_mouse(event, x, y, flags, param):

    # 鼠標左鍵按下,擡起,雙擊
    if event == cv2.EVENT_LBUTTONDOWN:
        print('左鍵按下 ({}, {})'.format(x, y))
    elif event == cv2.EVENT_LBUTTONUP:
        print('左鍵彈起 ({}, {})'.format(x, y))
    elif event == cv2.EVENT_LBUTTONDBLCLK:
        print('左鍵雙擊 ({}, {})'.format(x, y))

    # 鼠標右鍵按下,擡起,雙擊
    elif event == cv2.EVENT_RBUTTONDOWN:
        print('右鍵按下 ({}, {})'.format(x, y))
    elif event == cv2.EVENT_RBUTTONUP:
        print('右鍵彈起 ({}, {})'.format(x, y))
    elif event == cv2.EVENT_RBUTTONDBLCLK:
        print('右鍵雙擊 ({}, {})'.format(x, y))

    # 鼠標中/滾輪鍵(若是有的話)按下,擡起,雙擊
    elif event == cv2.EVENT_MBUTTONDOWN:
        print('中間鍵按下 ({}, {})'.format(x, y))
    elif event == cv2.EVENT_MBUTTONUP:
        print('中間鍵彈起 ({}, {})'.format(x, y))
    elif event == cv2.EVENT_MBUTTONDBLCLK:
        print('中間鍵雙擊 ({}, {})'.format(x, y))

    # 鼠標移動
    elif event == cv2.EVENT_MOUSEMOVE:
        print('移動到 ({}, {})'.format(x, y))

# 爲指定的窗口綁定自定義的回調函數
cv2.namedWindow('window title')
cv2.setMouseCallback('window title', on_mouse)  # 第一個參數爲要綁定的窗口名稱,第二個參數爲要綁定的鼠標事件
cv2.waitKey()
View Code

5、功能運用
6、小結

相關文章
相關標籤/搜索