1 /* 2 * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package com.sun.javafx.font.directwrite; 27 28 import com.sun.javafx.font.DisposerRecord; 29 import com.sun.javafx.font.FontResource; 30 import com.sun.javafx.font.FontStrikeDesc; 31 import com.sun.javafx.font.Glyph; 32 import com.sun.javafx.font.PrismFontFactory; 33 import com.sun.javafx.font.PrismFontStrike; 34 import com.sun.javafx.geom.Path2D; 35 import com.sun.javafx.geom.Point2D; 36 import com.sun.javafx.geom.RectBounds; 37 import com.sun.javafx.geom.transform.BaseTransform; 38 39 class DWFontStrike extends PrismFontStrike<DWFontFile> { 40 DWRITE_MATRIX matrix; 41 static final boolean SUBPIXEL_ON; 42 static final boolean SUBPIXEL_Y; 43 static final boolean SUBPIXEL_NATIVE; 44 static { 45 int mode = PrismFontFactory.getFontFactory().getSubPixelMode(); 46 SUBPIXEL_ON = (mode & PrismFontFactory.SUB_PIXEL_ON) != 0; 47 SUBPIXEL_Y = (mode & PrismFontFactory.SUB_PIXEL_Y) != 0; 48 SUBPIXEL_NATIVE = (mode & PrismFontFactory.SUB_PIXEL_NATIVE) != 0; 49 } 50 51 DWFontStrike(DWFontFile fontResource, float size, BaseTransform tx, 52 int aaMode, FontStrikeDesc desc) { 53 super(fontResource, size, tx, aaMode, desc); 54 float maxDim = 80f; 55 if (tx.isTranslateOrIdentity()) { 56 drawShapes = size > maxDim; 57 } else { 58 BaseTransform tx2d = getTransform(); 59 matrix = new DWRITE_MATRIX(); 60 matrix.m11 = (float)tx2d.getMxx(); 61 matrix.m12 = (float)tx2d.getMyx(); 62 matrix.m21 = (float)tx2d.getMxy(); 63 matrix.m22 = (float)tx2d.getMyy(); 64 65 if (Math.abs(matrix.m11 * size) > maxDim || 66 Math.abs(matrix.m12 * size) > maxDim || 67 Math.abs(matrix.m21 * size) > maxDim || 68 Math.abs(matrix.m22 * size) > maxDim) 69 { 70 drawShapes = true; 71 } 72 } 73 } 74 75 @Override protected DisposerRecord createDisposer(FontStrikeDesc desc) { 76 return null; 77 } 78 79 @Override 80 public int getQuantizedPosition(Point2D point) { 81 if (SUBPIXEL_ON && (matrix == null || SUBPIXEL_NATIVE)) { 82 /* Using DirectWrite to produce subpixel glyph masks for grayscale 83 * text and (by default) let Prism produce subpixel glyphs for LCD 84 * using shaders (thus, saving texture and memory). 85 */ 86 if (getAAMode() == FontResource.AA_GREYSCALE || SUBPIXEL_NATIVE) { 87 float subPixel = point.x; 88 point.x = (int)point.x; 89 subPixel -= point.x; 90 int index = 0; 91 if (subPixel >= 0.66f) { 92 index = 2; 93 } else if (subPixel >= 0.33f) { 94 index = 1; 95 } 96 if (SUBPIXEL_Y) { 97 subPixel = point.y; 98 point.y = (int)point.y; 99 subPixel -= point.y; 100 if (subPixel >= 0.66f) { 101 index += 6; 102 } else if (subPixel >= 0.33f) { 103 index += 3; 104 } 105 } else { 106 point.y = (float)Math.round(point.y); 107 } 108 return index; 109 } 110 } 111 return super.getQuantizedPosition(point); 112 } 113 114 IDWriteFontFace getFontFace() { 115 DWFontFile fontResource = getFontResource(); 116 return fontResource.getFontFace(); 117 } 118 119 RectBounds getBBox(int glyphCode) { 120 DWFontFile fontResource = getFontResource(); 121 return fontResource.getBBox(glyphCode, getSize()); 122 } 123 124 int getUpem() { 125 return getFontResource().getUnitsPerEm(); 126 } 127 128 @Override protected Path2D createGlyphOutline(int glyphCode) { 129 DWFontFile fontResource = getFontResource(); 130 return fontResource.getGlyphOutline(glyphCode, getSize()); 131 } 132 133 @Override protected Glyph createGlyph(int glyphCode) { 134 return new DWGlyph(this, glyphCode, drawShapes); 135 } 136 }