How can I track and measure the velocity of a moving object in a video?

165 views (last 30 days)
The video itself is quite simple. It's a high contrast capture of a droplet moving across the screen. How can I calculate the velocity of the droplet given that I already have the scale (pixels to mm)? Any input/direction would be appreciated.
  1 Comment
Jorge Mario Guerra González
I imagine you have a plain screen with a particle moving around, I would use the plain colour as a mask, then try to substract frame1-frame2, the number of pixels with X difference It's the movement.
But that's just an idea...

Sign in to comment.

Accepted Answer

Tohru Kikawada
Tohru Kikawada on 24 Jan 2017
You can easily calculate the velocity multiplying the distance of centroids between previous frame and current frame, the frame rate of the video and the scale of the unit is meter/pixel.
scale = 1/320; % meter/pixel
frameRate = 30; % frame/second
velocity = velociy_pix * frameRate * scale; % pixel/frame * frame/second * meter/pixel
Here is an example code that calculates the velocity of a moving ball (requires Computer Vision System Toolbox):
%%Create a video for detection
writerObj = VideoWriter('movingBall.avi');
open(writerObj);
bgI = zeros(240,320,'uint8');
pos_org = [160 120];
r = 10;
for k = 1: 300
f = 0.2*(1-exp(-k/200));
pos = pos_org + 50*[cos(2*pi*f/30*k) sin(2*pi*f/30*k)];
I = insertShape(bgI, 'FilledCircle', [pos r], 'Color', 'white');
I = I + uint8(randn(size(I)))*10;
writeVideo(writerObj,im2frame(I));
end
close(writerObj);
%%Calculate velocity of the ball
videoFileReader = vision.VideoFileReader('movingBall.avi');
S = info(videoFileReader);
frameRate = S.VideoFrameRate; % frame/second
scale = 1/320; % m/pixel
videoPlayer = vision.VideoPlayer('Position',[100 100 600 400]);
oldPoints = [];
while ~isDone(videoFileReader)
videoFrame = step(videoFileReader);
G = rgb2gray(videoFrame);
BW = G > 0.5;
BW2 = bwareaopen(BW, 30);
BW3 = imfill(BW2, 'holes');
stats = regionprops('table',BW3,'Centroid');
points = table2array(stats);
if ~isempty(oldPoints)
% Calculate velocity (pixels/frame)
vel_pix = sqrt(sum((points-oldPoints).^2,2));
vel = vel_pix * frameRate * scale; % pixels/frame * frame/seconds * meter/pixels
else
vel_pix = 0;
vel = 0;
end
% Visualize the velocity
videoFrameOut = insertObjectAnnotation(videoFrame, 'circle', ...
[points 10*ones(size(points,1),1)], ...
cellstr(num2str(vel,'%2.2f')));
step(videoPlayer, videoFrameOut);
oldPoints = points;
end
release(videoFileReader);
release(videoPlayer);
  10 Comments
muhammad choudhry
muhammad choudhry on 13 Aug 2020
Hi,
I am using this code on the particle tracking video and getting this error. Can you help?
Error:
Matrix dimensions must agree.
Error in velocity (line 39)
vel_pix = sqrt(sum((points-oldPoints).^2,2));
Dalia
Dalia on 12 Sep 2023
How can I estimate the velocity of water in a channel, the flow is turbulent ? I want to track a specific point and estimate its velocity but I cant write the code to specify this point as interset point.
Can you help?

Sign in to comment.

More Answers (0)

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!