畢業設計項目做了一個在遊戲GTA5中實現自動駕駛的項目,其中一個功能是汽車的碰撞檢測。爲了實現這個功能我首先需要能實現識別汽車,對比了使用了SSD和Faster-RCNN,我選擇了YOLOv3來實現這個功能,因爲它既有速度又有精度,還非常靈活,簡直是工業界良心。
當時在網上查閱相關教程的時候,很多教程只是講到調用一下文件實現視頻文件的檢測。然而我需要對屏幕上顯示的遊戲畫面進行檢測,所以很多教程都不適用。
現在畢設做好了比較空閒,所以記錄一下順便幫助後來人,這個教程會講如何用YOLOv3檢測屏幕上的畫面。
本文旨在幫助新手快速上手YOLOv3,不會涉及詳細的代碼和相應的算法原理,具體YOLO的原理等以後有時間再寫篇詳細的~
1、下載YOLOv3的Keras版(https://github.com/qqwweee/keras-yolo3) 裏面有成熟的代碼。
2、生成Keras的.h5文件,
需要:
- 1. yolo網絡結構配置文件 .cfg ,如 yolov3.cfg
- 2. yolo訓練好的權重文件 .weights ,如 yolov3.weights
權重文件:https://pjreddie.com/media/files/yolov3.weights,此權重文件包含一些預訓練的參數。
網絡結構配置文件:項目默認自帶了YOLOv3-416的網絡的.cfg。如果需要其他網絡,則以txt文件打開.cfg文件,將第8行和第9行的參數修改爲320或608。
下圖爲各種YOLOv3版本的準確度和速度對比,根據自己項目的準確度和速度需求,選擇自己的網絡(改那個.cfg)
下面爲官網對比(https://pjreddie.com/darknet/yolo/)
下載好上述兩個文件後,將權重文件放到項目根目錄下
3、運行convert.py,將 yolov3.weights轉換成Keras能使用的.h5文件
使用方法:
python convert.py yolov3.cfg yolov3.weights yolov3.h5
執行完成示意圖
執行完成之後在當前目錄下生成yolov3.h5文件,將其重命名爲yolo.h5並放入model_data文件夾中。
4、新建grabscreen.py文件,複製以下內容,此文件裏實現用Win32API截取屏幕。相比於使用PIL,這種方式截屏速度更快
import cv2
import numpy as np
import win32gui
import win32ui
import win32con
import win32api
def grab_screen(region=None):
hwin = win32gui.GetDesktopWindow()
if region:
left, top, x2, y2 = region
width = x2 - left + 1
height = y2 - top + 1
else:
width = win32api.GetSystemMetrics(win32con.SM_CXVIRTUALSCREEN)
height = win32api.GetSystemMetrics(win32con.SM_CYVIRTUALSCREEN)
left = win32api.GetSystemMetrics(win32con.SM_XVIRTUALSCREEN)
top = win32api.GetSystemMetrics(win32con.SM_YVIRTUALSCREEN)
hwindc = win32gui.GetWindowDC(hwin)
srcdc = win32ui.CreateDCFromHandle(hwindc)
memdc = srcdc.CreateCompatibleDC()
bmp = win32ui.CreateBitmap()
bmp.CreateCompatibleBitmap(srcdc, width, height)
memdc.SelectObject(bmp)
memdc.BitBlt((0, 0), (width, height), srcdc, (left, top), win32con.SRCCOPY)
signedIntsArray = bmp.GetBitmapBits(True)
img = np.fromstring(signedIntsArray, dtype='uint8')
img.shape = (height, width, 4)
srcdc.DeleteDC()
memdc.DeleteDC()
win32gui.ReleaseDC(hwin, hwindc)
win32gui.DeleteObject(bmp.GetHandle())
return cv2.cvtColor(img, cv2.COLOR_BGRA2RGB)
5、新建example.py文件,複製以下內容 ,並運行。
import numpy as np
import cv2
import time
from grabscreen import grab_screen
from PIL import Image
from yolo import YOLO
import tensorflow as tf
config = tf.ConfigProto()
config.gpu_options.per_process_gpu_memory_fraction = 0.8 #爆顯存的話可以在此調整程序的顯存佔用情況
session = tf.Session(config=config)
yolo = YOLO()
while True:
image_array = grab_screen(region=(0, 0, 1280, 720))
# 獲取屏幕,(0, 0, 1280, 720)表示從屏幕座標(0,0)即左上角,截取往右1280和往下720的畫面
array_to_image = Image.fromarray(image_array, mode='RGB') #將array轉成圖像,才能送入yolo進行預測
img = yolo.detect_image(array_to_image) #調用yolo文件裏的函數進行檢測
img = np.asarray(img) #將圖像轉成array
cv2.imshow('window',cv2.cvtColor(img, cv2.COLOR_BGR2RGB)) #將截取的畫面從另一窗口顯示出來,對速度會有一點點影響,不過也就截取每幀多了大約0.01s的時間
if cv2.waitKey(25) & 0xFF == ord('q'): #按q退出,記得輸入切成英語再按q
cv2.destroyAllWindows()
break
6、檢測結果:
左邊爲GTA5的遊戲畫面,右邊爲檢測結果,使用一個窗口顯示出來