Commit 87a21016 authored by Leonid Beynenson's avatar Leonid Beynenson

Implemented the first variant of working with masks in CascadeClassifier.…

Implemented the first variant of working with masks in CascadeClassifier. Probably, will be rewritten soon.
parent 4d3b1a4a
#include "perf_precomp.hpp" #include "perf_precomp.hpp"
#include <opencv2/imgproc/imgproc.hpp>
using namespace std; using namespace std;
using namespace cv; using namespace cv;
...@@ -8,7 +9,18 @@ typedef std::tr1::tuple<std::string, int> ImageName_MinSize_t; ...@@ -8,7 +9,18 @@ typedef std::tr1::tuple<std::string, int> ImageName_MinSize_t;
typedef perf::TestBaseWithParam<ImageName_MinSize_t> ImageName_MinSize; typedef perf::TestBaseWithParam<ImageName_MinSize_t> ImageName_MinSize;
PERF_TEST_P( ImageName_MinSize, CascadeClassifierLBPFrontalFace, PERF_TEST_P( ImageName_MinSize, CascadeClassifierLBPFrontalFace,
testing::Combine(testing::Values( std::string("cv/shared/lena.jpg")), testing::Values(24, 30, 40, 50, 60, 70, 80, 90) ) ) testing::Combine(testing::Values( std::string("cv/shared/lena.jpg"),
std::string("cv/shared/1_itseez-0000247.jpg"),
std::string("cv/shared/1_itseez-0000289.jpg"),
std::string("cv/shared/1_itseez-0000492.jpg"),
std::string("cv/shared/1_itseez-0000573.jpg"),
std::string("cv/shared/1_itseez-0000803.jpg"),
std::string("cv/shared/1_itseez-0000892.jpg"),
std::string("cv/shared/1_itseez-0000984.jpg"),
std::string("cv/shared/1_itseez-0001238.jpg"),
std::string("cv/shared/1_itseez-0001438.jpg"),
std::string("cv/shared/1_itseez-0002524.jpg")),
testing::Values(24, 30, 40, 50, 60, 70, 80, 90) ) )
{ {
const string filename = std::tr1::get<0>(GetParam()); const string filename = std::tr1::get<0>(GetParam());
int min_size = std::tr1::get<1>(GetParam()); int min_size = std::tr1::get<1>(GetParam());
...@@ -18,12 +30,13 @@ PERF_TEST_P( ImageName_MinSize, CascadeClassifierLBPFrontalFace, ...@@ -18,12 +30,13 @@ PERF_TEST_P( ImageName_MinSize, CascadeClassifierLBPFrontalFace,
if (cc.empty()) if (cc.empty())
FAIL() << "Can't load cascade file"; FAIL() << "Can't load cascade file";
Mat img=imread(getDataPath(filename)); Mat img=imread(getDataPath(filename), 0);
if (img.empty()) if (img.empty())
FAIL() << "Can't load source image"; FAIL() << "Can't load source image";
vector<Rect> res; vector<Rect> res;
declare.in(img);//.out(res) declare.in(img);//.out(res)
while(next()) while(next())
...@@ -31,6 +44,7 @@ PERF_TEST_P( ImageName_MinSize, CascadeClassifierLBPFrontalFace, ...@@ -31,6 +44,7 @@ PERF_TEST_P( ImageName_MinSize, CascadeClassifierLBPFrontalFace,
res.clear(); res.clear();
startTimer(); startTimer();
equalizeHist(img, img);
cc.detectMultiScale(img, res, 1.1, 3, 0, minSize); cc.detectMultiScale(img, res, 1.1, 3, 0, minSize);
stopTimer(); stopTimer();
} }
......
...@@ -861,9 +861,10 @@ bool CascadeClassifier::setImage( Ptr<FeatureEvaluator>& featureEvaluator, const ...@@ -861,9 +861,10 @@ bool CascadeClassifier::setImage( Ptr<FeatureEvaluator>& featureEvaluator, const
struct CascadeClassifierInvoker struct CascadeClassifierInvoker
{ {
CascadeClassifierInvoker( CascadeClassifier& _cc, Size _sz1, int _stripSize, int _yStep, double _factor, CascadeClassifierInvoker( const Mat& _image, CascadeClassifier& _cc, Size _sz1, int _stripSize, int _yStep, double _factor,
ConcurrentRectVector& _vec, vector<int>& _levels, vector<double>& _weights, bool outputLevels = false ) ConcurrentRectVector& _vec, vector<int>& _levels, vector<double>& _weights, bool outputLevels = false )
{ {
image=_image;
classifier = &_cc; classifier = &_cc;
processingRectSize = _sz1; processingRectSize = _sz1;
stripSize = _stripSize; stripSize = _stripSize;
...@@ -877,6 +878,10 @@ struct CascadeClassifierInvoker ...@@ -877,6 +878,10 @@ struct CascadeClassifierInvoker
void operator()(const BlockedRange& range) const void operator()(const BlockedRange& range) const
{ {
Ptr<FeatureEvaluator> evaluator = classifier->featureEvaluator->clone(); Ptr<FeatureEvaluator> evaluator = classifier->featureEvaluator->clone();
#ifdef HAVE_TEGRA_OPTIMIZATION
Mat currentMask=tegra::getCascadeClassifierMask(image, classifier->data.origWinSize);
#endif
Size winSize(cvRound(classifier->data.origWinSize.width * scalingFactor), cvRound(classifier->data.origWinSize.height * scalingFactor)); Size winSize(cvRound(classifier->data.origWinSize.width * scalingFactor), cvRound(classifier->data.origWinSize.height * scalingFactor));
int y1 = range.begin() * stripSize; int y1 = range.begin() * stripSize;
...@@ -885,6 +890,12 @@ struct CascadeClassifierInvoker ...@@ -885,6 +890,12 @@ struct CascadeClassifierInvoker
{ {
for( int x = 0; x < processingRectSize.width; x += yStep ) for( int x = 0; x < processingRectSize.width; x += yStep )
{ {
#ifdef HAVE_TEGRA_OPTIMIZATION
if ( (!currentMask.empty()) && (currentMask.at<uchar>(Point(x,y))==0)) {
continue;
}
#endif
double gypWeight; double gypWeight;
int result = classifier->runAt(evaluator, Point(x, y), gypWeight); int result = classifier->runAt(evaluator, Point(x, y), gypWeight);
if( rejectLevels ) if( rejectLevels )
...@@ -907,6 +918,7 @@ struct CascadeClassifierInvoker ...@@ -907,6 +918,7 @@ struct CascadeClassifierInvoker
} }
} }
Mat image;
CascadeClassifier* classifier; CascadeClassifier* classifier;
ConcurrentRectVector* rectangles; ConcurrentRectVector* rectangles;
Size processingRectSize; Size processingRectSize;
...@@ -930,14 +942,14 @@ bool CascadeClassifier::detectSingleScale( const Mat& image, int stripCount, Siz ...@@ -930,14 +942,14 @@ bool CascadeClassifier::detectSingleScale( const Mat& image, int stripCount, Siz
vector<double> levelWeights; vector<double> levelWeights;
if( outputRejectLevels ) if( outputRejectLevels )
{ {
parallel_for(BlockedRange(0, stripCount), CascadeClassifierInvoker( *this, processingRectSize, stripSize, yStep, factor, parallel_for(BlockedRange(0, stripCount), CascadeClassifierInvoker( image, *this, processingRectSize, stripSize, yStep, factor,
concurrentCandidates, rejectLevels, levelWeights, true)); concurrentCandidates, rejectLevels, levelWeights, true));
levels.insert( levels.end(), rejectLevels.begin(), rejectLevels.end() ); levels.insert( levels.end(), rejectLevels.begin(), rejectLevels.end() );
weights.insert( weights.end(), levelWeights.begin(), levelWeights.end() ); weights.insert( weights.end(), levelWeights.begin(), levelWeights.end() );
} }
else else
{ {
parallel_for(BlockedRange(0, stripCount), CascadeClassifierInvoker( *this, processingRectSize, stripSize, yStep, factor, parallel_for(BlockedRange(0, stripCount), CascadeClassifierInvoker( image, *this, processingRectSize, stripSize, yStep, factor,
concurrentCandidates, rejectLevels, levelWeights, false)); concurrentCandidates, rejectLevels, levelWeights, false));
} }
candidates.insert( candidates.end(), concurrentCandidates.begin(), concurrentCandidates.end() ); candidates.insert( candidates.end(), concurrentCandidates.begin(), concurrentCandidates.end() );
......
...@@ -60,4 +60,8 @@ ...@@ -60,4 +60,8 @@
#include "opencv2/features2d/features2d.hpp" #include "opencv2/features2d/features2d.hpp"
#include "opencv2/calib3d/calib3d.hpp" #include "opencv2/calib3d/calib3d.hpp"
#ifdef HAVE_TEGRA_OPTIMIZATION
#include "opencv2/objdetect/objdetect_tegra.hpp"
#endif
#endif #endif
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