RVAPI ci_errors RVCALLCONV ciNext( IN HCFG hCfg, IN const char * path, /* full path to nodeID */ OUT char * nextPath, /* buffer for next path in cfg */ IN UINT32 maxPathLen /* length of output buffer */ ) { int len, firstTime = 1; int root = rtRoot(__hCfg->tree); int nodeID = path? ciGetNodeID(hCfg, path) : root; pcfgValue cfgVal; if (root < 0) return ERR_CI_GENERALERROR; if (nodeID < 0) return ERR_CI_NOTFOUND; do { nodeID = rtNext(__hCfg->tree, root, nodeID); if (nodeID < 0) return ERR_CI_NOTFOUND; } while (rtParent(__hCfg->tree, nodeID) == root); /* skip first level */ /* build full path */ maxPathLen--; do { cfgVal = (pcfgValue)rtGetByPath(__hCfg->tree, nodeID); len = rpoolChunkSize(__hCfg->pool, cfgVal->name) + 1; if ((UINT32)len > maxPathLen) return ERR_CI_BUFFERTOOSMALL; if (firstTime) { rpoolCopyToExternal(__hCfg->pool, nextPath, cfgVal->name, 0, len); nextPath[len - 1] = '\0'; firstTime = 0; } else { memmove(nextPath + len, nextPath, strlen(nextPath) + 1); rpoolCopyToExternal(__hCfg->pool, nextPath, cfgVal->name, 0, len); nextPath[len - 1] = '.'; } maxPathLen -= len; nodeID = rtParent(__hCfg->tree, nodeID); } while (nodeID != root); return ERR_CI_NOERROR; }
RVAPI ci_errors RVCALLCONV ciDestruct(IN HCFG hCfg) { int nodeID,rootID; if (!hCfg) return ERR_CI_GENERALERROR; rootID=nodeID=rtRoot(__hCfg->tree); if (__hCfg->tree) rtDestruct (__hCfg->tree); if (__hCfg->pool) rpoolDestruct(__hCfg->pool); free((void *)hCfg); return ERR_CI_NOERROR; }
static int ciGetNodeID(IN HCFG hCfg, IN const char *path) { int nodeID; int len; char *dot; pcfgValue cfgVal; if (!path || !*path) return ERR_CI_GENERALERROR; if ((nodeID = rtHead(__hCfg->tree, rtRoot(__hCfg->tree))) < 0) return ERR_CI_GENERALERROR; while (*path) { dot = strchr(path, '.'); len = dot? dot - path : strlen(path); cfgVal = (pcfgValue)rtGetByPath(__hCfg->tree, nodeID); while (rpoolChunkSize(__hCfg->pool, cfgVal->name) != len || rpoolCompareExternal(__hCfg->pool, cfgVal->name, (void*)path, len)) { nodeID = rtBrother(__hCfg->tree, nodeID); if (nodeID < 0) return ERR_CI_NOTFOUND; cfgVal = (pcfgValue)rtGetByPath(__hCfg->tree, nodeID); } if (!dot) break; nodeID = rtHead(__hCfg->tree, nodeID); if (nodeID < 0) return ERR_CI_NOTFOUND; path = dot + 1; } return nodeID; }
void CFFLD::detect(const Mixture & mixture, int width, int height, const HOGPyramid & pyramid, double threshold, double overlap, const string image, ostream & out, const string & images, vector<Detection> & detections, vector<DetectionResult> & vResult ) { // Compute the scores vector<HOGPyramid::Matrix> scores; vector<Mixture::Indices> argmaxes; vector<vector<vector<Model::Positions> > > positions; if (!images.empty()) { mixture.convolve(pyramid, scores, argmaxes, &positions); } else { mixture.convolve(pyramid, scores, argmaxes); } //cout<<"conv"<<endl; // Cache the size of the models vector<pair<int, int> > sizes(mixture.models().size()); for (int i = 0; i < sizes.size(); ++i) { sizes[i] = mixture.models()[i].rootSize(); } // For each scale for (int i = pyramid.interval(); i < scores.size(); ++i) { // Scale = 8 / 2^(1 - i / interval) const double scale = pow(2.0, static_cast<double>(i) / pyramid.interval() + 2.0); const int rows = scores[i].rows(); const int cols = scores[i].cols(); for (int y = 0; y < rows; ++y) { for (int x = 0; x < cols; ++x) { const float score = scores[i](y, x); if (score > threshold) { if (((y == 0) || (x == 0) || (score > scores[i](y - 1, x - 1))) && ((y == 0) || (score > scores[i](y - 1, x))) && ((y == 0) || (x == cols - 1) || (score > scores[i](y - 1, x + 1))) && ((x == 0) || (score > scores[i](y, x - 1))) && ((x == cols - 1) || (score > scores[i](y, x + 1))) && ((y == rows - 1) || (x == 0) || (score > scores[i](y + 1, x - 1))) && ((y == rows - 1) || (score > scores[i](y + 1, x))) && ((y == rows - 1) || (x == cols - 1) || (score > scores[i](y + 1, x + 1)))) { FFLD::Rectangle bndbox((x - pyramid.padx()) * scale + 0.5, (y - pyramid.pady()) * scale + 0.5, sizes[argmaxes[i](y, x)].second * scale + 0.5, sizes[argmaxes[i](y, x)].first * scale + 0.5); // Truncate the object bndbox.setX(max(bndbox.x(), 0)); bndbox.setY(max(bndbox.y(), 0)); bndbox.setWidth(min(bndbox.width(), width - bndbox.x())); bndbox.setHeight(min(bndbox.height(), height - bndbox.y())); if (!bndbox.empty()) { detections.push_back(Detection(score, i, x, y, bndbox)); } } } } } } // Non maxima suppression sort(detections.begin(), detections.end()); for (int i = 1; i < detections.size(); ++i) detections.resize(remove_if(detections.begin() + i, detections.end(), Intersector(detections[i - 1], overlap, true)) - detections.begin()); // Print the detection const size_t lastDot = image.find_last_of('.'); string id = image.substr(0, lastDot); const size_t lastSlash = id.find_last_of("/\\"); if (lastSlash != string::npos) id = id.substr(lastSlash + 1); if (out) { #pragma omp critical for (int i = 0; i < detections.size(); ++i) { out << id << ' ' << detections[i].score << ' ' << (detections[i].left() + 1) << ' ' << (detections[i].top() + 1) << ' ' << (detections[i].right() + 1) << ' ' << (detections[i].bottom() + 1) << endl; } } // Output the result to OpenCV Rect for( int j = 0; j < detections.size(); j ++ ) { DetectionResult result; // The position of the root one octave below const int argmax = argmaxes[detections[j].l](detections[j].y, detections[j].x); const int x2 = detections[j].x * 2 - pyramid.padx(); const int y2 = detections[j].y * 2 - pyramid.pady(); const int l = detections[j].l - pyramid.interval(); const double scale = pow(2.0, static_cast<double>(l) / pyramid.interval() + 2.0); //cout<<positions[argmax].size()<<endl; for (int k = 0; k < positions[argmax].size(); ++k) { const FFLD::Rectangle bndbox((positions[argmax][k][l](y2, x2)(0) - pyramid.padx()) * scale + 0.5, (positions[argmax][k][l](y2, x2)(1) - pyramid.pady()) * scale + 0.5, mixture.models()[argmax].partSize().second * scale + 0.5, mixture.models()[argmax].partSize().second * scale + 0.5 ); Rect rtPart( bndbox.x_, bndbox.y_, bndbox.width_, bndbox.height_ ); //cout<<rtPart<<endl; result.vParts.push_back( rtPart ); } Rect rtRoot( detections[j].x_, detections[j].y_, detections[j].width_, detections[j].height_ ); result.rtRoot = rtRoot; vResult. push_back(result); } }
RVAPI ci_errors RVCALLCONV ciSetValue( IN HCFG hCfg, IN const char * path, /* full path to nodeID */ IN BOOL isString, IN INT32 value, /* data for ints, length for strings */ IN const char * str /* null for ints, data for strings */ ) { int nodeID = ciGetNodeID(hCfg, path), newNodeID; int len; char *dot; cfgValue cfgVal; pcfgValue pCfgVal; if (!path || !path[0]) return ERR_CI_GENERALERROR; if (nodeID < 0) /* no previous value, make a new node */ { /* values for dummy nodes */ cfgVal.isString = FALSE; cfgVal.value = 0; cfgVal.str = NULL; if ((nodeID = rtHead(__hCfg->tree, rtRoot(__hCfg->tree))) < 0) { /* a special case - an empty configuration */ dot = strchr(path, '.'); len = dot? dot - path : strlen(path); cfgVal.name = rpoolAllocCopyExternal(__hCfg->pool, path, len); newNodeID = rtAddTail(__hCfg->tree, rtRoot(__hCfg->tree), &cfgVal); nodeID = newNodeID; } while (*path) { dot = strchr(path, '.'); len = dot? dot - path : strlen(path); pCfgVal = (pcfgValue)rtGetByPath(__hCfg->tree, nodeID); while (rpoolChunkSize(__hCfg->pool, pCfgVal->name) != len || rpoolCompareExternal(__hCfg->pool, pCfgVal->name, (void*)path, len)) { newNodeID = rtBrother(__hCfg->tree, nodeID); if (newNodeID < 0) { cfgVal.name = rpoolAllocCopyExternal(__hCfg->pool, path, len); newNodeID = rtAddBrother(__hCfg->tree, nodeID, &cfgVal); nodeID = newNodeID; break; } nodeID = newNodeID; pCfgVal = (pcfgValue)rtGetByPath(__hCfg->tree, nodeID); } newNodeID = rtHead(__hCfg->tree, nodeID); path = dot + 1; /* if not found, insert a dummy value */ if (newNodeID < 0) { if (!dot) break; dot = strchr(path, '.'); len = dot? dot - path : strlen(path); cfgVal.name = rpoolAllocCopyExternal(__hCfg->pool, path, len); newNodeID = rtAddTail(__hCfg->tree, nodeID, &cfgVal); } nodeID = newNodeID; if (!dot) break; } } pCfgVal = (pcfgValue)rtGetByPath(__hCfg->tree, nodeID); if (pCfgVal == NULL) return ERR_CI_GENERALERROR; /* free, resize, or leave alone the old string buffer */ if (pCfgVal->isString) { if (!isString) { rpoolFree(__hCfg->pool, pCfgVal->str); pCfgVal->str = NULL; } else { if (pCfgVal->value != value) { rpoolFree(__hCfg->pool, pCfgVal->str); pCfgVal->str = rpoolAlloc(__hCfg->pool, value); } } } else { if (isString) { pCfgVal->str = rpoolAlloc(__hCfg->pool, value); } } pCfgVal->isString = isString; pCfgVal->value = value; if (isString) rpoolCopyFromExternal(__hCfg->pool, pCfgVal->str, (void *)str, 0, value); return ERR_CI_NOERROR; }