Example #1
0
inT16 POLY_BLOCK::winding_number(const ICOORD &point) {
  inT16 count;                   //winding count
  ICOORD pt;                     //current point
  ICOORD vec;                    //point to current point
  ICOORD vvec;                   //current point to next point
  inT32 cross;                   //cross product
  ICOORDELT_IT it = &vertices;   //iterator

  count = 0;
  do {
    pt = *it.data ();
    vec = pt - point;
    vvec = *it.data_relative (1) - pt;
                                 //crossing the line
    if (vec.y () <= 0 && vec.y () + vvec.y () > 0) {
      cross = vec * vvec;        //cross product
      if (cross > 0)
        count++;                 //crossing right half
      else if (cross == 0)
        return INTERSECTING;     //going through point
    }
    else if (vec.y () > 0 && vec.y () + vvec.y () <= 0) {
      cross = vec * vvec;
      if (cross < 0)
        count--;                 //crossing back
      else if (cross == 0)
        return INTERSECTING;     //illegal
    }
    else if (vec.y () == 0 && vec.x () == 0)
      return INTERSECTING;
    it.forward ();
  }
  while (!it.at_first ());
  return count;                  //winding number
}
Example #2
0
void POLY_BLOCK::compute_bb() {  //constructor
  ICOORD ibl, itr;               //integer bb
  ICOORD botleft;                //bounding box
  ICOORD topright;
  ICOORD pos;                    //current pos;
  ICOORDELT_IT pts = &vertices;  //iterator

  botleft = *pts.data ();
  topright = botleft;
  do {
    pos = *pts.data ();
    if (pos.x () < botleft.x ())
                                 //get bounding box
      botleft = ICOORD (pos.x (), botleft.y ());
    if (pos.y () < botleft.y ())
      botleft = ICOORD (botleft.x (), pos.y ());
    if (pos.x () > topright.x ())
      topright = ICOORD (pos.x (), topright.y ());
    if (pos.y () > topright.y ())
      topright = ICOORD (topright.x (), pos.y ());
    pts.forward ();
  }
  while (!pts.at_first ());
  ibl = ICOORD (botleft.x (), botleft.y ());
  itr = ICOORD (topright.x (), topright.y ());
  box = TBOX (ibl, itr);
}
Example #3
0
void POLY_BLOCK::move(ICOORD shift) {
  ICOORDELT *pt;                 //current point
  ICOORDELT_IT pts = &vertices;  //iterator

  do {
    pt = pts.data ();
    *pt += shift;
    pts.forward ();
  }
  while (!pts.at_first ());
  compute_bb();
}
Example #4
0
void POLY_BLOCK::reflect_in_y_axis() {
  ICOORDELT *pt;                 // current point
  ICOORDELT_IT pts = &vertices;  // Iterator.

  do {
    pt = pts.data();
    pt->set_x(-pt->x());
    pts.forward();
  }
  while (!pts.at_first());
  compute_bb();
}
BOOL8 POLY_BLOCK::overlap(  // do polys overlap
                          POLY_BLOCK *other) {
  inT16 count;                   //winding count
  ICOORDELT_IT it = &vertices;   //iterator
  ICOORD vertex;

  if (!box.overlap (*(other->bounding_box ())))
    return FALSE;                //can't be any overlap

  /* see if a vertex of this is inside other */

  do {
    vertex = *it.data ();
                                 //get winding number
    count = other->winding_number (vertex);
    if (count != INTERSECTING)
      if (count != 0)
        return (TRUE);
    it.forward ();
  }
  while (!it.at_first ());

  /* see if a vertex of other is inside this */

                                 //switch lists
  it.set_to_list (other->points ());
  do {
    vertex = *it.data ();
                                 //try other way round
    count = winding_number (vertex);
    if (count != INTERSECTING)
      if (count != 0)
        return (TRUE);
    it.forward ();
  }
  while (!it.at_first ());
  return FALSE;
}
BOOL8 POLY_BLOCK::contains(  //other outline
                           POLY_BLOCK *other) {
  inT16 count;                   //winding count
  ICOORDELT_IT it = &vertices;   //iterator
  ICOORD vertex;

  if (!box.overlap (*(other->bounding_box ())))
    return FALSE;                //can't be contained

  /* check that no vertex of this is inside other */

  do {
    vertex = *it.data ();
                                 //get winding number
    count = other->winding_number (vertex);
    if (count != INTERSECTING)
      if (count != 0)
        return (FALSE);
    it.forward ();
  }
  while (!it.at_first ());

  /* check that all vertices of other are inside this */

                                 //switch lists
  it.set_to_list (other->points ());
  do {
    vertex = *it.data ();
                                 //try other way round
    count = winding_number (vertex);
    if (count != INTERSECTING)
      if (count == 0)
        return (FALSE);
    it.forward ();
  }
  while (!it.at_first ());
  return TRUE;
}
Example #7
0
void POLY_BLOCK::rotate(FCOORD rotation) {
  FCOORD pos;                    //current pos;
  ICOORDELT *pt;                 //current point
  ICOORDELT_IT pts = &vertices;  //iterator

  do {
    pt = pts.data ();
    pos.set_x (pt->x ());
    pos.set_y (pt->y ());
    pos.rotate (rotation);
    pt->set_x ((inT16) (floor (pos.x () + 0.5)));
    pt->set_y ((inT16) (floor (pos.y () + 0.5)));
    pts.forward ();
  }
  while (!pts.at_first ());
  compute_bb();
}