< prev index next >

src/java.desktop/share/classes/sun/java2d/SunGraphics2D.java

Print this page




 857     }
 858 
 859     public FontMetrics getFontMetrics(Font font) {
 860         if ((this.fontMetrics != null) && (font == this.font)) {
 861             return this.fontMetrics;
 862         }
 863         FontMetrics fm =
 864           FontDesignMetrics.getMetrics(font, getFontRenderContext());
 865 
 866         if (this.font == font) {
 867             this.fontMetrics = fm;
 868         }
 869         return fm;
 870     }
 871 
 872     /**
 873      * Checks to see if a Path intersects the specified Rectangle in device
 874      * space.  The rendering attributes taken into account include the
 875      * clip, transform, and stroke attributes.
 876      * @param rect The area in device space to check for a hit.
 877      * @param p The path to check for a hit.
 878      * @param onStroke Flag to choose between testing the stroked or
 879      * the filled path.
 880      * @return True if there is a hit, false otherwise.
 881      * @see #setStroke
 882      * @see #fillPath
 883      * @see #drawPath
 884      * @see #transform
 885      * @see #setTransform
 886      * @see #clip
 887      * @see #setClip
 888      */
 889     public boolean hit(Rectangle rect, Shape s, boolean onStroke) {
 890         if (onStroke) {
 891             s = stroke.createStrokedShape(s);
 892         }
 893 
 894         s = transformShape(s);
 895         if ((constrainX|constrainY) != 0) {
 896             rect = new Rectangle(rect);
 897             rect.translate(constrainX, constrainY);
 898         }
 899 
 900         return s.intersects(rect);
 901     }
 902 
 903     /**


1278                         validFontInfo = false;
1279                         this.glyphVectorFontInfo = null;
1280                     }
1281                 }
1282                 if (hints != null) {
1283                     hints.put(hintKey, hintValue);
1284                 }
1285                 return;
1286             }
1287         }
1288         // Nothing we recognize so none of "our state" has changed
1289         if (hints == null) {
1290             hints = makeHints(null);
1291         }
1292         hints.put(hintKey, hintValue);
1293     }
1294 
1295 
1296     /**
1297      * Returns the preferences for the rendering algorithms.
1298      * @param hintCategory The category of hint to be set. The strings
1299      * are defined in the RenderingHints class.
1300      * @return The preferences for rendering algorithms. The strings
1301      * are defined in the RenderingHints class.
1302      * @see RenderingHints
1303      */
1304     public Object getRenderingHint(Key hintKey) {
1305         if (hints != null) {
1306             return hints.get(hintKey);
1307         }
1308         if (!(hintKey instanceof SunHints.Key)) {
1309             return null;
1310         }
1311         int keyindex = ((SunHints.Key)hintKey).getIndex();
1312         switch (keyindex) {
1313         case SunHints.INTKEY_RENDERING:
1314             return SunHints.Value.get(SunHints.INTKEY_RENDERING,
1315                                       renderHint);
1316         case SunHints.INTKEY_ANTIALIASING:
1317             return SunHints.Value.get(SunHints.INTKEY_ANTIALIASING,
1318                                       antialiasHint);


1560      * @param shy The factor by which coordinates are shifted towards the
1561      * positive Y axis direction according to their X coordinate
1562      */
1563     public void shear(double shx, double shy) {
1564         transform.shear(shx, shy);
1565         invalidateTransform();
1566     }
1567 
1568     /**
1569      * Composes a Transform object with the transform in this
1570      * Graphics2D according to the rule last-specified-first-applied.
1571      * If the currrent transform is Cx, the result of composition
1572      * with Tx is a new transform Cx'.  Cx' becomes the current
1573      * transform for this Graphics2D.
1574      * Transforming a point p by the updated transform Cx' is
1575      * equivalent to first transforming p by Tx and then transforming
1576      * the result by the original transform Cx.  In other words,
1577      * Cx'(p) = Cx(Tx(p)).
1578      * A copy of the Tx is made, if necessary, so further
1579      * modifications to Tx do not affect rendering.
1580      * @param Tx The Transform object to be composed with the current
1581      * transform.
1582      * @see #setTransform
1583      * @see AffineTransform
1584      */
1585     public void transform(AffineTransform xform) {
1586         this.transform.concatenate(xform);
1587         invalidateTransform();
1588     }
1589 
1590     /**
1591      * Translate
1592      */
1593     public void translate(int x, int y) {
1594         transform.translate(x, y);
1595         if (transformState <= TRANSFORM_INT_TRANSLATE) {
1596             transX += x;
1597             transY += y;
1598             transformState = (((transX | transY) == 0) ?
1599                               TRANSFORM_ISIDENT : TRANSFORM_INT_TRANSLATE);
1600         } else {
1601             invalidateTransform();
1602         }
1603     }
1604 
1605     /**
1606      * Sets the Transform in the current graphics state.
1607      * @param Tx The Transform object to be used in the rendering process.
1608      * @see #transform
1609      * @see TransformChain
1610      * @see AffineTransform
1611      */
1612     @Override
1613     public void setTransform(AffineTransform Tx) {
1614         if ((constrainX | constrainY) == 0) {
1615             transform.setTransform(Tx);
1616         } else {
1617             transform.setToTranslation(constrainX, constrainY);
1618             transform.concatenate(Tx);
1619         }
1620         invalidateTransform();
1621     }
1622 
1623     protected void invalidateTransform() {
1624         int type = transform.getType();
1625         int origTransformState = transformState;
1626         if (type == AffineTransform.TYPE_IDENTITY) {
1627             transformState = TRANSFORM_ISIDENT;
1628             transX = transY = 0;
1629         } else if (type == AffineTransform.TYPE_TRANSLATION) {


1772             }
1773             paintState = PAINT_ALPHACOLOR;
1774             if (imageComp == CompositeType.SrcOverNoEa) {
1775                 // special case where compState depends on opacity of paint
1776                 compositeState = COMP_ALPHA;
1777             }
1778         }
1779         validFontInfo = false;
1780         invalidatePipe();
1781     }
1782 
1783     /**
1784      * Sets the background color in this context used for clearing a region.
1785      * When Graphics2D is constructed for a component, the backgroung color is
1786      * inherited from the component. Setting the background color in the
1787      * Graphics2D context only affects the subsequent clearRect() calls and
1788      * not the background color of the component. To change the background
1789      * of the component, use appropriate methods of the component.
1790      * @param color The background color that should be used in
1791      * subsequent calls to clearRect().
1792      * @see getBackground
1793      * @see Graphics.clearRect()
1794      */
1795     public void setBackground(Color color) {
1796         backgroundColor = color;
1797     }
1798 
1799     /**
1800      * Returns the background color used for clearing a region.
1801      * @see setBackground
1802      */
1803     public Color getBackground() {
1804         return backgroundColor;
1805     }
1806 
1807     /**
1808      * Returns the current Stroke in the Graphics2D state.
1809      * @see setStroke
1810      */
1811     public Stroke getStroke() {
1812         return stroke;
1813     }
1814 
1815     public Rectangle getClipBounds() {
1816         if (clipState == CLIP_DEVICE) {
1817             return null;
1818         }
1819         return getClipBounds(new Rectangle());
1820     }
1821 
1822     public Rectangle getClipBounds(Rectangle r) {
1823         if (clipState != CLIP_DEVICE) {
1824             if (transformState <= TRANSFORM_INT_TRANSLATE) {
1825                 if (usrClip instanceof Rectangle) {
1826                     r.setBounds((Rectangle) usrClip);
1827                 } else {
1828                     r.setFrame(usrClip.getBounds2D());
1829                 }


2039 
2040     public void setClip(int x, int y, int w, int h) {
2041         setClip(new Rectangle(x, y, w, h));
2042     }
2043 
2044     public Shape getClip() {
2045         return untransformShape(usrClip);
2046     }
2047 
2048     public void setClip(Shape sh) {
2049         usrClip = transformShape(sh);
2050         validateCompClip();
2051     }
2052 
2053     /**
2054      * Intersects the current clip with the specified Path and sets the
2055      * current clip to the resulting intersection. The clip is transformed
2056      * with the current transform in the Graphics2D state before being
2057      * intersected with the current clip. This method is used to make the
2058      * current clip smaller. To make the clip larger, use any setClip method.
2059      * @param p The Path to be intersected with the current clip.
2060      */
2061     public void clip(Shape s) {
2062         s = transformShape(s);
2063         if (usrClip != null) {
2064             s = intersectShapes(usrClip, s, true, true);
2065         }
2066         usrClip = s;
2067         validateCompClip();
2068     }
2069 
2070     public void setPaintMode() {
2071         setComposite(AlphaComposite.SrcOver);
2072     }
2073 
2074     public void setXORMode(Color c) {
2075         if (c == null) {
2076             throw new IllegalArgumentException("null XORColor");
2077         }
2078         setComposite(new XORComposite(c, surfaceData));
2079     }


2466             // surfaceData.unlock();
2467         }
2468     }
2469 
2470     public void clearRect(int x, int y, int w, int h) {
2471         // REMIND: has some "interesting" consequences if threads are
2472         // not synchronized
2473         Composite c = composite;
2474         Paint p = paint;
2475         setComposite(AlphaComposite.Src);
2476         setColor(getBackground());
2477         fillRect(x, y, w, h);
2478         setPaint(p);
2479         setComposite(c);
2480     }
2481 
2482     /**
2483      * Strokes the outline of a Path using the settings of the current
2484      * graphics state.  The rendering attributes applied include the
2485      * clip, transform, paint or color, composite and stroke attributes.
2486      * @param p The path to be drawn.
2487      * @see #setStroke
2488      * @see #setPaint
2489      * @see java.awt.Graphics#setColor
2490      * @see #transform
2491      * @see #setTransform
2492      * @see #clip
2493      * @see #setClip
2494      * @see #setComposite
2495      */
2496     public void draw(Shape s) {
2497         try {
2498             shapepipe.draw(this, s);
2499         } catch (InvalidPipeException e) {
2500             try {
2501                 revalidateAll();
2502                 shapepipe.draw(this, s);
2503             } catch (InvalidPipeException e2) {
2504                 // Still catching the exception; we are not yet ready to
2505                 // validate the surfaceData correctly.  Fail for now and
2506                 // try again next time around.




 857     }
 858 
 859     public FontMetrics getFontMetrics(Font font) {
 860         if ((this.fontMetrics != null) && (font == this.font)) {
 861             return this.fontMetrics;
 862         }
 863         FontMetrics fm =
 864           FontDesignMetrics.getMetrics(font, getFontRenderContext());
 865 
 866         if (this.font == font) {
 867             this.fontMetrics = fm;
 868         }
 869         return fm;
 870     }
 871 
 872     /**
 873      * Checks to see if a Path intersects the specified Rectangle in device
 874      * space.  The rendering attributes taken into account include the
 875      * clip, transform, and stroke attributes.
 876      * @param rect The area in device space to check for a hit.
 877      * @param s The path to check for a hit.
 878      * @param onStroke Flag to choose between testing the stroked or
 879      * the filled path.
 880      * @return True if there is a hit, false otherwise.
 881      * @see #setStroke
 882      * @see #fill(Shape)
 883      * @see #draw(Shape)
 884      * @see #transform
 885      * @see #setTransform
 886      * @see #clip
 887      * @see #setClip
 888      */
 889     public boolean hit(Rectangle rect, Shape s, boolean onStroke) {
 890         if (onStroke) {
 891             s = stroke.createStrokedShape(s);
 892         }
 893 
 894         s = transformShape(s);
 895         if ((constrainX|constrainY) != 0) {
 896             rect = new Rectangle(rect);
 897             rect.translate(constrainX, constrainY);
 898         }
 899 
 900         return s.intersects(rect);
 901     }
 902 
 903     /**


1278                         validFontInfo = false;
1279                         this.glyphVectorFontInfo = null;
1280                     }
1281                 }
1282                 if (hints != null) {
1283                     hints.put(hintKey, hintValue);
1284                 }
1285                 return;
1286             }
1287         }
1288         // Nothing we recognize so none of "our state" has changed
1289         if (hints == null) {
1290             hints = makeHints(null);
1291         }
1292         hints.put(hintKey, hintValue);
1293     }
1294 
1295 
1296     /**
1297      * Returns the preferences for the rendering algorithms.
1298      * @param hintKey The category of hint to be set. The strings
1299      * are defined in the RenderingHints class.
1300      * @return The preferences for rendering algorithms. The strings
1301      * are defined in the RenderingHints class.
1302      * @see RenderingHints
1303      */
1304     public Object getRenderingHint(Key hintKey) {
1305         if (hints != null) {
1306             return hints.get(hintKey);
1307         }
1308         if (!(hintKey instanceof SunHints.Key)) {
1309             return null;
1310         }
1311         int keyindex = ((SunHints.Key)hintKey).getIndex();
1312         switch (keyindex) {
1313         case SunHints.INTKEY_RENDERING:
1314             return SunHints.Value.get(SunHints.INTKEY_RENDERING,
1315                                       renderHint);
1316         case SunHints.INTKEY_ANTIALIASING:
1317             return SunHints.Value.get(SunHints.INTKEY_ANTIALIASING,
1318                                       antialiasHint);


1560      * @param shy The factor by which coordinates are shifted towards the
1561      * positive Y axis direction according to their X coordinate
1562      */
1563     public void shear(double shx, double shy) {
1564         transform.shear(shx, shy);
1565         invalidateTransform();
1566     }
1567 
1568     /**
1569      * Composes a Transform object with the transform in this
1570      * Graphics2D according to the rule last-specified-first-applied.
1571      * If the currrent transform is Cx, the result of composition
1572      * with Tx is a new transform Cx'.  Cx' becomes the current
1573      * transform for this Graphics2D.
1574      * Transforming a point p by the updated transform Cx' is
1575      * equivalent to first transforming p by Tx and then transforming
1576      * the result by the original transform Cx.  In other words,
1577      * Cx'(p) = Cx(Tx(p)).
1578      * A copy of the Tx is made, if necessary, so further
1579      * modifications to Tx do not affect rendering.
1580      * @param xform The Transform object to be composed with the current
1581      * transform.
1582      * @see #setTransform
1583      * @see AffineTransform
1584      */
1585     public void transform(AffineTransform xform) {
1586         this.transform.concatenate(xform);
1587         invalidateTransform();
1588     }
1589 
1590     /**
1591      * Translate
1592      */
1593     public void translate(int x, int y) {
1594         transform.translate(x, y);
1595         if (transformState <= TRANSFORM_INT_TRANSLATE) {
1596             transX += x;
1597             transY += y;
1598             transformState = (((transX | transY) == 0) ?
1599                               TRANSFORM_ISIDENT : TRANSFORM_INT_TRANSLATE);
1600         } else {
1601             invalidateTransform();
1602         }
1603     }
1604 
1605     /**
1606      * Sets the Transform in the current graphics state.
1607      * @param Tx The Transform object to be used in the rendering process.
1608      * @see #transform

1609      * @see AffineTransform
1610      */
1611     @Override
1612     public void setTransform(AffineTransform Tx) {
1613         if ((constrainX | constrainY) == 0) {
1614             transform.setTransform(Tx);
1615         } else {
1616             transform.setToTranslation(constrainX, constrainY);
1617             transform.concatenate(Tx);
1618         }
1619         invalidateTransform();
1620     }
1621 
1622     protected void invalidateTransform() {
1623         int type = transform.getType();
1624         int origTransformState = transformState;
1625         if (type == AffineTransform.TYPE_IDENTITY) {
1626             transformState = TRANSFORM_ISIDENT;
1627             transX = transY = 0;
1628         } else if (type == AffineTransform.TYPE_TRANSLATION) {


1771             }
1772             paintState = PAINT_ALPHACOLOR;
1773             if (imageComp == CompositeType.SrcOverNoEa) {
1774                 // special case where compState depends on opacity of paint
1775                 compositeState = COMP_ALPHA;
1776             }
1777         }
1778         validFontInfo = false;
1779         invalidatePipe();
1780     }
1781 
1782     /**
1783      * Sets the background color in this context used for clearing a region.
1784      * When Graphics2D is constructed for a component, the backgroung color is
1785      * inherited from the component. Setting the background color in the
1786      * Graphics2D context only affects the subsequent clearRect() calls and
1787      * not the background color of the component. To change the background
1788      * of the component, use appropriate methods of the component.
1789      * @param color The background color that should be used in
1790      * subsequent calls to clearRect().
1791      * @see #getBackground
1792      * @see Graphics#clearRect
1793      */
1794     public void setBackground(Color color) {
1795         backgroundColor = color;
1796     }
1797 
1798     /**
1799      * Returns the background color used for clearing a region.
1800      * @see #setBackground
1801      */
1802     public Color getBackground() {
1803         return backgroundColor;
1804     }
1805 
1806     /**
1807      * Returns the current Stroke in the Graphics2D state.
1808      * @see #setStroke
1809      */
1810     public Stroke getStroke() {
1811         return stroke;
1812     }
1813 
1814     public Rectangle getClipBounds() {
1815         if (clipState == CLIP_DEVICE) {
1816             return null;
1817         }
1818         return getClipBounds(new Rectangle());
1819     }
1820 
1821     public Rectangle getClipBounds(Rectangle r) {
1822         if (clipState != CLIP_DEVICE) {
1823             if (transformState <= TRANSFORM_INT_TRANSLATE) {
1824                 if (usrClip instanceof Rectangle) {
1825                     r.setBounds((Rectangle) usrClip);
1826                 } else {
1827                     r.setFrame(usrClip.getBounds2D());
1828                 }


2038 
2039     public void setClip(int x, int y, int w, int h) {
2040         setClip(new Rectangle(x, y, w, h));
2041     }
2042 
2043     public Shape getClip() {
2044         return untransformShape(usrClip);
2045     }
2046 
2047     public void setClip(Shape sh) {
2048         usrClip = transformShape(sh);
2049         validateCompClip();
2050     }
2051 
2052     /**
2053      * Intersects the current clip with the specified Path and sets the
2054      * current clip to the resulting intersection. The clip is transformed
2055      * with the current transform in the Graphics2D state before being
2056      * intersected with the current clip. This method is used to make the
2057      * current clip smaller. To make the clip larger, use any setClip method.
2058      * @param s The Path to be intersected with the current clip.
2059      */
2060     public void clip(Shape s) {
2061         s = transformShape(s);
2062         if (usrClip != null) {
2063             s = intersectShapes(usrClip, s, true, true);
2064         }
2065         usrClip = s;
2066         validateCompClip();
2067     }
2068 
2069     public void setPaintMode() {
2070         setComposite(AlphaComposite.SrcOver);
2071     }
2072 
2073     public void setXORMode(Color c) {
2074         if (c == null) {
2075             throw new IllegalArgumentException("null XORColor");
2076         }
2077         setComposite(new XORComposite(c, surfaceData));
2078     }


2465             // surfaceData.unlock();
2466         }
2467     }
2468 
2469     public void clearRect(int x, int y, int w, int h) {
2470         // REMIND: has some "interesting" consequences if threads are
2471         // not synchronized
2472         Composite c = composite;
2473         Paint p = paint;
2474         setComposite(AlphaComposite.Src);
2475         setColor(getBackground());
2476         fillRect(x, y, w, h);
2477         setPaint(p);
2478         setComposite(c);
2479     }
2480 
2481     /**
2482      * Strokes the outline of a Path using the settings of the current
2483      * graphics state.  The rendering attributes applied include the
2484      * clip, transform, paint or color, composite and stroke attributes.
2485      * @param s The path to be drawn.
2486      * @see #setStroke
2487      * @see #setPaint
2488      * @see java.awt.Graphics#setColor
2489      * @see #transform
2490      * @see #setTransform
2491      * @see #clip
2492      * @see #setClip
2493      * @see #setComposite
2494      */
2495     public void draw(Shape s) {
2496         try {
2497             shapepipe.draw(this, s);
2498         } catch (InvalidPipeException e) {
2499             try {
2500                 revalidateAll();
2501                 shapepipe.draw(this, s);
2502             } catch (InvalidPipeException e2) {
2503                 // Still catching the exception; we are not yet ready to
2504                 // validate the surfaceData correctly.  Fail for now and
2505                 // try again next time around.


< prev index next >