001: /*
002: * (C) Copyright IBM Corp. 1998-2004. All Rights Reserved.
003: *
004: * The program is provided "as is" without any warranty express or
005: * implied, including the warranty of non-infringement and the implied
006: * warranties of merchantibility and fitness for a particular purpose.
007: * IBM will not be liable for any damages suffered by you as a result
008: * of using the Program. In no event will IBM be liable for any
009: * special, indirect or consequential damages or lost profits even if
010: * IBM has been advised of the possibility of their occurrence. IBM
011: * will not be liable for any third party claims against you.
012: */
013: // Requires Java2
014: package com.ibm.richtext.textformat;
015:
016: import java.awt.Shape; ///*JDK12IMPORTS
017: import java.awt.Graphics2D;
018: import java.awt.geom.Rectangle2D;
019: import java.awt.geom.PathIterator;
020: import java.awt.geom.Line2D;
021:
022: //JDK12IMPORTS*/
023: /*JDK11IMPORTS
024: import com.ibm.richtext.textlayout.Graphics2D;
025: import com.ibm.richtext.textlayout.Rectangle2D;
026: JDK11IMPORTS*/
027:
028: /**
029: * This class exists to work around a clipping bug in JDK 1.2.
030: */
031: final class ClipWorkaround {
032:
033: static final String COPYRIGHT = "(C) Copyright IBM Corp. 1998-1999 - All Rights Reserved";
034: ///*JDK12IMPORTS
035: private static final String excuse = "Sorry, this method is a very limited workaround for a JDK 1.2 bug.";
036:
037: //JDK12IMPORTS*/
038:
039: static Object saveClipState(Graphics2D g) {
040: ///*JDK12IMPORTS
041: return null;
042: //JDK12IMPORTS*/
043: /*JDK11IMPORTS
044: return g.getClip();
045: JDK11IMPORTS*/
046: }
047:
048: static void restoreClipState(Graphics2D g, Object state) {
049: ///*JDK12IMPORTS
050: if (state != null) {
051: throw new Error("Invalid clip state for this class.");
052: }
053: //JDK12IMPORTS*/
054: /*JDK11IMPORTS
055: g.setClip((Shape)state);
056: JDK11IMPORTS*/
057: }
058:
059: /**
060: * Draw the given Shape into the Graphics, translated by (dx, dy)
061: * and clipped to clipRect.
062: */
063: static void translateAndDrawShapeWithClip(Graphics2D g, int dx,
064: int dy, Rectangle2D clipRect, Shape shape) {
065: ///*JDK12IMPORTS
066: // really bogus implementation right now: basically only
067: // draws carets from a TextLayout.
068: // Oh yeah, it doesn't really clip correctly either...
069:
070: PathIterator pathIter = shape.getPathIterator(null);
071: float[] points = new float[6];
072:
073: int type = pathIter.currentSegment(points);
074: if (type != PathIterator.SEG_MOVETO) {
075: throw new Error(excuse);
076: }
077: float x1 = points[0] + dx;
078: float y1 = points[1] + dy;
079:
080: if (pathIter.isDone()) {
081: throw new Error(excuse);
082: }
083:
084: pathIter.next();
085: type = pathIter.currentSegment(points);
086: if (type != PathIterator.SEG_LINETO) {
087: throw new Error(excuse);
088: }
089: float x2 = points[0] + dx;
090: float y2 = points[1] + dy;
091:
092: float minY = (float) clipRect.getY();
093: float maxY = (float) clipRect.getMaxY();
094:
095: // Now clip within vertical limits in clipRect
096: if (y1 == y2) {
097: if (y1 < minY || y1 >= maxY) {
098: return;
099: }
100: } else {
101: if (y1 > y2) {
102: float t = x1;
103: x1 = x2;
104: x2 = t;
105: t = y1;
106: y1 = y2;
107: y2 = t;
108: }
109:
110: float invSlope = (x2 - x1) / (y2 - y1);
111: if (y1 < minY) {
112: x1 -= (minY - y1) * invSlope;
113: y1 = minY;
114: }
115: if (y2 >= maxY) {
116: x1 += (y2 - maxY) * invSlope;
117: y2 = maxY;
118: }
119: }
120:
121: g.draw(new Line2D.Float(x1, y1, x2, y2));
122: //JDK12IMPORTS*/
123: /*JDK11IMPORTS
124: g.setClip(clipRect);
125: g.translate(dx, dy);
126: try {
127: g.draw(shape);
128: }
129: finally {
130: g.translate(-dx, -dy);
131: }
132: JDK11IMPORTS*/
133: }
134: }
|