如何在MATLAB计算机视觉工具箱中仅对下落球体应用光流法测速?
仅对指定球体区域应用光流测量下落速度的MATLAB实现
要实现仅针对球体区域计算光流并测量速度,核心是先定义球体的初始感兴趣区域(ROI),在循环中只处理该区域的图像,同时根据光流结果动态更新ROI位置以跟踪球体,具体步骤和修改后的代码如下:
关键实现步骤
- 获取初始ROI:读取视频第一帧,手动框选球体所在区域,记录ROI的坐标和尺寸。
- 循环处理帧:每帧仅提取ROI内的灰度图像,计算该区域的光流。
- 计算下落速度:统计ROI内光流的平均y方向位移(对应下落方向),结合视频帧率转换为速度。
- 动态更新ROI:根据光流结果调整ROI位置,确保始终覆盖下落的球体。
修改后的完整代码
v = VideoReader('sphere.avi'); % 读取第一帧并手动选择球体初始ROI frameRGB = readFrame(v); frameGrey = im2gray(frameRGB); imshow(frameRGB); title('拖动鼠标框选球体区域,完成后按回车'); roi = drawrectangle; % MATLAB R2021a及以上版本可用,旧版用imrect roiPos = roi.Position; % 格式:[x起始坐标, y起始坐标, 宽度, 高度] v.CurrentTime = 0; % 重置视频到开头 opticFlow = opticalFlowFarneback; h = figure; movegui(h); while hasFrame(v) frameRGB = readFrame(v); frameGrey = im2gray(frameRGB); % 提取当前帧的ROI区域 roiGrey = imcrop(frameGrey, roiPos); % 计算ROI内的光流 flow = estimateFlow(opticFlow, roiGrey); % 计算下落速度(y方向为下落方向,单位:像素/秒) dt = 1 / v.FrameRate; % 每帧的时间间隔 avgYDisp = mean(flow.V(:)); % ROI内平均y方向位移(像素) pixelSpeedY = avgYDisp / dt; % 像素速度 % 动态更新ROI位置,跟踪球体 roiPos(2) = roiPos(2) + avgYDisp; % 更新y起始坐标 % 显示结果 imshow(frameRGB); hold on; % 画出ROI框 rectangle('Position', roiPos, 'EdgeColor', 'red', 'LineWidth', 2); title(sprintf('当前时间 = %.3f sec | 下落像素速度 = %.2f 像素/秒', ... v.CurrentTime, pixelSpeedY)); hold off; pause(1e-3); end release(v);
补充说明
- 实际速度转换:如果需要得到物理单位(如米/秒),需提前通过标定确定视频中像素与实际距离的比例(例如:1像素 = 0.001米),然后用
actualSpeed = pixelSpeedY * 比例系数计算。 - ROI跟踪优化:如果球体存在横向偏移,可同时计算x方向的平均位移
avgXDisp = mean(flow.U(:)),并更新ROI的x起始坐标roiPos(1) = roiPos(1) + avgXDisp。 - 兼容性:若使用MATLAB旧版本,将
drawrectangle替换为roi = imrect; roiPos = getPosition(roi);即可。
内容的提问来源于stack exchange,提问作者surim
相关产品推荐
相关产品推荐

