import org.eclipse.draw2d.AbstractConnectionAnchor;
import org.eclipse.draw2d.IFigure;
import org.eclipse.draw2d.geometry.Point;
import org.eclipse.draw2d.geometry.Rectangle;

public class DiamondAnchor extends AbstractConnectionAnchor {

	public DiamondAnchor() {
	}
	
	public DiamondAnchor(IFigure owner){
		super(owner);
	}
	
	/*** This function returns the point on which the anchor should reside.
	The anchors will fall only at the four corners of the diamond.  This is fitting with flowchart standards.
 	In order to determine which point we should allocate as the anchor point, we will determine which quadrant the 
 	point lies in, and then which is greater: dx, or dy, to decide which side of the quadrant to place the anchor.
 	***/ 
	public Point getLocation(Point reference){	
		
		// Pixel offset required to get it to look right
		int pixelOffset = 2;
		
		// The four corners of the diamond
		Point top, bottom, left, right;
		
		Rectangle r = Rectangle.SINGLETON;
		r.setBounds(getOwner().getBounds());
		
		// Assign the 4 corners their coordinates
		top = new Point(r.x + r.width / 2, r.y);
		right = new Point(((r.x + r.width) - pixelOffset), r.y + r.height/2);
		bottom = new Point(((r.x + r.width/2) - pixelOffset), r.y + r.height);
		left = new Point(r.x, r.y + r.height/2);
		
		// Process for... processing
		r.translate(-1, -1);
		r.resize(1, 1);
		getOwner().translateToAbsolute(r);

		float centerX = r.x + 0.5f * r.width;
		float centerY = r.y + 0.5f * r.height;
		
		if (r.isEmpty() || (reference.x == (int)centerX && reference.y == (int)centerY)) {
			return new Point((int)centerX, (int)centerY);  //This avoids divide-by-zero
		}
		
		// Compute our center
		float dx = reference.x - centerX;
		float dy = reference.y - centerY;
		
		/*** Cases for quadrant assignment ***/
		// If |y| > |x| then we want top or bottom corner
		if(Math.abs(dy) > Math.abs(dx) || Math.abs(dy) == Math.abs(dx)){
			if(dy < 0 || dy == 0)
			{
				return top;
			}
			if(dy > 0){
				return bottom;
			}
		}
		if(Math.abs(dy) < Math.abs(dx)){
			if(dx < 0 || dx == 0){
				return left;
			}
			if(dx > 0){
				return right;
			}
		}
		
		// Otherwise... return the center.  Something has gone wrong.
		return new Point(Math.round(centerX), Math.round(centerY));
	}

}
