Пример #1
0
int make_first_simplex(point_set *P, simplex **s){
  face f;
  point *p3;
  int min_index;

  // select the point p1 nearest to the plane 
  f.point[0] = P->point[P->size/2-1];	

  // select a second point p2 such that p2 is the nearest point to p1 on the other side of alpha
  minimum_distance(f.point[0], P, P->size/2, P->size, &min_index);
  if (!valid_index(P,min_index))
    return 0;
  f.point[1] = P->point[min_index];

  // search the point p3 such that the circum-circle around the 1-face (p1, p2) and the point p3 has the minimum
  //radius
  minimum_radius(f.point[0], f.point[1], P, 0, P->size, &min_index);
  if (!valid_index(P,min_index))
    return 0;

  p3 = P->point[min_index];      

  if (pointLocationRelativeToFace(&f,p3) != 1)
    revert_face(&f);

  build_simplex(s, &f, p3);
  revert_face((*s)->face[0]);    
  return 1;
}
Пример #2
0
void Features::getVertex(const Node *first, const Node *last,
                         int id,
                         std::vector<NodePair> *node_pairs) const {
  if (node_pairs->size() <= static_cast<size_t>(id))
    node_pairs->resize(id + 1);

  (*node_pairs)[id].first = first;
  (*node_pairs)[id].last = last;

  Node *best = 0;
  const float dist = minimum_distance(first, last, &best);

  static const float error = 0.001;
  if (dist > error) {
    getVertex(first, best, id * 2 + 1, node_pairs);
    getVertex(best,  last, id * 2 + 2, node_pairs);
  }
}
Пример #3
0
bool ContourFlip::update()
{
  //if (!ImageNode::update()) return false;
  if (!Contour::update()) return false;

  // TBD get dirtiness of in to see if flip map needs to be recomputed
  
  if (!isDirty(this, 23)) { return true;}

  cv::Mat to_flip = getImage("to_flip");
  if (to_flip.empty()) {
    VLOG(2) << name << " in is empty";
    return false;
  }
  
  cv::Mat flipped = cv::Mat(to_flip.size(), to_flip.type());
 
  bool valid;
  bool is_dirty;
  cv::Mat in = getImage("in", valid, is_dirty, 51);
  
  if (is_dirty) 
  {
  
  LOG(INFO) << "contour flip updating " << is_dirty;
  cv::Mat dist = cv::Mat(to_flip.size(), to_flip.type());

  const int wd = dist.cols;
  const int ht = dist.rows;

  // This is very slow for dense contours, maybe make
  // scale option that will process the image at a lower resolution 
  // then upscale the off_x,off_y for the remap
  for (int y = 0; y < ht; y++) {
  for (int x = 0; x < wd; x++) {

  float min_dist = 1e9;
  cv::Point2f min_closest;

  int count = 0;
  // TBD just find the nearest contour point for now, don't worry about long segment
  // or the actual normal of the segment - just flip the pixel on the nearest point
  for (int i = 0; i < contours0.size(); i++) {  
  for (int j = 0; j < contours0[i].size(); j++) { 
  
    cv::Point2f v = contours0[i][j]; 
    cv::Point2f w = contours0[i][ (j+1) % contours0[i].size() ]; 
    //const float dx = (contours0[i][j].x - x); 
    //const float dy = (contours0[i][j].y - y);
    //const float cur_dist = fabs(dx) + fabs(dy); 
    //const float cur_dist = sqrt(dx*dx + dy*dy);
    cv::Point2f closest;
    const float cur_dist = minimum_distance( v, w, cv::Point2f(x, y), closest ); 
    if (cur_dist < min_dist) {
      min_dist = cur_dist;
      min_closest = closest;
    }
    count++;
  }}

  if ( (x == 0) && ( y == 0) ) setSignal("count", count);

  // TBD make a reflection effect instead of straight rolling over the edges?
  const int src_x = ((x + (int) ( 2 * (min_closest.x - x) ) ) + wd) % wd; 
  const int src_y = ((y + (int) ( 2 * (min_closest.y - y) ) ) + ht) % ht;
 
  // TBD this could be a map for remap and if the in image doesn't change it will
  // be more efficient
  //flipped.at<cv::Vec4b>(y, x) = to_flip.at<cv::Vec4b>(src_y, src_x);
  off_x.at<float>(y, x) = src_x - x;
  off_y.at<float>(y, x) = src_y - y;
  //LOG_FIRST_N(INFO,20) << src_x << " " << x << ", " << src_y << " " << y;
  dist.at<cv::Vec4b>(y, x) = cv::Scalar::all(min_dist); // % 255);
  }}

  cv::Mat dist_x = base_x + (off_x); //_scaled - offsetx * scalex);
  cv::Mat dist_y = base_y + (off_y); //_scaled - offsety * scaley);

  cv::convertMaps(dist_x, dist_y, dist_xy16, dist_int, CV_16SC2, true);
  
  setImage("dist", dist);

  {
    cv::Mat dist_xy8;
    cv::Mat dist_xy16_temp;
    cv::convertMaps(off_x, off_y, dist_xy16_temp, dist_int, CV_16SC2, true);
    dist_xy16_temp.convertTo(dist_xy8, CV_8UC2, getSignal("map_scale"));
    cv::Mat mapx = cv::Mat( Config::inst()->getImSize(), CV_8UC4, cv::Scalar(0,0,0,0));
    cv::Mat mapy = cv::Mat( Config::inst()->getImSize(), CV_8UC4, cv::Scalar(0,0,0,0));

    int chx[] = {0,0, 0,1, 0,2};
    mixChannels(&dist_xy8, 1, &mapx, 1, chx, 3 );
    int chy[] = {1,0, 1,1, 1,2};
    mixChannels(&dist_xy8, 1, &mapy, 1, chy, 3 );

    setImage("mapx", mapx);
    setImage("mapy", mapy);
  }

  }
  
 
  if (!dist_xy16.empty()) 
    cv::remap(to_flip, flipped, dist_xy16, cv::Mat(), getModeType(), getBorderType());

  setImage("flipped", flipped);

  return true;
}