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

Print this page

        

*** 59,68 **** --- 59,69 ---- import java.awt.Stroke; import java.awt.FontMetrics; import java.awt.Rectangle; import java.text.AttributedCharacterIterator; import java.awt.Font; + import java.awt.Point; import java.awt.image.ImageObserver; import java.awt.Transparency; import java.awt.font.GlyphVector; import java.awt.font.TextLayout;
*** 91,100 **** --- 92,108 ---- import java.util.Map; import java.util.Iterator; import sun.misc.PerformanceLogger; import java.lang.annotation.Native; + import sun.awt.image.MultiResolutionImage; + + import static java.awt.geom.AffineTransform.TYPE_FLIP; + import static java.awt.geom.AffineTransform.TYPE_MASK_SCALE; + import static java.awt.geom.AffineTransform.TYPE_TRANSLATION; + import sun.awt.image.MultiResolutionToolkitImage; + import sun.awt.image.ToolkitImage; /** * This is a the master Graphics2D superclass for all of the Sun * Graphics implementations. This class relies on subclasses to * manage the various device information, but provides an overall
*** 235,244 **** --- 243,253 ---- public Region clipRegion; public Shape usrClip; protected Region devClip; // Actual physical drawable in pixels private final int devScale; // Actual physical scale factor + private int resolutionVariantHint; // cached state for text rendering private boolean validFontInfo; private FontInfo fontInfo; private FontInfo glyphVectorFontInfo;
*** 272,281 **** --- 281,291 ---- textAntialiasHint = SunHints.INTVAL_TEXT_ANTIALIAS_DEFAULT; fractionalMetricsHint = SunHints.INTVAL_FRACTIONALMETRICS_OFF; lcdTextContrast = lcdTextContrastDefaultValue; interpolationHint = -1; strokeHint = SunHints.INTVAL_STROKE_DEFAULT; + resolutionVariantHint = SunHints.INTVAL_RESOLUTION_VARIANT_DEFAULT; interpolationType = AffineTransformOp.TYPE_NEAREST_NEIGHBOR; validateColor();
*** 1247,1256 **** --- 1257,1270 ---- break; case SunHints.INTKEY_STROKE_CONTROL: stateChanged = (strokeHint != newHint); strokeHint = newHint; break; + case SunHints.INTKEY_RESOLUTION_VARIANT: + stateChanged = (resolutionVariantHint != newHint); + resolutionVariantHint = newHint; + break; default: recognized = false; stateChanged = false; break; }
*** 1320,1329 **** --- 1334,1346 ---- } return null; case SunHints.INTKEY_STROKE_CONTROL: return SunHints.Value.get(SunHints.INTKEY_STROKE_CONTROL, strokeHint); + case SunHints.INTKEY_RESOLUTION_VARIANT: + return SunHints.Value.get(SunHints.INTKEY_RESOLUTION_VARIANT, + resolutionVariantHint); } return null; } /**
*** 3048,3069 **** surfaceData.markDirty(); } } // end of text rendering methods ! private static boolean isHiDPIImage(final Image img) { ! return SurfaceManager.getImageScale(img) != 1; } private boolean drawHiDPIImage(Image img, int dx1, int dy1, int dx2, int dy2, int sx1, int sy1, int sx2, int sy2, Color bgcolor, ImageObserver observer) { final int scale = SurfaceManager.getImageScale(img); sx1 = Region.clipScale(sx1, scale); sx2 = Region.clipScale(sx2, scale); sy1 = Region.clipScale(sy1, scale); sy2 = Region.clipScale(sy2, scale); try { return imagepipe.scaleImage(this, img, dx1, dy1, dx2, dy2, sx1, sy1, sx2, sy2, bgcolor, observer); } catch (InvalidPipeException e) { try { --- 3065,3124 ---- surfaceData.markDirty(); } } // end of text rendering methods ! private boolean isHiDPIImage(final Image img) { ! return (SurfaceManager.getImageScale(img) != 1) || ! (resolutionVariantHint != SunHints.INTVAL_RESOLUTION_VARIANT_OFF ! && img instanceof MultiResolutionImage); } private boolean drawHiDPIImage(Image img, int dx1, int dy1, int dx2, int dy2, int sx1, int sy1, int sx2, int sy2, Color bgcolor, ImageObserver observer) { + + if (SurfaceManager.getImageScale(img) != 1) { // Volatile Image final int scale = SurfaceManager.getImageScale(img); sx1 = Region.clipScale(sx1, scale); sx2 = Region.clipScale(sx2, scale); sy1 = Region.clipScale(sy1, scale); sy2 = Region.clipScale(sy2, scale); + } else if (img instanceof MultiResolutionImage) { + // get scaled destination image size + + int width = img.getWidth(null); + int height = img.getHeight(null); + + Image resolutionVariant = getResolutionVariant( + (MultiResolutionImage) img, width, height, + dx1, dy1, dx2, dy2, sx1, sy1, sx2, sy2); + + if (resolutionVariant != img && resolutionVariant != null) { + // recalculate source region for the resolution variant + + int rvWidth = resolutionVariant.getWidth(null); + int rvHeight = resolutionVariant.getHeight(null); + + if (0 < width && 0 < height && 0 < rvWidth && 0 < rvHeight) { + + float widthScale = ((float) rvWidth) / width; + float heightScale = ((float) rvHeight) / height; + + sx1 = Region.clipScale(sx1, widthScale); + sy1 = Region.clipScale(sy1, heightScale); + sx2 = Region.clipScale(sx2, widthScale); + sy2 = Region.clipScale(sy2, heightScale); + + observer = MultiResolutionToolkitImage. + getResolutionVariantObserver(img, observer, + width, height, rvWidth, rvHeight); + img = resolutionVariant; + } + } + } + try { return imagepipe.scaleImage(this, img, dx1, dy1, dx2, dy2, sx1, sy1, sx2, sy2, bgcolor, observer); } catch (InvalidPipeException e) { try {
*** 3079,3088 **** --- 3134,3191 ---- } finally { surfaceData.markDirty(); } } + private Image getResolutionVariant(MultiResolutionImage img, + int srcWidth, int srcHeight, int dx1, int dy1, int dx2, int dy2, + int sx1, int sy1, int sx2, int sy2) { + + if (srcWidth <= 0 || srcHeight <= 0) { + return null; + } + + int sw = sx2 - sx1; + int sh = sy2 - sy1; + + if (sw == 0 || sh == 0) { + return null; + } + + int type = transform.getType(); + int dw = dx2 - dx1; + int dh = dy2 - dy1; + double destRegionWidth; + double destRegionHeight; + + if ((type & ~(TYPE_TRANSLATION | TYPE_FLIP)) == 0) { + destRegionWidth = dw; + destRegionHeight = dh; + } else if ((type & ~(TYPE_TRANSLATION | TYPE_FLIP | TYPE_MASK_SCALE)) == 0) { + destRegionWidth = dw * transform.getScaleX(); + destRegionHeight = dh * transform.getScaleY(); + } else { + destRegionWidth = dw * Math.hypot( + transform.getScaleX(), transform.getShearY()); + destRegionHeight = dh * Math.hypot( + transform.getShearX(), transform.getScaleY()); + } + + int destImageWidth = (int) Math.abs(srcWidth * destRegionWidth / sw); + int destImageHeight = (int) Math.abs(srcHeight * destRegionHeight / sh); + + Image resolutionVariant + = img.getResolutionVariant(destImageWidth, destImageHeight); + + if (resolutionVariant instanceof ToolkitImage + && ((ToolkitImage) resolutionVariant).hasError()) { + return null; + } + + return resolutionVariant; + } + /** * Draws an image scaled to x,y,w,h in nonblocking mode with a * callback object. */ public boolean drawImage(Image img, int x, int y, int width, int height,