1 /*M///////////////////////////////////////////////////////////////////////////////////////
3 // IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
5 // By downloading, copying, installing or using the software you agree to this license.
6 // If you do not agree to this license, do not download, install,
7 // copy or use the software.
11 // For Open Source Computer Vision Library
13 // Copyright (C) 2000-2008, Intel Corporation, all rights reserved.
14 // Copyright (C) 2009-2011, Willow Garage Inc., all rights reserved.
15 // Third party copyrights are property of their respective owners.
17 // Redistribution and use in source and binary forms, with or without modification,
18 // are permitted provided that the following conditions are met:
20 // * Redistribution's of source code must retain the above copyright notice,
21 // this list of conditions and the following disclaimer.
23 // * Redistribution's in binary form must reproduce the above copyright notice,
24 // this list of conditions and the following disclaimer in the documentation
25 // and/or other materials provided with the distribution.
27 // * The name of the copyright holders may not be used to endorse or promote products
28 // derived from this software without specific prior written permission.
30 // This software is provided by the copyright holders and contributors "as is" and
31 // any express or implied warranties, including, but not limited to, the implied
32 // warranties of merchantability and fitness for a particular purpose are disclaimed.
33 // In no event shall the Intel Corporation or contributors be liable for any direct,
34 // indirect, incidental, special, exemplary, or consequential damages
35 // (including, but not limited to, procurement of substitute goods or services;
36 // loss of use, data, or profits; or business interruption) however caused
37 // and on any theory of liability, whether in contract, strict liability,
38 // or tort (including negligence or otherwise) arising in any way out of
39 // the use of this software, even if advised of the possibility of such damage.
43 #include "precomp.hpp"
50 template<typename _KeyTp, typename _ValueTp> struct sorted_vector
53 void clear() { vec.clear(); }
54 size_t size() const { return vec.size(); }
55 _ValueTp& operator [](size_t idx) { return vec[idx]; }
56 const _ValueTp& operator [](size_t idx) const { return vec[idx]; }
58 void add(const _KeyTp& k, const _ValueTp& val)
60 pair<_KeyTp, _ValueTp> p(k, val);
62 size_t i = vec.size()-1;
63 for( ; i > 0 && vec[i].first < vec[i-1].first; i-- )
64 std::swap(vec[i-1], vec[i]);
65 CV_Assert( i == 0 || vec[i].first != vec[i-1].first );
68 bool find(const _KeyTp& key, _ValueTp& value) const
70 size_t a = 0, b = vec.size();
74 if( vec[c].first < key )
80 if( a < vec.size() && vec[a].first == key )
82 value = vec[a].second;
88 void get_keys(vector<_KeyTp>& keys) const
90 size_t i = 0, n = vec.size();
93 for( i = 0; i < n; i++ )
94 keys[i] = vec[i].first;
97 vector<pair<_KeyTp, _ValueTp> > vec;
101 template<typename _ValueTp> inline const _ValueTp* findstr(const sorted_vector<string, _ValueTp>& vec,
107 size_t a = 0, b = vec.vec.size();
110 size_t c = (a + b)/2;
111 if( strcmp(vec.vec[c].first.c_str(), key) < 0 )
117 if( ( a < vec.vec.size() ) && ( strcmp(vec.vec[a].first.c_str(), key) == 0 ))
118 return &vec.vec[a].second;
133 Param::Param(int _type, bool _readonly, int _offset,
134 Algorithm::Getter _getter, Algorithm::Setter _setter,
138 readonly = _readonly;
145 struct CV_EXPORTS AlgorithmInfoData
147 sorted_vector<string, Param> params;
152 static sorted_vector<string, Algorithm::Constructor>& alglist()
154 static sorted_vector<string, Algorithm::Constructor> alglist_var;
158 void Algorithm::getList(vector<string>& algorithms)
160 alglist().get_keys(algorithms);
163 Ptr<Algorithm> Algorithm::_create(const string& name)
165 Algorithm::Constructor c = 0;
166 if( !alglist().find(name, c) )
167 return Ptr<Algorithm>();
171 Algorithm::Algorithm()
175 Algorithm::~Algorithm()
179 string Algorithm::name() const
181 return info()->name();
184 void Algorithm::set(const string& parameter, int value)
186 info()->set(this, parameter.c_str(), ParamType<int>::type, &value);
189 void Algorithm::set(const string& parameter, double value)
191 info()->set(this, parameter.c_str(), ParamType<double>::type, &value);
194 void Algorithm::set(const string& parameter, bool value)
196 info()->set(this, parameter.c_str(), ParamType<bool>::type, &value);
199 void Algorithm::set(const string& parameter, const string& value)
201 info()->set(this, parameter.c_str(), ParamType<string>::type, &value);
204 void Algorithm::set(const string& parameter, const Mat& value)
206 info()->set(this, parameter.c_str(), ParamType<Mat>::type, &value);
209 void Algorithm::set(const string& parameter, const vector<Mat>& value)
211 info()->set(this, parameter.c_str(), ParamType<vector<Mat> >::type, &value);
214 void Algorithm::set(const string& parameter, const Ptr<Algorithm>& value)
216 info()->set(this, parameter.c_str(), ParamType<Algorithm>::type, &value);
219 void Algorithm::set(const char* parameter, int value)
221 info()->set(this, parameter, ParamType<int>::type, &value);
224 void Algorithm::set(const char* parameter, double value)
226 info()->set(this, parameter, ParamType<double>::type, &value);
229 void Algorithm::set(const char* parameter, bool value)
231 info()->set(this, parameter, ParamType<bool>::type, &value);
234 void Algorithm::set(const char* parameter, const string& value)
236 info()->set(this, parameter, ParamType<string>::type, &value);
239 void Algorithm::set(const char* parameter, const Mat& value)
241 info()->set(this, parameter, ParamType<Mat>::type, &value);
244 void Algorithm::set(const char* parameter, const vector<Mat>& value)
246 info()->set(this, parameter, ParamType<vector<Mat> >::type, &value);
249 void Algorithm::set(const char* parameter, const Ptr<Algorithm>& value)
251 info()->set(this, parameter, ParamType<Algorithm>::type, &value);
255 void Algorithm::setInt(const string& parameter, int value)
257 info()->set(this, parameter.c_str(), ParamType<int>::type, &value);
260 void Algorithm::setDouble(const string& parameter, double value)
262 info()->set(this, parameter.c_str(), ParamType<double>::type, &value);
265 void Algorithm::setBool(const string& parameter, bool value)
267 info()->set(this, parameter.c_str(), ParamType<bool>::type, &value);
270 void Algorithm::setString(const string& parameter, const string& value)
272 info()->set(this, parameter.c_str(), ParamType<string>::type, &value);
275 void Algorithm::setMat(const string& parameter, const Mat& value)
277 info()->set(this, parameter.c_str(), ParamType<Mat>::type, &value);
280 void Algorithm::setMatVector(const string& parameter, const vector<Mat>& value)
282 info()->set(this, parameter.c_str(), ParamType<vector<Mat> >::type, &value);
285 void Algorithm::setAlgorithm(const string& parameter, const Ptr<Algorithm>& value)
287 info()->set(this, parameter.c_str(), ParamType<Algorithm>::type, &value);
290 void Algorithm::setInt(const char* parameter, int value)
292 info()->set(this, parameter, ParamType<int>::type, &value);
295 void Algorithm::setDouble(const char* parameter, double value)
297 info()->set(this, parameter, ParamType<double>::type, &value);
300 void Algorithm::setBool(const char* parameter, bool value)
302 info()->set(this, parameter, ParamType<bool>::type, &value);
305 void Algorithm::setString(const char* parameter, const string& value)
307 info()->set(this, parameter, ParamType<string>::type, &value);
310 void Algorithm::setMat(const char* parameter, const Mat& value)
312 info()->set(this, parameter, ParamType<Mat>::type, &value);
315 void Algorithm::setMatVector(const char* parameter, const vector<Mat>& value)
317 info()->set(this, parameter, ParamType<vector<Mat> >::type, &value);
320 void Algorithm::setAlgorithm(const char* parameter, const Ptr<Algorithm>& value)
322 info()->set(this, parameter, ParamType<Algorithm>::type, &value);
328 int Algorithm::getInt(const string& parameter) const
330 return get<int>(parameter);
333 double Algorithm::getDouble(const string& parameter) const
335 return get<double>(parameter);
338 bool Algorithm::getBool(const string& parameter) const
340 return get<bool>(parameter);
343 string Algorithm::getString(const string& parameter) const
345 return get<string>(parameter);
348 Mat Algorithm::getMat(const string& parameter) const
350 return get<Mat>(parameter);
353 vector<Mat> Algorithm::getMatVector(const string& parameter) const
355 return get<vector<Mat> >(parameter);
358 Ptr<Algorithm> Algorithm::getAlgorithm(const string& parameter) const
360 return get<Algorithm>(parameter);
363 string Algorithm::paramHelp(const string& parameter) const
365 return info()->paramHelp(parameter.c_str());
368 int Algorithm::paramType(const string& parameter) const
370 return info()->paramType(parameter.c_str());
373 int Algorithm::paramType(const char* parameter) const
375 return info()->paramType(parameter);
378 void Algorithm::getParams(vector<string>& names) const
380 info()->getParams(names);
383 void Algorithm::write(FileStorage& fs) const
385 info()->write(this, fs);
388 void Algorithm::read(const FileNode& fn)
390 info()->read(this, fn);
394 AlgorithmInfo::AlgorithmInfo(const string& _name, Algorithm::Constructor create)
396 data = new AlgorithmInfoData;
398 if (!alglist().find(_name, create))
399 alglist().add(_name, create);
402 AlgorithmInfo::~AlgorithmInfo()
407 void AlgorithmInfo::write(const Algorithm* algo, FileStorage& fs) const
409 size_t i = 0, nparams = data->params.vec.size();
410 cv::write(fs, "name", algo->name());
411 for( i = 0; i < nparams; i++ )
413 const Param& p = data->params.vec[i].second;
414 const string& pname = data->params.vec[i].first;
415 if( p.type == Param::INT )
416 cv::write(fs, pname, algo->get<int>(pname));
417 else if( p.type == Param::BOOLEAN )
418 cv::write(fs, pname, (int)algo->get<bool>(pname));
419 else if( p.type == Param::SHORT )
420 cv::write(fs, pname, (int)algo->get<short>(pname));
421 else if( p.type == Param::REAL )
422 cv::write(fs, pname, algo->get<double>(pname));
423 else if( p.type == Param::STRING )
424 cv::write(fs, pname, algo->get<string>(pname));
425 else if( p.type == Param::MAT )
426 cv::write(fs, pname, algo->get<Mat>(pname));
427 else if( p.type == Param::MAT_VECTOR )
428 cv::write(fs, pname, algo->get<vector<Mat> >(pname));
429 else if( p.type == Param::ALGORITHM )
431 WriteStructContext ws(fs, pname, CV_NODE_MAP);
432 Ptr<Algorithm> nestedAlgo = algo->get<Algorithm>(pname);
433 nestedAlgo->write(fs);
435 else if( p.type == Param::FLOAT)
436 cv::write(fs, pname, algo->getDouble(pname));
437 else if( p.type == Param::UNSIGNED_INT)
438 cv::write(fs, pname, algo->getInt(pname));//TODO: implement cv::write(, , unsigned int)
439 else if( p.type == Param::UINT64)
440 cv::write(fs, pname, algo->getInt(pname));//TODO: implement cv::write(, , uint64)
441 else if( p.type == Param::UCHAR)
442 cv::write(fs, pname, algo->getInt(pname));
445 string msg = format("unknown/unsupported type of '%s' parameter == %d", pname.c_str(), p.type);
446 CV_Error( CV_StsUnsupportedFormat, msg.c_str());
451 void AlgorithmInfo::read(Algorithm* algo, const FileNode& fn) const
453 size_t i = 0, nparams = data->params.vec.size();
454 AlgorithmInfo* info = algo->info();
456 for( i = 0; i < nparams; i++ )
458 const Param& p = data->params.vec[i].second;
459 const string& pname = data->params.vec[i].first;
460 const FileNode n = fn[pname];
463 if( p.type == Param::INT || p.type == Param::SHORT )
466 info->set(algo, pname.c_str(), p.type, &val, true);
468 else if( p.type == Param::BOOLEAN )
470 bool val = (int)n != 0;
471 info->set(algo, pname.c_str(), p.type, &val, true);
473 else if( p.type == Param::REAL )
475 double val = (double)n;
476 info->set(algo, pname.c_str(), p.type, &val, true);
478 else if( p.type == Param::STRING )
480 string val = (string)n;
481 info->set(algo, pname.c_str(), p.type, &val, true);
483 else if( p.type == Param::MAT )
487 info->set(algo, pname.c_str(), p.type, &m, true);
489 else if( p.type == Param::MAT_VECTOR )
493 info->set(algo, pname.c_str(), p.type, &mv, true);
495 else if( p.type == Param::ALGORITHM )
497 Ptr<Algorithm> nestedAlgo = Algorithm::_create((string)n["name"]);
498 CV_Assert( !nestedAlgo.empty() );
500 info->set(algo, pname.c_str(), p.type, &nestedAlgo, true);
502 else if( p.type == Param::FLOAT )
504 float val = (float)n;
505 info->set(algo, pname.c_str(), p.type, &val, true);
507 else if( p.type == Param::UNSIGNED_INT )
509 unsigned int val = (unsigned int)((int)n);//TODO: implement conversion (unsigned int)FileNode
510 info->set(algo, pname.c_str(), p.type, &val, true);
512 else if( p.type == Param::UINT64)
514 uint64 val = (uint64)((int)n);//TODO: implement conversion (uint64)FileNode
515 info->set(algo, pname.c_str(), p.type, &val, true);
517 else if( p.type == Param::UCHAR)
519 uchar val = (uchar)((int)n);
520 info->set(algo, pname.c_str(), p.type, &val, true);
524 string msg = format("unknown/unsupported type of '%s' parameter == %d", pname.c_str(), p.type);
525 CV_Error( CV_StsUnsupportedFormat, msg.c_str());
530 string AlgorithmInfo::name() const
537 int (Algorithm::*get_int)() const;
538 bool (Algorithm::*get_bool)() const;
539 double (Algorithm::*get_double)() const;
540 string (Algorithm::*get_string)() const;
541 Mat (Algorithm::*get_mat)() const;
542 vector<Mat> (Algorithm::*get_mat_vector)() const;
543 Ptr<Algorithm> (Algorithm::*get_algo)() const;
544 float (Algorithm::*get_float)() const;
545 unsigned int (Algorithm::*get_uint)() const;
546 uint64 (Algorithm::*get_uint64)() const;
547 uchar (Algorithm::*get_uchar)() const;
549 void (Algorithm::*set_int)(int);
550 void (Algorithm::*set_bool)(bool);
551 void (Algorithm::*set_double)(double);
552 void (Algorithm::*set_string)(const string&);
553 void (Algorithm::*set_mat)(const Mat&);
554 void (Algorithm::*set_mat_vector)(const vector<Mat>&);
555 void (Algorithm::*set_algo)(const Ptr<Algorithm>&);
556 void (Algorithm::*set_float)(float);
557 void (Algorithm::*set_uint)(unsigned int);
558 void (Algorithm::*set_uint64)(uint64);
559 void (Algorithm::*set_uchar)(uchar);
562 static string getNameOfType(int argType);
564 static string getNameOfType(int argType)
568 case Param::INT: return "integer";
569 case Param::SHORT: return "short";
570 case Param::BOOLEAN: return "boolean";
571 case Param::REAL: return "double";
572 case Param::STRING: return "string";
573 case Param::MAT: return "cv::Mat";
574 case Param::MAT_VECTOR: return "std::vector<cv::Mat>";
575 case Param::ALGORITHM: return "algorithm";
576 case Param::FLOAT: return "float";
577 case Param::UNSIGNED_INT: return "unsigned int";
578 case Param::UINT64: return "unsigned int64";
579 case Param::UCHAR: return "unsigned char";
580 default: CV_Error(CV_StsBadArg, "Wrong argument type");
584 static string getErrorMessageForWrongArgumentInSetter(string algoName, string paramName, int paramType, int argType);
585 static string getErrorMessageForWrongArgumentInSetter(string algoName, string paramName, int paramType, int argType)
587 string message = string("Argument error: the setter")
588 + " method was called for the parameter '" + paramName + "' of the algorithm '" + algoName
589 +"', the parameter has " + getNameOfType(paramType) + " type, ";
591 if (paramType == Param::INT || paramType == Param::BOOLEAN || paramType == Param::REAL
592 || paramType == Param::FLOAT || paramType == Param::UNSIGNED_INT || paramType == Param::UINT64 || paramType == Param::UCHAR)
594 message += "so it should be set by integer, unsigned integer, uint64, unsigned char, boolean, float or double value, ";
596 else if (paramType == Param::SHORT)
598 message += "so it should be set by integer value, ";
600 message += "but the setter was called with " + getNameOfType(argType) + " value";
605 static string getErrorMessageForWrongArgumentInGetter(string algoName, string paramName, int paramType, int argType);
606 static string getErrorMessageForWrongArgumentInGetter(string algoName, string paramName, int paramType, int argType)
608 string message = string("Argument error: the getter")
609 + " method was called for the parameter '" + paramName + "' of the algorithm '" + algoName
610 +"', the parameter has " + getNameOfType(paramType) + " type, ";
612 if (paramType == Param::BOOLEAN)
614 message += "so it should be get as integer, unsigned integer, uint64, boolean, unsigned char, float or double value, ";
616 else if (paramType == Param::INT || paramType == Param::UNSIGNED_INT || paramType == Param::UINT64 || paramType == Param::UCHAR)
618 message += "so it should be get as integer, unsigned integer, uint64, unsigned char, float or double value, ";
620 else if (paramType == Param::SHORT)
622 message += "so it should be get as integer value, ";
624 else if (paramType == Param::FLOAT || paramType == Param::REAL)
626 message += "so it should be get as float or double value, ";
628 message += "but the getter was called to get a " + getNameOfType(argType) + " value";
633 void AlgorithmInfo::set(Algorithm* algo, const char* parameter, int argType, const void* value, bool force) const
635 const Param* p = findstr(data->params, parameter);
638 CV_Error_( CV_StsBadArg, ("No parameter '%s' is found", parameter ? parameter : "<NULL>") );
640 if( !force && p->readonly )
641 CV_Error_( CV_StsError, ("Parameter '%s' is readonly", parameter));
644 f.set_int = p->setter;
646 if( argType == Param::INT || argType == Param::BOOLEAN || argType == Param::REAL || argType == Param::SHORT
647 || argType == Param::FLOAT || argType == Param::UNSIGNED_INT || argType == Param::UINT64 || argType == Param::UCHAR)
649 if ( !( p->type == Param::INT || p->type == Param::REAL || p->type == Param::BOOLEAN
650 || p->type == Param::UNSIGNED_INT || p->type == Param::UINT64 || p->type == Param::FLOAT || p->type == Param::UCHAR
651 || (p->type == Param::SHORT && argType == Param::INT)) )
653 string message = getErrorMessageForWrongArgumentInSetter(algo->name(), parameter, p->type, argType);
654 CV_Error(CV_StsBadArg, message);
657 if( p->type == Param::INT )
660 int val = argType == Param::INT ? *(const int*)value :
661 argType == Param::BOOLEAN ? (int)*(const bool*)value :
662 argType == Param::REAL ? saturate_cast<int>(*(const double*)value) :
663 argType == Param::FLOAT ? saturate_cast<int>(*(const float*)value) :
664 argType == Param::UNSIGNED_INT ? (int)*(const unsigned int*)value :
665 argType == Param::UINT64 ? (int)*(const uint64*)value :
666 argType == Param::UCHAR ? (int)*(const uchar*)value :
667 (int)(is_ok = false);
671 CV_Error(CV_StsBadArg, "Wrong argument type in the setter");
675 (algo->*f.set_int)(val);
677 *(int*)((uchar*)algo + p->offset) = val;
679 else if( p->type == Param::SHORT )
681 CV_DbgAssert(argType == Param::INT);
682 int val = *(const int*)value;
684 (algo->*f.set_int)(val);
686 *(short*)((uchar*)algo + p->offset) = (short)val;
688 else if( p->type == Param::BOOLEAN )
691 bool val = argType == Param::INT ? *(const int*)value != 0 :
692 argType == Param::BOOLEAN ? *(const bool*)value :
693 argType == Param::REAL ? (*(const double*)value != 0) :
694 argType == Param::FLOAT ? (*(const float*)value != 0) :
695 argType == Param::UNSIGNED_INT ? (*(const unsigned int*)value != 0):
696 argType == Param::UINT64 ? (*(const uint64*)value != 0):
697 argType == Param::UCHAR ? (*(const uchar*)value != 0):
698 (int)(is_ok = false);
702 CV_Error(CV_StsBadArg, "Wrong argument type in the setter");
706 (algo->*f.set_bool)(val);
708 *(bool*)((uchar*)algo + p->offset) = val;
710 else if( p->type == Param::REAL )
713 double val = argType == Param::INT ? (double)*(const int*)value :
714 argType == Param::BOOLEAN ? (double)*(const bool*)value :
715 argType == Param::REAL ? (double)(*(const double*)value ) :
716 argType == Param::FLOAT ? (double)(*(const float*)value ) :
717 argType == Param::UNSIGNED_INT ? (double)(*(const unsigned int*)value ) :
718 argType == Param::UINT64 ? (double)(*(const uint64*)value ) :
719 argType == Param::UCHAR ? (double)(*(const uchar*)value ) :
720 (double)(is_ok = false);
724 CV_Error(CV_StsBadArg, "Wrong argument type in the setter");
727 (algo->*f.set_double)(val);
729 *(double*)((uchar*)algo + p->offset) = val;
731 else if( p->type == Param::FLOAT )
734 double val = argType == Param::INT ? (double)*(const int*)value :
735 argType == Param::BOOLEAN ? (double)*(const bool*)value :
736 argType == Param::REAL ? (double)(*(const double*)value ) :
737 argType == Param::FLOAT ? (double)(*(const float*)value ) :
738 argType == Param::UNSIGNED_INT ? (double)(*(const unsigned int*)value ) :
739 argType == Param::UINT64 ? (double)(*(const uint64*)value ) :
740 argType == Param::UCHAR ? (double)(*(const uchar*)value ) :
741 (double)(is_ok = false);
745 CV_Error(CV_StsBadArg, "Wrong argument type in the setter");
748 (algo->*f.set_float)((float)val);
750 *(float*)((uchar*)algo + p->offset) = (float)val;
752 else if( p->type == Param::UNSIGNED_INT )
755 unsigned int val = argType == Param::INT ? (unsigned int)*(const int*)value :
756 argType == Param::BOOLEAN ? (unsigned int)*(const bool*)value :
757 argType == Param::REAL ? saturate_cast<unsigned int>(*(const double*)value ) :
758 argType == Param::FLOAT ? saturate_cast<unsigned int>(*(const float*)value ) :
759 argType == Param::UNSIGNED_INT ? (unsigned int)(*(const unsigned int*)value ) :
760 argType == Param::UINT64 ? (unsigned int)(*(const uint64*)value ) :
761 argType == Param::UCHAR ? (unsigned int)(*(const uchar*)value ) :
762 (int)(is_ok = false);
766 CV_Error(CV_StsBadArg, "Wrong argument type in the setter");
769 (algo->*f.set_uint)(val);
771 *(unsigned int*)((uchar*)algo + p->offset) = val;
773 else if( p->type == Param::UINT64 )
776 uint64 val = argType == Param::INT ? (uint64)*(const int*)value :
777 argType == Param::BOOLEAN ? (uint64)*(const bool*)value :
778 argType == Param::REAL ? saturate_cast<uint64>(*(const double*)value ) :
779 argType == Param::FLOAT ? saturate_cast<uint64>(*(const float*)value ) :
780 argType == Param::UNSIGNED_INT ? (uint64)(*(const unsigned int*)value ) :
781 argType == Param::UINT64 ? (uint64)(*(const uint64*)value ) :
782 argType == Param::UCHAR ? (uint64)(*(const uchar*)value ) :
783 (int)(is_ok = false);
787 CV_Error(CV_StsBadArg, "Wrong argument type in the setter");
790 (algo->*f.set_uint64)(val);
792 *(uint64*)((uchar*)algo + p->offset) = val;
794 else if( p->type == Param::UCHAR )
797 uchar val = argType == Param::INT ? (uchar)*(const int*)value :
798 argType == Param::BOOLEAN ? (uchar)*(const bool*)value :
799 argType == Param::REAL ? saturate_cast<uchar>(*(const double*)value ) :
800 argType == Param::FLOAT ? saturate_cast<uchar>(*(const float*)value ) :
801 argType == Param::UNSIGNED_INT ? (uchar)(*(const unsigned int*)value ) :
802 argType == Param::UINT64 ? (uchar)(*(const uint64*)value ) :
803 argType == Param::UCHAR ? (uchar)(*(const uchar*)value ) :
804 (int)(is_ok = false);
808 CV_Error(CV_StsBadArg, "Wrong argument type in the setter");
811 (algo->*f.set_uchar)(val);
813 *(uchar*)((uchar*)algo + p->offset) = val;
816 CV_Error(CV_StsBadArg, "Wrong parameter type in the setter");
818 else if( argType == Param::STRING )
820 if( p->type != Param::STRING )
822 string message = getErrorMessageForWrongArgumentInSetter(algo->name(), parameter, p->type, argType);
823 CV_Error(CV_StsBadArg, message);
826 const string& val = *(const string*)value;
828 (algo->*f.set_string)(val);
830 *(string*)((uchar*)algo + p->offset) = val;
832 else if( argType == Param::MAT )
834 if( p->type != Param::MAT )
836 string message = getErrorMessageForWrongArgumentInSetter(algo->name(), parameter, p->type, argType);
837 CV_Error(CV_StsBadArg, message);
840 const Mat& val = *(const Mat*)value;
842 (algo->*f.set_mat)(val);
844 *(Mat*)((uchar*)algo + p->offset) = val;
846 else if( argType == Param::MAT_VECTOR )
848 if( p->type != Param::MAT_VECTOR )
850 string message = getErrorMessageForWrongArgumentInSetter(algo->name(), parameter, p->type, argType);
851 CV_Error(CV_StsBadArg, message);
854 const vector<Mat>& val = *(const vector<Mat>*)value;
856 (algo->*f.set_mat_vector)(val);
858 *(vector<Mat>*)((uchar*)algo + p->offset) = val;
860 else if( argType == Param::ALGORITHM )
862 if( p->type != Param::ALGORITHM )
864 string message = getErrorMessageForWrongArgumentInSetter(algo->name(), parameter, p->type, argType);
865 CV_Error(CV_StsBadArg, message);
868 const Ptr<Algorithm>& val = *(const Ptr<Algorithm>*)value;
870 (algo->*f.set_algo)(val);
872 *(Ptr<Algorithm>*)((uchar*)algo + p->offset) = val;
875 CV_Error(CV_StsBadArg, "Unknown/unsupported parameter type");
878 void AlgorithmInfo::get(const Algorithm* algo, const char* parameter, int argType, void* value) const
880 const Param* p = findstr(data->params, parameter);
882 CV_Error_( CV_StsBadArg, ("No parameter '%s' is found", parameter ? parameter : "<NULL>") );
885 f.get_int = p->getter;
887 if( argType == Param::INT || argType == Param::BOOLEAN || argType == Param::REAL || argType == Param::SHORT
888 || argType == Param::FLOAT || argType == Param::UNSIGNED_INT || argType == Param::UINT64 || argType == Param::UCHAR)
890 if( p->type == Param::INT )
892 if (!( argType == Param::INT || argType == Param::REAL || argType == Param::FLOAT || argType == Param::UNSIGNED_INT || argType == Param::UINT64 || argType == Param::UCHAR))
894 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
895 CV_Error(CV_StsBadArg, message);
897 int val = p->getter ? (algo->*f.get_int)() : *(int*)((uchar*)algo + p->offset);
899 if( argType == Param::INT )
900 *(int*)value = (int)val;
901 else if ( argType == Param::REAL )
902 *(double*)value = (double)val;
903 else if ( argType == Param::FLOAT)
904 *(float*)value = (float)val;
905 else if ( argType == Param::UNSIGNED_INT )
906 *(unsigned int*)value = (unsigned int)val;
907 else if ( argType == Param::UINT64 )
908 *(uint64*)value = (uint64)val;
909 else if ( argType == Param::UCHAR)
910 *(uchar*)value = (uchar)val;
912 CV_Error(CV_StsBadArg, "Wrong argument type");
915 else if( p->type == Param::SHORT )
917 if( argType != Param::INT )
919 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
920 CV_Error(CV_StsBadArg, message);
922 int val = p->getter ? (algo->*f.get_int)() : *(short*)((uchar*)algo + p->offset);
926 else if( p->type == Param::BOOLEAN )
928 if (!( argType == Param::INT || argType == Param::BOOLEAN || argType == Param::REAL || argType == Param::FLOAT || argType == Param::UNSIGNED_INT || argType == Param::UINT64 || argType == Param::UCHAR))
930 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
931 CV_Error(CV_StsBadArg, message);
933 bool val = p->getter ? (algo->*f.get_bool)() : *(bool*)((uchar*)algo + p->offset);
935 if( argType == Param::INT )
936 *(int*)value = (int)val;
937 else if( argType == Param::BOOLEAN )
939 else if ( argType == Param::REAL )
940 *(double*)value = (int)val;
941 else if ( argType == Param::FLOAT)
942 *(float*)value = (float)((int)val);
943 else if ( argType == Param::UNSIGNED_INT )
944 *(unsigned int*)value = (unsigned int)val;
945 else if ( argType == Param::UINT64 )
946 *(uint64*)value = (int)val;
947 else if ( argType == Param::UCHAR)
948 *(uchar*)value = (uchar)val;
950 CV_Error(CV_StsBadArg, "Wrong argument type");
952 else if( p->type == Param::REAL )
954 if(!( argType == Param::REAL || argType == Param::FLOAT))
956 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
957 CV_Error(CV_StsBadArg, message);
959 double val = p->getter ? (algo->*f.get_double)() : *(double*)((uchar*)algo + p->offset);
961 if ( argType == Param::REAL )
962 *(double*)value = val;
963 else if ( argType == Param::FLOAT)
964 *(float*)value = (float)val;
966 CV_Error(CV_StsBadArg, "Wrong argument type");
968 else if( p->type == Param::FLOAT )
970 if(!( argType == Param::REAL || argType == Param::FLOAT))
972 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
973 CV_Error(CV_StsBadArg, message);
975 float val = p->getter ? (algo->*f.get_float)() : *(float*)((uchar*)algo + p->offset);
977 if ( argType == Param::REAL )
978 *(double*)value = (double)val;
979 else if ( argType == Param::FLOAT)
980 *(float*)value = (float)val;
982 CV_Error(CV_StsBadArg, "Wrong argument type");
984 else if( p->type == Param::UNSIGNED_INT )
986 if (!( argType == Param::INT || argType == Param::REAL || argType == Param::FLOAT || argType == Param::UNSIGNED_INT || argType == Param::UINT64 || argType == Param::UCHAR))
988 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
989 CV_Error(CV_StsBadArg, message);
991 unsigned int val = p->getter ? (algo->*f.get_uint)() : *(unsigned int*)((uchar*)algo + p->offset);
993 if( argType == Param::INT )
994 *(int*)value = (int)val;
995 else if ( argType == Param::REAL )
996 *(double*)value = (double)val;
997 else if ( argType == Param::FLOAT)
998 *(float*)value = (float)val;
999 else if ( argType == Param::UNSIGNED_INT )
1000 *(unsigned int*)value = (unsigned int)val;
1001 else if ( argType == Param::UINT64 )
1002 *(uint64*)value = (uint64)val;
1003 else if ( argType == Param::UCHAR)
1004 *(uchar*)value = (uchar)val;
1006 CV_Error(CV_StsBadArg, "Wrong argument type");
1008 else if( p->type == Param::UINT64 )
1010 if (!( argType == Param::INT || argType == Param::REAL || argType == Param::FLOAT || argType == Param::UNSIGNED_INT || argType == Param::UINT64 || argType == Param::UCHAR))
1012 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
1013 CV_Error(CV_StsBadArg, message);
1015 uint64 val = p->getter ? (algo->*f.get_uint64)() : *(uint64*)((uchar*)algo + p->offset);
1017 if( argType == Param::INT )
1018 *(int*)value = (int)val;
1019 else if ( argType == Param::REAL )
1020 *(double*)value = (double)val;
1021 else if ( argType == Param::FLOAT)
1022 *(float*)value = (float)val;
1023 else if ( argType == Param::UNSIGNED_INT )
1024 *(unsigned int*)value = (unsigned int)val;
1025 else if ( argType == Param::UINT64 )
1026 *(uint64*)value = (uint64)val;
1027 else if ( argType == Param::UCHAR)
1028 *(uchar*)value = (uchar)val;
1030 CV_Error(CV_StsBadArg, "Wrong argument type");
1032 else if( p->type == Param::UCHAR )
1034 if (!( argType == Param::INT || argType == Param::REAL || argType == Param::FLOAT || argType == Param::UNSIGNED_INT || argType == Param::UINT64 || argType == Param::UCHAR))
1036 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
1037 CV_Error(CV_StsBadArg, message);
1039 uchar val = p->getter ? (algo->*f.get_uchar)() : *(uchar*)((uchar*)algo + p->offset);
1041 if( argType == Param::INT )
1043 else if ( argType == Param::REAL )
1044 *(double*)value = val;
1045 else if ( argType == Param::FLOAT)
1046 *(float*)value = val;
1047 else if ( argType == Param::UNSIGNED_INT )
1048 *(unsigned int*)value = val;
1049 else if ( argType == Param::UINT64 )
1050 *(uint64*)value = val;
1051 else if ( argType == Param::UCHAR)
1052 *(uchar*)value = val;
1054 CV_Error(CV_StsBadArg, "Wrong argument type");
1058 CV_Error(CV_StsBadArg, "Unknown/unsupported parameter type");
1060 else if( argType == Param::STRING )
1062 if( p->type != Param::STRING )
1064 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
1065 CV_Error(CV_StsBadArg, message);
1068 *(string*)value = p->getter ? (algo->*f.get_string)() :
1069 *(string*)((uchar*)algo + p->offset);
1071 else if( argType == Param::MAT )
1073 if( p->type != Param::MAT )
1075 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
1076 CV_Error(CV_StsBadArg, message);
1079 *(Mat*)value = p->getter ? (algo->*f.get_mat)() :
1080 *(Mat*)((uchar*)algo + p->offset);
1082 else if( argType == Param::MAT_VECTOR )
1084 if( p->type != Param::MAT_VECTOR )
1086 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
1087 CV_Error(CV_StsBadArg, message);
1090 *(vector<Mat>*)value = p->getter ? (algo->*f.get_mat_vector)() :
1091 *(vector<Mat>*)((uchar*)algo + p->offset);
1093 else if( argType == Param::ALGORITHM )
1095 if( p->type != Param::ALGORITHM )
1097 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
1098 CV_Error(CV_StsBadArg, message);
1101 *(Ptr<Algorithm>*)value = p->getter ? (algo->*f.get_algo)() :
1102 *(Ptr<Algorithm>*)((uchar*)algo + p->offset);
1106 string message = getErrorMessageForWrongArgumentInGetter(algo->name(), parameter, p->type, argType);
1107 CV_Error(CV_StsBadArg, message);
1112 int AlgorithmInfo::paramType(const char* parameter) const
1114 const Param* p = findstr(data->params, parameter);
1116 CV_Error_( CV_StsBadArg, ("No parameter '%s' is found", parameter ? parameter : "<NULL>") );
1121 string AlgorithmInfo::paramHelp(const char* parameter) const
1123 const Param* p = findstr(data->params, parameter);
1125 CV_Error_( CV_StsBadArg, ("No parameter '%s' is found", parameter ? parameter : "<NULL>") );
1130 void AlgorithmInfo::getParams(vector<string>& names) const
1132 data->params.get_keys(names);
1136 void AlgorithmInfo::addParam_(Algorithm& algo, const char* parameter, int argType,
1137 void* value, bool readOnly,
1138 Algorithm::Getter getter, Algorithm::Setter setter,
1141 CV_Assert( argType == Param::INT || argType == Param::BOOLEAN ||
1142 argType == Param::REAL || argType == Param::STRING ||
1143 argType == Param::MAT || argType == Param::MAT_VECTOR ||
1144 argType == Param::ALGORITHM || argType == Param::SHORT
1145 || argType == Param::FLOAT || argType == Param::UNSIGNED_INT || argType == Param::UINT64
1146 || argType == Param::UCHAR);
1147 data->params.add(string(parameter), Param(argType, readOnly,
1148 (int)((size_t)value - (size_t)(void*)&algo),
1149 getter, setter, help));
1153 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1154 int& value, bool readOnly,
1155 int (Algorithm::*getter)(),
1156 void (Algorithm::*setter)(int),
1159 addParam_(algo, parameter, ParamType<int>::type, &value, readOnly,
1160 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1163 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1164 short& value, bool readOnly,
1165 int (Algorithm::*getter)(),
1166 void (Algorithm::*setter)(int),
1169 addParam_(algo, parameter, ParamType<short>::type, &value, readOnly,
1170 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1173 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1174 bool& value, bool readOnly,
1175 int (Algorithm::*getter)(),
1176 void (Algorithm::*setter)(int),
1179 addParam_(algo, parameter, ParamType<bool>::type, &value, readOnly,
1180 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1183 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1184 double& value, bool readOnly,
1185 double (Algorithm::*getter)(),
1186 void (Algorithm::*setter)(double),
1189 addParam_(algo, parameter, ParamType<double>::type, &value, readOnly,
1190 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1193 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1194 string& value, bool readOnly,
1195 string (Algorithm::*getter)(),
1196 void (Algorithm::*setter)(const string&),
1199 addParam_(algo, parameter, ParamType<string>::type, &value, readOnly,
1200 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1203 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1204 Mat& value, bool readOnly,
1205 Mat (Algorithm::*getter)(),
1206 void (Algorithm::*setter)(const Mat&),
1209 addParam_(algo, parameter, ParamType<Mat>::type, &value, readOnly,
1210 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1213 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1214 vector<Mat>& value, bool readOnly,
1215 vector<Mat> (Algorithm::*getter)(),
1216 void (Algorithm::*setter)(const vector<Mat>&),
1219 addParam_(algo, parameter, ParamType<vector<Mat> >::type, &value, readOnly,
1220 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1223 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1224 Ptr<Algorithm>& value, bool readOnly,
1225 Ptr<Algorithm> (Algorithm::*getter)(),
1226 void (Algorithm::*setter)(const Ptr<Algorithm>&),
1229 addParam_(algo, parameter, ParamType<Algorithm>::type, &value, readOnly,
1230 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1233 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1234 float& value, bool readOnly,
1235 float (Algorithm::*getter)(),
1236 void (Algorithm::*setter)(float),
1239 addParam_(algo, parameter, ParamType<float>::type, &value, readOnly,
1240 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1243 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1244 unsigned int& value, bool readOnly,
1245 unsigned int (Algorithm::*getter)(),
1246 void (Algorithm::*setter)(unsigned int),
1249 addParam_(algo, parameter, ParamType<unsigned int>::type, &value, readOnly,
1250 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1253 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1254 uint64& value, bool readOnly,
1255 uint64 (Algorithm::*getter)(),
1256 void (Algorithm::*setter)(uint64),
1259 addParam_(algo, parameter, ParamType<uint64>::type, &value, readOnly,
1260 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);
1263 void AlgorithmInfo::addParam(Algorithm& algo, const char* parameter,
1264 uchar& value, bool readOnly,
1265 uchar (Algorithm::*getter)(),
1266 void (Algorithm::*setter)(uchar),
1269 addParam_(algo, parameter, ParamType<uchar>::type, &value, readOnly,
1270 (Algorithm::Getter)getter, (Algorithm::Setter)setter, help);