00001 package edu.stanford.hci.r3.paper;
00002
00003 import java.awt.Color;
00004 import java.awt.Shape;
00005 import java.awt.geom.AffineTransform;
00006 import java.awt.geom.GeneralPath;
00007 import java.awt.geom.PathIterator;
00008 import java.awt.geom.Rectangle2D;
00009 import java.util.ArrayList;
00010 import java.util.List;
00011
00012 import edu.stanford.hci.r3.events.EventHandler;
00013 import edu.stanford.hci.r3.render.RegionRenderer;
00014 import edu.stanford.hci.r3.units.Inches;
00015 import edu.stanford.hci.r3.units.Units;
00016 import edu.stanford.hci.r3.util.graphics.GraphicsUtils;
00017
00042 public class Region {
00043
00044 private static final Color LIGHT_LIGHT_GRAY = new Color(240, 240, 240);
00045
00049 private static final String WARNING_POST = " (see Region.java)";
00050
00054 private static final String WARNING_PRE = "WARNING: Using Default Renderer for ";
00055
00059 private boolean active = false;
00060
00067 private List<EventHandler> eventHandlers = new ArrayList<EventHandler>();
00068
00074 private Color fillColor = LIGHT_LIGHT_GRAY;
00075
00080 private String name;
00081
00089 private double opacity = 0;
00090
00091 private Sheet parentSheet;
00092
00097 protected Units referenceUnits;
00098
00105 protected double scaleX = 1.0;
00106
00111 protected double scaleY = 1.0;
00112
00118 private Shape shape;
00119
00123 private Color strokeColor = Color.BLACK;
00124
00129 private boolean visible = true;
00130
00139 public Region(String name, double xInches, double yInches, double wInches, double hInches) {
00140 this(name, new Rectangle2D.Double(xInches, yInches, wInches, hInches), Inches.ONE);
00141 }
00142
00151 public Region(String theName, Shape s, Units u) {
00152 shape = s;
00153 referenceUnits = u;
00154 name = theName;
00155 }
00156
00164 protected Region(String theName, Units u) {
00165 referenceUnits = u;
00166 name = theName;
00167 }
00168
00179 public Region(String name, Units x, Units y, Units w, Units h) {
00180 this(name, new Rectangle2D.Double(x.getValue(), y.getValueIn(x),
00181 w.getValueIn(x), h.getValueIn(x)), x);
00182 }
00183
00194 public void addEventHandler(EventHandler handler) {
00195 eventHandlers.add(handler);
00196
00197
00198
00199
00200 handler.addParentRegion(this);
00201
00202 active = true;
00203 }
00204
00208 public List<EventHandler> getEventHandlers() {
00209 return eventHandlers;
00210 }
00211
00215 public Color getFillColor() {
00216 return fillColor;
00217 }
00218
00222 public Units getHeight() {
00223 return referenceUnits.getUnitsObjectOfSameTypeWithValue(shape.getBounds2D().getHeight()
00224 * scaleY);
00225 }
00226
00230 public String getIsActiveString() {
00231 return " [" + (isActive() ? "ACTIVE" : "STATIC") + "]";
00232 }
00233
00237 public String getName() {
00238 return name;
00239 }
00240
00245 public double getOpacity() {
00246 return opacity;
00247 }
00248
00252 public Units getOriginX() {
00253 return referenceUnits.getUnitsObjectOfSameTypeWithValue(shape.getBounds2D().getX());
00254 }
00255
00259 public Units getOriginY() {
00260 return referenceUnits.getUnitsObjectOfSameTypeWithValue(shape.getBounds2D().getY());
00261 }
00262
00263 public Sheet getParentSheet() {
00264 return parentSheet;
00265 }
00266
00273 public RegionRenderer getRenderer() {
00274
00275
00276 if (!getClass().getSimpleName().equals("Region")) {
00277 System.out.println(WARNING_PRE + this + WARNING_POST);
00278 }
00279 return new RegionRenderer(this);
00280 }
00281
00285 public double getScaleX() {
00286 return scaleX;
00287 }
00288
00292 public double getScaleY() {
00293 return scaleY;
00294 }
00295
00301 public Shape getShape() {
00302 return shape;
00303 }
00304
00305 public Color getStrokeColor() {
00306 return strokeColor;
00307 }
00308
00314 public Units getUnits() {
00315 return referenceUnits;
00316 }
00317
00321 public Rectangle2D getUnscaledBounds2D() {
00322 return shape.getBounds2D();
00323 }
00324
00328 public Units getUnscaledBoundsHeight() {
00329 return referenceUnits.getUnitsObjectOfSameTypeWithValue(shape.getBounds2D().getHeight());
00330 }
00331
00335 public Units getUnscaledBoundsWidth() {
00336 return referenceUnits.getUnitsObjectOfSameTypeWithValue(shape.getBounds2D().getWidth());
00337 }
00338
00343 public Shape getUnscaledShapeCopy() {
00344 return new GeneralPath(shape);
00345 }
00346
00350 public Units getWidth() {
00351 return referenceUnits.getUnitsObjectOfSameTypeWithValue(shape.getBounds2D().getWidth()
00352 * scaleX);
00353 }
00354
00359 public boolean isActive() {
00360 return active;
00361 }
00362
00366 public boolean isVisible() {
00367 return visible;
00368 }
00369
00379 private Object readResolve() {
00380 if (eventHandlers == null) {
00381 System.err.println("Region.java:: [" + getName()
00382 + "]'s eventHandlers list was unexpectedly null upon "
00383 + "deserialization with XStream. Perhaps you need to "
00384 + "reserialize your Regions?");
00385 eventHandlers = new ArrayList<EventHandler>();
00386 }
00387 return this;
00388 }
00389
00393 public void resetScale() {
00394 setScale(1.0, 1.0);
00395 }
00396
00403 public void scaleRegion(double sX, double sY) {
00404 scaleX = scaleX * sX;
00405 scaleY = scaleY * sY;
00406 }
00407
00415 public void scaleRegionUniformly(double scale) {
00416 scaleRegion(scale, scale);
00417 }
00418
00423 public void setActive(boolean isRegionActive) {
00424 active = isRegionActive;
00425 }
00426
00430 public void setFillColor(Color theFillColor) {
00431 fillColor = theFillColor;
00432 }
00433
00439 public void setName(String theName) {
00440 name = theName;
00441 }
00442
00447 public void setOpacity(double theOpacityFrom0To1) {
00448 if (theOpacityFrom0To1 > 1) {
00449 theOpacityFrom0To1 = 1;
00450 } else if (theOpacityFrom0To1 < 0) {
00451 theOpacityFrom0To1 = 0;
00452 }
00453 opacity = theOpacityFrom0To1;
00454 }
00455
00461 public void setParentSheet(Sheet sheet) {
00462 parentSheet = sheet;
00463 }
00464
00471 public void setScale(double newScaleX, double newScaleY) {
00472 scaleX = newScaleX;
00473 scaleY = newScaleY;
00474 }
00475
00481 protected void setShape(Shape s) {
00482 shape = s;
00483 }
00484
00485 public void setStrokeColor(Color strokeCol) {
00486 strokeColor = strokeCol;
00487 }
00488
00493 public void setVisible(boolean v) {
00494 visible = v;
00495 }
00496
00504 public String toString() {
00505 final StringBuilder sb = new StringBuilder();
00506 final String className = shape.getClass().getName();
00507 sb.append(getName() + " of type ");
00508 sb.append(className.substring(className.lastIndexOf(".") + 1) + ": {");
00509
00510 final PathIterator pathIterator = shape.getPathIterator(AffineTransform.getScaleInstance(
00511 scaleX, scaleY));
00512
00513 sb.append(GraphicsUtils.getPathAsString(pathIterator));
00514
00515 sb.append("} in " + referenceUnits.getUnitName());
00516 sb.append(getIsActiveString());
00517 return sb.toString();
00518 }
00519
00520 }