Path: blob/aarch64-shenandoah-jdk8u272-b10/jdk/src/macosx/classes/sun/font/CFont.java
38827 views
/*1* Copyright (c) 2011, 2017, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation. Oracle designates this7* particular file as subject to the "Classpath" exception as provided8* by Oracle in the LICENSE file that accompanied this code.9*10* This code is distributed in the hope that it will be useful, but WITHOUT11* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or12* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License13* version 2 for more details (a copy is included in the LICENSE file that14* accompanied this code).15*16* You should have received a copy of the GNU General Public License version17* 2 along with this work; if not, write to the Free Software Foundation,18* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.19*20* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA21* or visit www.oracle.com if you need additional information or have any22* questions.23*/2425package sun.font;2627import java.awt.Font;28import java.awt.font.FontRenderContext;29import java.awt.geom.AffineTransform;30import java.awt.geom.GeneralPath;;31import java.awt.geom.Point2D;32import java.awt.geom.Rectangle2D;33import java.util.ArrayList;3435// Right now this class is final to avoid a problem with native code.36// For some reason the JNI IsInstanceOf was not working correctly37// so we are checking the class specifically. If we subclass this38// we need to modify the native code in CFontWrapper.m39public final class CFont extends PhysicalFont implements FontSubstitution {4041/* CFontStrike doesn't call these methods so they are unimplemented.42* They are here to meet the requirements of PhysicalFont, needed43* because a CFont can sometimes be returned where a PhysicalFont44* is expected.45*/46StrikeMetrics getFontMetrics(long pScalerContext) {47throw new InternalError("Not implemented");48}4950float getGlyphAdvance(long pScalerContext, int glyphCode) {51throw new InternalError("Not implemented");52}5354void getGlyphMetrics(long pScalerContext, int glyphCode,55Point2D.Float metrics) {56throw new InternalError("Not implemented");57}5859long getGlyphImage(long pScalerContext, int glyphCode) {60throw new InternalError("Not implemented");61}6263Rectangle2D.Float getGlyphOutlineBounds(long pScalerContext,64int glyphCode) {65throw new InternalError("Not implemented");66}6768GeneralPath getGlyphOutline(long pScalerContext, int glyphCode,69float x, float y) {70throw new InternalError("Not implemented");71}7273GeneralPath getGlyphVectorOutline(long pScalerContext,74int[] glyphs, int numGlyphs,75float x, float y) {76throw new InternalError("Not implemented");77}7879@Override80protected long getLayoutTableCache() {81return getLayoutTableCacheNative(getNativeFontPtr());82}8384@Override85protected byte[] getTableBytes(int tag) {86return getTableBytesNative(getNativeFontPtr(), tag);87}8889private native synchronized long getLayoutTableCacheNative(long nativeFontPtr);9091private native byte[] getTableBytesNative(long nativeFontPtr, int tag);9293private static native long createNativeFont(final String nativeFontName,94final int style);95private static native void disposeNativeFont(final long nativeFontPtr);9697private boolean isFakeItalic;98private String nativeFontName;99private long nativeFontPtr;100101private native float getWidthNative(final long nativeFontPtr);102private native float getWeightNative(final long nativeFontPtr);103104private int fontWidth = -1;105private int fontWeight = -1;106107@Override108public int getWidth() {109if (fontWidth == -1) {110// Apple use a range of -1 -> +1, where 0.0 is normal111// OpenType uses a % range from 50% -> 200% where 100% is normal112// and maps these onto the integer values 1->9.113// Since that is what Font2D.getWidth() expects, remap to that.114float fw = getWidthNative(getNativeFontPtr());115if (fw == 0.0) { // short cut the common case116fontWidth = Font2D.FWIDTH_NORMAL;117return fontWidth;118}119fw += 1.0; fw *= 100.0;120if (fw <= 50.0) {121fontWidth = 1;122} else if (fw <= 62.5) {123fontWidth = 2;124} else if (fw <= 75.0) {125fontWidth = 3;126} else if (fw <= 87.5) {127fontWidth = 4;128} else if (fw <= 100.0) {129fontWidth = 5;130} else if (fw <= 112.5) {131fontWidth = 6;132} else if (fw <= 125.0) {133fontWidth = 7;134} else if (fw <= 150.0) {135fontWidth = 8;136} else {137fontWidth = 9;138}139}140return fontWidth;141}142143@Override144public int getWeight() {145if (fontWeight == -1) {146// Apple use a range of -1 -> +1, where 0 is medium/regular147// Map this on to the OpenType range of 100->900 where148// 500 is medium/regular.149// We'll actually map to 0->1000 but that's close enough.150float fw = getWeightNative(getNativeFontPtr());151if (fw == 0) {152return Font2D.FWEIGHT_NORMAL;153}154fw += 1.0; fw *= 500;155fontWeight = (int)fw;156}157return fontWeight;158}159160// this constructor is called from CFontWrapper.m161public CFont(String name) {162this(name, name);163}164165public CFont(String name, String inFamilyName) {166handle = new Font2DHandle(this);167fullName = name;168familyName = inFamilyName;169nativeFontName = fullName;170setStyle();171}172173/* Called from CFontManager too */174public CFont(CFont other, String logicalFamilyName) {175handle = new Font2DHandle(this);176fullName = logicalFamilyName;177familyName = logicalFamilyName;178nativeFontName = other.nativeFontName;179style = other.style;180isFakeItalic = other.isFakeItalic;181}182183public CFont createItalicVariant() {184CFont font = new CFont(this, familyName);185font.nativeFontName = fullName;186font.fullName =187fullName + (style == Font.BOLD ? "" : "-") + "Italic-Derived";188font.style |= Font.ITALIC;189font.isFakeItalic = true;190return font;191}192193protected synchronized long getNativeFontPtr() {194if (nativeFontPtr == 0L) {195nativeFontPtr = createNativeFont(nativeFontName, style);196}197return nativeFontPtr;198}199200static native void getCascadeList(long nativeFontPtr, ArrayList<String> listOfString);201202private CompositeFont createCompositeFont() {203ArrayList<String> listOfString = new ArrayList<String>();204getCascadeList(nativeFontPtr, listOfString);205206// add JRE "Lucida Sans Regular" to the cascade list to enable fallback207// to happen to this JRE font in case the intended glyph is missing in208// fonts provided in the CoreText provided cascaded list209listOfString.add("Lucida Sans Regular");210FontManager fm = FontManagerFactory.getInstance();211int numFonts = 1 + listOfString.size();212PhysicalFont[] fonts = new PhysicalFont[numFonts];213fonts[0] = this;214int idx = 1;215for (String s : listOfString) {216if (s.equals(".AppleSymbolsFB")) {217// Don't know why we get the weird name above .. replace.218s = "AppleSymbols";219}220Font2D f2d = fm.findFont2D(s, Font.PLAIN, FontManager.NO_FALLBACK);221if (f2d == null || f2d == this) {222continue;223}224fonts[idx++] = (PhysicalFont)f2d;225}226if (idx < fonts.length) {227PhysicalFont[] orig = fonts;228fonts = new PhysicalFont[idx];229System.arraycopy(orig, 0, fonts, 0, idx);230}231CompositeFont compFont = new CompositeFont(fonts);232compFont.mapper = new CCompositeGlyphMapper(compFont);233return compFont;234}235236private CompositeFont compFont;237238public CompositeFont getCompositeFont2D() {239if (compFont == null) {240compFont = createCompositeFont();241}242return compFont;243}244245protected synchronized void finalize() {246if (nativeFontPtr != 0) {247disposeNativeFont(nativeFontPtr);248}249nativeFontPtr = 0;250}251252protected CharToGlyphMapper getMapper() {253if (mapper == null) {254mapper = new CCharToGlyphMapper(this);255}256return mapper;257}258259protected FontStrike createStrike(FontStrikeDesc desc) {260if (isFakeItalic) {261desc = new FontStrikeDesc(desc);262desc.glyphTx.concatenate(AffineTransform.getShearInstance(-0.2, 0));263}264return new CStrike(this, desc);265}266267// <rdar://problem/5321707> sun.font.Font2D caches the last used strike,268// but does not check if the properties of the strike match the properties269// of the incoming java.awt.Font object (size, style, etc).270// Simple answer: don't cache.271private static FontRenderContext DEFAULT_FRC =272new FontRenderContext(null, false, false);273public FontStrike getStrike(final Font font) {274return getStrike(font, DEFAULT_FRC);275}276277public String toString() {278return "CFont { fullName: " + fullName +279", familyName: " + familyName + ", style: " + style +280" } aka: " + super.toString();281}282}283284285