Commit 7b5a45ea authored by Andrey Kamaev's avatar Andrey Kamaev

Merged the trunk r8384:8407 (inclusive)

parent 72d2311e
This diff is collapsed.
if(MINGW)
# mingw compiler is known to produce unstable SSE code with -O3 hence we are trying to use -O2 instead
if(CMAKE_COMPILER_IS_GNUCXX)
foreach(flags CMAKE_CXX_FLAGS CMAKE_CXX_FLAGS_RELEASE CMAKE_CXX_FLAGS_DEBUG)
string(REPLACE "-O3" "-O2" ${flags} "${${flags}}")
endforeach()
endif()
if(CMAKE_COMPILER_IS_GNUCC)
foreach(flags CMAKE_C_FLAGS CMAKE_C_FLAGS_RELEASE CMAKE_C_FLAGS_DEBUG)
string(REPLACE "-O3" "-O2" ${flags} "${${flags}}")
endforeach()
endif()
endif()
if(MSVC) if(MSVC)
if(CMAKE_CXX_FLAGS STREQUAL CMAKE_CXX_FLAGS_INIT) if(CMAKE_CXX_FLAGS STREQUAL CMAKE_CXX_FLAGS_INIT)
# override cmake default exception handling option # override cmake default exception handling option
...@@ -14,18 +29,18 @@ set(OPENCV_EXTRA_EXE_LINKER_FLAGS_RELEASE "") ...@@ -14,18 +29,18 @@ set(OPENCV_EXTRA_EXE_LINKER_FLAGS_RELEASE "")
set(OPENCV_EXTRA_EXE_LINKER_FLAGS_DEBUG "") set(OPENCV_EXTRA_EXE_LINKER_FLAGS_DEBUG "")
if(MINGW) if(MINGW)
# mingw compiler is known to produce unstable SSE code # http://gcc.gnu.org/bugzilla/show_bug.cgi?id=40838
# here we are trying to workaround the problem # here we are trying to workaround the problem
include(CheckCXXCompilerFlag) include(CheckCXXCompilerFlag)
CHECK_CXX_COMPILER_FLAG(-mstackrealign HAVE_STACKREALIGN_FLAG) # CHECK_CXX_COMPILER_FLAG(-mstackrealign HAVE_STACKREALIGN_FLAG)
if(HAVE_STACKREALIGN_FLAG) # if(HAVE_STACKREALIGN_FLAG)
set(OPENCV_EXTRA_C_FLAGS "${OPENCV_EXTRA_C_FLAGS} -mstackrealign") # set(OPENCV_EXTRA_C_FLAGS "${OPENCV_EXTRA_C_FLAGS} -mstackrealign")
else() #else()
CHECK_CXX_COMPILER_FLAG(-mpreferred-stack-boundary=2 HAVE_PREFERRED_STACKBOUNDARY_FLAG) CHECK_CXX_COMPILER_FLAG(-mpreferred-stack-boundary=2 HAVE_PREFERRED_STACKBOUNDARY_FLAG)
if(HAVE_PREFERRED_STACKBOUNDARY_FLAG) if(HAVE_PREFERRED_STACKBOUNDARY_FLAG)
set(OPENCV_EXTRA_C_FLAGS "${OPENCV_EXTRA_C_FLAGS} -mstackrealign") set(OPENCV_EXTRA_C_FLAGS "${OPENCV_EXTRA_C_FLAGS} -mstackrealign")
endif() endif()
endif() #endif()
endif() endif()
if(CMAKE_COMPILER_IS_GNUCXX) if(CMAKE_COMPILER_IS_GNUCXX)
......
...@@ -8,7 +8,7 @@ file(TO_CMAKE_PATH "$ENV{HOME}" HOME_ENV_PATH) ...@@ -8,7 +8,7 @@ file(TO_CMAKE_PATH "$ENV{HOME}" HOME_ENV_PATH)
if(CMAKE_HOST_WIN32) if(CMAKE_HOST_WIN32)
set(ANDROID_SDK_OS windows) set(ANDROID_SDK_OS windows)
elseif(CMAKE_HOST_APPLE) elseif(CMAKE_HOST_APPLE)
set(ANDROID_SDK_OS mac) set(ANDROID_SDK_OS macosx)
else() else()
set(ANDROID_SDK_OS linux) set(ANDROID_SDK_OS linux)
endif() endif()
......
if(MSVC AND NOT PYTHON_EXECUTABLE) if(WIN32 AND NOT PYTHON_EXECUTABLE)
# search for executable with the same bitness as resulting binaries # search for executable with the same bitness as resulting binaries
# standard FindPythonInterp always prefers executable from system path # standard FindPythonInterp always prefers executable from system path
# this is really important because we are using the interpreter for numpy search and for choosing the install location # this is really important because we are using the interpreter for numpy search and for choosing the install location
......
...@@ -11,7 +11,7 @@ if(NOT COMMAND find_host_program) ...@@ -11,7 +11,7 @@ if(NOT COMMAND find_host_program)
endmacro() endmacro()
endif() endif()
#added include directories in such way that directories from the OpenCV source tree go first # adds include directories in such way that directories from the OpenCV source tree go first
function(ocv_include_directories) function(ocv_include_directories)
set(__add_before "") set(__add_before "")
foreach(dir ${ARGN}) foreach(dir ${ARGN})
...@@ -25,6 +25,12 @@ function(ocv_include_directories) ...@@ -25,6 +25,12 @@ function(ocv_include_directories)
include_directories(BEFORE ${__add_before}) include_directories(BEFORE ${__add_before})
endfunction() endfunction()
# clears all passed variables
macro(ocv_clear_vars)
foreach(_var ${ARGN})
unset(${_var} CACHE)
endforeach()
endmacro()
# Provides an option that the user can optionally select. # Provides an option that the user can optionally select.
# Can accept condition to control when option is available for user. # Can accept condition to control when option is available for user.
...@@ -352,10 +358,11 @@ macro(ocv_parse_header2 LIBNAME HDR_PATH VARNAME SCOPE) ...@@ -352,10 +358,11 @@ macro(ocv_parse_header2 LIBNAME HDR_PATH VARNAME SCOPE)
set(${LIBNAME}_VERSION_STRING "${${LIBNAME}_VERSION_STRING}.${${LIBNAME}_VERSION_TWEAK}" ${SCOPE}) set(${LIBNAME}_VERSION_STRING "${${LIBNAME}_VERSION_STRING}.${${LIBNAME}_VERSION_TWEAK}" ${SCOPE})
endif() endif()
else() else()
unset(${LIBNAME}_VERSION_MAJOR CACHE) ocv_clear_vars(${LIBNAME}_VERSION_MAJOR
unset(${LIBNAME}_VERSION_MINOR CACHE) ${LIBNAME}_VERSION_MAJOR
unset(${LIBNAME}_VERSION_PATCH CACHE) ${LIBNAME}_VERSION_MINOR
unset(${LIBNAME}_VERSION_TWEAK CACHE) ${LIBNAME}_VERSION_PATCH
unset(${LIBNAME}_VERSION_STRING CACHE) ${LIBNAME}_VERSION_TWEAK
${LIBNAME}_VERSION_STRING)
endif() endif()
endmacro() endmacro()
...@@ -107,12 +107,15 @@ class DetectionBasedTracker::SeparateDetectionWork ...@@ -107,12 +107,15 @@ class DetectionBasedTracker::SeparateDetectionWork
DetectionBasedTracker::SeparateDetectionWork::SeparateDetectionWork(DetectionBasedTracker& _detectionBasedTracker, const std::string& cascadeFilename) DetectionBasedTracker::SeparateDetectionWork::SeparateDetectionWork(DetectionBasedTracker& _detectionBasedTracker, const std::string& cascadeFilename)
:detectionBasedTracker(_detectionBasedTracker), :detectionBasedTracker(_detectionBasedTracker),
cascadeInThread(cascadeFilename), cascadeInThread(),
isObjectDetectingReady(false), isObjectDetectingReady(false),
shouldObjectDetectingResultsBeForgot(false), shouldObjectDetectingResultsBeForgot(false),
stateThread(STATE_THREAD_STOPPED), stateThread(STATE_THREAD_STOPPED),
timeWhenDetectingThreadStartedWork(-1) timeWhenDetectingThreadStartedWork(-1)
{ {
if(!cascadeInThread.load(cascadeFilename)) {
CV_Error(CV_StsBadArg, "DetectionBasedTracker::SeparateDetectionWork::SeparateDetectionWork: Cannot load a cascade from the file '"+cascadeFilename+"'");
}
int res=0; int res=0;
res=pthread_mutex_init(&mutex, NULL);//TODO: should be attributes? res=pthread_mutex_init(&mutex, NULL);//TODO: should be attributes?
if (res) { if (res) {
...@@ -439,14 +442,17 @@ DetectionBasedTracker::InnerParameters::InnerParameters() ...@@ -439,14 +442,17 @@ DetectionBasedTracker::InnerParameters::InnerParameters()
DetectionBasedTracker::DetectionBasedTracker(const std::string& cascadeFilename, const Parameters& params) DetectionBasedTracker::DetectionBasedTracker(const std::string& cascadeFilename, const Parameters& params)
:separateDetectionWork(), :separateDetectionWork(),
innerParameters(), innerParameters(),
numTrackedSteps(0), numTrackedSteps(0)
cascadeForTracking(cascadeFilename)
{ {
CV_Assert( (params.minObjectSize > 0) CV_Assert( (params.minObjectSize > 0)
&& (params.maxObjectSize >= 0) && (params.maxObjectSize >= 0)
&& (params.scaleFactor > 1.0) && (params.scaleFactor > 1.0)
&& (params.maxTrackLifetime >= 0) ); && (params.maxTrackLifetime >= 0) );
if (!cascadeForTracking.load(cascadeFilename)) {
CV_Error(CV_StsBadArg, "DetectionBasedTracker::DetectionBasedTracker: Cannot load a cascade from the file '"+cascadeFilename+"'");
}
parameters=params; parameters=params;
separateDetectionWork=new SeparateDetectionWork(*this, cascadeFilename); separateDetectionWork=new SeparateDetectionWork(*this, cascadeFilename);
......
...@@ -233,6 +233,34 @@ CV_INLINE IppiSize ippiSize(int width, int height) ...@@ -233,6 +233,34 @@ CV_INLINE IppiSize ippiSize(int width, int height)
} }
#endif #endif
#define CV_INIT_ALGORITHM(classname, algname, memberinit) \
static Algorithm* create##classname() \
{ \
return new classname; \
} \
\
static AlgorithmInfo& classname##_info() \
{ \
static AlgorithmInfo classname##_info_var(algname, create##classname); \
return classname##_info_var; \
} \
\
static AlgorithmInfo& classname##_info_auto = classname##_info(); \
\
AlgorithmInfo* classname::info() const \
{ \
static volatile bool initialized = false; \
\
if( !initialized ) \
{ \
initialized = true; \
classname obj; \
memberinit; \
} \
return &classname##_info(); \
}
#endif #endif
/* maximal size of vector to run matrix operations on it inline (i.e. w/o ipp calls) */ /* maximal size of vector to run matrix operations on it inline (i.e. w/o ipp calls) */
......
...@@ -322,7 +322,10 @@ inline Mat Mat::diag(const Mat& d) ...@@ -322,7 +322,10 @@ inline Mat Mat::diag(const Mat& d)
CV_Assert( d.cols == 1 || d.rows == 1 ); CV_Assert( d.cols == 1 || d.rows == 1 );
int len = d.rows + d.cols - 1; int len = d.rows + d.cols - 1;
Mat m(len, len, d.type(), Scalar(0)), md = m.diag(); Mat m(len, len, d.type(), Scalar(0)), md = m.diag();
if( d.cols == 1 )
d.copyTo(md); d.copyTo(md);
else
transpose(d, md);
return m; return m;
} }
......
This diff is collapsed.
This diff is collapsed.
...@@ -48,6 +48,10 @@ ...@@ -48,6 +48,10 @@
#endif #endif
#define COMPILE_MULTIMON_STUBS // Required for multi-monitor support #define COMPILE_MULTIMON_STUBS // Required for multi-monitor support
#ifndef _MULTIMON_USE_SECURE_CRT
# define _MULTIMON_USE_SECURE_CRT 0 // some MinGW platforms have no strncpy_s
#endif
#if defined SM_CMONITORS && !defined MONITOR_DEFAULTTONEAREST #if defined SM_CMONITORS && !defined MONITOR_DEFAULTTONEAREST
# define MONITOR_DEFAULTTONULL 0x00000000 # define MONITOR_DEFAULTTONULL 0x00000000
# define MONITOR_DEFAULTTOPRIMARY 0x00000001 # define MONITOR_DEFAULTTOPRIMARY 0x00000001
...@@ -974,6 +978,11 @@ CV_IMPL int cvNamedWindow( const char* name, int flags ) ...@@ -974,6 +978,11 @@ CV_IMPL int cvNamedWindow( const char* name, int flags )
DWORD defStyle = WS_VISIBLE | WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_SYSMENU; DWORD defStyle = WS_VISIBLE | WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_SYSMENU;
int len; int len;
CvRect rect; CvRect rect;
#ifdef HAVE_OPENGL
bool useGl;
HDC hGLDC;
HGLRC hGLRC;
#endif
cvInitSystem(0,0); cvInitSystem(0,0);
...@@ -1009,9 +1018,9 @@ CV_IMPL int cvNamedWindow( const char* name, int flags ) ...@@ -1009,9 +1018,9 @@ CV_IMPL int cvNamedWindow( const char* name, int flags )
if (flags & CV_WINDOW_OPENGL) if (flags & CV_WINDOW_OPENGL)
CV_ERROR( CV_OpenGlNotSupported, "Library was built without OpenGL support" ); CV_ERROR( CV_OpenGlNotSupported, "Library was built without OpenGL support" );
#else #else
bool useGl = false; useGl = false;
HDC hGLDC = 0; hGLDC = 0;
HGLRC hGLRC = 0; hGLRC = 0;
if (flags & CV_WINDOW_OPENGL) if (flags & CV_WINDOW_OPENGL)
createGlContext(hWnd, hGLDC, hGLRC, useGl); createGlContext(hWnd, hGLDC, hGLRC, useGl);
......
...@@ -224,7 +224,7 @@ void cv::copyMakeBorder( InputArray _src, OutputArray _dst, int top, int bottom, ...@@ -224,7 +224,7 @@ void cv::copyMakeBorder( InputArray _src, OutputArray _dst, int top, int bottom,
if(top == 0 && left == 0 && bottom == 0 && right == 0) if(top == 0 && left == 0 && bottom == 0 && right == 0)
{ {
if(src.data != dst.data) if(src.data != dst.data || src.step != dst.step)
src.copyTo(dst); src.copyTo(dst);
return; return;
} }
......
...@@ -45,31 +45,14 @@ ...@@ -45,31 +45,14 @@
namespace cv namespace cv
{ {
static Algorithm* createEM() CV_INIT_ALGORITHM(EM, "StatModel.EM",
{ obj.info()->addParam(obj, "nclusters", obj.nclusters);
return new EM; obj.info()->addParam(obj, "covMatType", obj.covMatType);
} obj.info()->addParam(obj, "maxIters", obj.maxIters);
static AlgorithmInfo em_info("StatModel.EM", createEM); obj.info()->addParam(obj, "epsilon", obj.epsilon);
obj.info()->addParam(obj, "weights", obj.weights, true);
AlgorithmInfo* EM::info() const obj.info()->addParam(obj, "means", obj.means, true);
{ obj.info()->addParam(obj, "covs", obj.covs, true));
static volatile bool initialized = false;
if( !initialized )
{
EM obj;
em_info.addParam(obj, "nclusters", obj.nclusters);
em_info.addParam(obj, "covMatType", obj.covMatType);
em_info.addParam(obj, "maxIters", obj.maxIters);
em_info.addParam(obj, "epsilon", obj.epsilon);
em_info.addParam(obj, "weights", obj.weights, true);
em_info.addParam(obj, "means", obj.means, true);
em_info.addParam(obj, "covs", obj.covs, true);
initialized = true;
}
return &em_info;
}
bool initModule_ml(void) bool initModule_ml(void)
{ {
......
...@@ -47,64 +47,21 @@ namespace cv ...@@ -47,64 +47,21 @@ namespace cv
/////////////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////////////
static Algorithm* createSURF() CV_INIT_ALGORITHM(SURF, "Feature2D.SURF",
{ obj.info()->addParam(obj, "hessianThreshold", obj.hessianThreshold);
return new SURF; obj.info()->addParam(obj, "nOctaves", obj.nOctaves);
} obj.info()->addParam(obj, "nOctaveLayers", obj.nOctaveLayers);
obj.info()->addParam(obj, "extended", obj.extended);
static AlgorithmInfo& surf_info() obj.info()->addParam(obj, "upright", obj.upright));
{
static AlgorithmInfo surf_info_var("Feature2D.SURF", createSURF);
return surf_info_var;
}
static AlgorithmInfo& surf_info_auto = surf_info();
AlgorithmInfo* SURF::info() const
{
static volatile bool initialized = false;
if( !initialized )
{
SURF obj;
surf_info().addParam(obj, "hessianThreshold", obj.hessianThreshold);
surf_info().addParam(obj, "nOctaves", obj.nOctaves);
surf_info().addParam(obj, "nOctaveLayers", obj.nOctaveLayers);
surf_info().addParam(obj, "extended", obj.extended);
surf_info().addParam(obj, "upright", obj.upright);
initialized = true;
}
return &surf_info();
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////////////
static Algorithm* createSIFT() { return new SIFT; } CV_INIT_ALGORITHM(SIFT, "Feature2D.SIFT",
obj.info()->addParam(obj, "nFeatures", obj.nfeatures);
static AlgorithmInfo& sift_info() obj.info()->addParam(obj, "nOctaveLayers", obj.nOctaveLayers);
{ obj.info()->addParam(obj, "contrastThreshold", obj.contrastThreshold);
static AlgorithmInfo sift_info_var("Feature2D.SIFT", createSIFT); obj.info()->addParam(obj, "edgeThreshold", obj.edgeThreshold);
return sift_info_var; obj.info()->addParam(obj, "sigma", obj.sigma));
}
static AlgorithmInfo& sift_info_auto = sift_info();
AlgorithmInfo* SIFT::info() const
{
static volatile bool initialized = false;
if( !initialized )
{
SIFT obj;
sift_info().addParam(obj, "nFeatures", obj.nfeatures);
sift_info().addParam(obj, "nOctaveLayers", obj.nOctaveLayers);
sift_info().addParam(obj, "contrastThreshold", obj.contrastThreshold);
sift_info().addParam(obj, "edgeThreshold", obj.edgeThreshold);
sift_info().addParam(obj, "sigma", obj.sigma);
initialized = true;
}
return &sift_info();
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////////////
......
...@@ -304,7 +304,7 @@ enum ...@@ -304,7 +304,7 @@ enum
}; };
//! constructs a pyramid which can be used as input for calcOpticalFlowPyrLK //! constructs a pyramid which can be used as input for calcOpticalFlowPyrLK
CV_EXPORTS_W int buildOpticalFlowPyramid(InputArray _img, OutputArrayOfArrays pyramid, CV_EXPORTS_W int buildOpticalFlowPyramid(InputArray img, OutputArrayOfArrays pyramid,
Size winSize, int maxLevel, bool withDerivatives = true, Size winSize, int maxLevel, bool withDerivatives = true,
int pyrBorder = BORDER_REFLECT_101, int derivBorder = BORDER_CONSTANT, int pyrBorder = BORDER_REFLECT_101, int derivBorder = BORDER_CONSTANT,
bool tryReuseInputImage = true); bool tryReuseInputImage = true);
......
...@@ -28,12 +28,12 @@ void FormTrackingPointsArray(vector<Point2f>& points, int width, int height, int ...@@ -28,12 +28,12 @@ void FormTrackingPointsArray(vector<Point2f>& points, int width, int height, int
} }
} }
PERF_TEST_P(Path_Idx_Cn_NPoints_WSize, OpticalFlowPyrLK, testing::Combine( PERF_TEST_P(Path_Idx_Cn_NPoints_WSize, OpticalFlowPyrLK_full, testing::Combine(
testing::Values<std::string>("cv/optflow/frames/VGA_%02d.png", "cv/optflow/frames/720p_%02d.jpg"), testing::Values<std::string>("cv/optflow/frames/VGA_%02d.png", "cv/optflow/frames/720p_%02d.jpg"),
testing::Range(0, 3), testing::Range(1, 3),
testing::Values(1, 3, 4), testing::Values(1, 3, 4),
testing::Values(make_tuple(9, 9), make_tuple(15, 15)), testing::Values(make_tuple(9, 9), make_tuple(15, 15)),
testing::Values(7, 11, 21, 25) testing::Values(7, 11, 25)
) )
) )
{ {
...@@ -48,6 +48,7 @@ PERF_TEST_P(Path_Idx_Cn_NPoints_WSize, OpticalFlowPyrLK, testing::Combine( ...@@ -48,6 +48,7 @@ PERF_TEST_P(Path_Idx_Cn_NPoints_WSize, OpticalFlowPyrLK, testing::Combine(
int nPointsX = min(get<0>(get<3>(GetParam())), img1.cols); int nPointsX = min(get<0>(get<3>(GetParam())), img1.cols);
int nPointsY = min(get<1>(get<3>(GetParam())), img1.rows); int nPointsY = min(get<1>(get<3>(GetParam())), img1.rows);
int winSize = get<4>(GetParam()); int winSize = get<4>(GetParam());
int maxLevel = 2; int maxLevel = 2;
TermCriteria criteria(CV_TERMCRIT_ITER|CV_TERMCRIT_EPS, 7, 0.001); TermCriteria criteria(CV_TERMCRIT_ITER|CV_TERMCRIT_EPS, 7, 0.001);
int flags = 0; int flags = 0;
...@@ -91,3 +92,120 @@ PERF_TEST_P(Path_Idx_Cn_NPoints_WSize, OpticalFlowPyrLK, testing::Combine( ...@@ -91,3 +92,120 @@ PERF_TEST_P(Path_Idx_Cn_NPoints_WSize, OpticalFlowPyrLK, testing::Combine(
flags, minEigThreshold); flags, minEigThreshold);
} }
} }
typedef tr1::tuple<std::string, int, int, tr1::tuple<int,int>, int, bool> Path_Idx_Cn_NPoints_WSize_Deriv_t;
typedef TestBaseWithParam<Path_Idx_Cn_NPoints_WSize_Deriv_t> Path_Idx_Cn_NPoints_WSize_Deriv;
PERF_TEST_P(Path_Idx_Cn_NPoints_WSize_Deriv, OpticalFlowPyrLK_self, testing::Combine(
testing::Values<std::string>("cv/optflow/frames/VGA_%02d.png", "cv/optflow/frames/720p_%02d.jpg"),
testing::Range(1, 3),
testing::Values(1, 3, 4),
testing::Values(make_tuple(9, 9), make_tuple(15, 15)),
testing::Values(7, 11, 25),
testing::Bool()
)
)
{
string filename1 = getDataPath(cv::format(get<0>(GetParam()).c_str(), get<1>(GetParam())));
string filename2 = getDataPath(cv::format(get<0>(GetParam()).c_str(), get<1>(GetParam()) + 1));
Mat img1 = imread(filename1);
Mat img2 = imread(filename2);
if (img1.empty()) FAIL() << "Unable to load source image " << filename1;
if (img2.empty()) FAIL() << "Unable to load source image " << filename2;
int cn = get<2>(GetParam());
int nPointsX = min(get<0>(get<3>(GetParam())), img1.cols);
int nPointsY = min(get<1>(get<3>(GetParam())), img1.rows);
int winSize = get<4>(GetParam());
bool withDerivatives = get<5>(GetParam());
int maxLevel = 2;
TermCriteria criteria(CV_TERMCRIT_ITER|CV_TERMCRIT_EPS, 7, 0.001);
int flags = 0;
double minEigThreshold = 1e-4;
Mat frame1, frame2;
switch(cn)
{
case 1:
cvtColor(img1, frame1, COLOR_BGR2GRAY, cn);
cvtColor(img2, frame2, COLOR_BGR2GRAY, cn);
break;
case 3:
frame1 = img1;
frame2 = img2;
break;
case 4:
cvtColor(img1, frame1, COLOR_BGR2BGRA, cn);
cvtColor(img2, frame2, COLOR_BGR2BGRA, cn);
break;
default:
FAIL() << "Unexpected number of channels: " << cn;
}
vector<Point2f> inPoints;
vector<Point2f> outPoints;
vector<uchar> status;
vector<float> err;
FormTrackingPointsArray(inPoints, frame1.cols, frame1.rows, nPointsX, nPointsY);
outPoints.resize(inPoints.size());
status.resize(inPoints.size());
err.resize(inPoints.size());
std::vector<Mat> pyramid1, pyramid2;
maxLevel = buildOpticalFlowPyramid(frame1, pyramid1, Size(winSize, winSize), maxLevel, withDerivatives);
maxLevel = buildOpticalFlowPyramid(frame2, pyramid2, Size(winSize, winSize), maxLevel, withDerivatives);
declare.in(pyramid1, pyramid2, inPoints).out(outPoints);
TEST_CYCLE()
{
calcOpticalFlowPyrLK(pyramid1, pyramid2, inPoints, outPoints, status, err,
Size(winSize, winSize), maxLevel, criteria,
flags, minEigThreshold);
}
}
CV_ENUM(PyrBorderMode, BORDER_DEFAULT, BORDER_TRANSPARENT);
typedef tr1::tuple<std::string, int, bool, PyrBorderMode, bool> Path_Win_Deriv_Border_Reuse_t;
typedef TestBaseWithParam<Path_Win_Deriv_Border_Reuse_t> Path_Win_Deriv_Border_Reuse;
PERF_TEST_P(Path_Win_Deriv_Border_Reuse, OpticalFlowPyrLK_pyr, testing::Combine(
testing::Values<std::string>("cv/optflow/frames/720p_01.jpg"),
testing::Values(7, 11),
testing::Bool(),
testing::ValuesIn(PyrBorderMode::all()),
testing::Bool()
)
)
{
string filename = getDataPath(get<0>(GetParam()));
Mat img = imread(filename);
Size winSize(get<1>(GetParam()), get<1>(GetParam()));
bool withDerivatives = get<2>(GetParam());
int derivBorder = get<3>(GetParam());
int pyrBorder = derivBorder;
if(derivBorder != BORDER_TRANSPARENT)
{
derivBorder = BORDER_CONSTANT;
pyrBorder = BORDER_REFLECT_101;
}
bool tryReuseInputImage = get<4>(GetParam());
std::vector<Mat> pyramid;
img.adjustROI(winSize.height, winSize.height, winSize.width, winSize.width);
int maxLevel = buildOpticalFlowPyramid(img, pyramid, winSize, 1000, withDerivatives, BORDER_CONSTANT, BORDER_CONSTANT, tryReuseInputImage);
declare.in(img).out(pyramid);
TEST_CYCLE()
{
buildOpticalFlowPyramid(img, pyramid, winSize, maxLevel, withDerivatives, pyrBorder, derivBorder, tryReuseInputImage);
}
SANITY_CHECK(pyramid);
}
\ No newline at end of file
...@@ -41,18 +41,23 @@ ...@@ -41,18 +41,23 @@
#include "precomp.hpp" #include "precomp.hpp"
#include <float.h> #include <float.h>
#include <stdio.h> #include <stdio.h>
#include "lkpyramid.hpp"
namespace cv namespace
{ {
static void calcSharrDeriv(const cv::Mat& src, cv::Mat& dst)
typedef short deriv_type;
static void calcSharrDeriv(const Mat& src, Mat& dst)
{ {
using namespace cv;
using cv::detail::deriv_type;
int rows = src.rows, cols = src.cols, cn = src.channels(), colsn = cols*cn, depth = src.depth(); int rows = src.rows, cols = src.cols, cn = src.channels(), colsn = cols*cn, depth = src.depth();
CV_Assert(depth == CV_8U); CV_Assert(depth == CV_8U);
dst.create(rows, cols, CV_MAKETYPE(DataType<deriv_type>::depth, cn*2)); dst.create(rows, cols, CV_MAKETYPE(DataType<deriv_type>::depth, cn*2));
#ifdef HAVE_TEGRA_OPTIMIZATION
if (tegra::calcSharrDeriv(src, dst))
return;
#endif
int x, y, delta = (int)alignSize((cols + 2)*cn, 16); int x, y, delta = (int)alignSize((cols + 2)*cn, 16);
AutoBuffer<deriv_type> _tempBuf(delta*2 + 64); AutoBuffer<deriv_type> _tempBuf(delta*2 + 64);
deriv_type *trow0 = alignPtr(_tempBuf + cn, 16), *trow1 = alignPtr(trow0 + delta, 16); deriv_type *trow0 = alignPtr(_tempBuf + cn, 16), *trow1 = alignPtr(trow0 + delta, 16);
...@@ -127,15 +132,15 @@ static void calcSharrDeriv(const Mat& src, Mat& dst) ...@@ -127,15 +132,15 @@ static void calcSharrDeriv(const Mat& src, Mat& dst)
} }
} }
}//namespace
struct LKTrackerInvoker cv::detail::LKTrackerInvoker::LKTrackerInvoker(
{ const Mat& _prevImg, const Mat& _prevDeriv, const Mat& _nextImg,
LKTrackerInvoker( const Mat& _prevImg, const Mat& _prevDeriv, const Mat& _nextImg,
const Point2f* _prevPts, Point2f* _nextPts, const Point2f* _prevPts, Point2f* _nextPts,
uchar* _status, float* _err, uchar* _status, float* _err,
Size _winSize, TermCriteria _criteria, Size _winSize, TermCriteria _criteria,
int _level, int _maxLevel, int _flags, float _minEigThreshold ) int _level, int _maxLevel, int _flags, float _minEigThreshold )
{ {
prevImg = &_prevImg; prevImg = &_prevImg;
prevDeriv = &_prevDeriv; prevDeriv = &_prevDeriv;
nextImg = &_nextImg; nextImg = &_nextImg;
...@@ -149,10 +154,10 @@ struct LKTrackerInvoker ...@@ -149,10 +154,10 @@ struct LKTrackerInvoker
maxLevel = _maxLevel; maxLevel = _maxLevel;
flags = _flags; flags = _flags;
minEigThreshold = _minEigThreshold; minEigThreshold = _minEigThreshold;
} }
void operator()(const BlockedRange& range) const void cv::detail::LKTrackerInvoker::operator()(const BlockedRange& range) const
{ {
Point2f halfWin((winSize.width-1)*0.5f, (winSize.height-1)*0.5f); Point2f halfWin((winSize.width-1)*0.5f, (winSize.height-1)*0.5f);
const Mat& I = *prevImg; const Mat& I = *prevImg;
const Mat& J = *nextImg; const Mat& J = *nextImg;
...@@ -474,26 +479,8 @@ struct LKTrackerInvoker ...@@ -474,26 +479,8 @@ struct LKTrackerInvoker
err[ptidx] = errval * 1.f/(32*winSize.width*cn*winSize.height); err[ptidx] = errval * 1.f/(32*winSize.width*cn*winSize.height);
} }
} }
}
const Mat* prevImg;
const Mat* nextImg;
const Mat* prevDeriv;
const Point2f* prevPts;
Point2f* nextPts;
uchar* status;
float* err;
Size winSize;
TermCriteria criteria;
int level;
int maxLevel;
int flags;
float minEigThreshold;
};
} }
int cv::buildOpticalFlowPyramid(InputArray _img, OutputArrayOfArrays pyramid, Size winSize, int maxLevel, bool withDerivatives, int cv::buildOpticalFlowPyramid(InputArray _img, OutputArrayOfArrays pyramid, Size winSize, int maxLevel, bool withDerivatives,
int pyrBorder, int derivBorder, bool tryReuseInputImage) int pyrBorder, int derivBorder, bool tryReuseInputImage)
{ {
...@@ -503,7 +490,7 @@ int cv::buildOpticalFlowPyramid(InputArray _img, OutputArrayOfArrays pyramid, Si ...@@ -503,7 +490,7 @@ int cv::buildOpticalFlowPyramid(InputArray _img, OutputArrayOfArrays pyramid, Si
pyramid.create(1, (maxLevel + 1) * pyrstep, 0 /*type*/, -1, true, 0); pyramid.create(1, (maxLevel + 1) * pyrstep, 0 /*type*/, -1, true, 0);
int derivType = CV_MAKETYPE(DataType<deriv_type>::depth, img.channels() * 2); int derivType = CV_MAKETYPE(DataType<cv::detail::deriv_type>::depth, img.channels() * 2);
//level 0 //level 0
bool lvl0IsSet = false; bool lvl0IsSet = false;
...@@ -597,12 +584,8 @@ void cv::calcOpticalFlowPyrLK( InputArray _prevImg, InputArray _nextImg, ...@@ -597,12 +584,8 @@ void cv::calcOpticalFlowPyrLK( InputArray _prevImg, InputArray _nextImg,
TermCriteria criteria, TermCriteria criteria,
int flags, double minEigThreshold ) int flags, double minEigThreshold )
{ {
#ifdef HAVE_TEGRA_OPTIMIZATION
if (tegra::calcOpticalFlowPyrLK(_prevImg, _nextImg, _prevPts, _nextPts, _status, _err, winSize, maxLevel, criteria, flags, minEigThreshold))
return;
#endif
Mat prevPtsMat = _prevPts.getMat(); Mat prevPtsMat = _prevPts.getMat();
const int derivDepth = DataType<deriv_type>::depth; const int derivDepth = DataType<cv::detail::deriv_type>::depth;
CV_Assert( maxLevel >= 0 && winSize.width > 2 && winSize.height > 2 ); CV_Assert( maxLevel >= 0 && winSize.width > 2 && winSize.height > 2 );
...@@ -744,6 +727,12 @@ void cv::calcOpticalFlowPyrLK( InputArray _prevImg, InputArray _nextImg, ...@@ -744,6 +727,12 @@ void cv::calcOpticalFlowPyrLK( InputArray _prevImg, InputArray _nextImg,
CV_Assert(prevPyr[level * lvlStep1].size() == nextPyr[level * lvlStep2].size()); CV_Assert(prevPyr[level * lvlStep1].size() == nextPyr[level * lvlStep2].size());
CV_Assert(prevPyr[level * lvlStep1].type() == nextPyr[level * lvlStep2].type()); CV_Assert(prevPyr[level * lvlStep1].type() == nextPyr[level * lvlStep2].type());
#ifdef HAVE_TEGRA_OPTIMIZATION
typedef tegra::LKTrackerInvoker<cv::detail::LKTrackerInvoker> LKTrackerInvoker;
#else
typedef cv::detail::LKTrackerInvoker LKTrackerInvoker;
#endif
parallel_for(BlockedRange(0, npoints), LKTrackerInvoker(prevPyr[level * lvlStep1], derivI, parallel_for(BlockedRange(0, npoints), LKTrackerInvoker(prevPyr[level * lvlStep1], derivI,
nextPyr[level * lvlStep2], prevPts, nextPts, nextPyr[level * lvlStep2], prevPts, nextPts,
status, err, status, err,
......
#pragma once
namespace cv
{
namespace detail
{
typedef short deriv_type;
struct LKTrackerInvoker
{
LKTrackerInvoker( const Mat& _prevImg, const Mat& _prevDeriv, const Mat& _nextImg,
const Point2f* _prevPts, Point2f* _nextPts,
uchar* _status, float* _err,
Size _winSize, TermCriteria _criteria,
int _level, int _maxLevel, int _flags, float _minEigThreshold );
void operator()(const BlockedRange& range) const;
const Mat* prevImg;
const Mat* nextImg;
const Mat* prevDeriv;
const Point2f* prevPts;
Point2f* nextPts;
uchar* status;
float* err;
Size winSize;
TermCriteria criteria;
int level;
int maxLevel;
int flags;
float minEigThreshold;
};
}// namespace detail
}// namespace cv
\ No newline at end of file
...@@ -47,72 +47,24 @@ namespace cv ...@@ -47,72 +47,24 @@ namespace cv
/////////////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////////////
static Algorithm* createMOG() CV_INIT_ALGORITHM(BackgroundSubtractorMOG, "BackgroundSubtractor.MOG",
{ obj.info()->addParam(obj, "history", obj.history);
return new BackgroundSubtractorMOG; obj.info()->addParam(obj, "nmixtures", obj.nmixtures);
} obj.info()->addParam(obj, "backgroundRatio", obj.backgroundRatio);
obj.info()->addParam(obj, "noiseSigma", obj.noiseSigma));
static AlgorithmInfo& mog_info()
{
static AlgorithmInfo mog_info_var("BackgroundSubtractor.MOG", createMOG);
return mog_info_var;
}
static AlgorithmInfo& mog_info_auto = mog_info();
AlgorithmInfo* BackgroundSubtractorMOG::info() const
{
static volatile bool initialized = false;
if( !initialized )
{
BackgroundSubtractorMOG obj;
mog_info().addParam(obj, "history", obj.history);
mog_info().addParam(obj, "nmixtures", obj.nmixtures);
mog_info().addParam(obj, "backgroundRatio", obj.backgroundRatio);
mog_info().addParam(obj, "noiseSigma", obj.noiseSigma);
initialized = true;
}
return &mog_info();
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////////////
static Algorithm* createMOG2() CV_INIT_ALGORITHM(BackgroundSubtractorMOG2, "BackgroundSubtractor.MOG2",
{ obj.info()->addParam(obj, "history", obj.history);
return new BackgroundSubtractorMOG2; obj.info()->addParam(obj, "varThreshold", obj.varThreshold);
} obj.info()->addParam(obj, "detectShadows", obj.bShadowDetection));
static AlgorithmInfo& mog2_info()
{
static AlgorithmInfo mog2_info_var("BackgroundSubtractor.MOG2", createMOG2);
return mog2_info_var;
}
static AlgorithmInfo& mog2_info_auto = mog2_info();
AlgorithmInfo* BackgroundSubtractorMOG2::info() const
{
static volatile bool initialized = false;
if( !initialized )
{
BackgroundSubtractorMOG2 obj;
mog2_info().addParam(obj, "history", obj.history);
mog2_info().addParam(obj, "varThreshold", obj.varThreshold);
mog2_info().addParam(obj, "detectShadows", obj.bShadowDetection);
initialized = true;
}
return &mog2_info();
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////////////
bool initModule_video(void) bool initModule_video(void)
{ {
Ptr<Algorithm> mog = createMOG(), mog2 = createMOG2(); Ptr<Algorithm> mog = createBackgroundSubtractorMOG(), mog2 = createBackgroundSubtractorMOG2();
return mog->info() != 0 && mog2->info() != 0; return mog->info() != 0 && mog2->info() != 0;
} }
......
#include "opencv2/highgui/highgui.hpp" #include "opencv2/highgui/highgui.hpp"
#include "opencv2/imgproc/imgproc.hpp" #include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/features2d/features2d.hpp" #include "opencv2/features2d/features2d.hpp"
#include "opencv2/nonfree/nonfree.hpp"
#include "opencv2/ml/ml.hpp" #include "opencv2/ml/ml.hpp"
#include <fstream> #include <fstream>
...@@ -2515,6 +2516,8 @@ int main(int argc, char** argv) ...@@ -2515,6 +2516,8 @@ int main(int argc, char** argv)
return -1; return -1;
} }
cv::initModule_nonfree();
const string vocPath = argv[1], resPath = argv[2]; const string vocPath = argv[1], resPath = argv[2];
// Read or set default parameters // Read or set default parameters
......
...@@ -2,6 +2,7 @@ ...@@ -2,6 +2,7 @@
#include "opencv2/calib3d/calib3d.hpp" #include "opencv2/calib3d/calib3d.hpp"
#include "opencv2/imgproc/imgproc.hpp" #include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/features2d/features2d.hpp" #include "opencv2/features2d/features2d.hpp"
#include "opencv2/nonfree/nonfree.hpp"
#include <iostream> #include <iostream>
...@@ -235,6 +236,9 @@ int main(int argc, char** argv) ...@@ -235,6 +236,9 @@ int main(int argc, char** argv)
help(argv); help(argv);
return -1; return -1;
} }
cv::initModule_nonfree();
bool isWarpPerspective = argc == 7; bool isWarpPerspective = argc == 7;
double ransacReprojThreshold = -1; double ransacReprojThreshold = -1;
if( !isWarpPerspective ) if( !isWarpPerspective )
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment