package Geometry;

/**
 * Class to represent half an edge (a directed edge).
 * Written by Chris Studholme
 * Licenced for redistribution under the GNU General Public Licence
 */
public class HalfEdge {
    /** Location of origin of directed edge.  The other end of the edge can
     * be found from either next.origin or twin.origin.
     */
    public NVector origin;

    /** Other half of the edge.
     */
    public HalfEdge twin;

    /** Previous edge in doublely linked list.
     */
    public HalfEdge prev;

    /** Next edge in doublely linked list.
     */
    public HalfEdge next;

    /** Facet this edge is a boundary of.
     */
    public Facet facet;

    /**
     * Default constructor.
     */
    public HalfEdge() {
    }

    /**
     * Create an edge linked to the specified twin.
     * @param twin twin of this edge
     */
    public HalfEdge(HalfEdge twin) {
	this.twin=twin;
	if (twin.twin!=null)
	    System.err.println("HalfEdge.HalfEdge() already connected!");
	twin.twin=this;
	if (twin.next!=null) {
	    origin = twin.next.origin;
	    if (origin.equals(twin.origin))
		System.err.println("HalfEdge.HalfEdge() zero length!");
	}
    }

    /**
     * Create an edge linked to the specified twin and a boundary of the
     * specified facet.
     * @param twin twin of this edge
     * @param facet facet bounded by this edge
     */
    public HalfEdge(HalfEdge twin, Facet facet) {
	this(twin);
	this.facet = facet;
    }

    /**
     * Create an edge with the specified origin.
     * @param origin origin of this edge
     */
    public HalfEdge(NVector origin) {
	this.origin=origin;
    }

    /**
     * Create an edge with the specified origin and bounding the specified
     * facet.
     * @param origin origin of this edge
     * @param facet facet bounded by this edge
     */
    public HalfEdge(NVector origin, Facet facet) {
	this(origin);
	this.facet = facet;
    }

    /**
     * Create an edge with the specified origin and the specified previous
     * edge.
     * @param origin origin of this edge
     * @param prev previous edge in linked list
     */
    public HalfEdge(NVector origin, HalfEdge prev) {
	this(origin);
	this.prev=prev;
	this.prev.next=this;
    }

    /**
     * Create an edge with the specified origin, the specified previous edge,
     * and bounding the specified facet.
     * @param origin origin of this edge
     * @param prev previous edge in linked list
     * @param facet facet bounded by this edge
     */
    public HalfEdge(NVector origin, HalfEdge prev, Facet facet) {
	this(origin,prev);
	this.facet=facet;
    }
}
