// (c) MIT 2003.  All rights reserved.

package rec.geo;

import edu.mit.sketch.geom.Point;
import edu.mit.sketch.geom.Polygon;
import edu.mit.sketch.geom.GeneralPath;
import java.awt.Graphics;
import java.awt.Rectangle;
import rec.geo.GPoint;
import rec.geo.Location;
import rec.sys.VisibleWidget;
import rec.util.Assert;
import java.awt.geom.AffineTransform;
import java.awt.geom.Point2D;

/**
 * 
 * <p>
 * Created:   Tue Mar 19 12:14:42 2002<br>
 * Copyright: Copyright (C) 2002 by MIT.  All rights reserved.<br>
 * 
 * @author <a href="mailto:moltmans@ai.mit.edu">Michael Oltmans</a>
 * @version $Id: GComplex.java,v 1.3 2003/03/06 00:40:47 moltmans Exp $
 **/

public class GComplex extends GShape
{
    private GeneralPath m_generalPath;
    private double m_length;
    
  public GComplex( GeneralPath generalPath, double length )
  {
    Assert.notNull( generalPath, "Can't have a complex with a null general path" );
    m_generalPath = generalPath;
    m_length = length;
  }


//   public GComplex( GeneralPath generalPath )
//   {
//     Assert.notNull( generalPath, "Can't have a complex with a null general path" );
//     m_generalPath = generalPath;
//   }

    public GPoint getStartPoint(){
	Point start = m_generalPath.getStartPosition();
	return new GPoint(start.x, start.y);
    }

    public GPoint getEndPoint(){
	Point2D end = m_generalPath.getCurrentPoint();
	return new GPoint(end.getX(), end.getY());
    }


  /**
   * the length of the diagonal of the bounding box.
   **/
  public double size()
  {
    java.awt.Rectangle bounds = m_generalPath.getBounds();
    return Math.sqrt( (bounds.x * bounds.x) + (bounds.y * bounds.y) );
  }

  /**
   * Unsupported operation.
   **/
  public void resize( double scaleFactor )
  {
    throw( new UnsupportedOperationException( "Unimplimented resize method" ) );
  }

  /////////////////////////////////////////////////////////////////////////////

  public void display( Graphics g )
  {
    m_generalPath.paint( g );
  }

  /**
   * Check of gp is within offset distance of the path.
   **/
  public boolean includes( GPoint gp, double offset )
  {
    return m_generalPath.pointIsOn( new Point( (int)gp.getX(), (int)gp.getY() ), (int)offset );
  }

    public boolean includes( GPoint gp)
    {
	return includes (gp, 0);
    }
    


  /**
   * Check if gp is on the given path.
   **/
  public boolean contains( GPoint gp )
  {
    return includes( gp, 3 );
  }

  public void translate( double x, double y )
  {
      GPoint center = getLocation().getCenter();
      m_generalPath.transform(AffineTransform.getTranslateInstance( x - center.getX(),
								    y - center.getY()));
  }
  public void rotate( GPoint gp, double angle )
  {

      throw( new UnsupportedOperationException( "Unimplimented rotate method" ) );
  }

  public void reflect( )
    {
      
	throw( new UnsupportedOperationException( "Unimplimented reflect method" ) );
    }

  public Location getLocation()
  {
    return new Location( getBounds() );
  }

  public Rectangle getBounds()
  {
    return m_generalPath.getBounds();
  }

  public double getLength()
  {
      return m_length;
  }

  public GeneralPath getToolkitPath() 
  {
    return m_generalPath;
  }

    public GShape copy()
    {
	GeneralPath gp = (GeneralPath) m_generalPath.copy();
	
	return new GComplex(gp, m_length);
    }


    public int hashCode()
    {
	return (int) (getStartPoint().x + getStartPoint().y 
		      + getEndPoint().x + getEndPoint().y);
    }  
    
}
