コード例 #1
0
ファイル: visibility.c プロジェクト: ChristianBusch/gegl
static gboolean
TryVisibilityAroundBlock(P2trPSLG        *PSLG,
                         P2trVector2     *P,
                         P2trPSLG        *ToSee,
                         P2trPSLG        *KnownBlocks,
                         GQueue          *BlocksForTest,
                         /* Try on the edges of this block */
                         const P2trBoundedLine *BlockBeingTested,
                         const P2trVector2     *SideOfBlock)
{
  const P2trVector2 *S = SideOfBlock;
  P2trVector2 ClosestIntersection;
  P2trBoundedLine PS;
  
  p2tr_bounded_line_init (&PS, P, S);

  if (find_closest_intersection (ToSee, &PS.infinite, P, &ClosestIntersection))
    {
      P2trPSLGIter iter;
      P2trBoundedLine PK;
      const P2trBoundedLine *Segment = NULL;
      p2tr_bounded_line_init (&PK, P, &ClosestIntersection);

      /* Now we must make sure that the bounded line PK is inside
       * the polygon, because otherwise it is not considered as a
       * valid visibility path */

      p2tr_pslg_iter_init (&iter, PSLG);
      while (p2tr_pslg_iter_next (&iter, &Segment))
        {
          if (Segment == BlockBeingTested)
              continue;

          /* If we have two segments with a shared point,
           * the point should not be blocked by any of them
           */
          if (p2tr_vector2_is_same (SideOfBlock, &(Segment->start))
              || p2tr_vector2_is_same (SideOfBlock, &(Segment->end)))
              continue;

          if (p2tr_bounded_line_intersect (Segment, &PK))
            {
              if (g_queue_find (BlocksForTest, Segment))
                {
                  g_queue_push_tail (BlocksForTest, (P2trBoundedLine*)Segment);
                }
              /* obstruction found! */
              return FALSE;
            }
        }

      if (LineIsOutsidePolygon (&PK, PSLG))
        return FALSE;

      /* No obstruction! */
      return TRUE;
    }
  /* No intersection for this attempt, continue */
  return FALSE;
}
コード例 #2
0
ファイル: cdt.c プロジェクト: MichaelMure/poly2tri-c
gboolean
p2tr_cdt_visible_from_edge (P2trCDT     *self,
                            P2trEdge    *e,
                            P2trVector2 *p)
{
    P2trBoundedLine line;

    p2tr_bounded_line_init (&line, &P2TR_EDGE_START(e)->c, &e->end->c);

    return p2tr_visibility_is_visible_from_edges (self->outline, p, &line, 1);
}
コード例 #3
0
ファイル: cdt.c プロジェクト: MichaelMure/poly2tri-c
static gboolean
p2tr_cdt_visible_from_tri (P2trCDT      *self,
                           P2trTriangle *tri,
                           P2trVector2  *p)
{
    P2trBoundedLine lines[3];
    gint i;

    for (i = 0; i < 3; i++)
        p2tr_bounded_line_init (&lines[i],
                                &P2TR_EDGE_START(tri->edges[i])->c,
                                &tri->edges[i]->end->c);

    return p2tr_visibility_is_visible_from_edges (self->outline, p, lines, 3);
}
コード例 #4
0
ファイル: visibility.c プロジェクト: ChristianBusch/gegl
gboolean
p2tr_pslg_visibility_check (P2trPSLG    *pslg,
                            P2trVector2 *point,
                            P2trPSLG    *polygon)
{
    P2trPSLG *known_blocks;
    GArray   *second_points;
    gboolean  found_visibility_path = FALSE;

    /* W <- Some point in T (for example, center of weight) */
    P2trVector2 W;
    find_point_in_polygon (polygon, &W);

    /* KnownBlocks <- {} */
    known_blocks = p2tr_pslg_new ();

    /* SecondPoint <- {W} */
    second_points   = g_array_new (FALSE, FALSE, sizeof(P2trVector2));
    g_array_append_val (second_points, W);

    while ((! found_visibility_path) && second_points->len > 0)
    {
        P2trVector2 S;
        P2trBoundedLine PS;
        P2trVector2 poly_intersection;

        /* S <- Some point from SecondPoint */
        p2tr_vector2_copy (&S, &g_array_index(second_points, P2trVector2, 0));
        /* SecondPoint <- SecondPoint \ {S} */
        g_array_remove_index_fast (second_points, 0);

        /* PS <- The infinite line going through P and S */
        p2tr_bounded_line_init (&PS, &S, point);

        /* IF PS intersects @Poly */
        if (find_closest_intersection (polygon, &PS.infinite, point, &poly_intersection))
        {
            P2trBoundedLine PS_exact, *B;

            /* IF there is an edge B=(u,v) (from E) that intersects PS */
            p2tr_bounded_line_init (&PS_exact, point, &poly_intersection);
            B = pslg_line_intersection (pslg, &PS_exact);

            if (B != NULL)
            {
                /* IF B is not in KnownBlocks: */
                if (! p2tr_pslg_contains_line (known_blocks, B))
                {
                    /* SecondPoint <- SecondPoint + {u,v} */
                    g_array_append_val (second_points, B->start);
                    g_array_append_val (second_points, B->end);
                    /* KnownBlocks <- KnownBlocks + {B} */
                    p2tr_pslg_add_existing_line (known_blocks, B);
                }
            }
            else
            {
                found_visibility_path = TRUE;
            }
        }
    }

    g_array_free (second_points, TRUE);
    p2tr_pslg_free (known_blocks);

    return found_visibility_path;
}