**非常詳細的視頻和文字教程,講解常見的openmv教程包括 巡線、物體識別、圓環(huán)識別、閾值自動獲取等。非常適合學習openmv、K210、K230等項目
視頻合集鏈接在
openmv教程合集 openmv入門到項目開發(fā) openmv和STM32通信 openmv和opencv區(qū)別 openmv巡線 openmv數(shù)字識別教程LCD
??痮penmv視覺文章鏈接:
https://blog.csdn.net/qq_46187594/category_12900902.html
一種常見的識別算法優(yōu)化方法,先根據(jù)物體特征縮小識別范圍,在特征的范圍內(nèi)進行某種識別算法,比如根據(jù)數(shù)字是黑色方框框起來的特征,先識別黑色框,然后框內(nèi)進行匹配。
我們使用3.5.2中的2的進行優(yōu)化,優(yōu)化方式是 先讓openmv識別框,然后框內(nèi)進行數(shù)字模板匹配
效果還可以幀率20左右,可以識別到的框然后進行數(shù)字識別的,偶爾會識別不到兩個數(shù)字,可能只能識別一個數(shù)字
下面這個代碼幀率20,可以同時識別兩個數(shù)字,
# 多模板匹配系統(tǒng)
import time
import sensor
import image
# ******************** 硬件初始化配置 ********************
sensor.reset() # 復位攝像頭硬件
sensor.set_contrast(1) # 設置對比度(范圍0-3)
sensor.set_gainceiling(16) # 設置最大增益值(2^16)
sensor.set_framesize(sensor.QQVGA) # 設置分辨率160x120(低分辨率提升處理速度)
sensor.set_pixformat(sensor.GRAYSCALE) # 灰度圖像模式(減少計算量)
sensor.set_vflip(True) # 垂直翻轉圖像(適配攝像頭安裝方向)
sensor.set_hmirror(True) # 水平鏡像圖像(解決鏡頭鏡像問題)
# ******************** 用戶可調參數(shù) ********************
TEMPLATE_PATHS = [ # 模板文件路徑列表(按0-9順序)
"/0.pgm", "/1.pgm", "/2.pgm",
"/3.pgm", "/4.pgm", "/5.pgm",
"/6.pgm", "/7.pgm", "/8.pgm",
"/9.pgm"
]
MATCH_THRESHOLD = 0.65 # 模板匹配相似度閾值(0.0-1.0)
RECT_THRESHOLD = 25000 # 矩形檢測敏感度(值越小敏感度越高)
MIN_RECT_WIDTH = 15 # 最小矩形寬度(需大于最大模板寬度)
MIN_RECT_HEIGHT = 15 # 最小矩形高度(需大于最大模板高度)
TEXT_COLOR = 255 # 顯示顏色(灰度值,255為白色)
TEXT_OFFSET = 5 # 文本標注偏移量(像素)
# ******************** 模板管理系統(tǒng) ********************
class TemplateLoader:
def __init__(self):
self.templates = [] # 存儲加載的模板信息
self.min_template_w = 999 # 記錄最小模板寬度(用于尺寸校驗)
self.min_template_h = 999 # 記錄最小模板高度
self.load_templates() # 初始化時自動加載模板
def load_templates(self):
"""模板加載與管理系統(tǒng)
功能:批量加載模板文件并記錄尺寸信息
安全機制:異常捕獲+詳細加載報告"""
print("n====== 模板加載報告 ======")
for path in TEMPLATE_PATHS:
try:
# 加載模板圖像并提取尺寸信息
template_img = image.Image(path)
w, h = template_img.width(), template_img.height()
# 更新最小模板尺寸記錄
self.min_template_w = min(self.min_template_w, w)
self.min_template_h = min(self.min_template_h, h)
# 存儲模板元數(shù)據(jù)
self.templates.append({
"image": template_img, # 模板圖像對象
"name": path.split("/")[-1].split(".")[0], # 提取數(shù)字名稱
"path": path, # 完整文件路徑
"width": w, # 模板寬度
"height": h # 模板高度
})
print(f"成功加載 {w}x{h} 模板: {path}")
except Exception as e:
print(f"加載失敗: {path} ({str(e)})")
print("=========================n")
# ******************** 主程序流程 ********************
template_loader = TemplateLoader() # 實例化模板加載器
clock = time.clock() # 創(chuàng)建幀率計算器
while True:
clock.tick() # 開始幀計時
# 圖像采集與預處理
img = sensor.snapshot().lens_corr(strength=1.8) # 捕獲圖像并校正鏡頭畸變
# 階段1:矩形檢測與預處理
rects = img.find_rects(threshold=RECT_THRESHOLD) # 查找所有矩形區(qū)域
for rect in rects:
x, y, w, h = rect.rect() # 提取矩形坐標和尺寸
# 區(qū)域過濾(尺寸+面積雙重校驗)
if (w < MIN_RECT_WIDTH or h < MIN_RECT_HEIGHT or
w * h < MIN_RECT_WIDTH * MIN_RECT_HEIGHT):
continue # 跳過過小區(qū)域
# ROI安全邊界處理(防止越界訪問)
img_w, img_h = img.width(), img.height()
roi_x = max(0, x) # 左邊界保護
roi_y = max(0, y) # 上邊界保護
roi_w = min(w, img_w - roi_x) # 寬度邊界保護
roi_h = min(h, img_h - roi_y) # 高度邊界保護
# 繪制矩形標記(輪廓+角點)
img.draw_rectangle(x, y, w, h, color=TEXT_COLOR) # 繪制矩形框
for (cx, cy) in rect.corners(): # 繪制四個角點
img.draw_circle(int(cx), int(cy), 3, color=TEXT_COLOR)
# 階段2:模板匹配 - 找出相似度最高的模板
best_match = None # 存儲最佳匹配結果
best_similarity = 0.0 # 最高相似度記錄
best_name = None # 對應模板名稱
for template in template_loader.templates:
# 動態(tài)尺寸校驗(ROI必須大于等于模板尺寸)
if roi_w < template["width"] or roi_h < template["height"]:
continue # 跳過尺寸不匹配的模板
try:
# 執(zhí)行模板匹配(核心算法)
result = img.find_template(
template["image"], # 模板圖像
MATCH_THRESHOLD, # 相似度閾值
roi=(roi_x, roi_y, roi_w, roi_h) # 搜索區(qū)域
)
# 結果處理
if result:
rx, ry, rw, rh = result # 解包匹配結果坐標
similarity = MATCH_THRESHOLD # 使用閾值作為相似度基準值
if similarity > best_similarity:
best_similarity = similarity
best_match = (rx, ry, rw, rh)
best_name = template["name"]
except Exception as e:
print(f"模板匹配出錯: {str(e)}") # 異常捕獲
# 結果可視化與輸出
if best_match:
rx, ry, rw, rh = best_match
# 繪制匹配區(qū)域框
img.draw_rectangle(rx, ry, rw, rh, color=TEXT_COLOR)
# 計算文本位置(防越界)
text_y = ry - TEXT_OFFSET if ry > TEXT_OFFSET else 0
# 繪制識別結果文本
img.draw_string(rx, text_y, best_name,
color=TEXT_COLOR,
scale=1, # 字體大小
mono_space=True # 等寬字體
)
# 增強數(shù)據(jù)輸出(帶時間戳和坐標信息)
print("[{:.0f}] 區(qū)域[{},{} {}x{}] 識別到{} 相似度{:.2f} 位置({},{})".format(
time.ticks_ms(), # 時間戳
x, y, w, h, # 原始區(qū)域信息
best_name, # 識別結果
best_similarity, # 匹配度
rx + rw // 2, # 中心X坐標
ry + rh // 2 # 中心Y坐標
))
# 性能顯示(右上角FPS計數(shù)器)
img.draw_string(5, 5, "FPS:%.1f" % clock.fps(), color=TEXT_COLOR)