第2章:OpenCV基础与环境搭建
说实话,每次带新人入门计算机视觉,我都要先问一句:「OpenCV装好了吗?」
这玩意儿就像厨师的菜刀。刀不好使,菜做得再好也白搭。我自己踩过太多环境坑了,今天就把这些经验一股脑倒给你。
2.1 OpenCV安装:别让环境卡住你
安装OpenCV其实就一行命令的事。但我见过太多人卡在版本兼容性上。
推荐安装方式(Python版)
# 基础安装
pip install opencv-python
# 如果需要额外模块(比如特征匹配、人脸识别等)
pip install opencv-contrib-python
# 国内用户加个镜像源,速度快很多
pip install opencv-python -i https://pypi.tuna.tsinghua.edu.cn/simple
我个人习惯用 opencv-contrib-python。为什么?因为有一次做项目,需要SIFT特征提取,结果发现基础版里没有。嗯,从那以后我就学乖了。
小技巧:装完后跑一下 import cv2; print(cv2.__version__),看到版本号就说明成了。
2.2 图像读取与显示:第一行代码
图像读取,说白了就是把硬盘上的图片搬到内存里。OpenCV用 imread 搞定。
import cv2
# 读取图像
img = cv2.imread('cat.jpg')
# 显示图像
cv2.imshow('My Cat', img)
cv2.waitKey(0) # 等待按键
cv2.destroyAllWindows()
这里有个坑,我当初就栽过——OpenCV默认读取的是BGR格式,不是RGB。你想想看,如果你用matplotlib显示,颜色就全乱了。
注意:BGR和RGB的通道顺序是反的。显示时记得转换:cv2.cvtColor(img, cv2.COLOR_BGR2RGB)
保存图像也很简单:
cv2.imwrite('output.jpg', img)
我在项目中遇到过一个问题:读取中文路径的图片会失败。后来发现,用 cv2.imdecode 配合 numpy 就能解决。
2.3 视频流处理基础:让画面动起来
视频说白了就是一帧一帧的图片快速播放。OpenCV处理视频的核心逻辑就是:循环读取每一帧。
cap = cv2.VideoCapture(0) # 0表示默认摄像头
while True:
ret, frame = cap.read()
if not ret:
break
# 在这里处理每一帧
cv2.imshow('Video', frame)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
cap.release()
cv2.destroyAllWindows()
你可能会问:为什么要用 0xFF?这是因为在某些系统上,waitKey 返回的值可能超过8位,加个掩码更安全。我以前没加这个,结果在Linux上程序死活退不出来。
核心要点:视频处理 = 循环 + 帧读取 + 帧处理 + 退出条件
处理视频文件也一样,把 VideoCapture(0) 换成文件路径就行:
cap = cv2.VideoCapture('video.mp4')
2.4 鼠标交互事件:让程序听懂你的点击
鼠标交互,说白了就是让OpenCV响应你的点击、移动、拖拽。这在目标点标注时特别有用。
OpenCV用 setMouseCallback 来注册鼠标事件。你需要写一个回调函数:
def mouse_callback(event, x, y, flags, param):
if event == cv2.EVENT_LBUTTONDOWN:
print(f'点击位置:({x}, {y})')
# 在图上画个点
cv2.circle(img, (x, y), 5, (0, 0, 255), -1)
cv2.imshow('Image', img)
cv2.namedWindow('Image')
cv2.setMouseCallback('Image', mouse_callback)
常用的鼠标事件有这些:
| 事件名称 | 说明 |
|---|---|
| EVENT_LBUTTONDOWN | 左键按下 |
| EVENT_RBUTTONDOWN | 右键按下 |
| EVENT_MOUSEMOVE | 鼠标移动 |
| EVENT_LBUTTONUP | 左键释放 |
我曾经做过一个标注工具,用户需要框选目标区域。用鼠标事件记录按下和释放的位置,就能画出矩形框。代码大概长这样:
start_point = None
def draw_rectangle(event, x, y, flags, param):
global start_point
if event == cv2.EVENT_LBUTTONDOWN:
start_point = (x, y)
elif event == cv2.EVENT_LBUTTONUP:
cv2.rectangle(img, start_point, (x, y), (0, 255, 0), 2)
cv2.imshow('Image', img)
经验之谈:鼠标回调函数里不要做耗时操作,否则画面会卡顿。需要复杂计算的话,把坐标存下来,主循环里处理。
2.5 本章知识体系
下面这张图,是我梳理的本章核心逻辑。你看一眼就能明白各个知识点之间的关系。
这张图把本章内容串起来了。你从安装出发,学会图像和视频的基本操作,最后用鼠标交互让程序活起来。每一步都是下一章目标点跟踪的基石。
一句话总结:环境搭好、图像能看、视频能动、鼠标能点——你就具备了做目标点跟踪的所有前置技能。
可可精品资料库