Hello,
When running DIS Optical Flow twice (as in the example below), it crashes. I'm not sure if this is a bug. I would appreciate a lot if somebody can help to fix this issue.
Thank you very much in advance!
#include <iostream>
#include <string>
#include <opencv2/opencv.hpp>
#include "opencv2/optflow.hpp"
using namespace std;
using namespace cv;
using namespace optflow;
Mat flowToDisplay(const Mat &flow)
{
Mat flow_split[2];
Mat magnitude, angle;
Mat hsv_split[3], hsv, rgb;
split(flow, flow_split);
cartToPolar(flow_split[0], flow_split[1], magnitude, angle, true);
normalize(magnitude, magnitude, 0, 1, NORM_MINMAX);
hsv_split[0] = angle; // already in degrees - no normalization needed
hsv_split[1] = Mat::ones(angle.size(), angle.type());
hsv_split[2] = magnitude;
merge(hsv_split, 3, hsv);
cvtColor(hsv, rgb, COLOR_HSV2BGR);
return rgb;
}
double computeDistance(const Mat &im1_, const Mat &im2_, const string &optflow_method = "DISflow_medium")
{
Mat_<Point2f> flow;
Mat im1 = im1_.clone();
Mat im2 = im2_.clone();
if ( !im1.data || !im2.data )
{
printf("No image data \n");
return -1;
}
if ( im1.size() != im2.size() || im1.channels() != im2.channels() )
{
printf("Dimension mismatch between input images\n");
return -1;
}
// 8-bit images expected by all algorithms
if ( im1.depth() != CV_8U )
im1.convertTo(im1, CV_8U);
if ( im2.depth() != CV_8U )
im2.convertTo(im2, CV_8U);
if ( (optflow_method == "farneback" || optflow_method == "tvl1" || optflow_method == "deepflow"
|| optflow_method == "DISflow_ultrafast" || optflow_method == "DISflow_fast"
|| optflow_method == "DISflow_medium") && im1.channels() == 3 )
{ // 1-channel images are expected
cvtColor(im1, im1, COLOR_BGR2GRAY);
cvtColor(im2, im2, COLOR_BGR2GRAY);
} else if ( optflow_method == "simpleflow" && im1.channels() == 1 )
{ // 3-channel images expected
cvtColor(im1, im1, COLOR_GRAY2BGR);
cvtColor(im2, im2, COLOR_GRAY2BGR);
}
flow = Mat(im1.size[0], im1.size[1], CV_32FC2);
Ptr<DenseOpticalFlow> algorithm;
if ( optflow_method == "farneback" )
algorithm = createOptFlow_Farneback();
else if ( optflow_method == "simpleflow" )
algorithm = createOptFlow_SimpleFlow();
else if ( optflow_method == "tvl1" )
algorithm = createOptFlow_DualTVL1();
else if ( optflow_method == "deepflow" )
algorithm = createOptFlow_DeepFlow();
else if ( optflow_method == "sparsetodenseflow" )
algorithm = createOptFlow_SparseToDense();
else if ( optflow_method == "pcaflow" )
algorithm = createOptFlow_PCAFlow();
else if ( optflow_method == "DISflow_ultrafast" )
algorithm = createOptFlow_DIS(DISOpticalFlow::PRESET_ULTRAFAST);
else if (optflow_method == "DISflow_fast")
algorithm = createOptFlow_DIS(DISOpticalFlow::PRESET_FAST);
else if (optflow_method == "DISflow_medium")
algorithm = createOptFlow_DIS(DISOpticalFlow::PRESET_MEDIUM);
else
{
printf("Wrong optical flow method!\n");
return -1;
}
//double startTick, time;
//startTick = (double) getTickCount(); // measure time
algorithm->calc(im1, im2, flow);
Mat flow_image = flowToDisplay(flow);
namedWindow( "Computed flow", WINDOW_NORMAL );
imshow( "Computed flow", flow_image );
waitKey(0);
// Compute the total displacement
double dist = 0.0;
for(int y = 0; y < flow.rows; y++){
for(int x = 0; x < flow.cols; x++){
dist += cv::norm(flow.at<Point2f>(y,x));
}
}
return dist;
}
int main(int argc, char* argv[])
{
string input("../video.mp4");
VideoCapture cap(input); // open the video file
if(!cap.isOpened()) // check if we succeeded
return;
int numFrame = cap.get(CV_CAP_PROP_FRAME_COUNT);
vector<Mat> frames;
frames.reserve(numFrame);
for(;;)
{
Mat frame;
cap >> frame; // get a new frame from camera
if (frame.empty())
break;
frames.push_back(frame);
}
double d;
d = computeDistance(frames[0], frames[3]); // no problem here
d = computeDistance(frames[0], frames[4]); // problem here (if the above line is removed then this line has no problem as well)
return 0;
}