Search code examples
matlabpointobject-detectionmatlab-cvstvideo-tracking

Can I get Points from each frame?


How can I get 'points' for each frame? Right now I get 'points' for the last frame. I want to get 'points' x and y coordinates for each frame and not for the last one.

clear all;
clc;
videoFileReader=vision.VideoFileReader('Test.avi');
videoPlayer=vision.VideoPlayer('Position', [100, 100, 680, 520]);
objectFrame=step(videoFileReader);
objectRegion=[1121, 353, 16, 16];
objectImage=insertShape(objectFrame, 'Rectangle', objectRegion,'Color', 'red');
figure;
imshow(objectImage);
title('Yellow box shows object region');
points=detectMinEigenFeatures(rgb2gray(objectFrame), 'ROI', objectRegion);
pointImage=insertMarker(objectFrame, points.Location, '+', 'Color', 'white');
figure,
imshow(pointImage),
title('Detected interest points');
tracker=vision.PointTracker('MaxBidirectionalError', 1);
initialize(tracker, points.Location, objectFrame);
while ~isDone(videoFileReader)
    frame=step(videoFileReader);
    [points, validity]=step(tracker, frame);
    out=insertMarker(frame, points(validity, :), '+');
    step(videoPlayer, out);
end
release(videoPlayer);
release(videoFileReader);

Solution

  • You are overwriting points with each new frame. So by the time all the code is finished, only the most recent points are saved. One problem with VideoFileReader is you can't easily find out how many frames there are until you read them all. (I could be wrong, so someone feel free to correct me). So you could create a cell array. Cells can hold all kinds of data, Singular values, vectors, matricies. It is also nice because unlike concatenation of regular arrays, each layer doesnt have to be the same size. So lets say you have 10 points in frame 1 and 3 in frame 2 simply doing an array concatenation would fail because they aren't the same size. Cells on the other hand don't really care about that.

    So before your loop I create an empty cell array to store the values for each frame. Then inside the loop, it increments the index and stores the current points into the cell array. At the end of processing each frame will have its own entry in hist_points hope this helps

    %initialize frame count and cell array
    num_frame=1;
    hist_points = {};
    
    while ~isDone(videoFileReader)
        frame=step(videoFileReader);
    
        [points, validity]=step(tracker, frame);
    
        %this should work no matter what dimension points is, and even if points is
        %a different size each iteration
        hist_points{num_frame} = points;
    
        out=insertMarker(frame, points(validity, :), '+');
        step(videoPlayer, out);
    
        %moves to next array location 
        num_frame = num_frame+1
    end