示例#1
0
bool DictionaryBased::detect(const cv::Mat &in, int & marker_id,int &nRotations) {
     assert(in.rows == in.cols);
    cv::Mat grey;
    if (in.type() == CV_8UC1) grey = in;
    else cv::cvtColor(in, grey, CV_BGR2GRAY);
    // threshold image
    cv::threshold(grey, grey, 125, 255, cv::THRESH_BINARY | cv::THRESH_OTSU);

     std::vector<uint64_t> ids;
    //get the ids in the four rotations (if possible)
    if ( !getInnerCode( grey,_dic.nbits(),ids)) return false;

     //find the best one
    for(int i=0;i<4;i++){
            if ( _dic.is(ids[i])){//is in the set?
                nRotations=i;//how many rotations are and its id
                marker_id=_dic[ids[i]];
                return true;//bye bye
            }
    }

    //you get here, no valid id :(
    //lets try error correction

    if(_maxCorrectionAllowed>0){//find distance to map elements
        for(auto ci:_dic.getMapCode()){
            for(int i=0;i<4;i++){
                if (hamm_distance(ci.first,ids[i])<_maxCorrectionAllowed){
                    marker_id=ci.second;
                    nRotations=i;
                    return true;
                }
            }
        }
    }
    else  return false;

 }
    bool DictionaryBased::detect(const cv::Mat& in, int& marker_id, int& nRotations, std::string &additionalInfo)
    {
        assert(in.rows == in.cols);

        cv::Mat grey;
        if (in.type() == CV_8UC1) grey = in;
        else cv::cvtColor(in, grey, CV_BGR2GRAY);
        // threshold image
        cv::threshold(grey, grey, 125, 255, cv::THRESH_BINARY | cv::THRESH_OTSU);

        std::map<uint32_t,std::vector<uint64_t> > nbits_ids;
        //for each
        for(auto &bitsids:nbits_dict){
            int nbits=bitsids.first;
            std::vector<uint64_t> ids;
            getInnerCode(grey,nbits,ids);
            if (ids.size()>0){
                if (ids[0]!=0){
                    nbits_ids[nbits]=ids;
                }
            }
        }
        //how many  are there?

        if ( nbits_ids.size()==0)return false;
        //check if any dictionary recognizes it
        for(auto nbits:nbits_ids){
            const auto &ids=nbits.second;
            //check in every dictionary
            for(auto &dic:nbits_dict[nbits.first]){
                //try a perfecf match
                for(int rot=0;rot<4;rot++)
                    if ( dic->is( ids[rot])){
                        //  std::cout<<"MATCH:"<<dic->getName()<<" "<<ids[rot]<<std::endl;
                        nRotations = rot;  // how many rotations are and its id
                        marker_id = dic->at (ids[rot]);
                        additionalInfo=dic->getName();
                        return true;
                    }

                //try with some error/correction if allowed
                if (_max_correction_rate > 0)
                {  // find distance to map elements
                    int _maxCorrectionAllowed = static_cast<int>( static_cast<float>(dic->tau()) * _max_correction_rate);
                    for (auto ci : dic->getMapCode())
                    {
                        for (int i = 0; i < 4; i++)
                        {
                            if (hamm_distance(ci.first, ids[i]) < _maxCorrectionAllowed)
                            {
                                marker_id = ci.second;
                                nRotations = i;
                                additionalInfo=dic->getName();
                                return true;
                            }
                        }
                    }
                }

            }


        }


        return false;
    }