Ejemplo n.º 1
0
QImage visualize_parts(const PartConfig &conf, const PartWindowParam &window_param, const Annotation &annotation)
{
  assert(annotation.size() > 0);

  double scale = (annotation[0].bottom() - annotation[0].top())/window_param.train_object_height();
  cout << "visualize_parts, scale: " << scale << endl;

  QImage _img;
  cout << "loading image" << endl;
  assert(_img.load(annotation.imageName().c_str()));
  QImage img = _img.convertToFormat(QImage::Format_RGB32);

  QPainter painter(&img);  
  for (int pidx = 0; pidx < conf.part_size(); ++pidx) {
    PartBBox part_bbox;
    get_part_bbox(annotation[0], conf.part(pidx), part_bbox, scale);

    int coloridx = 1;
    int pen_width = 2;

    if (conf.part(pidx).is_detect()) {
      if (conf.part(pidx).is_root()) 
	draw_bbox(painter, part_bbox, 2, pen_width);
      else
	draw_bbox(painter, part_bbox, coloridx, pen_width);
    }
    else
      draw_bbox(painter, part_bbox, -1); // only draw center point and axis (skip bounding box)

  }

  cout << "done" << endl;
  return img;
}
  int get_app_group_idx(const PartConfig &part_conf, int pid)
  {
    for (int agidx = 0; agidx < part_conf.app_group_size(); ++agidx) 
      for (int idx = 0; idx < part_conf.app_group(agidx).part_id_size(); ++idx) {
        if (part_conf.app_group(agidx).part_id(idx) == pid)
          return agidx;
      }

    return -1;
  }
  int pidx_from_pid(const PartConfig &part_conf, int pid)
  {
    for (int pidx = 0; pidx < part_conf.part_size(); ++pidx) {
      assert(part_conf.part(pidx).has_part_id());

      if (part_conf.part(pidx).part_id() == pid)
        return pidx;
    }

    assert(false && "part id not found");
    return -1;
  }
  /**
     compute the average size of part bounding box
  */
  void compute_part_window_param(const AnnotationList &annolist, const PartConfig &partconf, PartWindowParam &windowparam)
  {
    int nParts = partconf.part_size();
    int nImages = annolist.size();

    /** 
        compute reference object height, use only rectangles that have all parts 
        annotated (rectangles with missing parts are sometimes smaller then reference object height)
    */
    double train_object_height = 0;
    int n = 0;
    for (int imgidx = 0; imgidx < nImages; ++imgidx) {
      int nRects = annolist[imgidx].size(); 
      for (int ridx = 0; ridx < nRects; ++ridx) {

        bool bHasAllParts = true;

        //for (int pidx = 0; pidx < partconf.part_size(); ++pidx) 
        /** 
            
        TEMPORARY !!!!  Needed for experiments on HumanEva when training is done on the combined set of images
        from Buffy, Ramanan, and TUD Pedestrians

         */
//         assert(partconf.part_size() == 10);
//         for (int pidx = 0; pidx < 6; ++pidx) 
//           if (!annorect_has_part(annolist[imgidx][ridx], partconf.part(pidx))) {
//             bHasAllParts = false;
//             break;
//           }

        if (bHasAllParts) {
          train_object_height += abs(annolist[imgidx][ridx].bottom() - annolist[imgidx][ridx].top());
          ++n;
        }

      }// rectangles
    }// images

    assert(n > 0);
    
    train_object_height /= n;
    windowparam.set_train_object_height(train_object_height);
    
    cout << "train_object_height: " << train_object_height << endl;
  
    /** determine average dimensions of the parts */
    windowparam.clear_part();
    for (int pidx = 0; pidx < nParts; ++pidx) {
      PartWindowParam::PartParam *pPartParam = windowparam.add_part();
      pPartParam->set_part_id(partconf.part(pidx).part_id());
      pPartParam->set_window_size_x(0);
      pPartParam->set_window_size_y(0);
      pPartParam->set_pos_offset_x(0);
      pPartParam->set_pos_offset_y(0);

      /** begin debug */
      cout << "part_pos_size:" << partconf.part(pidx).part_pos_size() << endl;
      for (int idx = 0; idx < partconf.part(pidx).part_pos_size(); ++idx)
        cout << "\tapidx: " << partconf.part(pidx).part_pos(idx) << endl;
      /** end debug */

      if (partconf.part(pidx).is_detect()) {
        double sum_window_size_x = 0;
        double sum_window_size_y = 0;
        double sum_pos_offset_x = 0;
        double sum_pos_offset_y = 0;
    
        int nAnnoRects = 0;
        for (int imgidx = 0; imgidx < nImages; ++imgidx) {
          int nRects = annolist[imgidx].size(); 

          for (int ridx = 0; ridx < nRects; ++ridx) {

//             cout << "pidx: " << pidx << 
//               " imgidx: " << imgidx << 
//               ", ridx: " << ridx << 
//               ", has_part: " << annorect_has_part(annolist[imgidx][ridx], partconf.part(pidx)) << endl;

            if (annorect_has_part(annolist[imgidx][ridx], partconf.part(pidx))) {
              PartBBox bbox;
              get_part_bbox(annolist[imgidx][ridx], partconf.part(pidx), bbox);

              sum_window_size_x += (bbox.max_proj_x - bbox.min_proj_x);
              sum_window_size_y += (bbox.max_proj_y - bbox.min_proj_y);
              sum_pos_offset_x += bbox.min_proj_x;
              sum_pos_offset_y += bbox.min_proj_y;

              ++nAnnoRects;
            }
          }// rects

        }// images

        assert(nAnnoRects > 0);
        cout << "processed rects: " << nAnnoRects << endl;

        pPartParam->set_window_size_x((int)(sum_window_size_x/nAnnoRects));
        pPartParam->set_window_size_y((int)(sum_window_size_y/nAnnoRects));

        /* average offset of part position with respect to top/left corner */
        pPartParam->set_pos_offset_x((int)(-sum_pos_offset_x/nAnnoRects));
        pPartParam->set_pos_offset_y((int)(-sum_pos_offset_y/nAnnoRects));
      }

    }// parts

    /** compute offset of the root part with respect to bounding box center */

    int rootpart_idx = -1;

    for (int pidx = 0; pidx < nParts; ++pidx) {

      if (partconf.part(pidx).is_root()) {
        rootpart_idx = pidx;
        break;
      }
    }

    assert(rootpart_idx >=0 && "missing root part");
    double_vector bbox_offset = boost_math::double_zero_vector(2);

    int total_rects = 0;
    for (int imgidx = 0; imgidx < nImages; ++imgidx) {

      for (uint ridx = 0; ridx < annolist[imgidx].size(); ++ridx) {
        bool bHasAllParts = true;

        //for (int pidx = 0; pidx < partconf.part_size(); ++pidx) 
        // TEMPORARY !!!! needed for training of HumanEva on combined training set
//         assert(partconf.part_size() == 10);
//         for (int pidx = 0; pidx < 6; ++pidx) 
//           if (!annorect_has_part(annolist[imgidx][ridx], partconf.part(pidx))) {
//             bHasAllParts = false;
//             break;
//           }

        //if (annorect_has_part(annolist[imgidx][ridx], partconf.part(rootpart_idx))) {
        if (bHasAllParts) {
          PartBBox bbox;
          get_part_bbox(annolist[imgidx][ridx], partconf.part(rootpart_idx), bbox);
      
          double_vector bbox_center(2);
          bbox_center(0) = 0.5*(annolist[imgidx][ridx].left() + annolist[imgidx][ridx].right());
          bbox_center(1) = 0.5*(annolist[imgidx][ridx].top() + annolist[imgidx][ridx].bottom());

          bbox_offset += bbox_center - bbox.part_pos;
          ++total_rects;
        }
      }
    }
    bbox_offset /= total_rects;

    windowparam.set_bbox_offset_x(bbox_offset(0));
    windowparam.set_bbox_offset_y(bbox_offset(1));
  }