00001 package edu.stanford.hci.r3.paper.regions;
00002
00003 import java.awt.geom.Rectangle2D;
00004 import java.util.HashMap;
00005 import java.util.Map;
00006 import java.util.Set;
00007
00008 import edu.stanford.hci.r3.paper.Region;
00009 import edu.stanford.hci.r3.render.RegionRenderer;
00010 import edu.stanford.hci.r3.render.regions.CompoundRenderer;
00011 import edu.stanford.hci.r3.units.Inches;
00012 import edu.stanford.hci.r3.units.Units;
00013 import edu.stanford.hci.r3.units.coordinates.Coordinates;
00014
00026 public class CompoundRegion extends Region {
00027
00031 private Map<Region, Coordinates> regionsAndRelativeLocations = new HashMap<Region, Coordinates>();
00032
00036 private Units x;
00037
00038 private Units y;
00039
00043 public CompoundRegion(String name, Units xOrigin, Units yOrigin) {
00044
00045 super(name, xOrigin, yOrigin, new Inches(0), new Inches(0));
00046
00047
00048 x = xOrigin;
00049 y = yOrigin.getUnitsObjectOfSameLengthIn(x);
00050 }
00051
00062 public void addChild(Region childRegion, Coordinates relativeCoord) {
00063 regionsAndRelativeLocations.put(childRegion, relativeCoord);
00064
00065
00066 final Rectangle2D myBounds = (Rectangle2D) getShape();
00067 final Units myUnits = getUnits();
00068
00069
00070
00071 final Rectangle2D childBounds = childRegion.getShape().getBounds2D();
00072 final Units childUnits = childRegion.getUnits();
00073
00074
00075 final double c = childUnits.getConversionTo(myUnits);
00076
00077 final Rectangle2D childBoundsInOurUnits = new Rectangle2D.Double(
00078 childBounds.getX() * c, childBounds.getY() * c,
00079 childBounds.getWidth() * childRegion.getScaleX() * c,
00080 childBounds.getHeight() * childRegion.getScaleY() * c);
00081
00082
00083 final double childXTranslated = x.getValue() + childBoundsInOurUnits.getX()
00084 + relativeCoord.getX().getValueIn(myUnits);
00085 final double childYTranslated = y.getValue() + childBoundsInOurUnits.getY()
00086 + relativeCoord.getY().getValueIn(myUnits);
00087
00088 final Rectangle2D childBoundsTranslated = new Rectangle2D.Double(
00089 childXTranslated, childYTranslated,
00090 childBoundsInOurUnits.getWidth(),
00091 childBoundsInOurUnits.getHeight());
00092
00093
00094
00095
00096
00097 final Rectangle2D unionOfMyBoundsAndChildBounds = myBounds
00098 .createUnion(childBoundsTranslated);
00099 setShape(unionOfMyBoundsAndChildBounds);
00100 }
00101
00106 public Coordinates getChildOffset(Region child) {
00107 return regionsAndRelativeLocations.get(child);
00108 }
00109
00113 public Set<Region> getChildren() {
00114 return regionsAndRelativeLocations.keySet();
00115 }
00116
00120 public RegionRenderer getRenderer() {
00121 return new CompoundRenderer(this);
00122 }
00123
00127 public String toString() {
00128 final Set<Region> children = regionsAndRelativeLocations.keySet();
00129 final StringBuilder childNames = new StringBuilder();
00130 int i = 0;
00131 for (Region r : children) {
00132 childNames.append(r.getName());
00133 if (i < children.size() - 1) {
00134 childNames.append(", ");
00135 }
00136 i++;
00137 }
00138 return "Compound Region {" + childNames.toString() + "} at Bounds: [x="
00139 + getOriginX().getValue() + " y=" + getOriginY().getValue() + " w="
00140 + getShape().getBounds2D().getWidth() + " h="
00141 + getShape().getBounds2D().getHeight() + "] in " + referenceUnits.getUnitName();
00142 }
00143 }