blob: 22dd2b6019fbdcc178d42e66728e2fce76bc9bee [file] [log] [blame]
/******************************************************************************
* Copyright (c) 2002, 2006 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* IBM Corporation - initial API and implementation
****************************************************************************/
package org.eclipse.gmf.runtime.draw2d.ui.figures;
import org.eclipse.draw2d.Graphics;
import org.eclipse.draw2d.IFigure;
import org.eclipse.draw2d.PositionConstants;
import org.eclipse.draw2d.geometry.Dimension;
import org.eclipse.draw2d.geometry.Point;
import org.eclipse.draw2d.geometry.Rectangle;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Color;
import org.eclipse.swt.graphics.RGB;
/**
* A set of methods that are useful when manipulating figures. These are often
* used in the paint routines or locators of IFigure implementors to do complex
* geometry calculations that may be common across different parts of a hierarchy.
*
* @author sshaw
*/
public class FigureUtilities extends org.eclipse.draw2d.FigureUtilities {
/**
* Method colorToInteger.
* converts from a Color to an Integer representation
* @param c
* @return Integer
*/
public static Integer colorToInteger(Color c) {
return new Integer(
(c.getBlue() << 16) | (c.getGreen() << 8) | c.getRed());
}
/**
* Method integerToColor.
* converts from an Integer to a Color representation
*
* Note: Normally, colors should be instantiated
* using the AbstractResourceManager.
*
* @param i
* @return Color
*/
public static Color integerToColor(Integer i) {
if (i == null)
return null;
int color = i.intValue();
return new Color(
null,
(color & 0x000000FF),
(color & 0x0000FF00) >> 8,
(color & 0x00FF0000) >> 16);
}
/**
* Method RGBToInteger
* converts from an RGB to an Integer representation
* @param rgb
* @return Integer
*/
public static Integer RGBToInteger(RGB rgb) {
return new Integer((rgb.blue << 16) | (rgb.green << 8) | rgb.red);
}
/**
* Method integerToRGB
* converts from an Integer to an RGB representation
* @param color
* @return RGB
*/
public static RGB integerToRGB(Integer color) {
int n = color.intValue();
return new RGB(
(n & 0x000000FF),
(n & 0x0000FF00) >> 8,
(n & 0x00FF0000) >> 16);
}
/**
* Return the location within the supplied constraint the supplied rectangle requires to be
* positioned according to the alignment parameter <i>pos</i>.
*
* <pre>
* NW-----N------NE
* | |
* W NS/EW E
* | |
* SW-----S------SE
*
* </pre>
* <P>
* @param pos a geographic PositionConstant (N,E,W,S,NW,NW,NS,EW)
* @param topos the rectangle to be (re)positioned.
* @param constraint the containing bounds.
* @return a new location.
*/
public static Point getLocation(
int pos,
final Rectangle topos,
final Rectangle constraint) {
Rectangle b = constraint.getCopy();
Point svb = new Point(b.x, b.y);
switch (pos) {
case PositionConstants.NORTH :
svb.x += b.width / 2;
break;
case PositionConstants.SOUTH :
svb.x += b.width / 2;
svb.y += b.height;
break;
case PositionConstants.WEST :
svb.y += b.height / 2 - topos.height / 2;
break;
case PositionConstants.EAST :
svb.x += b.width;
svb.y += b.height / 2 - topos.height / 2;
break;
case PositionConstants.NORTH_EAST : //top right
svb.x += b.width - topos.width;
break;
case PositionConstants.SOUTH_EAST : //bottom right
svb.x += b.width - topos.width;
svb.y += b.height - topos.height;
break;
case PositionConstants.SOUTH_WEST : //bottom left
svb.x += b.width;
svb.y += topos.height;
break;
case PositionConstants.NORTH_SOUTH : // center of bounds area
case PositionConstants.EAST_WEST :
svb.x += b.width / 2 - topos.width / 2;
svb.y += b.height / 2 - topos.height / 2;
break;
case PositionConstants.NORTH_WEST : //top left
default :
break;
}
return svb;
}
/**
* Return the location within the supplied constraint of an object of dimension <i>dim</i>
* according to the alignment parameter.
* @see #getLocation(int, Rectangle, Rectangle)
* @param pos a geographic PositionConstant (N,E,W,S,NW,NW,NS,EW)
* @param dim some dimension.
* @param constraint the containing bounds.
* @return a new location.
*/
public static Point getLocation(
int pos,
final Dimension dim,
final Rectangle constraint) {
return getLocation(
pos,
new Rectangle(0, 0, dim.width, dim.height),
constraint);
}
/**
* Helper method to paint a grid. Painting is optimized as it is restricted to the
* Graphics' clip.
*
* @param g The Graphics object to be used for painting
* @param f The figure in which the grid is to be painted
* @param origin Any point where the grid lines are expected to intersect
* @param distanceX Distance between vertical grid lines; if 0 or less, vertical grid
* lines will not be drawn
* @param distanceY Distance between horizontal grid lines; if 0 or less, horizontal
* grid lines will not be drawn
* @param lineStyle Line style to be used for painting the grid lines
* @param dashes Dash pattern to be used for the grid line (ignored if lineStyle != LINE_CUSTOM)
*
*/
public static void paintGridWithStyle(Graphics g, IFigure f,
org.eclipse.draw2d.geometry.Point origin, int distanceX, int distanceY, int lineStyle, int[] dashes) {
Rectangle clip = g.getClip(Rectangle.SINGLETON);
int origLineStyle = g.getLineStyle();
if (distanceX > 0) {
if (origin.x >= clip.x)
while (origin.x - distanceX >= clip.x)
origin.x -= distanceX;
else
while (origin.x < clip.x)
origin.x += distanceX;
for (int i = origin.x; i < clip.x + clip.width; i += distanceX) {
g.setLineStyle(lineStyle);
if ((dashes != null) && (lineStyle == SWT.LINE_CUSTOM)) g.setLineDash(dashes);
g.drawLine(i, clip.y, i, clip.y + clip.height);
g.setLineStyle(origLineStyle);
}
}
if (distanceY > 0) {
if (origin.y >= clip.y)
while (origin.y - distanceY >= clip.y)
origin.y -= distanceY;
else
while (origin.y < clip.y)
origin.y += distanceY;
for (int i = origin.y; i < clip.y + clip.height; i += distanceY) {
g.setLineStyle(lineStyle);
if ((dashes != null) && (lineStyle == SWT.LINE_CUSTOM)) g.setLineDash(dashes);
g.drawLine(clip.x, i, clip.x + clip.width, i);
g.setLineStyle(origLineStyle);
}
}
}
/**
* Calculates the anchorable figure bounds. There could be cases that a figure
* implements both <code>IOvalAnchorableFigure</code> and <code>IPolygonAnchorableFigure</code>
* interfaces. The latter interface is more popular because any figure can be approximated
* with line segments including ellipse. Therefore, we need to check first if it's an
* ellipse like figure and then if it's some kind of a polygon.
*
* @param figure the figure
* @return the bounding <code>Rectangle</code> of the anchorable part of the figure
*/
public static Rectangle getAnchorableFigureBounds(IFigure figure) {
if (figure instanceof IOvalAnchorableFigure) {
return ((IOvalAnchorableFigure)figure).getOvalBounds().getCopy();
} else if (figure instanceof IPolygonAnchorableFigure) {
return ((IPolygonAnchorableFigure)figure).getPolygonPoints().getBounds();
} else if (figure instanceof IFigure) {
return figure.getBounds().getCopy();
}
return null;
}
}