1 #include <caffe2/video/optical_flow.h> 5 void OpticalFlowExtractor(
6 const cv::Mat& prev_gray,
7 const cv::Mat& curr_gray,
8 const int flow_alg_type,
10 cv::Ptr<cv::DualTVL1OpticalFlow> tvl1 = cv::DualTVL1OpticalFlow::create();
11 switch (flow_alg_type) {
12 case FLowAlgType::FarnebackOpticalFlow:
13 cv::calcOpticalFlowFarneback(
23 cv::OPTFLOW_FARNEBACK_GAUSSIAN);
25 case FLowAlgType::DensePyrLKOpticalFlow:
26 LOG(ERROR) <<
"DensePyrLKOpticalFlow only has sparse version on CPU";
28 case FLowAlgType::BroxOpticalFlow:
29 LOG(ERROR) <<
"BroxOpticalFlow on CPU is not available";
31 case FLowAlgType::OpticalFlowDual_TVL1:
32 tvl1->calc(prev_gray, curr_gray, flow);
35 LOG(ERROR) <<
"Unsupported optical flow type " << flow_alg_type;
40 void MergeOpticalFlow(cv::Mat& prev_flow,
const cv::Mat& curr_flow) {
41 const int rows = prev_flow.rows;
42 const int cols = prev_flow.cols;
45 for (
int y = 0; y < rows; y++) {
46 for (
int x = 0; x < cols; x++) {
47 cv::Point2f u = prev_flow.at<cv::Point2f>(y, x);
49 int x_new = std::min(cols - 1, std::max(0, cvRound(u.x + x)));
50 int y_new = std::min(rows - 1, std::max(0, cvRound(u.y + y)));
51 cv::Point2f u_new = curr_flow.at<cv::Point2f>(y_new, x_new);
54 prev_flow.at<cv::Point2f>(y, x) += u_new;
59 void MultiFrameOpticalFlowExtractor(
60 const std::vector<cv::Mat>& grays,
61 const int optical_flow_alg_type,
63 int num_frames = grays.size();
64 CAFFE_ENFORCE_GE(num_frames, 2,
"need at least 2 frames!");
67 std::vector<cv::Mat> flows;
68 for (
int i = 0; i < num_frames - 1; i++) {
70 OpticalFlowExtractor(grays[i], grays[i + 1], optical_flow_alg_type, tmp);
74 flows[0].copyTo(flow);
76 for (
int i = 1; i < num_frames - 1; i++) {
77 MergeOpticalFlow(flow, flows[i]);
A global dictionary that holds information about what Caffe2 modules have been loaded in the current ...