jdk/src/share/classes/sun/font/FontManager.java
author xdono
Wed, 02 Jul 2008 12:55:45 -0700
changeset 715 f16baef3a20e
parent 560 3a8029083a72
child 889 6549643c008c
permissions -rw-r--r--
6719955: Update copyright year Summary: Update copyright year for files that have been modified in 2008 Reviewed-by: ohair, tbell
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     1
/*
715
f16baef3a20e 6719955: Update copyright year
xdono
parents: 560
diff changeset
     2
 * Copyright 2003-2008 Sun Microsystems, Inc.  All Rights Reserved.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
90ce3da70b43 Initial load
duke
parents:
diff changeset
     4
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
90ce3da70b43 Initial load
duke
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
90ce3da70b43 Initial load
duke
parents:
diff changeset
     7
 * published by the Free Software Foundation.  Sun designates this
90ce3da70b43 Initial load
duke
parents:
diff changeset
     8
 * particular file as subject to the "Classpath" exception as provided
90ce3da70b43 Initial load
duke
parents:
diff changeset
     9
 * by Sun in the LICENSE file that accompanied this code.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    10
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    11
 * This code is distributed in the hope that it will be useful, but WITHOUT
90ce3da70b43 Initial load
duke
parents:
diff changeset
    12
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
90ce3da70b43 Initial load
duke
parents:
diff changeset
    13
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
90ce3da70b43 Initial load
duke
parents:
diff changeset
    14
 * version 2 for more details (a copy is included in the LICENSE file that
90ce3da70b43 Initial load
duke
parents:
diff changeset
    15
 * accompanied this code).
90ce3da70b43 Initial load
duke
parents:
diff changeset
    16
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    17
 * You should have received a copy of the GNU General Public License version
90ce3da70b43 Initial load
duke
parents:
diff changeset
    18
 * 2 along with this work; if not, write to the Free Software Foundation,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    19
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    20
 *
90ce3da70b43 Initial load
duke
parents:
diff changeset
    21
 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
90ce3da70b43 Initial load
duke
parents:
diff changeset
    22
 * CA 95054 USA or visit www.sun.com if you need additional information or
90ce3da70b43 Initial load
duke
parents:
diff changeset
    23
 * have any questions.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    24
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    25
90ce3da70b43 Initial load
duke
parents:
diff changeset
    26
package sun.font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    27
90ce3da70b43 Initial load
duke
parents:
diff changeset
    28
import java.awt.Font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    29
import java.awt.GraphicsEnvironment;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    30
import java.awt.FontFormatException;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    31
import java.io.File;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    32
import java.io.FilenameFilter;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    33
import java.security.AccessController;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    34
import java.security.PrivilegedAction;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    35
import java.util.ArrayList;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    36
import java.util.HashMap;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    37
import java.util.HashSet;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    38
import java.util.Hashtable;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    39
import java.util.Iterator;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    40
import java.util.Locale;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    41
import java.util.Map;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    42
import java.util.NoSuchElementException;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    43
import java.util.StringTokenizer;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    44
import java.util.TreeMap;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    45
import java.util.Vector;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    46
import java.util.concurrent.ConcurrentHashMap;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    47
import java.util.logging.Level;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    48
import java.util.logging.Logger;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    49
import javax.swing.plaf.FontUIResource;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    50
90ce3da70b43 Initial load
duke
parents:
diff changeset
    51
import sun.awt.AppContext;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    52
import sun.awt.FontConfiguration;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    53
import sun.awt.SunHints;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    54
import sun.awt.SunToolkit;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    55
import sun.java2d.HeadlessGraphicsEnvironment;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    56
import sun.java2d.SunGraphicsEnvironment;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    57
90ce3da70b43 Initial load
duke
parents:
diff changeset
    58
import java.awt.geom.GeneralPath;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    59
import java.awt.geom.Point2D;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    60
import java.awt.geom.Rectangle2D;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    61
90ce3da70b43 Initial load
duke
parents:
diff changeset
    62
import java.lang.reflect.Constructor;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    63
90ce3da70b43 Initial load
duke
parents:
diff changeset
    64
import sun.java2d.Disposer;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    65
90ce3da70b43 Initial load
duke
parents:
diff changeset
    66
/*
90ce3da70b43 Initial load
duke
parents:
diff changeset
    67
 * Interface between Java Fonts (java.awt.Font) and the underlying
90ce3da70b43 Initial load
duke
parents:
diff changeset
    68
 * font files/native font resources and the Java and native font scalers.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    69
 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    70
public final class FontManager {
90ce3da70b43 Initial load
duke
parents:
diff changeset
    71
90ce3da70b43 Initial load
duke
parents:
diff changeset
    72
    public static final int FONTFORMAT_NONE      = -1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    73
    public static final int FONTFORMAT_TRUETYPE  = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    74
    public static final int FONTFORMAT_TYPE1     = 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    75
    public static final int FONTFORMAT_T2K       = 2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    76
    public static final int FONTFORMAT_TTC       = 3;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    77
    public static final int FONTFORMAT_COMPOSITE = 4;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    78
    public static final int FONTFORMAT_NATIVE    = 5;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    79
90ce3da70b43 Initial load
duke
parents:
diff changeset
    80
    public static final int NO_FALLBACK         = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    81
    public static final int PHYSICAL_FALLBACK   = 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    82
    public static final int LOGICAL_FALLBACK    = 2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    83
90ce3da70b43 Initial load
duke
parents:
diff changeset
    84
    public static final int QUADPATHTYPE = 1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    85
    public static final int CUBICPATHTYPE = 2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    86
90ce3da70b43 Initial load
duke
parents:
diff changeset
    87
    /* Pool of 20 font file channels chosen because some UTF-8 locale
90ce3da70b43 Initial load
duke
parents:
diff changeset
    88
     * composite fonts can use up to 16 platform fonts (including the
90ce3da70b43 Initial load
duke
parents:
diff changeset
    89
     * Lucida fall back). This should prevent channel thrashing when
90ce3da70b43 Initial load
duke
parents:
diff changeset
    90
     * dealing with one of these fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    91
     * The pool array stores the fonts, rather than directly referencing
90ce3da70b43 Initial load
duke
parents:
diff changeset
    92
     * the channels, as the font needs to do the open/close work.
90ce3da70b43 Initial load
duke
parents:
diff changeset
    93
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
    94
    private static final int CHANNELPOOLSIZE = 20;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    95
    private static int lastPoolIndex = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
    96
    private static FileFont fontFileCache[] = new FileFont[CHANNELPOOLSIZE];
90ce3da70b43 Initial load
duke
parents:
diff changeset
    97
90ce3da70b43 Initial load
duke
parents:
diff changeset
    98
    /* Need to implement a simple linked list scheme for fast
90ce3da70b43 Initial load
duke
parents:
diff changeset
    99
     * traversal and lookup.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   100
     * Also want to "fast path" dialog so there's minimal overhead.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   101
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   102
    /* There are at exactly 20 composite fonts: 5 faces (but some are not
90ce3da70b43 Initial load
duke
parents:
diff changeset
   103
     * usually different), in 4 styles. The array may be auto-expanded
90ce3da70b43 Initial load
duke
parents:
diff changeset
   104
     * later if more are needed, eg for user-defined composites or locale
90ce3da70b43 Initial load
duke
parents:
diff changeset
   105
     * variants.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   106
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   107
    private static int maxCompFont = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   108
    private static CompositeFont [] compFonts = new CompositeFont[20];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   109
    private static ConcurrentHashMap<String, CompositeFont>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   110
        compositeFonts = new ConcurrentHashMap<String, CompositeFont>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   111
    private static ConcurrentHashMap<String, PhysicalFont>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   112
        physicalFonts = new ConcurrentHashMap<String, PhysicalFont>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   113
    private static ConcurrentHashMap<String, PhysicalFont>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   114
        registeredFontFiles = new ConcurrentHashMap<String, PhysicalFont>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   115
90ce3da70b43 Initial load
duke
parents:
diff changeset
   116
    /* given a full name find the Font. Remind: there's duplication
90ce3da70b43 Initial load
duke
parents:
diff changeset
   117
     * here in that this contains the content of compositeFonts +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   118
     * physicalFonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   119
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   120
    private static ConcurrentHashMap<String, Font2D>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   121
        fullNameToFont = new ConcurrentHashMap<String, Font2D>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   122
90ce3da70b43 Initial load
duke
parents:
diff changeset
   123
    /* TrueType fonts have localised names. Support searching all
90ce3da70b43 Initial load
duke
parents:
diff changeset
   124
     * of these before giving up on a name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   125
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   126
    private static HashMap<String, TrueTypeFont> localeFullNamesToFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   127
90ce3da70b43 Initial load
duke
parents:
diff changeset
   128
    private static PhysicalFont defaultPhysicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   129
90ce3da70b43 Initial load
duke
parents:
diff changeset
   130
    /* deprecated, unsupported hack - actually invokes a bug! */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   131
    private static boolean usePlatformFontMetrics = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   132
90ce3da70b43 Initial load
duke
parents:
diff changeset
   133
    public static Logger logger = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   134
    public static boolean logging;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   135
    static boolean longAddresses;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   136
    static String osName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   137
    static boolean useT2K;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   138
    static boolean isWindows;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   139
    static boolean isSolaris;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   140
    public static boolean isSolaris8; // needed to check for JA wavedash fix.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   141
    public static boolean isSolaris9; // needed to check for songti font usage.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   142
    private static boolean loaded1dot0Fonts = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   143
    static SunGraphicsEnvironment sgEnv;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   144
    static boolean loadedAllFonts = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   145
    static boolean loadedAllFontFiles = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   146
    static TrueTypeFont eudcFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   147
    static HashMap<String,String> jreFontMap;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   148
    static HashSet<String> jreLucidaFontFiles;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   149
    static String[] jreOtherFontFiles;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   150
    static boolean noOtherJREFontFiles = false; // initial assumption.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   151
90ce3da70b43 Initial load
duke
parents:
diff changeset
   152
    /* Used to indicate required return type from toArray(..); */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   153
    private static String[] STR_ARRAY = new String[0];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   154
90ce3da70b43 Initial load
duke
parents:
diff changeset
   155
    private static void initJREFontMap() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   156
90ce3da70b43 Initial load
duke
parents:
diff changeset
   157
        /* Key is familyname+style value as an int.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   158
         * Value is filename containing the font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   159
         * If no mapping exists, it means there is no font file for the style
90ce3da70b43 Initial load
duke
parents:
diff changeset
   160
         * If the mapping exists but the file doesn't exist in the deferred
90ce3da70b43 Initial load
duke
parents:
diff changeset
   161
         * list then it means its not installed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   162
         * This looks like a lot of code and strings but if it saves even
90ce3da70b43 Initial load
duke
parents:
diff changeset
   163
         * a single file being opened at JRE start-up there's a big payoff.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   164
         * Lucida Sans is probably the only important case as the others
90ce3da70b43 Initial load
duke
parents:
diff changeset
   165
         * are rarely used. Consider removing the other mappings if there's
90ce3da70b43 Initial load
duke
parents:
diff changeset
   166
         * no evidence they are useful in practice.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   167
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   168
        jreFontMap = new HashMap<String,String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   169
        jreLucidaFontFiles = new HashSet<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   170
        if (SunGraphicsEnvironment.isOpenJDK()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   171
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   172
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   173
        /* Lucida Sans Family */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   174
        jreFontMap.put("lucida sans0",   "LucidaSansRegular.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   175
        jreFontMap.put("lucida sans1",   "LucidaSansDemiBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   176
        /* Lucida Sans full names (map Bold and DemiBold to same file) */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   177
        jreFontMap.put("lucida sans regular0", "LucidaSansRegular.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   178
        jreFontMap.put("lucida sans regular1", "LucidaSansDemiBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   179
        jreFontMap.put("lucida sans bold1", "LucidaSansDemiBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   180
        jreFontMap.put("lucida sans demibold1", "LucidaSansDemiBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   181
90ce3da70b43 Initial load
duke
parents:
diff changeset
   182
        /* Lucida Sans Typewriter Family */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   183
        jreFontMap.put("lucida sans typewriter0",
90ce3da70b43 Initial load
duke
parents:
diff changeset
   184
                       "LucidaTypewriterRegular.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   185
        jreFontMap.put("lucida sans typewriter1", "LucidaTypewriterBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   186
        /* Typewriter full names (map Bold and DemiBold to same file) */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   187
        jreFontMap.put("lucida sans typewriter regular0",
90ce3da70b43 Initial load
duke
parents:
diff changeset
   188
                       "LucidaTypewriter.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   189
        jreFontMap.put("lucida sans typewriter regular1",
90ce3da70b43 Initial load
duke
parents:
diff changeset
   190
                       "LucidaTypewriterBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   191
        jreFontMap.put("lucida sans typewriter bold1",
90ce3da70b43 Initial load
duke
parents:
diff changeset
   192
                       "LucidaTypewriterBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   193
        jreFontMap.put("lucida sans typewriter demibold1",
90ce3da70b43 Initial load
duke
parents:
diff changeset
   194
                       "LucidaTypewriterBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   195
90ce3da70b43 Initial load
duke
parents:
diff changeset
   196
        /* Lucida Bright Family */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   197
        jreFontMap.put("lucida bright0", "LucidaBrightRegular.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   198
        jreFontMap.put("lucida bright1", "LucidaBrightDemiBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   199
        jreFontMap.put("lucida bright2", "LucidaBrightItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   200
        jreFontMap.put("lucida bright3", "LucidaBrightDemiItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   201
        /* Lucida Bright full names (map Bold and DemiBold to same file) */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   202
        jreFontMap.put("lucida bright regular0", "LucidaBrightRegular.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   203
        jreFontMap.put("lucida bright regular1", "LucidaBrightDemiBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   204
        jreFontMap.put("lucida bright regular2", "LucidaBrightItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   205
        jreFontMap.put("lucida bright regular3", "LucidaBrightDemiItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   206
        jreFontMap.put("lucida bright bold1", "LucidaBrightDemiBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   207
        jreFontMap.put("lucida bright bold3", "LucidaBrightDemiItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   208
        jreFontMap.put("lucida bright demibold1", "LucidaBrightDemiBold.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   209
        jreFontMap.put("lucida bright demibold3","LucidaBrightDemiItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   210
        jreFontMap.put("lucida bright italic2", "LucidaBrightItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   211
        jreFontMap.put("lucida bright italic3", "LucidaBrightDemiItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   212
        jreFontMap.put("lucida bright bold italic3",
90ce3da70b43 Initial load
duke
parents:
diff changeset
   213
                       "LucidaBrightDemiItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   214
        jreFontMap.put("lucida bright demibold italic3",
90ce3da70b43 Initial load
duke
parents:
diff changeset
   215
                       "LucidaBrightDemiItalic.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   216
        for (String ffile : jreFontMap.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   217
            jreLucidaFontFiles.add(ffile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   218
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   219
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   220
90ce3da70b43 Initial load
duke
parents:
diff changeset
   221
    static {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   222
90ce3da70b43 Initial load
duke
parents:
diff changeset
   223
        if (SunGraphicsEnvironment.debugFonts) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   224
            logger = Logger.getLogger("sun.java2d", null);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   225
            logging = logger.getLevel() != Level.OFF;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   226
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   227
        initJREFontMap();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   228
90ce3da70b43 Initial load
duke
parents:
diff changeset
   229
        java.security.AccessController.doPrivileged(
90ce3da70b43 Initial load
duke
parents:
diff changeset
   230
                                    new java.security.PrivilegedAction() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   231
           public Object run() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   232
               FontManagerNativeLibrary.load();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   233
90ce3da70b43 Initial load
duke
parents:
diff changeset
   234
               // JNI throws an exception if a class/method/field is not found,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   235
               // so there's no need to do anything explicit here.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   236
               initIDs();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   237
90ce3da70b43 Initial load
duke
parents:
diff changeset
   238
               switch (StrikeCache.nativeAddressSize) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   239
               case 8: longAddresses = true; break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   240
               case 4: longAddresses = false; break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   241
               default: throw new RuntimeException("Unexpected address size");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   242
               }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   243
90ce3da70b43 Initial load
duke
parents:
diff changeset
   244
               osName = System.getProperty("os.name", "unknownOS");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   245
               isSolaris = osName.startsWith("SunOS");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   246
550
e85f91b9bb95 6656651: Windows Look and Feel LCD glyph images have some differences from native applications.
prr
parents: 532
diff changeset
   247
               String t2kStr = System.getProperty("sun.java2d.font.scaler");
e85f91b9bb95 6656651: Windows Look and Feel LCD glyph images have some differences from native applications.
prr
parents: 532
diff changeset
   248
               if (t2kStr != null) {
e85f91b9bb95 6656651: Windows Look and Feel LCD glyph images have some differences from native applications.
prr
parents: 532
diff changeset
   249
                   useT2K = "t2k".equals(t2kStr);
e85f91b9bb95 6656651: Windows Look and Feel LCD glyph images have some differences from native applications.
prr
parents: 532
diff changeset
   250
               }
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   251
               if (isSolaris) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   252
                   String version = System.getProperty("os.version", "unk");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   253
                   isSolaris8 = version.equals("5.8");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   254
                   isSolaris9 = version.equals("5.9");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   255
               } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   256
                   isWindows = osName.startsWith("Windows");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   257
                   if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   258
                       String eudcFile =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   259
                           SunGraphicsEnvironment.eudcFontFileName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   260
                       if (eudcFile != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   261
                           try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   262
                               eudcFont = new TrueTypeFont(eudcFile, null, 0,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   263
                                                           true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   264
                           } catch (FontFormatException e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   265
                           }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   266
                       }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   267
                       String prop =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   268
                           System.getProperty("java2d.font.usePlatformFont");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   269
                       if (("true".equals(prop) || getPlatformFontVar())) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   270
                           usePlatformFontMetrics = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   271
                           System.out.println("Enabling platform font metrics for win32. This is an unsupported option.");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   272
                           System.out.println("This yields incorrect composite font metrics as reported by 1.1.x releases.");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   273
                           System.out.println("It is appropriate only for use by applications which do not use any Java 2");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   274
                           System.out.println("functionality. This property will be removed in a later release.");
90ce3da70b43 Initial load
duke
parents:
diff changeset
   275
                       }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   276
                   }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   277
               }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   278
               return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   279
           }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   280
        });
90ce3da70b43 Initial load
duke
parents:
diff changeset
   281
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   282
90ce3da70b43 Initial load
duke
parents:
diff changeset
   283
    /* Initialise ptrs used by JNI methods */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   284
    private static native void initIDs();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   285
90ce3da70b43 Initial load
duke
parents:
diff changeset
   286
    public static void addToPool(FileFont font) {
532
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   287
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   288
        FileFont fontFileToClose = null;
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   289
        int freeSlot = -1;
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   290
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   291
        synchronized (fontFileCache) {
532
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   292
            /* Avoid duplicate entries in the pool, and don't close() it,
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   293
             * since this method is called only from within open().
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   294
             * Seeing a duplicate is most likely to happen if the thread
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   295
             * was interrupted during a read, forcing perhaps repeated
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   296
             * close and open calls and it eventually it ends up pointing
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   297
             * at the same slot.
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   298
             */
532
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   299
            for (int i=0;i<CHANNELPOOLSIZE;i++) {
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   300
                if (fontFileCache[i] == font) {
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   301
                    return;
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   302
                }
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   303
                if (fontFileCache[i] == null && freeSlot < 0) {
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   304
                    freeSlot = i;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   305
                }
532
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   306
            }
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   307
            if (freeSlot >= 0) {
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   308
                fontFileCache[freeSlot] = font;
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   309
                return;
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   310
            } else {
532
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   311
                /* replace with new font. */
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   312
                fontFileToClose = fontFileCache[lastPoolIndex];
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   313
                fontFileCache[lastPoolIndex] = font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   314
                /* lastPoolIndex is updated so that the least recently opened
90ce3da70b43 Initial load
duke
parents:
diff changeset
   315
                 * file will be closed next.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   316
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   317
                lastPoolIndex = (lastPoolIndex+1) % CHANNELPOOLSIZE;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   318
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   319
        }
532
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   320
        /* Need to close the font file outside of the synchronized block,
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   321
         * since its possible some other thread is in an open() call on
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   322
         * this font file, and could be holding its lock and the pool lock.
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   323
         * Releasing the pool lock allows that thread to continue, so it can
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   324
         * then release the lock on this font, allowing the close() call
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   325
         * below to proceed.
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   326
         * Also, calling close() is safe because any other thread using
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   327
         * the font we are closing() synchronizes all reading, so we
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   328
         * will not close the file while its in use.
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   329
         */
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   330
        if (fontFileToClose != null) {
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   331
            fontFileToClose.close();
6eb7f9aa0b05 6640532: Graphics.getFontMetrics() throws NullPointerException
prr
parents: 2
diff changeset
   332
        }
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
   333
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   334
90ce3da70b43 Initial load
duke
parents:
diff changeset
   335
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
   336
     * In the normal course of events, the pool of fonts can remain open
90ce3da70b43 Initial load
duke
parents:
diff changeset
   337
     * ready for quick access to their contents. The pool is sized so
90ce3da70b43 Initial load
duke
parents:
diff changeset
   338
     * that it is not an excessive consumer of system resources whilst
90ce3da70b43 Initial load
duke
parents:
diff changeset
   339
     * facilitating performance by providing ready access to the most
90ce3da70b43 Initial load
duke
parents:
diff changeset
   340
     * recently used set of font files.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   341
     * The only reason to call removeFromPool(..) is for a Font that
90ce3da70b43 Initial load
duke
parents:
diff changeset
   342
     * you want to to have GC'd. Currently this would apply only to fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
   343
     * created with java.awt.Font.createFont(..).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   344
     * In this case, the caller is expected to have arranged for the file
90ce3da70b43 Initial load
duke
parents:
diff changeset
   345
     * to be closed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   346
     * REMIND: consider how to know when a createFont created font should
90ce3da70b43 Initial load
duke
parents:
diff changeset
   347
     * be closed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   348
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   349
    public static void removeFromPool(FileFont font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   350
        synchronized (fontFileCache) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   351
            for (int i=0; i<CHANNELPOOLSIZE; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   352
                if (fontFileCache[i] == font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   353
                    fontFileCache[i] = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   354
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   355
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   356
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   357
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   358
90ce3da70b43 Initial load
duke
parents:
diff changeset
   359
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   360
     * This method is provided for internal and exclusive use by Swing.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   361
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   362
     * @param font representing a physical font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   363
     * @return true if the underlying font is a TrueType or OpenType font
90ce3da70b43 Initial load
duke
parents:
diff changeset
   364
     * that claims to support the Microsoft Windows encoding corresponding to
90ce3da70b43 Initial load
duke
parents:
diff changeset
   365
     * the default file.encoding property of this JRE instance.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   366
     * This narrow value is useful for Swing to decide if the font is useful
90ce3da70b43 Initial load
duke
parents:
diff changeset
   367
     * for the the Windows Look and Feel, or, if a  composite font should be
90ce3da70b43 Initial load
duke
parents:
diff changeset
   368
     * used instead.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   369
     * The information used to make the decision is obtained from
90ce3da70b43 Initial load
duke
parents:
diff changeset
   370
     * the ulCodePageRange fields in the font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   371
     * A caller can use isLogicalFont(Font) in this class before calling
90ce3da70b43 Initial load
duke
parents:
diff changeset
   372
     * this method and would not need to call this method if that
90ce3da70b43 Initial load
duke
parents:
diff changeset
   373
     * returns true.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   374
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   375
//     static boolean fontSupportsDefaultEncoding(Font font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   376
//      String encoding =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   377
//          (String) java.security.AccessController.doPrivileged(
90ce3da70b43 Initial load
duke
parents:
diff changeset
   378
//                new sun.security.action.GetPropertyAction("file.encoding"));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   379
90ce3da70b43 Initial load
duke
parents:
diff changeset
   380
//      if (encoding == null || font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   381
//          return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   382
//      }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   383
90ce3da70b43 Initial load
duke
parents:
diff changeset
   384
//      encoding = encoding.toLowerCase(Locale.ENGLISH);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   385
90ce3da70b43 Initial load
duke
parents:
diff changeset
   386
//      return FontManager.fontSupportsEncoding(font, encoding);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   387
//     }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   388
90ce3da70b43 Initial load
duke
parents:
diff changeset
   389
    /* Revise the implementation to in fact mean "font is a composite font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   390
     * This ensures that Swing components will always benefit from the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   391
     * fall back fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
   392
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   393
    public static boolean fontSupportsDefaultEncoding(Font font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   394
        return getFont2D(font) instanceof CompositeFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   395
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   396
90ce3da70b43 Initial load
duke
parents:
diff changeset
   397
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
   398
     * This method is provided for internal and exclusive use by Swing.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   399
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   400
     * It may be used in conjunction with fontSupportsDefaultEncoding(Font)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   401
     * In the event that a desktop properties font doesn't directly
90ce3da70b43 Initial load
duke
parents:
diff changeset
   402
     * support the default encoding, (ie because the host OS supports
90ce3da70b43 Initial load
duke
parents:
diff changeset
   403
     * adding support for the current locale automatically for native apps),
90ce3da70b43 Initial load
duke
parents:
diff changeset
   404
     * then Swing calls this method to get a font which  uses the specified
90ce3da70b43 Initial load
duke
parents:
diff changeset
   405
     * font for the code points it covers, but also supports this locale
90ce3da70b43 Initial load
duke
parents:
diff changeset
   406
     * just as the standard composite fonts do.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   407
     * Note: this will over-ride any setting where an application
90ce3da70b43 Initial load
duke
parents:
diff changeset
   408
     * specifies it prefers locale specific composite fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   409
     * The logic for this, is that this method is used only where the user or
90ce3da70b43 Initial load
duke
parents:
diff changeset
   410
     * application has specified that the native L&F be used, and that
90ce3da70b43 Initial load
duke
parents:
diff changeset
   411
     * we should honour that request to use the same font as native apps use.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   412
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   413
     * The behaviour of this method is to construct a new composite
90ce3da70b43 Initial load
duke
parents:
diff changeset
   414
     * Font object that uses the specified physical font as its first
90ce3da70b43 Initial load
duke
parents:
diff changeset
   415
     * component, and adds all the components of "dialog" as fall back
90ce3da70b43 Initial load
duke
parents:
diff changeset
   416
     * components.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   417
     * The method currently assumes that only the size and style attributes
90ce3da70b43 Initial load
duke
parents:
diff changeset
   418
     * are set on the specified font. It doesn't copy the font transform or
90ce3da70b43 Initial load
duke
parents:
diff changeset
   419
     * other attributes because they aren't set on a font created from
90ce3da70b43 Initial load
duke
parents:
diff changeset
   420
     * the desktop. This will need to be fixed if use is broadened.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   421
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   422
     * Operations such as Font.deriveFont will work properly on the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   423
     * font returned by this method for deriving a different point size.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   424
     * Additionally it tries to support a different style by calling
90ce3da70b43 Initial load
duke
parents:
diff changeset
   425
     * getNewComposite() below. That also supports replacing slot zero
90ce3da70b43 Initial load
duke
parents:
diff changeset
   426
     * with a different physical font but that is expected to be "rare".
90ce3da70b43 Initial load
duke
parents:
diff changeset
   427
     * Deriving with a different style is needed because its been shown
90ce3da70b43 Initial load
duke
parents:
diff changeset
   428
     * that some applications try to do this for Swing FontUIResources.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   429
     * Also operations such as new Font(font.getFontName(..), Font.PLAIN, 14);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   430
     * will NOT yield the same result, as the new underlying CompositeFont
90ce3da70b43 Initial load
duke
parents:
diff changeset
   431
     * cannot be "looked up" in the font registry.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   432
     * This returns a FontUIResource as that is the Font sub-class needed
90ce3da70b43 Initial load
duke
parents:
diff changeset
   433
     * by Swing.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   434
     * Suggested usage is something like :
90ce3da70b43 Initial load
duke
parents:
diff changeset
   435
     * FontUIResource fuir;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   436
     * Font desktopFont = getDesktopFont(..);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   437
     * // NOTE even if fontSupportsDefaultEncoding returns true because
90ce3da70b43 Initial load
duke
parents:
diff changeset
   438
     * // you get Tahoma and are running in an English locale, you may
90ce3da70b43 Initial load
duke
parents:
diff changeset
   439
     * // still want to just call getCompositeFontUIResource() anyway
90ce3da70b43 Initial load
duke
parents:
diff changeset
   440
     * // as only then will you get fallback fonts - eg for CJK.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   441
     * if (FontManager.fontSupportsDefaultEncoding(desktopFont)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   442
     *   fuir = new FontUIResource(..);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   443
     * } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   444
     *   fuir = FontManager.getCompositeFontUIResource(desktopFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   445
     * }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   446
     * return fuir;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   447
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   448
    public static FontUIResource getCompositeFontUIResource(Font font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   449
90ce3da70b43 Initial load
duke
parents:
diff changeset
   450
        FontUIResource fuir =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   451
            new FontUIResource(font.getName(),font.getStyle(),font.getSize());
90ce3da70b43 Initial load
duke
parents:
diff changeset
   452
        Font2D font2D = getFont2D(font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   453
90ce3da70b43 Initial load
duke
parents:
diff changeset
   454
        if (!(font2D instanceof PhysicalFont)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   455
            /* Swing should only be calling this when a font is obtained
90ce3da70b43 Initial load
duke
parents:
diff changeset
   456
             * from desktop properties, so should generally be a physical font,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   457
             * an exception might be for names like "MS Serif" which are
90ce3da70b43 Initial load
duke
parents:
diff changeset
   458
             * automatically mapped to "Serif", so there's no need to do
90ce3da70b43 Initial load
duke
parents:
diff changeset
   459
             * anything special in that case. But note that suggested usage
90ce3da70b43 Initial load
duke
parents:
diff changeset
   460
             * is first to call fontSupportsDefaultEncoding(Font) and this
90ce3da70b43 Initial load
duke
parents:
diff changeset
   461
             * method should not be called if that were to return true.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   462
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   463
             return fuir;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   464
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   465
90ce3da70b43 Initial load
duke
parents:
diff changeset
   466
        CompositeFont dialog2D =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   467
          (CompositeFont)findFont2D("dialog", font.getStyle(), NO_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   468
        if (dialog2D == null) { /* shouldn't happen */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   469
            return fuir;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   470
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   471
        PhysicalFont physicalFont = (PhysicalFont)font2D;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   472
        CompositeFont compFont = new CompositeFont(physicalFont, dialog2D);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   473
        setFont2D(fuir, compFont.handle);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   474
        /* marking this as a created font is needed as only created fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
   475
         * copy their creator's handles.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   476
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   477
        setCreatedFont(fuir);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   478
        return fuir;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   479
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   480
90ce3da70b43 Initial load
duke
parents:
diff changeset
   481
    public static Font2DHandle getNewComposite(String family, int style,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   482
                                               Font2DHandle handle) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   483
90ce3da70b43 Initial load
duke
parents:
diff changeset
   484
        if (!(handle.font2D instanceof CompositeFont)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   485
            return handle;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   486
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   487
90ce3da70b43 Initial load
duke
parents:
diff changeset
   488
        CompositeFont oldComp = (CompositeFont)handle.font2D;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   489
        PhysicalFont oldFont = oldComp.getSlotFont(0);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   490
90ce3da70b43 Initial load
duke
parents:
diff changeset
   491
        if (family == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   492
            family = oldFont.getFamilyName(null);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   493
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   494
        if (style == -1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   495
            style = oldComp.getStyle();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   496
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   497
90ce3da70b43 Initial load
duke
parents:
diff changeset
   498
        Font2D newFont = findFont2D(family, style, NO_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   499
        if (!(newFont instanceof PhysicalFont)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   500
            newFont = oldFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   501
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   502
        PhysicalFont physicalFont = (PhysicalFont)newFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   503
        CompositeFont dialog2D =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   504
            (CompositeFont)findFont2D("dialog", style, NO_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   505
        if (dialog2D == null) { /* shouldn't happen */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   506
            return handle;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   507
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   508
        CompositeFont compFont = new CompositeFont(physicalFont, dialog2D);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   509
        Font2DHandle newHandle = new Font2DHandle(compFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   510
        return newHandle;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   511
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   512
90ce3da70b43 Initial load
duke
parents:
diff changeset
   513
    public static native void setFont2D(Font font, Font2DHandle font2DHandle);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   514
90ce3da70b43 Initial load
duke
parents:
diff changeset
   515
    private static native boolean isCreatedFont(Font font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   516
    private static native void setCreatedFont(Font font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   517
90ce3da70b43 Initial load
duke
parents:
diff changeset
   518
    public static void registerCompositeFont(String compositeName,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   519
                                             String[] componentFileNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   520
                                             String[] componentNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   521
                                             int numMetricsSlots,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   522
                                             int[] exclusionRanges,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   523
                                             int[] exclusionMaxIndex,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   524
                                             boolean defer) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   525
90ce3da70b43 Initial load
duke
parents:
diff changeset
   526
        CompositeFont cf = new CompositeFont(compositeName,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   527
                                             componentFileNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   528
                                             componentNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   529
                                             numMetricsSlots,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   530
                                             exclusionRanges,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   531
                                             exclusionMaxIndex, defer);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   532
        addCompositeToFontList(cf, Font2D.FONT_CONFIG_RANK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   533
        synchronized (compFonts) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   534
            compFonts[maxCompFont++] = cf;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   535
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   536
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   537
90ce3da70b43 Initial load
duke
parents:
diff changeset
   538
    /* This variant is used only when the application specifies
90ce3da70b43 Initial load
duke
parents:
diff changeset
   539
     * a variant of composite fonts which prefers locale specific or
90ce3da70b43 Initial load
duke
parents:
diff changeset
   540
     * proportional fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   541
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   542
    public static void registerCompositeFont(String compositeName,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   543
                                             String[] componentFileNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   544
                                             String[] componentNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   545
                                             int numMetricsSlots,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   546
                                             int[] exclusionRanges,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   547
                                             int[] exclusionMaxIndex,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   548
                                             boolean defer,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   549
                                             ConcurrentHashMap<String, Font2D>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   550
                                             altNameCache) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   551
90ce3da70b43 Initial load
duke
parents:
diff changeset
   552
        CompositeFont cf = new CompositeFont(compositeName,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   553
                                             componentFileNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   554
                                             componentNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   555
                                             numMetricsSlots,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   556
                                             exclusionRanges,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   557
                                             exclusionMaxIndex, defer);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   558
        /* if the cache has an existing composite for this case, make
90ce3da70b43 Initial load
duke
parents:
diff changeset
   559
         * its handle point to this new font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   560
         * This ensures that when the altNameCache that is passed in
90ce3da70b43 Initial load
duke
parents:
diff changeset
   561
         * is the global mapNameCache - ie we are running as an application -
90ce3da70b43 Initial load
duke
parents:
diff changeset
   562
         * that any statically created java.awt.Font instances which already
90ce3da70b43 Initial load
duke
parents:
diff changeset
   563
         * have a Font2D instance will have that re-directed to the new Font
90ce3da70b43 Initial load
duke
parents:
diff changeset
   564
         * on subsequent uses. This is particularly important for "the"
90ce3da70b43 Initial load
duke
parents:
diff changeset
   565
         * default font instance, or similar cases where a UI toolkit (eg
90ce3da70b43 Initial load
duke
parents:
diff changeset
   566
         * Swing) has cached a java.awt.Font. Note that if Swing is using
90ce3da70b43 Initial load
duke
parents:
diff changeset
   567
         * a custom composite APIs which update the standard composites have
90ce3da70b43 Initial load
duke
parents:
diff changeset
   568
         * no effect - this is typically the case only when using the Windows
90ce3da70b43 Initial load
duke
parents:
diff changeset
   569
         * L&F where these APIs would conflict with that L&F anyway.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   570
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   571
        Font2D oldFont = (Font2D)
90ce3da70b43 Initial load
duke
parents:
diff changeset
   572
            altNameCache.get(compositeName.toLowerCase(Locale.ENGLISH));
90ce3da70b43 Initial load
duke
parents:
diff changeset
   573
        if (oldFont instanceof CompositeFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   574
            oldFont.handle.font2D = cf;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   575
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   576
        altNameCache.put(compositeName.toLowerCase(Locale.ENGLISH), cf);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   577
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   578
90ce3da70b43 Initial load
duke
parents:
diff changeset
   579
    private static void addCompositeToFontList(CompositeFont f, int rank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   580
90ce3da70b43 Initial load
duke
parents:
diff changeset
   581
        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   582
            logger.info("Add to Family "+ f.familyName +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   583
                        ", Font " + f.fullName + " rank="+rank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   584
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   585
        f.setRank(rank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   586
        compositeFonts.put(f.fullName, f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   587
        fullNameToFont.put(f.fullName.toLowerCase(Locale.ENGLISH), f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   588
90ce3da70b43 Initial load
duke
parents:
diff changeset
   589
        FontFamily family = FontFamily.getFamily(f.familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   590
        if (family == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   591
            family = new FontFamily(f.familyName, true, rank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   592
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   593
        family.setFont(f, f.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   594
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   595
90ce3da70b43 Initial load
duke
parents:
diff changeset
   596
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
   597
     * Systems may have fonts with the same name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   598
     * We want to register only one of such fonts (at least until
90ce3da70b43 Initial load
duke
parents:
diff changeset
   599
     * such time as there might be APIs which can accommodate > 1).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   600
     * Rank is 1) font configuration fonts, 2) JRE fonts, 3) OT/TT fonts,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   601
     * 4) Type1 fonts, 5) native fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   602
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   603
     * If the new font has the same name as the old font, the higher
90ce3da70b43 Initial load
duke
parents:
diff changeset
   604
     * ranked font gets added, replacing the lower ranked one.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   605
     * If the fonts are of equal rank, then make a special case of
90ce3da70b43 Initial load
duke
parents:
diff changeset
   606
     * font configuration rank fonts, which are on closer inspection,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   607
     * OT/TT fonts such that the larger font is registered. This is
90ce3da70b43 Initial load
duke
parents:
diff changeset
   608
     * a heuristic since a font may be "larger" in the sense of more
90ce3da70b43 Initial load
duke
parents:
diff changeset
   609
     * code points, or be a larger "file" because it has more bitmaps.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   610
     * So it is possible that using filesize may lead to less glyphs, and
90ce3da70b43 Initial load
duke
parents:
diff changeset
   611
     * using glyphs may lead to lower quality display. Probably number
90ce3da70b43 Initial load
duke
parents:
diff changeset
   612
     * of glyphs is the ideal, but filesize is information we already
90ce3da70b43 Initial load
duke
parents:
diff changeset
   613
     * have and is good enough for the known cases.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   614
     * Also don't want to register fonts that match JRE font families
90ce3da70b43 Initial load
duke
parents:
diff changeset
   615
     * but are coming from a source other than the JRE.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   616
     * This will ensure that we will algorithmically style the JRE
90ce3da70b43 Initial load
duke
parents:
diff changeset
   617
     * plain font and get the same set of glyphs for all styles.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   618
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
   619
     * Note that this method returns a value
90ce3da70b43 Initial load
duke
parents:
diff changeset
   620
     * if it returns the same object as its argument that means this
90ce3da70b43 Initial load
duke
parents:
diff changeset
   621
     * font was newly registered.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   622
     * If it returns a different object it means this font already exists,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   623
     * and you should use that one.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   624
     * If it returns null means this font was not registered and none
90ce3da70b43 Initial load
duke
parents:
diff changeset
   625
     * in that name is registered. The caller must find a substitute
90ce3da70b43 Initial load
duke
parents:
diff changeset
   626
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   627
    private static PhysicalFont addToFontList(PhysicalFont f, int rank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   628
90ce3da70b43 Initial load
duke
parents:
diff changeset
   629
        String fontName = f.fullName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   630
        String familyName = f.familyName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   631
        if (fontName == null || "".equals(fontName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   632
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   633
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   634
        if (compositeFonts.containsKey(fontName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   635
            /* Don't register any font that has the same name as a composite */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   636
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   637
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   638
        f.setRank(rank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   639
        if (!physicalFonts.containsKey(fontName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   640
            if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   641
                logger.info("Add to Family "+familyName +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   642
                            ", Font " + fontName + " rank="+rank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   643
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   644
            physicalFonts.put(fontName, f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   645
            FontFamily family = FontFamily.getFamily(familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   646
            if (family == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   647
                family = new FontFamily(familyName, false, rank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   648
                family.setFont(f, f.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   649
            } else if (family.getRank() >= rank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   650
                family.setFont(f, f.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   651
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   652
            fullNameToFont.put(fontName.toLowerCase(Locale.ENGLISH), f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   653
            return f;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   654
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   655
            PhysicalFont newFont = f;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   656
            PhysicalFont oldFont = physicalFonts.get(fontName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   657
            if (oldFont == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   658
                return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   659
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   660
            /* If the new font is of an equal or higher rank, it is a
90ce3da70b43 Initial load
duke
parents:
diff changeset
   661
             * candidate to replace the current one, subject to further tests.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   662
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   663
            if (oldFont.getRank() >= rank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   664
90ce3da70b43 Initial load
duke
parents:
diff changeset
   665
                /* All fonts initialise their mapper when first
90ce3da70b43 Initial load
duke
parents:
diff changeset
   666
                 * used. If the mapper is non-null then this font
90ce3da70b43 Initial load
duke
parents:
diff changeset
   667
                 * has been accessed at least once. In that case
90ce3da70b43 Initial load
duke
parents:
diff changeset
   668
                 * do not replace it. This may be overly stringent,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   669
                 * but its probably better not to replace a font that
90ce3da70b43 Initial load
duke
parents:
diff changeset
   670
                 * someone is already using without a compelling reason.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   671
                 * Additionally the primary case where it is known
90ce3da70b43 Initial load
duke
parents:
diff changeset
   672
                 * this behaviour is important is in certain composite
90ce3da70b43 Initial load
duke
parents:
diff changeset
   673
                 * fonts, and since all the components of a given
90ce3da70b43 Initial load
duke
parents:
diff changeset
   674
                 * composite are usually initialised together this
90ce3da70b43 Initial load
duke
parents:
diff changeset
   675
                 * is unlikely. For this to be a problem, there would
90ce3da70b43 Initial load
duke
parents:
diff changeset
   676
                 * have to be a case where two different composites used
90ce3da70b43 Initial load
duke
parents:
diff changeset
   677
                 * different versions of the same-named font, and they
90ce3da70b43 Initial load
duke
parents:
diff changeset
   678
                 * were initialised and used at separate times.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   679
                 * In that case we continue on and allow the new font to
90ce3da70b43 Initial load
duke
parents:
diff changeset
   680
                 * be installed, but replaceFont will continue to allow
90ce3da70b43 Initial load
duke
parents:
diff changeset
   681
                 * the original font to be used in Composite fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   682
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   683
                if (oldFont.mapper != null && rank > Font2D.FONT_CONFIG_RANK) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   684
                    return oldFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   685
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   686
90ce3da70b43 Initial load
duke
parents:
diff changeset
   687
                /* Normally we require a higher rank to replace a font,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   688
                 * but as a special case, if the two fonts are the same rank,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   689
                 * and are instances of TrueTypeFont we want the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   690
                 * more complete (larger) one.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   691
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   692
                if (oldFont.getRank() == rank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   693
                    if (oldFont instanceof TrueTypeFont &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
   694
                        newFont instanceof TrueTypeFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   695
                        TrueTypeFont oldTTFont = (TrueTypeFont)oldFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   696
                        TrueTypeFont newTTFont = (TrueTypeFont)newFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   697
                        if (oldTTFont.fileSize >= newTTFont.fileSize) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   698
                            return oldFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   699
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   700
                    } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   701
                        return oldFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   702
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   703
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   704
                /* Don't replace ever JRE fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   705
                 * This test is in case a font configuration references
90ce3da70b43 Initial load
duke
parents:
diff changeset
   706
                 * a Lucida font, which has been mapped to a Lucida
90ce3da70b43 Initial load
duke
parents:
diff changeset
   707
                 * from the host O/S. The assumption here is that any
90ce3da70b43 Initial load
duke
parents:
diff changeset
   708
                 * such font configuration file is probably incorrect, or
90ce3da70b43 Initial load
duke
parents:
diff changeset
   709
                 * the host O/S version is for the use of AWT.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   710
                 * In other words if we reach here, there's a possible
90ce3da70b43 Initial load
duke
parents:
diff changeset
   711
                 * problem with our choice of font configuration fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   712
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   713
                if (oldFont.platName.startsWith(
90ce3da70b43 Initial load
duke
parents:
diff changeset
   714
                           SunGraphicsEnvironment.jreFontDirName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   715
                    if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   716
                        logger.warning("Unexpected attempt to replace a JRE " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   717
                                       " font " + fontName + " from " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   718
                                        oldFont.platName +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   719
                                       " with " + newFont.platName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   720
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   721
                    return oldFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   722
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   723
90ce3da70b43 Initial load
duke
parents:
diff changeset
   724
                if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   725
                    logger.info("Replace in Family " + familyName +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   726
                                ",Font " + fontName + " new rank="+rank +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   727
                                " from " + oldFont.platName +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   728
                                " with " + newFont.platName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   729
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   730
                replaceFont(oldFont, newFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   731
                physicalFonts.put(fontName, newFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   732
                fullNameToFont.put(fontName.toLowerCase(Locale.ENGLISH),
90ce3da70b43 Initial load
duke
parents:
diff changeset
   733
                                   newFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   734
90ce3da70b43 Initial load
duke
parents:
diff changeset
   735
                FontFamily family = FontFamily.getFamily(familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   736
                if (family == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   737
                    family = new FontFamily(familyName, false, rank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   738
                    family.setFont(newFont, newFont.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   739
                } else if (family.getRank() >= rank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   740
                    family.setFont(newFont, newFont.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   741
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   742
                return newFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   743
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   744
                return oldFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   745
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   746
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   747
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   748
90ce3da70b43 Initial load
duke
parents:
diff changeset
   749
    public static Font2D[] getRegisteredFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   750
        PhysicalFont[] physFonts = getPhysicalFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   751
        int mcf = maxCompFont; /* for MT-safety */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   752
        Font2D[] regFonts = new Font2D[physFonts.length+mcf];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   753
        System.arraycopy(compFonts, 0, regFonts, 0, mcf);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   754
        System.arraycopy(physFonts, 0, regFonts, mcf, physFonts.length);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   755
        return regFonts;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   756
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   757
90ce3da70b43 Initial load
duke
parents:
diff changeset
   758
    public static PhysicalFont[] getPhysicalFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   759
        return physicalFonts.values().toArray(new PhysicalFont[0]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   760
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   761
90ce3da70b43 Initial load
duke
parents:
diff changeset
   762
90ce3da70b43 Initial load
duke
parents:
diff changeset
   763
    /* The class FontRegistrationInfo is used when a client says not
90ce3da70b43 Initial load
duke
parents:
diff changeset
   764
     * to register a font immediately. This mechanism is used to defer
90ce3da70b43 Initial load
duke
parents:
diff changeset
   765
     * initialisation of all the components of composite fonts at JRE
90ce3da70b43 Initial load
duke
parents:
diff changeset
   766
     * start-up. The CompositeFont class is "aware" of this and when it
90ce3da70b43 Initial load
duke
parents:
diff changeset
   767
     * is first used it asks for the registration of its components.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   768
     * Also in the event that any physical font is requested the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   769
     * deferred fonts are initialised before triggering a search of the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   770
     * system.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   771
     * Two maps are used. One to track the deferred fonts. The
90ce3da70b43 Initial load
duke
parents:
diff changeset
   772
     * other to track the fonts that have been initialised through this
90ce3da70b43 Initial load
duke
parents:
diff changeset
   773
     * mechanism.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   774
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   775
90ce3da70b43 Initial load
duke
parents:
diff changeset
   776
    private static final class FontRegistrationInfo {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   777
90ce3da70b43 Initial load
duke
parents:
diff changeset
   778
        String fontFilePath;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   779
        String[] nativeNames;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   780
        int fontFormat;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   781
        boolean javaRasterizer;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   782
        int fontRank;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   783
90ce3da70b43 Initial load
duke
parents:
diff changeset
   784
        FontRegistrationInfo(String fontPath, String[] names, int format,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   785
                             boolean useJavaRasterizer, int rank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   786
            this.fontFilePath = fontPath;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   787
            this.nativeNames = names;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   788
            this.fontFormat = format;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   789
            this.javaRasterizer = useJavaRasterizer;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   790
            this.fontRank = rank;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   791
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   792
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   793
90ce3da70b43 Initial load
duke
parents:
diff changeset
   794
    private static final ConcurrentHashMap<String, FontRegistrationInfo>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   795
        deferredFontFiles =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   796
        new ConcurrentHashMap<String, FontRegistrationInfo>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   797
    private static final ConcurrentHashMap<String, Font2DHandle>
90ce3da70b43 Initial load
duke
parents:
diff changeset
   798
        initialisedFonts = new ConcurrentHashMap<String, Font2DHandle>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   799
90ce3da70b43 Initial load
duke
parents:
diff changeset
   800
    /* Remind: possibly enhance initialiseDeferredFonts() to be
90ce3da70b43 Initial load
duke
parents:
diff changeset
   801
     * optionally given a name and a style and it could stop when it
90ce3da70b43 Initial load
duke
parents:
diff changeset
   802
     * finds that font - but this would be a problem if two of the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   803
     * fonts reference the same font face name (cf the Solaris
90ce3da70b43 Initial load
duke
parents:
diff changeset
   804
     * euro fonts).
90ce3da70b43 Initial load
duke
parents:
diff changeset
   805
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   806
    public static synchronized void initialiseDeferredFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   807
        for (String fileName : deferredFontFiles.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   808
            initialiseDeferredFont(fileName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   809
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   810
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   811
90ce3da70b43 Initial load
duke
parents:
diff changeset
   812
    public static synchronized void registerDeferredJREFonts(String jreDir) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   813
        for (FontRegistrationInfo info : deferredFontFiles.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   814
            if (info.fontFilePath != null &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
   815
                info.fontFilePath.startsWith(jreDir)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   816
                initialiseDeferredFont(info.fontFilePath);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   817
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   818
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   819
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   820
90ce3da70b43 Initial load
duke
parents:
diff changeset
   821
    /* We keep a map of the files which contain the Lucida fonts so we
90ce3da70b43 Initial load
duke
parents:
diff changeset
   822
     * don't need to search for them.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   823
     * But since we know what fonts these files contain, we can also avoid
90ce3da70b43 Initial load
duke
parents:
diff changeset
   824
     * opening them to look for a font name we don't recognise - see
90ce3da70b43 Initial load
duke
parents:
diff changeset
   825
     * findDeferredFont().
90ce3da70b43 Initial load
duke
parents:
diff changeset
   826
     * For typical cases where the font isn't a JRE one the overhead is
90ce3da70b43 Initial load
duke
parents:
diff changeset
   827
     * this method call, HashMap.get() and null reference test, then
90ce3da70b43 Initial load
duke
parents:
diff changeset
   828
     * a boolean test of noOtherJREFontFiles.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   829
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   830
    private static PhysicalFont findJREDeferredFont(String name, int style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   831
90ce3da70b43 Initial load
duke
parents:
diff changeset
   832
        PhysicalFont physicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   833
        String nameAndStyle = name.toLowerCase(Locale.ENGLISH) + style;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   834
        String fileName = jreFontMap.get(nameAndStyle);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   835
        if (fileName != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   836
            initSGEnv(); /* ensure jreFontDirName is initialised */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   837
            fileName = SunGraphicsEnvironment.jreFontDirName +
90ce3da70b43 Initial load
duke
parents:
diff changeset
   838
                File.separator + fileName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   839
            if (deferredFontFiles.get(fileName) != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   840
                physicalFont = initialiseDeferredFont(fileName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   841
                if (physicalFont != null &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
   842
                    (physicalFont.getFontName(null).equalsIgnoreCase(name) ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   843
                     physicalFont.getFamilyName(null).equalsIgnoreCase(name))
90ce3da70b43 Initial load
duke
parents:
diff changeset
   844
                    && physicalFont.style == style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   845
                    return physicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   846
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   847
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   848
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   849
90ce3da70b43 Initial load
duke
parents:
diff changeset
   850
        /* Iterate over the deferred font files looking for any in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   851
         * jre directory that we didn't recognise, open each of these.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   852
         * In almost all installations this will quickly fall through
90ce3da70b43 Initial load
duke
parents:
diff changeset
   853
         * because only the Lucidas will be present and jreOtherFontFiles
90ce3da70b43 Initial load
duke
parents:
diff changeset
   854
         * will be empty.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   855
         * noOtherJREFontFiles is used so we can skip this block as soon
90ce3da70b43 Initial load
duke
parents:
diff changeset
   856
         * as its determined that its not needed - almost always after the
90ce3da70b43 Initial load
duke
parents:
diff changeset
   857
         * very first time through.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   858
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   859
        if (noOtherJREFontFiles) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   860
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   861
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   862
        synchronized (jreLucidaFontFiles) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   863
            if (jreOtherFontFiles == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   864
                HashSet<String> otherFontFiles = new HashSet<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   865
                for (String deferredFile : deferredFontFiles.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   866
                    File file = new File(deferredFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   867
                    String dir = file.getParent();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   868
                    String fname = file.getName();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   869
                    /* skip names which aren't absolute, aren't in the JRE
90ce3da70b43 Initial load
duke
parents:
diff changeset
   870
                     * directory, or are known Lucida fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   871
                     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   872
                    if (dir == null ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   873
                        !dir.equals(SunGraphicsEnvironment.jreFontDirName) ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   874
                        jreLucidaFontFiles.contains(fname)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   875
                        continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   876
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   877
                    otherFontFiles.add(deferredFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   878
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   879
                jreOtherFontFiles = otherFontFiles.toArray(STR_ARRAY);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   880
                if (jreOtherFontFiles.length == 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   881
                    noOtherJREFontFiles = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   882
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   883
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   884
90ce3da70b43 Initial load
duke
parents:
diff changeset
   885
            for (int i=0; i<jreOtherFontFiles.length;i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   886
                fileName = jreOtherFontFiles[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
   887
                if (fileName == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   888
                    continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   889
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   890
                jreOtherFontFiles[i] = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   891
                physicalFont = initialiseDeferredFont(fileName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   892
                if (physicalFont != null &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
   893
                    (physicalFont.getFontName(null).equalsIgnoreCase(name) ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   894
                     physicalFont.getFamilyName(null).equalsIgnoreCase(name))
90ce3da70b43 Initial load
duke
parents:
diff changeset
   895
                    && physicalFont.style == style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   896
                    return physicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   897
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   898
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   899
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   900
90ce3da70b43 Initial load
duke
parents:
diff changeset
   901
        return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   902
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   903
90ce3da70b43 Initial load
duke
parents:
diff changeset
   904
    /* This skips JRE installed fonts. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   905
    private static PhysicalFont findOtherDeferredFont(String name, int style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   906
        for (String fileName : deferredFontFiles.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   907
            File file = new File(fileName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   908
            String dir = file.getParent();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   909
            String fname = file.getName();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   910
            if (dir != null &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
   911
                dir.equals(SunGraphicsEnvironment.jreFontDirName) &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
   912
                jreLucidaFontFiles.contains(fname)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   913
                continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   914
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   915
            PhysicalFont physicalFont = initialiseDeferredFont(fileName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   916
            if (physicalFont != null &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
   917
                (physicalFont.getFontName(null).equalsIgnoreCase(name) ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
   918
                physicalFont.getFamilyName(null).equalsIgnoreCase(name)) &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
   919
                physicalFont.style == style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   920
                return physicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   921
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   922
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   923
        return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   924
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   925
90ce3da70b43 Initial load
duke
parents:
diff changeset
   926
    private static PhysicalFont findDeferredFont(String name, int style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   927
90ce3da70b43 Initial load
duke
parents:
diff changeset
   928
        PhysicalFont physicalFont = findJREDeferredFont(name, style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   929
        if (physicalFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   930
            return physicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   931
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   932
            return findOtherDeferredFont(name, style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   933
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   934
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   935
90ce3da70b43 Initial load
duke
parents:
diff changeset
   936
    public static void registerDeferredFont(String fileNameKey,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   937
                                            String fullPathName,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   938
                                            String[] nativeNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   939
                                            int fontFormat,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   940
                                            boolean useJavaRasterizer,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   941
                                            int fontRank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   942
        FontRegistrationInfo regInfo =
90ce3da70b43 Initial load
duke
parents:
diff changeset
   943
            new FontRegistrationInfo(fullPathName, nativeNames, fontFormat,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   944
                                     useJavaRasterizer, fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   945
        deferredFontFiles.put(fileNameKey, regInfo);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   946
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   947
90ce3da70b43 Initial load
duke
parents:
diff changeset
   948
90ce3da70b43 Initial load
duke
parents:
diff changeset
   949
    public static synchronized
90ce3da70b43 Initial load
duke
parents:
diff changeset
   950
         PhysicalFont initialiseDeferredFont(String fileNameKey) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   951
90ce3da70b43 Initial load
duke
parents:
diff changeset
   952
        if (fileNameKey == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   953
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   954
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   955
        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   956
            logger.info("Opening deferred font file " + fileNameKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   957
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   958
90ce3da70b43 Initial load
duke
parents:
diff changeset
   959
        PhysicalFont physicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   960
        FontRegistrationInfo regInfo = deferredFontFiles.get(fileNameKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   961
        if (regInfo != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   962
            deferredFontFiles.remove(fileNameKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   963
            physicalFont = registerFontFile(regInfo.fontFilePath,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   964
                                            regInfo.nativeNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   965
                                            regInfo.fontFormat,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   966
                                            regInfo.javaRasterizer,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   967
                                            regInfo.fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   968
90ce3da70b43 Initial load
duke
parents:
diff changeset
   969
90ce3da70b43 Initial load
duke
parents:
diff changeset
   970
            if (physicalFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   971
                /* Store the handle, so that if a font is bad, we
90ce3da70b43 Initial load
duke
parents:
diff changeset
   972
                 * retrieve the substituted font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   973
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   974
                initialisedFonts.put(fileNameKey, physicalFont.handle);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   975
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   976
                initialisedFonts.put(fileNameKey,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   977
                                     getDefaultPhysicalFont().handle);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   978
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   979
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   980
            Font2DHandle handle = initialisedFonts.get(fileNameKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   981
            if (handle == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   982
                /* Probably shouldn't happen, but just in case */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   983
                physicalFont = getDefaultPhysicalFont();
90ce3da70b43 Initial load
duke
parents:
diff changeset
   984
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
   985
                physicalFont = (PhysicalFont)(handle.font2D);
90ce3da70b43 Initial load
duke
parents:
diff changeset
   986
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   987
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   988
        return physicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
   989
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
   990
90ce3da70b43 Initial load
duke
parents:
diff changeset
   991
    /* Note that the return value from this method is not always
90ce3da70b43 Initial load
duke
parents:
diff changeset
   992
     * derived from this file, and may be null. See addToFontList for
90ce3da70b43 Initial load
duke
parents:
diff changeset
   993
     * some explanation of this.
90ce3da70b43 Initial load
duke
parents:
diff changeset
   994
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
   995
    public static PhysicalFont registerFontFile(String fileName,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   996
                                                String[] nativeNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   997
                                                int fontFormat,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   998
                                                boolean useJavaRasterizer,
90ce3da70b43 Initial load
duke
parents:
diff changeset
   999
                                                int fontRank) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1000
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1001
        PhysicalFont regFont = registeredFontFiles.get(fileName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1002
        if (regFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1003
            return regFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1004
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1005
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1006
        PhysicalFont physicalFont = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1007
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1008
            String name;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1009
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1010
            switch (fontFormat) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1011
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1012
            case FontManager.FONTFORMAT_TRUETYPE:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1013
                int fn = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1014
                TrueTypeFont ttf;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1015
                do {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1016
                    ttf = new TrueTypeFont(fileName, nativeNames, fn++,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1017
                                           useJavaRasterizer);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1018
                    PhysicalFont pf = addToFontList(ttf, fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1019
                    if (physicalFont == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1020
                        physicalFont = pf;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1021
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1022
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1023
                while (fn < ttf.getFontCount());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1024
                break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1025
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1026
            case FontManager.FONTFORMAT_TYPE1:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1027
                Type1Font t1f = new Type1Font(fileName, nativeNames);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1028
                physicalFont = addToFontList(t1f, fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1029
                break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1030
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1031
            case FontManager.FONTFORMAT_NATIVE:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1032
                NativeFont nf = new NativeFont(fileName, false);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1033
                physicalFont = addToFontList(nf, fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1034
            default:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1035
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1036
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1037
            if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1038
                logger.info("Registered file " + fileName + " as font " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1039
                            physicalFont + " rank="  + fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1040
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1041
        } catch (FontFormatException ffe) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1042
            if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1043
                logger.warning("Unusable font: " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1044
                               fileName + " " + ffe.toString());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1045
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1046
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1047
        if (physicalFont != null &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1048
            fontFormat != FontManager.FONTFORMAT_NATIVE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1049
            registeredFontFiles.put(fileName, physicalFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1050
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1051
        return physicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1052
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1053
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1054
    public static void registerFonts(String[] fileNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1055
                                     String[][] nativeNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1056
                                     int fontCount,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1057
                                     int fontFormat,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1058
                                     boolean useJavaRasterizer,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1059
                                     int fontRank, boolean defer) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1060
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1061
        for (int i=0; i < fontCount; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1062
            if (defer) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1063
                registerDeferredFont(fileNames[i],fileNames[i], nativeNames[i],
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1064
                                     fontFormat, useJavaRasterizer, fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1065
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1066
                registerFontFile(fileNames[i], nativeNames[i],
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1067
                                 fontFormat, useJavaRasterizer, fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1068
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1069
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1070
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1071
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1072
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1073
     * This is the Physical font used when some other font on the system
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1074
     * can't be located. There has to be at least one font or the font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1075
     * system is not useful and the graphics environment cannot sustain
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1076
     * the Java platform.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1077
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1078
    public static PhysicalFont getDefaultPhysicalFont() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1079
        if (defaultPhysicalFont == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1080
            /* findFont2D will load all fonts before giving up the search.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1081
             * If the JRE Lucida isn't found (eg because the JRE fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1082
             * directory is missing), it could find another version of Lucida
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1083
             * from the host system. This is OK because at that point we are
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1084
             * trying to gracefully handle/recover from a system
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1085
             * misconfiguration and this is probably a reasonable substitution.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1086
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1087
            defaultPhysicalFont = (PhysicalFont)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1088
                findFont2D("Lucida Sans Regular", Font.PLAIN, NO_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1089
            if (defaultPhysicalFont == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1090
                defaultPhysicalFont = (PhysicalFont)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1091
                    findFont2D("Arial", Font.PLAIN, NO_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1092
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1093
            if (defaultPhysicalFont == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1094
                /* Because of the findFont2D call above, if we reach here, we
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1095
                 * know all fonts have already been loaded, just accept any
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1096
                 * match at this point. If this fails we are in real trouble
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1097
                 * and I don't know how to recover from there being absolutely
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1098
                 * no fonts anywhere on the system.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1099
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1100
                Iterator i = physicalFonts.values().iterator();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1101
                if (i.hasNext()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1102
                    defaultPhysicalFont = (PhysicalFont)i.next();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1103
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1104
                    throw new Error("Probable fatal error:No fonts found.");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1105
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1106
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1107
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1108
        return defaultPhysicalFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1109
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1110
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1111
    public static CompositeFont getDefaultLogicalFont(int style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1112
        return (CompositeFont)findFont2D("dialog", style, NO_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1113
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1114
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1115
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1116
     * return String representation of style prepended with "."
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1117
     * This is useful for performance to avoid unnecessary string operations.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1118
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1119
    private static String dotStyleStr(int num) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1120
        switch(num){
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1121
          case Font.BOLD:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1122
            return ".bold";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1123
          case Font.ITALIC:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1124
            return ".italic";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1125
          case Font.ITALIC | Font.BOLD:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1126
            return ".bolditalic";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1127
          default:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1128
            return ".plain";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1129
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1130
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1131
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1132
    static void initSGEnv() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1133
        if (sgEnv == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1134
            GraphicsEnvironment ge =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1135
                GraphicsEnvironment.getLocalGraphicsEnvironment();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1136
            if (ge instanceof HeadlessGraphicsEnvironment) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1137
                HeadlessGraphicsEnvironment hgEnv =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1138
                    (HeadlessGraphicsEnvironment)ge;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1139
                sgEnv = (SunGraphicsEnvironment)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1140
                    hgEnv.getSunGraphicsEnvironment();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1141
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1142
                sgEnv = (SunGraphicsEnvironment)ge;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1143
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1144
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1145
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1146
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1147
    /* This is implemented only on windows and is called from code that
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1148
     * executes only on windows. This isn't pretty but its not a precedent
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1149
     * in this file. This very probably should be cleaned up at some point.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1150
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1151
    private static native void
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1152
        populateFontFileNameMap(HashMap<String,String> fontToFileMap,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1153
                                HashMap<String,String> fontToFamilyNameMap,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1154
                                HashMap<String,ArrayList<String>>
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1155
                                familyToFontListMap,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1156
                                Locale locale);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1157
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1158
    /* Obtained from Platform APIs (windows only)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1159
     * Map from lower-case font full name to basename of font file.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1160
     * Eg "arial bold" -> ARIALBD.TTF.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1161
     * For TTC files, there is a mapping for each font in the file.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1162
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1163
    private static HashMap<String,String> fontToFileMap = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1164
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1165
    /* Obtained from Platform APIs (windows only)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1166
     * Map from lower-case font full name to the name of its font family
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1167
     * Eg "arial bold" -> "Arial"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1168
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1169
    private static HashMap<String,String> fontToFamilyNameMap = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1170
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1171
    /* Obtained from Platform APIs (windows only)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1172
     * Map from a lower-case family name to a list of full names of
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1173
     * the member fonts, eg:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1174
     * "arial" -> ["Arial", "Arial Bold", "Arial Italic","Arial Bold Italic"]
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1175
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1176
    private static HashMap<String,ArrayList<String>> familyToFontListMap= null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1177
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1178
    /* The directories which contain platform fonts */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1179
    private static String[] pathDirs = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1180
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1181
    private static boolean haveCheckedUnreferencedFontFiles;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1182
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1183
    private static String[] getFontFilesFromPath(boolean noType1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1184
        final FilenameFilter filter;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1185
        if (noType1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1186
            filter = SunGraphicsEnvironment.ttFilter;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1187
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1188
            filter = new SunGraphicsEnvironment.TTorT1Filter();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1189
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1190
        return (String[])AccessController.doPrivileged(new PrivilegedAction() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1191
            public Object run() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1192
                if (pathDirs.length == 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1193
                    File dir = new File(pathDirs[0]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1194
                    String[] files = dir.list(filter);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1195
                    if (files == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1196
                        return new String[0];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1197
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1198
                    for (int f=0; f<files.length; f++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1199
                        files[f] = files[f].toLowerCase();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1200
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1201
                    return files;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1202
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1203
                    ArrayList<String> fileList = new ArrayList<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1204
                    for (int i = 0; i< pathDirs.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1205
                        File dir = new File(pathDirs[i]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1206
                        String[] files = dir.list(filter);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1207
                        if (files == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1208
                            continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1209
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1210
                        for (int f=0; f<files.length ; f++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1211
                            fileList.add(files[f].toLowerCase());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1212
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1213
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1214
                    return fileList.toArray(STR_ARRAY);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1215
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1216
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1217
        });
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1218
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1219
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1220
    /* This is needed since some windows registry names don't match
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1221
     * the font names.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1222
     * - UPC styled font names have a double space, but the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1223
     * registry entry mapping to a file doesn't.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1224
     * - Marlett is in a hidden file not listed in the registry
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1225
     * - The registry advertises that the file david.ttf contains a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1226
     * font with the full name "David Regular" when in fact its
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1227
     * just "David".
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1228
     * Directly fix up these known cases as this is faster.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1229
     * If a font which doesn't match these known cases has no file,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1230
     * it may be a font that has been temporarily added to the known set
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1231
     * or it may be an installed font with a missing registry entry.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1232
     * Installed fonts are those in the windows font directories.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1233
     * Make a best effort attempt to locate these.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1234
     * We obtain the list of TrueType fonts in these directories and
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1235
     * filter out all the font files we already know about from the registry.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1236
     * What remains may be "bad" fonts, duplicate fonts, or perhaps the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1237
     * missing font(s) we are looking for.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1238
     * Open each of these files to find out.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1239
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1240
    private static void resolveWindowsFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1241
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1242
        ArrayList<String> unmappedFontNames = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1243
        for (String font : fontToFamilyNameMap.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1244
            String file = fontToFileMap.get(font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1245
            if (file == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1246
                if (font.indexOf("  ") > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1247
                    String newName = font.replaceFirst("  ", " ");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1248
                    file = fontToFileMap.get(newName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1249
                    /* If this name exists and isn't for a valid name
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1250
                     * replace the mapping to the file with this font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1251
                     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1252
                    if (file != null &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1253
                        !fontToFamilyNameMap.containsKey(newName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1254
                        fontToFileMap.remove(newName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1255
                        fontToFileMap.put(font, file);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1256
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1257
                } else if (font.equals("marlett")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1258
                    fontToFileMap.put(font, "marlett.ttf");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1259
                } else if (font.equals("david")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1260
                    file = fontToFileMap.get("david regular");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1261
                    if (file != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1262
                        fontToFileMap.remove("david regular");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1263
                        fontToFileMap.put("david", file);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1264
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1265
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1266
                    if (unmappedFontNames == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1267
                        unmappedFontNames = new ArrayList<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1268
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1269
                    unmappedFontNames.add(font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1270
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1271
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1272
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1273
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1274
        if (unmappedFontNames != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1275
            HashSet<String> unmappedFontFiles = new HashSet<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1276
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1277
            /* Every font key in fontToFileMap ought to correspond to a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1278
             * font key in fontToFamilyNameMap. Entries that don't seem
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1279
             * to correspond are likely fonts that were named differently
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1280
             * by GDI than in the registry. One known cause of this is when
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1281
             * Windows has had its regional settings changed so that from
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1282
             * GDI we get a localised (eg Chinese or Japanese) name for the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1283
             * font, but the registry retains the English version of the name
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1284
             * that corresponded to the "install" locale for windows.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1285
             * Since we are in this code block because there are unmapped
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1286
             * font names, we can look to find unused font->file mappings
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1287
             * and then open the files to read the names. We don't generally
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1288
             * want to open font files, as its a performance hit, but this
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1289
             * occurs only for a small number of fonts on specific system
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1290
             * configs - ie is believed that a "true" Japanese windows would
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1291
             * have JA names in the registry too.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1292
             * Clone fontToFileMap and remove from the clone all keys which
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1293
             * match a fontToFamilyNameMap key. What remains maps to the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1294
             * files we want to open to find the fonts GDI returned.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1295
             * A font in such a file is added to the fontToFileMap after
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1296
             * checking its one of the unmappedFontNames we are looking for.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1297
             * The original name that didn't map is removed from fontToFileMap
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1298
             * so essentially this "fixes up" fontToFileMap to use the same
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1299
             * name as GDI.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1300
             * Also note that typically the fonts for which this occurs in
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1301
             * CJK locales are TTC fonts and not all fonts in a TTC may have
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1302
             * localised names. Eg MSGOTHIC.TTC contains 3 fonts and one of
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1303
             * them "MS UI Gothic" has no JA name whereas the other two do.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1304
             * So not every font in these files is unmapped or new.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1305
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1306
            HashMap<String,String> ffmapCopy =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1307
                (HashMap<String,String>)(fontToFileMap.clone());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1308
            for (String key : fontToFamilyNameMap.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1309
                ffmapCopy.remove(key);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1310
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1311
            for (String key : ffmapCopy.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1312
                unmappedFontFiles.add(ffmapCopy.get(key));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1313
                fontToFileMap.remove(key);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1314
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1315
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1316
            resolveFontFiles(unmappedFontFiles, unmappedFontNames);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1317
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1318
            /* If there are still unmapped font names, this means there's
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1319
             * something that wasn't in the registry. We need to get all
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1320
             * the font files directly and look at the ones that weren't
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1321
             * found in the registry.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1322
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1323
            if (unmappedFontNames.size() > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1324
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1325
                /* getFontFilesFromPath() returns all lower case names.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1326
                 * To compare we also need lower case
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1327
                 * versions of the names from the registry.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1328
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1329
                ArrayList<String> registryFiles = new ArrayList<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1330
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1331
                for (String regFile : fontToFileMap.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1332
                    registryFiles.add(regFile.toLowerCase());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1333
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1334
                /* We don't look for Type1 files here as windows will
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1335
                 * not enumerate these, so aren't useful in reconciling
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1336
                 * GDI's unmapped files. We do find these later when
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1337
                 * we enumerate all fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1338
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1339
                for (String pathFile : getFontFilesFromPath(true)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1340
                    if (!registryFiles.contains(pathFile)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1341
                        unmappedFontFiles.add(pathFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1342
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1343
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1344
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1345
                resolveFontFiles(unmappedFontFiles, unmappedFontNames);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1346
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1347
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1348
            /* remove from the set of names that will be returned to the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1349
             * user any fonts that can't be mapped to files.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1350
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1351
            if (unmappedFontNames.size() > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1352
                int sz = unmappedFontNames.size();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1353
                for (int i=0; i<sz; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1354
                    String name = unmappedFontNames.get(i);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1355
                    String familyName = fontToFamilyNameMap.get(name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1356
                    if (familyName != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1357
                        ArrayList family = familyToFontListMap.get(familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1358
                        if (family != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1359
                            if (family.size() <= 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1360
                                familyToFontListMap.remove(familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1361
                            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1362
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1363
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1364
                    fontToFamilyNameMap.remove(name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1365
                    if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1366
                        logger.info("No file for font:" + name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1367
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1368
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1369
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1370
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1371
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1372
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1373
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1374
     * In some cases windows may have fonts in the fonts folder that
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1375
     * don't show up in the registry or in the GDI calls to enumerate fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1376
     * The only way to find these is to list the directory. We invoke this
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1377
     * only in getAllFonts/Families, so most searches for a specific
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1378
     * font that is satisfied by the GDI/registry calls don't take the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1379
     * additional hit of listing the directory. This hit is small enough
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1380
     * that its not significant in these 'enumerate all the fonts' cases.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1381
     * The basic approach is to cross-reference the files windows found
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1382
     * with the ones in the directory listing approach, and for each
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1383
     * in the latter list that is missing from the former list, register it.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1384
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1385
    private static synchronized void checkForUnreferencedFontFiles() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1386
        if (haveCheckedUnreferencedFontFiles) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1387
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1388
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1389
        haveCheckedUnreferencedFontFiles = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1390
        if (!isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1391
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1392
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1393
        /* getFontFilesFromPath() returns all lower case names.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1394
         * To compare we also need lower case
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1395
         * versions of the names from the registry.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1396
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1397
        ArrayList<String> registryFiles = new ArrayList<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1398
        for (String regFile : fontToFileMap.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1399
            registryFiles.add(regFile.toLowerCase());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1400
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1401
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1402
        /* To avoid any issues with concurrent modification, create
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1403
         * copies of the existing maps, add the new fonts into these
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1404
         * and then replace the references to the old ones with the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1405
         * new maps. ConcurrentHashmap is another option but its a lot
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1406
         * more changes and with this exception, these maps are intended
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1407
         * to be static.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1408
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1409
        HashMap<String,String> fontToFileMap2 = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1410
        HashMap<String,String> fontToFamilyNameMap2 = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1411
        HashMap<String,ArrayList<String>> familyToFontListMap2 = null;;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1412
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1413
        for (String pathFile : getFontFilesFromPath(false)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1414
            if (!registryFiles.contains(pathFile)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1415
                if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1416
                    logger.info("Found non-registry file : " + pathFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1417
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1418
                PhysicalFont f = registerFontFile(getPathName(pathFile));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1419
                if (f == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1420
                    continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1421
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1422
                if (fontToFileMap2 == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1423
                    fontToFileMap2 = new HashMap<String,String>(fontToFileMap);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1424
                    fontToFamilyNameMap2 =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1425
                        new HashMap<String,String>(fontToFamilyNameMap);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1426
                    familyToFontListMap2 = new
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1427
                        HashMap<String,ArrayList<String>>(familyToFontListMap);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1428
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1429
                String fontName = f.getFontName(null);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1430
                String family = f.getFamilyName(null);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1431
                String familyLC = family.toLowerCase();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1432
                fontToFamilyNameMap2.put(fontName, family);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1433
                fontToFileMap2.put(fontName, pathFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1434
                ArrayList<String> fonts = familyToFontListMap2.get(familyLC);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1435
                if (fonts == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1436
                    fonts = new ArrayList<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1437
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1438
                    fonts = new ArrayList<String>(fonts);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1439
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1440
                fonts.add(fontName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1441
                familyToFontListMap2.put(familyLC, fonts);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1442
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1443
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1444
        if (fontToFileMap2 != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1445
            fontToFileMap = fontToFileMap2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1446
            familyToFontListMap = familyToFontListMap2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1447
            fontToFamilyNameMap = fontToFamilyNameMap2;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1448
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1449
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1450
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1451
    private static void resolveFontFiles(HashSet<String> unmappedFiles,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1452
                                         ArrayList<String> unmappedFonts) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1453
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1454
        Locale l = SunToolkit.getStartupLocale();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1455
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1456
        for (String file : unmappedFiles) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1457
            try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1458
                int fn = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1459
                TrueTypeFont ttf;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1460
                String fullPath = getPathName(file);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1461
                if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1462
                    logger.info("Trying to resolve file " + fullPath);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1463
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1464
                do {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1465
                    ttf = new TrueTypeFont(fullPath, null, fn++, true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1466
                    //  prefer the font's locale name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1467
                    String fontName = ttf.getFontName(l).toLowerCase();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1468
                    if (unmappedFonts.contains(fontName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1469
                        fontToFileMap.put(fontName, file);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1470
                        unmappedFonts.remove(fontName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1471
                        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1472
                            logger.info("Resolved absent registry entry for " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1473
                                        fontName + " located in " + fullPath);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1474
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1475
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1476
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1477
                while (fn < ttf.getFontCount());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1478
            } catch (Exception e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1479
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1480
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1481
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1482
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1483
    private static synchronized HashMap<String,String> getFullNameToFileMap() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1484
        if (fontToFileMap == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1485
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1486
            initSGEnv();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1487
            pathDirs = sgEnv.getPlatformFontDirs();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1488
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1489
            fontToFileMap = new HashMap<String,String>(100);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1490
            fontToFamilyNameMap = new HashMap<String,String>(100);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1491
            familyToFontListMap = new HashMap<String,ArrayList<String>>(50);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1492
            populateFontFileNameMap(fontToFileMap,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1493
                                    fontToFamilyNameMap,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1494
                                    familyToFontListMap,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1495
                                    Locale.ENGLISH);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1496
            if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1497
                resolveWindowsFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1498
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1499
            if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1500
                logPlatformFontInfo();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1501
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1502
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1503
        return fontToFileMap;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1504
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1505
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1506
    private static void logPlatformFontInfo() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1507
        for (int i=0; i< pathDirs.length;i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1508
            logger.info("fontdir="+pathDirs[i]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1509
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1510
        for (String keyName : fontToFileMap.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1511
            logger.info("font="+keyName+" file="+ fontToFileMap.get(keyName));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1512
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1513
        for (String keyName : fontToFamilyNameMap.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1514
            logger.info("font="+keyName+" family="+
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1515
                        fontToFamilyNameMap.get(keyName));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1516
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1517
        for (String keyName : familyToFontListMap.keySet()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1518
            logger.info("family="+keyName+ " fonts="+
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1519
                        familyToFontListMap.get(keyName));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1520
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1521
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1522
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1523
    /* Note this return list excludes logical fonts and JRE fonts */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1524
    public static String[] getFontNamesFromPlatform() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1525
        if (getFullNameToFileMap().size() == 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1526
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1527
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1528
        checkForUnreferencedFontFiles();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1529
        /* This odd code with TreeMap is used to preserve a historical
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1530
         * behaviour wrt the sorting order .. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1531
        ArrayList<String> fontNames = new ArrayList<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1532
        for (ArrayList<String> a : familyToFontListMap.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1533
            for (String s : a) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1534
                fontNames.add(s);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1535
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1536
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1537
        return fontNames.toArray(STR_ARRAY);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1538
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1539
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1540
    public static boolean gotFontsFromPlatform() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1541
        return getFullNameToFileMap().size() != 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1542
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1543
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1544
    public static String getFileNameForFontName(String fontName) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1545
        String fontNameLC = fontName.toLowerCase(Locale.ENGLISH);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1546
        return fontToFileMap.get(fontNameLC);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1547
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1548
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1549
    private static PhysicalFont registerFontFile(String file) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1550
        if (new File(file).isAbsolute() &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1551
            !registeredFontFiles.contains(file)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1552
            int fontFormat = FONTFORMAT_NONE;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1553
            int fontRank = Font2D.UNKNOWN_RANK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1554
            if (SunGraphicsEnvironment.ttFilter.accept(null, file)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1555
                fontFormat = FONTFORMAT_TRUETYPE;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1556
                fontRank = Font2D.TTF_RANK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1557
            } else if
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1558
                (SunGraphicsEnvironment.t1Filter.accept(null, file)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1559
                fontFormat = FONTFORMAT_TYPE1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1560
                fontRank = Font2D.TYPE1_RANK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1561
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1562
            if (fontFormat == FONTFORMAT_NONE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1563
                return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1564
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1565
            return registerFontFile(file, null, fontFormat, false, fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1566
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1567
        return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1568
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1569
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1570
    /* Used to register any font files that are found by platform APIs
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1571
     * that weren't previously found in the standard font locations.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1572
     * the isAbsolute() check is needed since that's whats stored in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1573
     * set, and on windows, the fonts in the system font directory that
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1574
     * are in the fontToFileMap are just basenames. We don't want to try
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1575
     * to register those again, but we do want to register other registry
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1576
     * installed fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1577
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1578
    public static void registerOtherFontFiles(HashSet registeredFontFiles) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1579
        if (getFullNameToFileMap().size() == 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1580
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1581
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1582
        for (String file : fontToFileMap.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1583
            registerFontFile(file);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1584
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1585
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1586
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1587
    public static boolean
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1588
        getFamilyNamesFromPlatform(TreeMap<String,String> familyNames,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1589
                                   Locale requestedLocale) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1590
        if (getFullNameToFileMap().size() == 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1591
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1592
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1593
        checkForUnreferencedFontFiles();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1594
        for (String name : fontToFamilyNameMap.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1595
            familyNames.put(name.toLowerCase(requestedLocale), name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1596
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1597
        return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1598
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1599
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1600
    /* Path may be absolute or a base file name relative to one of
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1601
     * the platform font directories
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1602
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1603
    private static String getPathName(String s) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1604
        File f = new File(s);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1605
        if (f.isAbsolute()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1606
            return s;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1607
        } else if (pathDirs.length==1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1608
            return pathDirs[0] + File.separator + s;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1609
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1610
            for (int p=0; p<pathDirs.length; p++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1611
                f = new File(pathDirs[p] + File.separator + s);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1612
                if (f.exists()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1613
                    return f.getAbsolutePath();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1614
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1615
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1616
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1617
        return s; // shouldn't happen, but harmless
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1618
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1619
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1620
    /* lcName is required to be lower case for use as a key.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1621
     * lcName may be a full name, or a family name, and style may
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1622
     * be specified in addition to either of these. So be sure to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1623
     * get the right one. Since an app *could* ask for "Foo Regular"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1624
     * and later ask for "Foo Italic", if we don't register all the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1625
     * styles, then logic in findFont2D may try to style the original
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1626
     * so we register the entire family if we get a match here.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1627
     * This is still a big win because this code is invoked where
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1628
     * otherwise we would register all fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1629
     * It's also useful for the case where "Foo Bold" was specified with
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1630
     * style Font.ITALIC, as we would want in that case to try to return
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1631
     * "Foo Bold Italic" if it exists, and it is only by locating "Foo Bold"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1632
     * and opening it that we really "know" it's Bold, and can look for
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1633
     * a font that supports that and the italic style.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1634
     * The code in here is not overtly windows-specific but in fact it
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1635
     * is unlikely to be useful as is on other platforms. It is maintained
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1636
     * in this shared source file to be close to its sole client and
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1637
     * because so much of the logic is intertwined with the logic in
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1638
     * findFont2D.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1639
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1640
    private static Font2D findFontFromPlatform(String lcName, int style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1641
        if (getFullNameToFileMap().size() == 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1642
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1643
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1644
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1645
        ArrayList<String> family = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1646
        String fontFile = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1647
        String familyName = fontToFamilyNameMap.get(lcName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1648
        if (familyName != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1649
            fontFile = fontToFileMap.get(lcName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1650
            family = familyToFontListMap.get
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1651
                (familyName.toLowerCase(Locale.ENGLISH));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1652
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1653
            family = familyToFontListMap.get(lcName); // is lcName is a family?
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1654
            if (family != null && family.size() > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1655
                String lcFontName = family.get(0).toLowerCase(Locale.ENGLISH);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1656
                if (lcFontName != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1657
                    familyName = fontToFamilyNameMap.get(lcFontName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1658
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1659
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1660
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1661
        if (family == null || familyName == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1662
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1663
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1664
        String [] fontList = (String[])family.toArray(STR_ARRAY);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1665
        if (fontList.length == 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1666
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1667
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1668
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1669
        /* first check that for every font in this family we can find
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1670
         * a font file. The specific reason for doing this is that
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1671
         * in at least one case on Windows a font has the face name "David"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1672
         * but the registry entry is "David Regular". That is the "unique"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1673
         * name of the font but in other cases the registry contains the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1674
         * "full" name. See the specifications of name ids 3 and 4 in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1675
         * TrueType 'name' table.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1676
         * In general this could cause a problem that we fail to register
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1677
         * if we all members of a family that we may end up mapping to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1678
         * the wrong font member: eg return Bold when Plain is needed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1679
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1680
        for (int f=0;f<fontList.length;f++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1681
            String fontNameLC = fontList[f].toLowerCase(Locale.ENGLISH);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1682
            String fileName = fontToFileMap.get(fontNameLC);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1683
            if (fileName == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1684
                if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1685
                    logger.info("Platform lookup : No file for font " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1686
                                fontList[f] + " in family " +familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1687
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1688
                return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1689
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1690
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1691
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1692
        /* Currently this code only looks for TrueType fonts, so format
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1693
         * and rank can be specified without looking at the filename.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1694
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1695
        PhysicalFont physicalFont = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1696
        if (fontFile != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1697
            physicalFont = registerFontFile(getPathName(fontFile), null,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1698
                                            FONTFORMAT_TRUETYPE, false,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1699
                                            Font2D.TTF_RANK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1700
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1701
        /* Register all fonts in this family. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1702
        for (int f=0;f<fontList.length;f++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1703
            String fontNameLC = fontList[f].toLowerCase(Locale.ENGLISH);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1704
            String fileName = fontToFileMap.get(fontNameLC);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1705
            if (fontFile != null && fontFile.equals(fileName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1706
                continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1707
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1708
            /* Currently this code only looks for TrueType fonts, so format
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1709
             * and rank can be specified without looking at the filename.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1710
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1711
            registerFontFile(getPathName(fileName), null,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1712
                             FONTFORMAT_TRUETYPE, false, Font2D.TTF_RANK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1713
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1714
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1715
        Font2D font = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1716
        FontFamily fontFamily = FontFamily.getFamily(familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1717
        /* Handle case where request "MyFont Bold", style=Font.ITALIC */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1718
        if (physicalFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1719
            style |= physicalFont.style;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1720
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1721
        if (fontFamily != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1722
            font = fontFamily.getFont(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1723
            if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1724
                font = fontFamily.getClosestStyle(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1725
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1726
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1727
        return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1728
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1729
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1730
    private static ConcurrentHashMap<String, Font2D> fontNameCache =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1731
        new ConcurrentHashMap<String, Font2D>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1732
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1733
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1734
     * The client supplies a name and a style.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1735
     * The name could be a family name, or a full name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1736
     * A font may exist with the specified style, or it may
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1737
     * exist only in some other style. For non-native fonts the scaler
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1738
     * may be able to emulate the required style.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1739
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1740
    public static Font2D findFont2D(String name, int style, int fallback) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1741
        String lowerCaseName = name.toLowerCase(Locale.ENGLISH);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1742
        String mapName = lowerCaseName + dotStyleStr(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1743
        Font2D font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1744
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1745
        /* If preferLocaleFonts() or preferProportionalFonts() has been
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1746
         * called we may be using an alternate set of composite fonts in this
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1747
         * app context. The presence of a pre-built name map indicates whether
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1748
         * this is so, and gives access to the alternate composite for the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1749
         * name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1750
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1751
        if (usingPerAppContextComposites) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1752
            ConcurrentHashMap<String, Font2D> altNameCache =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1753
                (ConcurrentHashMap<String, Font2D>)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1754
                AppContext.getAppContext().get(CompositeFont.class);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1755
            if (altNameCache != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1756
                font = (Font2D)altNameCache.get(mapName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1757
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1758
                font = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1759
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1760
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1761
            font = fontNameCache.get(mapName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1762
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1763
        if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1764
            return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1765
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1766
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1767
        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1768
            logger.info("Search for font: " + name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1769
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1770
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1771
        // The check below is just so that the bitmap fonts being set by
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1772
        // AWT and Swing thru the desktop properties do not trigger the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1773
        // the load fonts case. The two bitmap fonts are now mapped to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1774
        // appropriate equivalents for serif and sansserif.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1775
        // Note that the cost of this comparison is only for the first
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1776
        // call until the map is filled.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1777
        if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1778
            if (lowerCaseName.equals("ms sans serif")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1779
                name = "sansserif";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1780
            } else if (lowerCaseName.equals("ms serif")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1781
                name = "serif";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1782
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1783
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1784
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1785
        /* This isn't intended to support a client passing in the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1786
         * string default, but if a client passes in null for the name
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1787
         * the java.awt.Font class internally substitutes this name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1788
         * So we need to recognise it here to prevent a loadFonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1789
         * on the unrecognised name. The only potential problem with
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1790
         * this is it would hide any real font called "default"!
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1791
         * But that seems like a potential problem we can ignore for now.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1792
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1793
        if (lowerCaseName.equals("default")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1794
            name = "dialog";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1795
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1796
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1797
        /* First see if its a family name. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1798
        FontFamily family = FontFamily.getFamily(name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1799
        if (family != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1800
            font = family.getFontWithExactStyleMatch(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1801
            if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1802
                font = findDeferredFont(name, style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1803
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1804
            if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1805
                font = family.getFont(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1806
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1807
            if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1808
                font = family.getClosestStyle(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1809
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1810
            if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1811
                fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1812
                return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1813
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1814
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1815
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1816
        /* If it wasn't a family name, it should be a full name of
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1817
         * either a composite, or a physical font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1818
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1819
        font = fullNameToFont.get(lowerCaseName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1820
        if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1821
            /* Check that the requested style matches the matched font's style.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1822
             * But also match style automatically if the requested style is
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1823
             * "plain". This because the existing behaviour is that the fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1824
             * listed via getAllFonts etc always list their style as PLAIN.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1825
             * This does lead to non-commutative behaviours where you might
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1826
             * start with "Lucida Sans Regular" and ask for a BOLD version
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1827
             * and get "Lucida Sans DemiBold" but if you ask for the PLAIN
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1828
             * style of "Lucida Sans DemiBold" you get "Lucida Sans DemiBold".
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1829
             * This consistent however with what happens if you have a bold
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1830
             * version of a font and no plain version exists - alg. styling
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1831
             * doesn't "unbolden" the font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1832
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1833
            if (font.style == style || style == Font.PLAIN) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1834
                fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1835
                return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1836
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1837
                /* If it was a full name like "Lucida Sans Regular", but
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1838
                 * the style requested is "bold", then we want to see if
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1839
                 * there's the appropriate match against another font in
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1840
                 * that family before trying to load all fonts, or applying a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1841
                 * algorithmic styling
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1842
                 */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1843
                family = FontFamily.getFamily(font.getFamilyName(null));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1844
                if (family != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1845
                    Font2D familyFont = family.getFont(style|font.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1846
                    /* We exactly matched the requested style, use it! */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1847
                    if (familyFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1848
                        fontNameCache.put(mapName, familyFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1849
                        return familyFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1850
                    } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1851
                        /* This next call is designed to support the case
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1852
                         * where bold italic is requested, and if we must
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1853
                         * style, then base it on either bold or italic -
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1854
                         * not on plain!
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1855
                         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1856
                        familyFont = family.getClosestStyle(style|font.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1857
                        if (familyFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1858
                            /* The next check is perhaps one
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1859
                             * that shouldn't be done. ie if we get this
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1860
                             * far we have probably as close a match as we
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1861
                             * are going to get. We could load all fonts to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1862
                             * see if somehow some parts of the family are
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1863
                             * loaded but not all of it.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1864
                             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1865
                            if (familyFont.canDoStyle(style|font.style)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1866
                                fontNameCache.put(mapName, familyFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1867
                                return familyFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1868
                            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1869
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1870
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1871
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1872
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1873
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1874
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1875
        /* If reach here its possible that this is in a client which never
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1876
         * loaded the GraphicsEnvironment, so we haven't even loaded ANY of
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1877
         * the fonts from the environment. Do so now and recurse.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1878
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1879
        if (sgEnv == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1880
            initSGEnv();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1881
            return findFont2D(name, style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1882
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1883
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1884
        if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1885
            /* Don't want Windows to return a Lucida Sans font from
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1886
             * C:\Windows\Fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1887
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1888
            if (deferredFontFiles.size() > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1889
                font = findJREDeferredFont(lowerCaseName, style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1890
                if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1891
                    fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1892
                    return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1893
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1894
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1895
            font = findFontFromPlatform(lowerCaseName, style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1896
            if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1897
                if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1898
                    logger.info("Found font via platform API for request:\"" +
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1899
                                name + "\":, style="+style+
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1900
                                " found font: " + font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1901
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1902
                fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1903
                return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1904
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1905
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1906
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1907
        /* If reach here and no match has been located, then if there are
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1908
         * uninitialised deferred fonts, load as many of those as needed
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1909
         * to find the deferred font. If none is found through that
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1910
         * search continue on.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1911
         * There is possibly a minor issue when more than one
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1912
         * deferred font implements the same font face. Since deferred
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1913
         * fonts are only those in font configuration files, this is a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1914
         * controlled situation, the known case being Solaris euro_fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1915
         * versions of Arial, Times New Roman, Courier New. However
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1916
         * the larger font will transparently replace the smaller one
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1917
         *  - see addToFontList() - when it is needed by the composite font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1918
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1919
        if (deferredFontFiles.size() > 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1920
            font = findDeferredFont(name, style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1921
            if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1922
                fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1923
                return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1924
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1925
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1926
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1927
        /* Some apps use deprecated 1.0 names such as helvetica and courier. On
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1928
         * Solaris these are Type1 fonts in /usr/openwin/lib/X11/fonts/Type1.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1929
         * If running on Solaris will register all the fonts in this
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1930
         * directory.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1931
         * May as well register the whole directory without actually testing
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1932
         * the font name is one of the deprecated names as the next step would
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1933
         * load all fonts which are in this directory anyway.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1934
         * In the event that this lookup is successful it potentially "hides"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1935
         * TrueType versions of such fonts that are elsewhere but since they
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1936
         * do not exist on Solaris this is not a problem.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1937
         * Set a flag to indicate we've done this registration to avoid
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1938
         * repetition and more seriously, to avoid recursion.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1939
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1940
        if (isSolaris&&!loaded1dot0Fonts) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1941
            /* "timesroman" is a special case since that's not the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1942
             * name of any known font on Solaris or elsewhere.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1943
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1944
            if (lowerCaseName.equals("timesroman")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1945
                font = findFont2D("serif", style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1946
                fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1947
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1948
            sgEnv.register1dot0Fonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1949
            loaded1dot0Fonts = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1950
            Font2D ff = findFont2D(name, style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1951
            return ff;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1952
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1953
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1954
        /* We check for application registered fonts before
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1955
         * explicitly loading all fonts as if necessary the registration
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1956
         * code will have done so anyway. And we don't want to needlessly
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1957
         * load the actual files for all fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1958
         * Just as for installed fonts we check for family before fullname.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1959
         * We do not add these fonts to fontNameCache for the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1960
         * app context case which eliminates the overhead of a per context
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1961
         * cache for these.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1962
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1963
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1964
        if (fontsAreRegistered || fontsAreRegisteredPerAppContext) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1965
            Hashtable<String, FontFamily> familyTable = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1966
            Hashtable<String, Font2D> nameTable;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1967
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1968
            if (fontsAreRegistered) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1969
                familyTable = createdByFamilyName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1970
                nameTable = createdByFullName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1971
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1972
                AppContext appContext = AppContext.getAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1973
                familyTable =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1974
                    (Hashtable<String,FontFamily>)appContext.get(regFamilyKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1975
                nameTable =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1976
                    (Hashtable<String,Font2D>)appContext.get(regFullNameKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1977
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1978
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1979
            family = familyTable.get(lowerCaseName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1980
            if (family != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1981
                font = family.getFontWithExactStyleMatch(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1982
                if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1983
                    font = family.getFont(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1984
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1985
                if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1986
                    font = family.getClosestStyle(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1987
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1988
                if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1989
                    if (fontsAreRegistered) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1990
                        fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1991
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1992
                    return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1993
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1994
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1995
            font = nameTable.get(lowerCaseName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1996
            if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1997
                if (fontsAreRegistered) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1998
                    fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  1999
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2000
                return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2001
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2002
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2003
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2004
        /* If reach here and no match has been located, then if all fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2005
         * are not yet loaded, do so, and then recurse.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2006
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2007
        if (!loadedAllFonts) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2008
            if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2009
                logger.info("Load fonts looking for:" + name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2010
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2011
            sgEnv.loadFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2012
            loadedAllFonts = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2013
            return findFont2D(name, style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2014
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2015
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2016
        if (!loadedAllFontFiles) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2017
            if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2018
                logger.info("Load font files looking for:" + name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2019
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2020
            sgEnv.loadFontFiles();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2021
            loadedAllFontFiles = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2022
            return findFont2D(name, style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2023
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2024
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2025
        /* The primary name is the locale default - ie not US/English but
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2026
         * whatever is the default in this locale. This is the way it always
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2027
         * has been but may be surprising to some developers if "Arial Regular"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2028
         * were hard-coded in their app and yet "Arial Regular" was not the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2029
         * default name. Fortunately for them, as a consequence of the JDK
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2030
         * supporting returning names and family names for arbitrary locales,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2031
         * we also need to support searching all localised names for a match.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2032
         * But because this case of the name used to reference a font is not
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2033
         * the same as the default for this locale is rare, it makes sense to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2034
         * search a much shorter list of default locale names and only go to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2035
         * a longer list of names in the event that no match was found.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2036
         * So add here code which searches localised names too.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2037
         * As in 1.4.x this happens only after loading all fonts, which
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2038
         * is probably the right order.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2039
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2040
        if ((font = findFont2DAllLocales(name, style)) != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2041
            fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2042
            return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2043
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2044
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2045
        /* Perhaps its a "compatibility" name - timesroman, helvetica,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2046
         * or courier, which 1.0 apps used for logical fonts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2047
         * We look for these "late" after a loadFonts as we must not
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2048
         * hide real fonts of these names.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2049
         * Map these appropriately:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2050
         * On windows this means according to the rules specified by the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2051
         * FontConfiguration : do it only for encoding==Cp1252
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2052
         *
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2053
         * REMIND: this is something we plan to remove.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2054
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2055
        if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2056
            String compatName =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2057
                sgEnv.getFontConfiguration().getFallbackFamilyName(name, null);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2058
            if (compatName != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2059
                font = findFont2D(compatName, style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2060
                fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2061
                return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2062
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2063
        } else if (lowerCaseName.equals("timesroman")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2064
            font = findFont2D("serif", style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2065
            fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2066
            return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2067
        } else if (lowerCaseName.equals("helvetica")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2068
            font = findFont2D("sansserif", style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2069
            fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2070
            return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2071
        } else if (lowerCaseName.equals("courier")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2072
            font = findFont2D("monospaced", style, fallback);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2073
            fontNameCache.put(mapName, font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2074
            return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2075
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2076
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2077
        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2078
            logger.info("No font found for:" + name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2079
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2080
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2081
        switch (fallback) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2082
        case PHYSICAL_FALLBACK: return getDefaultPhysicalFont();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2083
        case LOGICAL_FALLBACK: return getDefaultLogicalFont(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2084
        default: return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2085
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2086
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2087
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2088
    /* This method can be more efficient as it will only need to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2089
     * do the lookup once, and subsequent calls on the java.awt.Font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2090
     * instance can utilise the cached Font2D on that object.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2091
     * Its unfortunate it needs to be a native method, but the font2D
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2092
     * variable has to be private.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2093
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2094
    public static native Font2D getFont2D(Font font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2095
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2096
    /* Stuff below was in NativeFontWrapper and needed a new home */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2097
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2098
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2099
     * Workaround for apps which are dependent on a font metrics bug
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2100
     * in JDK 1.1. This is an unsupported win32 private setting.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2101
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2102
    public static boolean usePlatformFontMetrics() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2103
        return usePlatformFontMetrics;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2104
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2105
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2106
    static native boolean getPlatformFontVar();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2107
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2108
    private static final short US_LCID = 0x0409;  // US English - default
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2109
    private static Map<String, Short> lcidMap;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2110
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2111
    // Return a Microsoft LCID from the given Locale.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2112
    // Used when getting localized font data.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2113
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2114
    public static short getLCIDFromLocale(Locale locale) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2115
        // optimize for common case
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2116
        if (locale.equals(Locale.US)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2117
            return US_LCID;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2118
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2119
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2120
        if (lcidMap == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2121
            createLCIDMap();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2122
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2123
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2124
        String key = locale.toString();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2125
        while (!"".equals(key)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2126
            Short lcidObject = (Short) lcidMap.get(key);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2127
            if (lcidObject != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2128
                return lcidObject.shortValue();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2129
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2130
            int pos = key.lastIndexOf('_');
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2131
            if (pos < 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2132
                return US_LCID;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2133
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2134
            key = key.substring(0, pos);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2135
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2136
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2137
        return US_LCID;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2138
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2139
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2140
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2141
    private static void addLCIDMapEntry(Map<String, Short> map,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2142
                                        String key, short value) {
438
2ae294e4518c 6613529: Avoid duplicate object creation within JDK packages
dav
parents: 2
diff changeset
  2143
        map.put(key, Short.valueOf(value));
2
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2144
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2145
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2146
    private static synchronized void createLCIDMap() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2147
        if (lcidMap != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2148
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2149
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2150
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2151
        Map<String, Short> map = new HashMap<String, Short>(200);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2152
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2153
        // the following statements are derived from the langIDMap
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2154
        // in src/windows/native/java/lang/java_props_md.c using the following
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2155
        // awk script:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2156
        //    $1~/\/\*/   { next}
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2157
        //    $3~/\?\?/   { next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2158
        //    $3!~/_/     { next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2159
        //    $1~/0x0409/ { next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2160
        //    $1~/0x0c0a/ { next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2161
        //    $1~/0x042c/ { next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2162
        //    $1~/0x0443/ { next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2163
        //    $1~/0x0812/ { next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2164
        //    $1~/0x04/   { print "        addLCIDMapEntry(map, " substr($3, 0, 3) "\", (short) " substr($1, 0, 6) ");" ; next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2165
        //    $3~/,/      { print "        addLCIDMapEntry(map, " $3  " (short) " substr($1, 0, 6) ");" ; next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2166
        //                { print "        addLCIDMapEntry(map, " $3 ", (short) " substr($1, 0, 6) ");" ; next }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2167
        // The lines of this script:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2168
        // - eliminate comments
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2169
        // - eliminate questionable locales
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2170
        // - eliminate language-only locales
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2171
        // - eliminate the default LCID value
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2172
        // - eliminate a few other unneeded LCID values
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2173
        // - print language-only locale entries for x04* LCID values
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2174
        //   (apparently Microsoft doesn't use language-only LCID values -
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2175
        //   see http://www.microsoft.com/OpenType/otspec/name.htm
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2176
        // - print complete entries for all other LCID values
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2177
        // Run
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2178
        //     awk -f awk-script langIDMap > statements
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2179
        addLCIDMapEntry(map, "ar", (short) 0x0401);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2180
        addLCIDMapEntry(map, "bg", (short) 0x0402);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2181
        addLCIDMapEntry(map, "ca", (short) 0x0403);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2182
        addLCIDMapEntry(map, "zh", (short) 0x0404);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2183
        addLCIDMapEntry(map, "cs", (short) 0x0405);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2184
        addLCIDMapEntry(map, "da", (short) 0x0406);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2185
        addLCIDMapEntry(map, "de", (short) 0x0407);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2186
        addLCIDMapEntry(map, "el", (short) 0x0408);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2187
        addLCIDMapEntry(map, "es", (short) 0x040a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2188
        addLCIDMapEntry(map, "fi", (short) 0x040b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2189
        addLCIDMapEntry(map, "fr", (short) 0x040c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2190
        addLCIDMapEntry(map, "iw", (short) 0x040d);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2191
        addLCIDMapEntry(map, "hu", (short) 0x040e);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2192
        addLCIDMapEntry(map, "is", (short) 0x040f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2193
        addLCIDMapEntry(map, "it", (short) 0x0410);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2194
        addLCIDMapEntry(map, "ja", (short) 0x0411);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2195
        addLCIDMapEntry(map, "ko", (short) 0x0412);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2196
        addLCIDMapEntry(map, "nl", (short) 0x0413);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2197
        addLCIDMapEntry(map, "no", (short) 0x0414);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2198
        addLCIDMapEntry(map, "pl", (short) 0x0415);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2199
        addLCIDMapEntry(map, "pt", (short) 0x0416);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2200
        addLCIDMapEntry(map, "rm", (short) 0x0417);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2201
        addLCIDMapEntry(map, "ro", (short) 0x0418);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2202
        addLCIDMapEntry(map, "ru", (short) 0x0419);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2203
        addLCIDMapEntry(map, "hr", (short) 0x041a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2204
        addLCIDMapEntry(map, "sk", (short) 0x041b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2205
        addLCIDMapEntry(map, "sq", (short) 0x041c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2206
        addLCIDMapEntry(map, "sv", (short) 0x041d);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2207
        addLCIDMapEntry(map, "th", (short) 0x041e);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2208
        addLCIDMapEntry(map, "tr", (short) 0x041f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2209
        addLCIDMapEntry(map, "ur", (short) 0x0420);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2210
        addLCIDMapEntry(map, "in", (short) 0x0421);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2211
        addLCIDMapEntry(map, "uk", (short) 0x0422);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2212
        addLCIDMapEntry(map, "be", (short) 0x0423);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2213
        addLCIDMapEntry(map, "sl", (short) 0x0424);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2214
        addLCIDMapEntry(map, "et", (short) 0x0425);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2215
        addLCIDMapEntry(map, "lv", (short) 0x0426);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2216
        addLCIDMapEntry(map, "lt", (short) 0x0427);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2217
        addLCIDMapEntry(map, "fa", (short) 0x0429);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2218
        addLCIDMapEntry(map, "vi", (short) 0x042a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2219
        addLCIDMapEntry(map, "hy", (short) 0x042b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2220
        addLCIDMapEntry(map, "eu", (short) 0x042d);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2221
        addLCIDMapEntry(map, "mk", (short) 0x042f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2222
        addLCIDMapEntry(map, "tn", (short) 0x0432);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2223
        addLCIDMapEntry(map, "xh", (short) 0x0434);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2224
        addLCIDMapEntry(map, "zu", (short) 0x0435);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2225
        addLCIDMapEntry(map, "af", (short) 0x0436);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2226
        addLCIDMapEntry(map, "ka", (short) 0x0437);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2227
        addLCIDMapEntry(map, "fo", (short) 0x0438);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2228
        addLCIDMapEntry(map, "hi", (short) 0x0439);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2229
        addLCIDMapEntry(map, "mt", (short) 0x043a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2230
        addLCIDMapEntry(map, "se", (short) 0x043b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2231
        addLCIDMapEntry(map, "gd", (short) 0x043c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2232
        addLCIDMapEntry(map, "ms", (short) 0x043e);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2233
        addLCIDMapEntry(map, "kk", (short) 0x043f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2234
        addLCIDMapEntry(map, "ky", (short) 0x0440);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2235
        addLCIDMapEntry(map, "sw", (short) 0x0441);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2236
        addLCIDMapEntry(map, "tt", (short) 0x0444);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2237
        addLCIDMapEntry(map, "bn", (short) 0x0445);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2238
        addLCIDMapEntry(map, "pa", (short) 0x0446);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2239
        addLCIDMapEntry(map, "gu", (short) 0x0447);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2240
        addLCIDMapEntry(map, "ta", (short) 0x0449);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2241
        addLCIDMapEntry(map, "te", (short) 0x044a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2242
        addLCIDMapEntry(map, "kn", (short) 0x044b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2243
        addLCIDMapEntry(map, "ml", (short) 0x044c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2244
        addLCIDMapEntry(map, "mr", (short) 0x044e);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2245
        addLCIDMapEntry(map, "sa", (short) 0x044f);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2246
        addLCIDMapEntry(map, "mn", (short) 0x0450);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2247
        addLCIDMapEntry(map, "cy", (short) 0x0452);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2248
        addLCIDMapEntry(map, "gl", (short) 0x0456);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2249
        addLCIDMapEntry(map, "dv", (short) 0x0465);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2250
        addLCIDMapEntry(map, "qu", (short) 0x046b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2251
        addLCIDMapEntry(map, "mi", (short) 0x0481);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2252
        addLCIDMapEntry(map, "ar_IQ", (short) 0x0801);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2253
        addLCIDMapEntry(map, "zh_CN", (short) 0x0804);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2254
        addLCIDMapEntry(map, "de_CH", (short) 0x0807);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2255
        addLCIDMapEntry(map, "en_GB", (short) 0x0809);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2256
        addLCIDMapEntry(map, "es_MX", (short) 0x080a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2257
        addLCIDMapEntry(map, "fr_BE", (short) 0x080c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2258
        addLCIDMapEntry(map, "it_CH", (short) 0x0810);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2259
        addLCIDMapEntry(map, "nl_BE", (short) 0x0813);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2260
        addLCIDMapEntry(map, "no_NO_NY", (short) 0x0814);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2261
        addLCIDMapEntry(map, "pt_PT", (short) 0x0816);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2262
        addLCIDMapEntry(map, "ro_MD", (short) 0x0818);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2263
        addLCIDMapEntry(map, "ru_MD", (short) 0x0819);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2264
        addLCIDMapEntry(map, "sr_CS", (short) 0x081a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2265
        addLCIDMapEntry(map, "sv_FI", (short) 0x081d);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2266
        addLCIDMapEntry(map, "az_AZ", (short) 0x082c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2267
        addLCIDMapEntry(map, "se_SE", (short) 0x083b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2268
        addLCIDMapEntry(map, "ga_IE", (short) 0x083c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2269
        addLCIDMapEntry(map, "ms_BN", (short) 0x083e);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2270
        addLCIDMapEntry(map, "uz_UZ", (short) 0x0843);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2271
        addLCIDMapEntry(map, "qu_EC", (short) 0x086b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2272
        addLCIDMapEntry(map, "ar_EG", (short) 0x0c01);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2273
        addLCIDMapEntry(map, "zh_HK", (short) 0x0c04);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2274
        addLCIDMapEntry(map, "de_AT", (short) 0x0c07);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2275
        addLCIDMapEntry(map, "en_AU", (short) 0x0c09);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2276
        addLCIDMapEntry(map, "fr_CA", (short) 0x0c0c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2277
        addLCIDMapEntry(map, "sr_CS", (short) 0x0c1a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2278
        addLCIDMapEntry(map, "se_FI", (short) 0x0c3b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2279
        addLCIDMapEntry(map, "qu_PE", (short) 0x0c6b);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2280
        addLCIDMapEntry(map, "ar_LY", (short) 0x1001);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2281
        addLCIDMapEntry(map, "zh_SG", (short) 0x1004);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2282
        addLCIDMapEntry(map, "de_LU", (short) 0x1007);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2283
        addLCIDMapEntry(map, "en_CA", (short) 0x1009);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2284
        addLCIDMapEntry(map, "es_GT", (short) 0x100a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2285
        addLCIDMapEntry(map, "fr_CH", (short) 0x100c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2286
        addLCIDMapEntry(map, "hr_BA", (short) 0x101a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2287
        addLCIDMapEntry(map, "ar_DZ", (short) 0x1401);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2288
        addLCIDMapEntry(map, "zh_MO", (short) 0x1404);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2289
        addLCIDMapEntry(map, "de_LI", (short) 0x1407);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2290
        addLCIDMapEntry(map, "en_NZ", (short) 0x1409);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2291
        addLCIDMapEntry(map, "es_CR", (short) 0x140a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2292
        addLCIDMapEntry(map, "fr_LU", (short) 0x140c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2293
        addLCIDMapEntry(map, "bs_BA", (short) 0x141a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2294
        addLCIDMapEntry(map, "ar_MA", (short) 0x1801);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2295
        addLCIDMapEntry(map, "en_IE", (short) 0x1809);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2296
        addLCIDMapEntry(map, "es_PA", (short) 0x180a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2297
        addLCIDMapEntry(map, "fr_MC", (short) 0x180c);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2298
        addLCIDMapEntry(map, "sr_BA", (short) 0x181a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2299
        addLCIDMapEntry(map, "ar_TN", (short) 0x1c01);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2300
        addLCIDMapEntry(map, "en_ZA", (short) 0x1c09);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2301
        addLCIDMapEntry(map, "es_DO", (short) 0x1c0a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2302
        addLCIDMapEntry(map, "sr_BA", (short) 0x1c1a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2303
        addLCIDMapEntry(map, "ar_OM", (short) 0x2001);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2304
        addLCIDMapEntry(map, "en_JM", (short) 0x2009);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2305
        addLCIDMapEntry(map, "es_VE", (short) 0x200a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2306
        addLCIDMapEntry(map, "ar_YE", (short) 0x2401);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2307
        addLCIDMapEntry(map, "es_CO", (short) 0x240a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2308
        addLCIDMapEntry(map, "ar_SY", (short) 0x2801);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2309
        addLCIDMapEntry(map, "en_BZ", (short) 0x2809);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2310
        addLCIDMapEntry(map, "es_PE", (short) 0x280a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2311
        addLCIDMapEntry(map, "ar_JO", (short) 0x2c01);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2312
        addLCIDMapEntry(map, "en_TT", (short) 0x2c09);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2313
        addLCIDMapEntry(map, "es_AR", (short) 0x2c0a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2314
        addLCIDMapEntry(map, "ar_LB", (short) 0x3001);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2315
        addLCIDMapEntry(map, "en_ZW", (short) 0x3009);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2316
        addLCIDMapEntry(map, "es_EC", (short) 0x300a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2317
        addLCIDMapEntry(map, "ar_KW", (short) 0x3401);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2318
        addLCIDMapEntry(map, "en_PH", (short) 0x3409);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2319
        addLCIDMapEntry(map, "es_CL", (short) 0x340a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2320
        addLCIDMapEntry(map, "ar_AE", (short) 0x3801);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2321
        addLCIDMapEntry(map, "es_UY", (short) 0x380a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2322
        addLCIDMapEntry(map, "ar_BH", (short) 0x3c01);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2323
        addLCIDMapEntry(map, "es_PY", (short) 0x3c0a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2324
        addLCIDMapEntry(map, "ar_QA", (short) 0x4001);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2325
        addLCIDMapEntry(map, "es_BO", (short) 0x400a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2326
        addLCIDMapEntry(map, "es_SV", (short) 0x440a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2327
        addLCIDMapEntry(map, "es_HN", (short) 0x480a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2328
        addLCIDMapEntry(map, "es_NI", (short) 0x4c0a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2329
        addLCIDMapEntry(map, "es_PR", (short) 0x500a);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2330
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2331
        lcidMap = map;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2332
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2333
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2334
    public static int getNumFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2335
        return physicalFonts.size()+maxCompFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2336
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2337
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2338
    private static boolean fontSupportsEncoding(Font font, String encoding) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2339
        return getFont2D(font).supportsEncoding(encoding);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2340
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2341
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2342
    public synchronized static native String getFontPath(boolean noType1Fonts);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2343
    public synchronized static native void setNativeFontPath(String fontPath);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2344
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2345
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2346
    private static Thread fileCloser = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2347
    static Vector<File> tmpFontFiles = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2348
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2349
    public static Font2D createFont2D(File fontFile, int fontFormat,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2350
                                      boolean isCopy)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2351
        throws FontFormatException {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2352
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2353
        String fontFilePath = fontFile.getPath();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2354
        FileFont font2D = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2355
        final File fFile = fontFile;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2356
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2357
            switch (fontFormat) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2358
            case Font.TRUETYPE_FONT:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2359
                font2D = new TrueTypeFont(fontFilePath, null, 0, true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2360
                break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2361
            case Font.TYPE1_FONT:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2362
                font2D = new Type1Font(fontFilePath, null);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2363
                break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2364
            default:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2365
                throw new FontFormatException("Unrecognised Font Format");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2366
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2367
        } catch (FontFormatException e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2368
            if (isCopy) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2369
                java.security.AccessController.doPrivileged(
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2370
                     new java.security.PrivilegedAction() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2371
                          public Object run() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2372
                              fFile.delete();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2373
                              return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2374
                          }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2375
                });
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2376
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2377
            throw(e);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2378
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2379
        if (isCopy) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2380
            font2D.setFileToRemove(fontFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2381
            synchronized (FontManager.class) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2382
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2383
                if (tmpFontFiles == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2384
                    tmpFontFiles = new Vector<File>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2385
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2386
                tmpFontFiles.add(fontFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2387
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2388
                if (fileCloser == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2389
                    final Runnable fileCloserRunnable = new Runnable() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2390
                      public void run() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2391
                         java.security.AccessController.doPrivileged(
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2392
                         new java.security.PrivilegedAction() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2393
                         public Object run() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2394
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2395
                            for (int i=0;i<CHANNELPOOLSIZE;i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2396
                                if (fontFileCache[i] != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2397
                                    try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2398
                                        fontFileCache[i].close();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2399
                                    } catch (Exception e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2400
                                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2401
                                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2402
                            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2403
                            if (tmpFontFiles != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2404
                                File[] files = new File[tmpFontFiles.size()];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2405
                                files = tmpFontFiles.toArray(files);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2406
                                for (int f=0; f<files.length;f++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2407
                                    try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2408
                                        files[f].delete();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2409
                                    } catch (Exception e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2410
                                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2411
                                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2412
                            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2413
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2414
                            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2415
                          }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2416
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2417
                          });
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2418
                      }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2419
                    };
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2420
                    java.security.AccessController.doPrivileged(
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2421
                       new java.security.PrivilegedAction() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2422
                          public Object run() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2423
                              /* The thread must be a member of a thread group
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2424
                               * which will not get GCed before VM exit.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2425
                               * Make its parent the top-level thread group.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2426
                               */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2427
                              ThreadGroup tg =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2428
                                  Thread.currentThread().getThreadGroup();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2429
                              for (ThreadGroup tgn = tg;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2430
                                   tgn != null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2431
                                   tg = tgn, tgn = tg.getParent());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2432
                              fileCloser = new Thread(tg, fileCloserRunnable);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2433
                              Runtime.getRuntime().addShutdownHook(fileCloser);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2434
                              return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2435
                          }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2436
                    });
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2437
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2438
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2439
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2440
        return font2D;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2441
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2442
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2443
    /* remind: used in X11GraphicsEnvironment and called often enough
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2444
     * that we ought to obsolete this code
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2445
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2446
    public synchronized static String getFullNameByFileName(String fileName) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2447
        PhysicalFont[] physFonts = getPhysicalFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2448
        for (int i=0;i<physFonts.length;i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2449
            if (physFonts[i].platName.equals(fileName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2450
                return (physFonts[i].getFontName(null));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2451
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2452
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2453
        return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2454
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2455
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2456
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2457
     * This is called when font is determined to be invalid/bad.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2458
     * It designed to be called (for example) by the font scaler
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2459
     * when in processing a font file it is discovered to be incorrect.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2460
     * This is different than the case where fonts are discovered to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2461
     * be incorrect during initial verification, as such fonts are
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2462
     * never registered.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2463
     * Handles to this font held are re-directed to a default font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2464
     * This default may not be an ideal substitute buts it better than
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2465
     * crashing This code assumes a PhysicalFont parameter as it doesn't
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2466
     * make sense for a Composite to be "bad".
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2467
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2468
    public static synchronized void deRegisterBadFont(Font2D font2D) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2469
        if (!(font2D instanceof PhysicalFont)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2470
            /* We should never reach here, but just in case */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2471
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2472
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2473
            if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2474
                logger.severe("Deregister bad font: " + font2D);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2475
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2476
            replaceFont((PhysicalFont)font2D, getDefaultPhysicalFont());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2477
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2478
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2479
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2480
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2481
     * This encapsulates all the work that needs to be done when a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2482
     * Font2D is replaced by a different Font2D.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2483
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2484
    public static synchronized void replaceFont(PhysicalFont oldFont,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2485
                                                PhysicalFont newFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2486
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2487
        if (oldFont.handle.font2D != oldFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2488
            /* already done */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2489
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2490
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2491
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2492
        /* If we try to replace the font with itself, that won't work,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2493
         * so pick any alternative physical font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2494
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2495
        if (oldFont == newFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2496
            if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2497
                logger.severe("Can't replace bad font with itself " + oldFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2498
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2499
            PhysicalFont[] physFonts = getPhysicalFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2500
            for (int i=0; i<physFonts.length;i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2501
                if (physFonts[i] != newFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2502
                    newFont = physFonts[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2503
                    break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2504
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2505
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2506
            if (oldFont == newFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2507
                if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2508
                    logger.severe("This is bad. No good physicalFonts found.");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2509
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2510
                return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2511
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2512
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2513
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2514
        /* eliminate references to this font, so it won't be located
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2515
         * by future callers, and will be eligible for GC when all
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2516
         * references are removed
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2517
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2518
        oldFont.handle.font2D = newFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2519
        physicalFonts.remove(oldFont.fullName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2520
        fullNameToFont.remove(oldFont.fullName.toLowerCase(Locale.ENGLISH));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2521
        FontFamily.remove(oldFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2522
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2523
        if (localeFullNamesToFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2524
            Map.Entry[] mapEntries =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2525
                (Map.Entry[])localeFullNamesToFont.entrySet().
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2526
                toArray(new Map.Entry[0]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2527
            /* Should I be replacing these, or just I just remove
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2528
             * the names from the map?
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2529
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2530
            for (int i=0; i<mapEntries.length;i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2531
                if (mapEntries[i].getValue() == oldFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2532
                    try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2533
                        mapEntries[i].setValue(newFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2534
                    } catch (Exception e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2535
                        /* some maps don't support this operation.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2536
                         * In this case just give up and remove the entry.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2537
                         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2538
                        localeFullNamesToFont.remove(mapEntries[i].getKey());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2539
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2540
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2541
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2542
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2543
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2544
        for (int i=0; i<maxCompFont; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2545
            /* Deferred initialization of composites shouldn't be
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2546
             * a problem for this case, since a font must have been
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2547
             * initialised to be discovered to be bad.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2548
             * Some JRE composites on Solaris use two versions of the same
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2549
             * font. The replaced font isn't bad, just "smaller" so there's
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2550
             * no need to make the slot point to the new font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2551
             * Since composites have a direct reference to the Font2D (not
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2552
             * via a handle) making this substitution is not safe and could
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2553
             * cause an additional problem and so this substitution is
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2554
             * warranted only when a font is truly "bad" and could cause
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2555
             * a crash. So we now replace it only if its being substituted
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2556
             * with some font other than a fontconfig rank font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2557
             * Since in practice a substitution will have the same rank
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2558
             * this may never happen, but the code is safer even if its
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2559
             * also now a no-op.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2560
             * The only obvious "glitch" from this stems from the current
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2561
             * implementation that when asked for the number of glyphs in a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2562
             * composite it lies and returns the number in slot 0 because
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2563
             * composite glyphs aren't contiguous. Since we live with that
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2564
             * we can live with the glitch that depending on how it was
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2565
             * initialised a composite may return different values for this.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2566
             * Fixing the issues with composite glyph ids is tricky as
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2567
             * there are exclusion ranges and unlike other fonts even the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2568
             * true "numGlyphs" isn't a contiguous range. Likely the only
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2569
             * solution is an API that returns an array of glyph ranges
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2570
             * which takes precedence over the existing API. That might
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2571
             * also need to address excluding ranges which represent a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2572
             * code point supported by an earlier component.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2573
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2574
            if (newFont.getRank() > Font2D.FONT_CONFIG_RANK) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2575
                compFonts[i].replaceComponentFont(oldFont, newFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2576
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2577
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2578
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2579
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2580
    private static synchronized void loadLocaleNames() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2581
        if (localeFullNamesToFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2582
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2583
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2584
        localeFullNamesToFont = new HashMap<String, TrueTypeFont>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2585
        Font2D[] fonts = getRegisteredFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2586
        for (int i=0; i<fonts.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2587
            if (fonts[i] instanceof TrueTypeFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2588
                TrueTypeFont ttf = (TrueTypeFont)fonts[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2589
                String[] fullNames = ttf.getAllFullNames();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2590
                for (int n=0; n<fullNames.length; n++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2591
                    localeFullNamesToFont.put(fullNames[n], ttf);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2592
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2593
                FontFamily family = FontFamily.getFamily(ttf.familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2594
                if (family != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2595
                    FontFamily.addLocaleNames(family, ttf.getAllFamilyNames());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2596
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2597
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2598
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2599
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2600
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2601
    /* This replicate the core logic of findFont2D but operates on
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2602
     * all the locale names. This hasn't been merged into findFont2D to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2603
     * keep the logic simpler and reduce overhead, since this case is
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2604
     * almost never used. The main case in which it is called is when
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2605
     * a bogus font name is used and we need to check all possible names
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2606
     * before returning the default case.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2607
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2608
    private static Font2D findFont2DAllLocales(String name, int style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2609
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2610
        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2611
            logger.info("Searching localised font names for:" + name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2612
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2613
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2614
        /* If reach here and no match has been located, then if we have
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2615
         * not yet built the map of localeFullNamesToFont for TT fonts, do so
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2616
         * now. This method must be called after all fonts have been loaded.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2617
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2618
        if (localeFullNamesToFont == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2619
            loadLocaleNames();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2620
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2621
        String lowerCaseName = name.toLowerCase();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2622
        Font2D font = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2623
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2624
        /* First see if its a family name. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2625
        FontFamily family = FontFamily.getLocaleFamily(lowerCaseName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2626
        if (family != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2627
          font = family.getFont(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2628
          if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2629
            font = family.getClosestStyle(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2630
          }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2631
          if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2632
              return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2633
          }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2634
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2635
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2636
        /* If it wasn't a family name, it should be a full name. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2637
        synchronized (FontManager.class) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2638
            font = localeFullNamesToFont.get(name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2639
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2640
        if (font != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2641
            if (font.style == style || style == Font.PLAIN) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2642
                return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2643
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2644
                family = FontFamily.getFamily(font.getFamilyName(null));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2645
                if (family != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2646
                    Font2D familyFont = family.getFont(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2647
                    /* We exactly matched the requested style, use it! */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2648
                    if (familyFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2649
                        return familyFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2650
                    } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2651
                        familyFont = family.getClosestStyle(style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2652
                        if (familyFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2653
                            /* The next check is perhaps one
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2654
                             * that shouldn't be done. ie if we get this
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2655
                             * far we have probably as close a match as we
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2656
                             * are going to get. We could load all fonts to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2657
                             * see if somehow some parts of the family are
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2658
                             * loaded but not all of it.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2659
                             * This check is commented out for now.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2660
                             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2661
                            if (!familyFont.canDoStyle(style)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2662
                                familyFont = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2663
                            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2664
                            return familyFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2665
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2666
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2667
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2668
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2669
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2670
        return font;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2671
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2672
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2673
    /* Supporting "alternate" composite fonts on 2D graphics objects
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2674
     * is accessed by the application by calling methods on the local
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2675
     * GraphicsEnvironment. The overall implementation is described
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2676
     * in one place, here, since otherwise the implementation is spread
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2677
     * around it may be difficult to track.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2678
     * The methods below call into SunGraphicsEnvironment which creates a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2679
     * new FontConfiguration instance. The FontConfiguration class,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2680
     * and its platform sub-classes are updated to take parameters requesting
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2681
     * these behaviours. This is then used to create new composite font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2682
     * instances. Since this calls the initCompositeFont method in
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2683
     * SunGraphicsEnvironment it performs the same initialization as is
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2684
     * performed normally. There may be some duplication of effort, but
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2685
     * that code is already written to be able to perform properly if called
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2686
     * to duplicate work. The main difference is that if we detect we are
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2687
     * running in an applet/browser/Java plugin environment these new fonts
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2688
     * are not placed in the "default" maps but into an AppContext instance.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2689
     * The font lookup mechanism in java.awt.Font.getFont2D() is also updated
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2690
     * so that look-up for composite fonts will in that case always
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2691
     * do a lookup rather than returning a cached result.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2692
     * This is inefficient but necessary else singleton java.awt.Font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2693
     * instances would not retrieve the correct Font2D for the appcontext.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2694
     * sun.font.FontManager.findFont2D is also updated to that it uses
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2695
     * a name map cache specific to that appcontext.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2696
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2697
     * Getting an AppContext is expensive, so there is a global variable
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2698
     * that records whether these methods have ever been called and can
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2699
     * avoid the expense for almost all applications. Once the correct
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2700
     * CompositeFont is associated with the Font, everything should work
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2701
     * through existing mechanisms.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2702
     * A special case is that GraphicsEnvironment.getAllFonts() must
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2703
     * return an AppContext specific list.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2704
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2705
     * Calling the methods below is "heavyweight" but it is expected that
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2706
     * these methods will be called very rarely.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2707
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2708
     * If usingPerAppContextComposites is true, we are in "applet"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2709
     * (eg browser) enviroment and at least one context has selected
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2710
     * an alternate composite font behaviour.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2711
     * If usingAlternateComposites is true, we are not in an "applet"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2712
     * environment and the (single) application has selected
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2713
     * an alternate composite font behaviour.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2714
     *
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2715
     * - Printing: The implementation delegates logical fonts to an AWT
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2716
     * mechanism which cannot use these alternate configurations.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2717
     * We can detect that alternate fonts are in use and back-off to 2D, but
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2718
     * that uses outlines. Much of this can be fixed with additional work
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2719
     * but that may have to wait. The results should be correct, just not
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2720
     * optimal.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2721
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2722
    private static final Object altJAFontKey       = new Object();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2723
    private static final Object localeFontKey       = new Object();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2724
    private static final Object proportionalFontKey = new Object();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2725
    public static boolean usingPerAppContextComposites = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2726
    private static boolean usingAlternateComposites = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2727
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2728
    /* These values are used only if we are running as a standalone
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2729
     * application, as determined by maybeMultiAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2730
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2731
    private static boolean gAltJAFont = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2732
    private static boolean gLocalePref = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2733
    private static boolean gPropPref = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2734
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2735
    /* This method doesn't check if alternates are selected in this app
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2736
     * context. Its used by the FontMetrics caching code which in such
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2737
     * a case cannot retrieve a cached metrics solely on the basis of
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2738
     * the Font.equals() method since it needs to also check if the Font2D
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2739
     * is the same.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2740
     * We also use non-standard composites for Swing native L&F fonts on
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2741
     * Windows. In that case the policy is that the metrics reported are
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2742
     * based solely on the physical font in the first slot which is the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2743
     * visible java.awt.Font. So in that case the metrics cache which tests
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2744
     * the Font does what we want. In the near future when we expand the GTK
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2745
     * logical font definitions we may need to revisit this if GTK reports
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2746
     * combined metrics instead. For now though this test can be simple.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2747
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2748
    static boolean maybeUsingAlternateCompositeFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2749
       return usingAlternateComposites || usingPerAppContextComposites;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2750
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2751
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2752
    public static boolean usingAlternateCompositeFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2753
        return (usingAlternateComposites ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2754
                (usingPerAppContextComposites &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2755
                AppContext.getAppContext().get(CompositeFont.class) != null));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2756
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2757
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2758
    private static boolean maybeMultiAppContext() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2759
        Boolean appletSM = (Boolean)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2760
            java.security.AccessController.doPrivileged(
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2761
                new java.security.PrivilegedAction() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2762
                        public Object run() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2763
                            SecurityManager sm = System.getSecurityManager();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2764
                            return new Boolean
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2765
                                (sm instanceof sun.applet.AppletSecurity);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2766
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2767
                    });
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2768
        return appletSM.booleanValue();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2769
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2770
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2771
    /* Modifies the behaviour of a subsequent call to preferLocaleFonts()
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2772
     * to use Mincho instead of Gothic for dialoginput in JA locales
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2773
     * on windows. Not needed on other platforms.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2774
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2775
    public static synchronized void useAlternateFontforJALocales() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2776
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2777
        if (!isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2778
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2779
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2780
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2781
        initSGEnv();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2782
        if (!maybeMultiAppContext()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2783
            gAltJAFont = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2784
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2785
            AppContext appContext = AppContext.getAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2786
            appContext.put(altJAFontKey, altJAFontKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2787
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2788
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2789
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2790
    public static boolean usingAlternateFontforJALocales() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2791
        if (!maybeMultiAppContext()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2792
            return gAltJAFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2793
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2794
            AppContext appContext = AppContext.getAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2795
            return appContext.get(altJAFontKey) == altJAFontKey;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2796
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2797
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2798
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2799
    public static synchronized void preferLocaleFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2800
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2801
        initSGEnv();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2802
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2803
        /* Test if re-ordering will have any effect */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2804
        if (!FontConfiguration.willReorderForStartupLocale()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2805
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2806
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2807
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2808
        if (!maybeMultiAppContext()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2809
            if (gLocalePref == true) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2810
                return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2811
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2812
            gLocalePref = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2813
            sgEnv.createCompositeFonts(fontNameCache, gLocalePref, gPropPref);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2814
            usingAlternateComposites = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2815
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2816
            AppContext appContext = AppContext.getAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2817
            if (appContext.get(localeFontKey) == localeFontKey) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2818
                return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2819
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2820
            appContext.put(localeFontKey, localeFontKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2821
            boolean acPropPref =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2822
                appContext.get(proportionalFontKey) == proportionalFontKey;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2823
            ConcurrentHashMap<String, Font2D>
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2824
                altNameCache = new ConcurrentHashMap<String, Font2D> ();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2825
            /* If there is an existing hashtable, we can drop it. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2826
            appContext.put(CompositeFont.class, altNameCache);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2827
            usingPerAppContextComposites = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2828
            sgEnv.createCompositeFonts(altNameCache, true, acPropPref);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2829
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2830
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2831
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2832
    public static synchronized void preferProportionalFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2833
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2834
        /* If no proportional fonts are configured, there's no need
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2835
         * to take any action.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2836
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2837
        if (!FontConfiguration.hasMonoToPropMap()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2838
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2839
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2840
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2841
        initSGEnv();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2842
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2843
        if (!maybeMultiAppContext()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2844
            if (gPropPref == true) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2845
                return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2846
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2847
            gPropPref = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2848
            sgEnv.createCompositeFonts(fontNameCache, gLocalePref, gPropPref);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2849
            usingAlternateComposites = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2850
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2851
            AppContext appContext = AppContext.getAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2852
            if (appContext.get(proportionalFontKey) == proportionalFontKey) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2853
                return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2854
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2855
            appContext.put(proportionalFontKey, proportionalFontKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2856
            boolean acLocalePref =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2857
                appContext.get(localeFontKey) == localeFontKey;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2858
            ConcurrentHashMap<String, Font2D>
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2859
                altNameCache = new ConcurrentHashMap<String, Font2D> ();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2860
            /* If there is an existing hashtable, we can drop it. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2861
            appContext.put(CompositeFont.class, altNameCache);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2862
            usingPerAppContextComposites = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2863
            sgEnv.createCompositeFonts(altNameCache, acLocalePref, true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2864
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2865
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2866
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2867
    private static HashSet<String> installedNames = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2868
    private static HashSet<String> getInstalledNames() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2869
        if (installedNames == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2870
           Locale l = sgEnv.getSystemStartupLocale();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2871
           String[] installedFamilies = sgEnv.getInstalledFontFamilyNames(l);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2872
           Font[] installedFonts = sgEnv.getAllInstalledFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2873
           HashSet<String> names = new HashSet<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2874
           for (int i=0; i<installedFamilies.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2875
               names.add(installedFamilies[i].toLowerCase(l));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2876
           }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2877
           for (int i=0; i<installedFonts.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2878
               names.add(installedFonts[i].getFontName(l).toLowerCase(l));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2879
           }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2880
           installedNames = names;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2881
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2882
        return installedNames;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2883
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2884
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2885
    /* Keys are used to lookup per-AppContext Hashtables */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2886
    private static final Object regFamilyKey  = new Object();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2887
    private static final Object regFullNameKey = new Object();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2888
    private static Hashtable<String,FontFamily> createdByFamilyName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2889
    private static Hashtable<String,Font2D>     createdByFullName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2890
    private static boolean fontsAreRegistered = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2891
    private static boolean fontsAreRegisteredPerAppContext = false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2892
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2893
    public static boolean registerFont(Font font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2894
        /* This method should not be called with "null".
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2895
         * It is the caller's responsibility to ensure that.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2896
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2897
        if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2898
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2899
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2900
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2901
        /* Initialise these objects only once we start to use this API */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2902
        synchronized (regFamilyKey) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2903
            if (createdByFamilyName == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2904
                createdByFamilyName = new Hashtable<String,FontFamily>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2905
                createdByFullName = new Hashtable<String,Font2D>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2906
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2907
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2908
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2909
        if (!isCreatedFont(font)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2910
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2911
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2912
        if (sgEnv == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2913
            initSGEnv();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2914
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2915
        /* We want to ensure that this font cannot override existing
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2916
         * installed fonts. Check these conditions :
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2917
         * - family name is not that of an installed font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2918
         * - full name is not that of an installed font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2919
         * - family name is not the same as the full name of an installed font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2920
         * - full name is not the same as the family name of an installed font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2921
         * The last two of these may initially look odd but the reason is
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2922
         * that (unfortunately) Font constructors do not distinuguish these.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2923
         * An extreme example of such a problem would be a font which has
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2924
         * family name "Dialog.Plain" and full name of "Dialog".
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2925
         * The one arguably overly stringent restriction here is that if an
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2926
         * application wants to supply a new member of an existing family
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2927
         * It will get rejected. But since the JRE can perform synthetic
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2928
         * styling in many cases its not necessary.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2929
         * We don't apply the same logic to registered fonts. If apps want
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2930
         * to do this lets assume they have a reason. It won't cause problems
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2931
         * except for themselves.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2932
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2933
        HashSet<String> names = getInstalledNames();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2934
        Locale l = sgEnv.getSystemStartupLocale();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2935
        String familyName = font.getFamily(l).toLowerCase();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2936
        String fullName = font.getFontName(l).toLowerCase();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2937
        if (names.contains(familyName) || names.contains(fullName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2938
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2939
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2940
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2941
        /* Checks passed, now register the font */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2942
        Hashtable<String,FontFamily> familyTable;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2943
        Hashtable<String,Font2D> fullNameTable;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2944
        if (!maybeMultiAppContext()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2945
            familyTable = createdByFamilyName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2946
            fullNameTable = createdByFullName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2947
            fontsAreRegistered = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2948
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2949
            AppContext appContext = AppContext.getAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2950
            familyTable =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2951
                (Hashtable<String,FontFamily>)appContext.get(regFamilyKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2952
            fullNameTable =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2953
                (Hashtable<String,Font2D>)appContext.get(regFullNameKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2954
            if (familyTable == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2955
                familyTable = new Hashtable<String,FontFamily>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2956
                fullNameTable = new Hashtable<String,Font2D>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2957
                appContext.put(regFamilyKey, familyTable);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2958
                appContext.put(regFullNameKey, fullNameTable);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2959
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2960
            fontsAreRegisteredPerAppContext = true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2961
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2962
        /* Create the FontFamily and add font to the tables */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2963
        Font2D font2D = getFont2D(font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2964
        int style = font2D.getStyle();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2965
        FontFamily family = familyTable.get(familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2966
        if (family == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2967
            family = new FontFamily(font.getFamily(l));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2968
            familyTable.put(familyName, family);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2969
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2970
        /* Remove name cache entries if not using app contexts.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2971
         * To accommodate a case where code may have registered first a plain
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2972
         * family member and then used it and is now registering a bold family
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2973
         * member, we need to remove all members of the family, so that the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2974
         * new style can get picked up rather than continuing to synthesise.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2975
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2976
        if (fontsAreRegistered) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2977
            removeFromCache(family.getFont(Font.PLAIN));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2978
            removeFromCache(family.getFont(Font.BOLD));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2979
            removeFromCache(family.getFont(Font.ITALIC));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2980
            removeFromCache(family.getFont(Font.BOLD|Font.ITALIC));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2981
            removeFromCache(fullNameTable.get(fullName));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2982
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2983
        family.setFont(font2D, style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2984
        fullNameTable.put(fullName, font2D);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2985
        return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2986
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2987
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2988
    /* Remove from the name cache all references to the Font2D */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2989
    private static void removeFromCache(Font2D font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2990
        if (font == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2991
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2992
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2993
        String[] keys = (String[])(fontNameCache.keySet().toArray(STR_ARRAY));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2994
        for (int k=0; k<keys.length;k++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2995
            if (fontNameCache.get(keys[k]) == font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2996
                fontNameCache.remove(keys[k]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2997
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2998
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  2999
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3000
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3001
    // It may look odd to use TreeMap but its more convenient to the caller.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3002
    public static TreeMap<String, String> getCreatedFontFamilyNames() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3003
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3004
        Hashtable<String,FontFamily> familyTable;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3005
        if (fontsAreRegistered) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3006
            familyTable = createdByFamilyName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3007
        } else if (fontsAreRegisteredPerAppContext) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3008
            AppContext appContext = AppContext.getAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3009
            familyTable =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3010
                (Hashtable<String,FontFamily>)appContext.get(regFamilyKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3011
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3012
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3013
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3014
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3015
        Locale l = sgEnv.getSystemStartupLocale();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3016
        synchronized (familyTable) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3017
            TreeMap<String, String> map = new TreeMap<String, String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3018
            for (FontFamily f : familyTable.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3019
                Font2D font2D = f.getFont(Font.PLAIN);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3020
                if (font2D == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3021
                    font2D = f.getClosestStyle(Font.PLAIN);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3022
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3023
                String name = font2D.getFamilyName(l);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3024
                map.put(name.toLowerCase(l), name);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3025
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3026
            return map;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3027
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3028
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3029
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3030
    public static Font[] getCreatedFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3031
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3032
        Hashtable<String,Font2D> nameTable;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3033
        if (fontsAreRegistered) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3034
            nameTable = createdByFullName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3035
        } else if (fontsAreRegisteredPerAppContext) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3036
            AppContext appContext = AppContext.getAppContext();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3037
            nameTable =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3038
                (Hashtable<String,Font2D>)appContext.get(regFullNameKey);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3039
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3040
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3041
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3042
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3043
        Locale l = sgEnv.getSystemStartupLocale();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3044
        synchronized (nameTable) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3045
            Font[] fonts = new Font[nameTable.size()];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3046
            int i=0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3047
            for (Font2D font2D : nameTable.values()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3048
                fonts[i++] = new Font(font2D.getFontName(l), Font.PLAIN, 1);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3049
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3050
            return fonts;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3051
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3052
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3053
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3054
    /* Begin support for GTK Look and Feel - query libfontconfig and
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3055
     * return a composite Font to Swing that uses the desktop font(s).
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3056
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3057
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3058
    /* A small "map" from GTK/fontconfig names to the equivalent JDK
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3059
     * logical font name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3060
    */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3061
    private static final String[][] nameMap = {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3062
        {"sans",       "sansserif"},
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3063
        {"sans-serif", "sansserif"},
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3064
        {"serif",      "serif"},
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3065
        {"monospace",  "monospaced"}
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3066
    };
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3067
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3068
    public static String mapFcName(String name) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3069
        for (int i = 0; i < nameMap.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3070
            if (name.equals(nameMap[i][0])) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3071
                return nameMap[i][1];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3072
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3073
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3074
        return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3075
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3076
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3077
    /* fontconfig recognises slants roman, italic, as well as oblique,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3078
     * and a slew of weights, where the ones that matter here are
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3079
     * regular and bold.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3080
     * To fully qualify what we want, we can for example ask for (eg)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3081
     * Font.PLAIN             : "serif:regular:roman"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3082
     * Font.BOLD              : "serif:bold:roman"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3083
     * Font.ITALIC            : "serif:regular:italic"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3084
     * Font.BOLD|Font.ITALIC  : "serif:bold:italic"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3085
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3086
    private static String[] fontConfigNames = {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3087
        "sans:regular:roman",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3088
        "sans:bold:roman",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3089
        "sans:regular:italic",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3090
        "sans:bold:italic",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3091
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3092
        "serif:regular:roman",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3093
        "serif:bold:roman",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3094
        "serif:regular:italic",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3095
        "serif:bold:italic",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3096
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3097
        "monospace:regular:roman",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3098
        "monospace:bold:roman",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3099
        "monospace:regular:italic",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3100
        "monospace:bold:italic",
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3101
    };
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3102
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3103
    /* This class is just a data structure.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3104
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3105
    private static class FontConfigInfo {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3106
        String fcName;            // eg sans
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3107
        String fcFamily;          // eg sans
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3108
        String jdkName;           // eg sansserif
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3109
        int style;                // eg 0=PLAIN
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3110
        String familyName;        // eg Bitstream Vera Sans
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3111
        String fontFile;          // eg /usr/X11/lib/fonts/foo.ttf
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3112
        //boolean preferBitmaps;    // if embedded bitmaps preferred over AA
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3113
        CompositeFont compFont;   // null if not yet created/known.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3114
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3115
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3116
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3117
    private static String getFCLocaleStr() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3118
        Locale l = SunToolkit.getStartupLocale();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3119
        String localeStr = l.getLanguage();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3120
        String country = l.getCountry();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3121
        if (!country.equals("")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3122
            localeStr = localeStr + "-" + country;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3123
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3124
        return localeStr;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3125
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3126
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3127
    private static native int
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3128
        getFontConfigAASettings(String locale, String fcFamily);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3129
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3130
    /* This is public solely so that for debugging purposes it can be called
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3131
     * with other names, which might (eg) include a size, eg "sans-24"
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3132
     * The return value is a text aa rendering hint value.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3133
     * Normally we should call the no-args version.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3134
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3135
    public static Object getFontConfigAAHint(String fcFamily) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3136
        if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3137
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3138
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3139
            int hint = getFontConfigAASettings(getFCLocaleStr(), fcFamily);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3140
            if (hint < 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3141
                return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3142
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3143
                return SunHints.Value.get(SunHints.INTKEY_TEXT_ANTIALIASING,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3144
                                          hint);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3145
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3146
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3147
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3148
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3149
    /* Called from code that needs to know what are the AA settings
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3150
     * that apps using FC would pick up for the default desktop font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3151
     * Note apps can change the default desktop font. etc, so this
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3152
     * isn't certain to be right but its going to correct for most cases.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3153
     * Native return values map to the text aa values in sun.awt.SunHints.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3154
     * which is used to look up the renderinghint value object.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3155
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3156
    public static Object getFontConfigAAHint() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3157
        return getFontConfigAAHint("sans");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3158
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3159
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3160
    /* This array has the array elements created in Java code and is
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3161
     * passed down to native to be filled in.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3162
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3163
    private static FontConfigInfo[] fontConfigFonts;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3164
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3165
    /* Return an array of FontConfigInfo structs describing the primary
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3166
     * font located for each of fontconfig/GTK/Pango's logical font names.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3167
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3168
    private static native void getFontConfig(String locale,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3169
                                             FontConfigInfo[] fonts);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3170
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3171
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3172
    /* This can be made public if it's needed to force a re-read
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3173
     * rather than using the cached values. The re-read would be needed
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3174
     * only if some event signalled that the fontconfig has changed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3175
     * In that event this method would need to return directly the array
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3176
     * to be used by the caller in case it subsequently changed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3177
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3178
    private static void initFontConfigFonts() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3179
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3180
        if (fontConfigFonts != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3181
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3182
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3183
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3184
        if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3185
            return;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3186
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3187
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3188
        long t0 = 0;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3189
        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3190
            t0 = System.currentTimeMillis();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3191
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3192
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3193
        FontConfigInfo[] fontArr = new FontConfigInfo[fontConfigNames.length];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3194
        for (int i = 0; i< fontArr.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3195
            fontArr[i] = new FontConfigInfo();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3196
            fontArr[i].fcName = fontConfigNames[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3197
            int colonPos = fontArr[i].fcName.indexOf(':');
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3198
            fontArr[i].fcFamily = fontArr[i].fcName.substring(0, colonPos);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3199
            fontArr[i].jdkName = mapFcName(fontArr[i].fcFamily);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3200
            fontArr[i].style = i % 4; // depends on array order.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3201
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3202
        getFontConfig(getFCLocaleStr(), fontArr);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3203
        fontConfigFonts = fontArr;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3204
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3205
        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3206
            long t1 = System.currentTimeMillis();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3207
            logger.info("Time spent accessing fontconfig="+(t1-t0)+"ms.");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3208
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3209
            for (int i = 0; i< fontConfigFonts.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3210
                FontConfigInfo fci = fontConfigFonts[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3211
                logger.info("FC font " + fci.fcName+" maps to family " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3212
                            fci.familyName + " in file " + fci.fontFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3213
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3214
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3215
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3216
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3217
    private static PhysicalFont registerFromFcInfo(FontConfigInfo fcInfo) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3218
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3219
        /* If it's a TTC file we need to know that as we will need to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3220
         * make sure we return the right font */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3221
        int offset = fcInfo.fontFile.length()-4;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3222
        if (offset <= 0) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3223
            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3224
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3225
        String ext = fcInfo.fontFile.substring(offset).toLowerCase();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3226
        boolean isTTC = ext.equals(".ttc");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3227
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3228
        /* If this file is already registered, can just return its font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3229
         * However we do need to check in case it's a TTC as we need
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3230
         * a specific font, so rather than directly returning it, let
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3231
         * findFont2D resolve that.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3232
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3233
        PhysicalFont physFont = registeredFontFiles.get(fcInfo.fontFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3234
        if (physFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3235
            if (isTTC) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3236
                Font2D f2d = findFont2D(fcInfo.familyName,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3237
                                        fcInfo.style, NO_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3238
                if (f2d instanceof PhysicalFont) { /* paranoia */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3239
                    return (PhysicalFont)f2d;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3240
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3241
                    return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3242
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3243
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3244
                return physFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3245
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3246
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3247
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3248
        /* If the font may hide a JRE font (eg fontconfig says it is
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3249
         * Lucida Sans), we want to use the JRE version, so make it
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3250
         * point to the JRE font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3251
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3252
        physFont = findJREDeferredFont(fcInfo.familyName, fcInfo.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3253
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3254
        /* It is also possible the font file is on the "deferred" list,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3255
         * in which case we can just initialise it now.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3256
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3257
        if (physFont == null &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3258
            deferredFontFiles.get(fcInfo.fontFile) != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3259
            physFont = initialiseDeferredFont(fcInfo.fontFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3260
            /* use findFont2D to get the right font from TTC's */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3261
            if (physFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3262
                if (isTTC) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3263
                    Font2D f2d = findFont2D(fcInfo.familyName,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3264
                                            fcInfo.style, NO_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3265
                    if (f2d instanceof PhysicalFont) { /* paranoia */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3266
                        return (PhysicalFont)f2d;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3267
                    } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3268
                        return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3269
                    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3270
                } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3271
                    return physFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3272
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3273
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3274
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3275
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3276
        /* In the majority of cases we reach here, and need to determine
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3277
         * the type and rank to register the font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3278
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3279
        if (physFont == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3280
            int fontFormat = FONTFORMAT_NONE;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3281
            int fontRank = Font2D.UNKNOWN_RANK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3282
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3283
            if (ext.equals(".ttf") || isTTC) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3284
                fontFormat = FONTFORMAT_TRUETYPE;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3285
                fontRank = Font2D.TTF_RANK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3286
            } else if (ext.equals(".pfa") || ext.equals(".pfb")) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3287
                fontFormat = FONTFORMAT_TYPE1;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3288
                fontRank = Font2D.TYPE1_RANK;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3289
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3290
            physFont = registerFontFile(fcInfo.fontFile, null,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3291
                                      fontFormat, true, fontRank);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3292
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3293
        return physFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3294
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3295
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3296
    private static String[] getPlatformFontDirs() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3297
        String path = getFontPath(true);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3298
        StringTokenizer parser =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3299
            new StringTokenizer(path, File.pathSeparator);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3300
        ArrayList<String> pathList = new ArrayList<String>();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3301
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3302
            while (parser.hasMoreTokens()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3303
                pathList.add(parser.nextToken());
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3304
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3305
        } catch (NoSuchElementException e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3306
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3307
        return pathList.toArray(new String[0]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3308
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3309
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3310
    /** returns an array of two strings. The first element is the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3311
     * name of the font. The second element is the file name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3312
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3313
    private static String[] defaultPlatformFont = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3314
    public static String[] getDefaultPlatformFont() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3315
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3316
        if (defaultPlatformFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3317
            return defaultPlatformFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3318
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3319
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3320
        String[] info = new String[2];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3321
        if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3322
            info[0] = "Arial";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3323
            info[1] = "c:\\windows\\fonts";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3324
            final String[] dirs = getPlatformFontDirs();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3325
            if (dirs.length > 1) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3326
                String dir = (String)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3327
                    AccessController.doPrivileged(new PrivilegedAction() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3328
                        public Object run() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3329
                            for (int i=0; i<dirs.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3330
                                String path =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3331
                                    dirs[i] + File.separator + "arial.ttf";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3332
                                File file = new File(path);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3333
                                if (file.exists()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3334
                                    return dirs[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3335
                                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3336
                            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3337
                            return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3338
                        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3339
                });
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3340
                if (dir != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3341
                    info[1] = dir;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3342
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3343
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3344
                info[1] = dirs[0];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3345
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3346
            info[1] = info[1] + File.separator + "arial.ttf";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3347
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3348
            initFontConfigFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3349
            for (int i=0; i<fontConfigFonts.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3350
                if ("sans".equals(fontConfigFonts[i].fcFamily) &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3351
                    0 == fontConfigFonts[i].style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3352
                    info[0] = fontConfigFonts[i].familyName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3353
                    info[1] = fontConfigFonts[i].fontFile;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3354
                    break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3355
                }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3356
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3357
            /* Absolute last ditch attempt in the face of fontconfig problems.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3358
             * If we didn't match, pick the first, or just make something
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3359
             * up so we don't NPE.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3360
             */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3361
            if (info[0] == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3362
                 if (fontConfigFonts.length > 0 &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3363
                     fontConfigFonts[0].fontFile != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3364
                     info[0] = fontConfigFonts[0].familyName;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3365
                     info[1] = fontConfigFonts[0].fontFile;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3366
                 } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3367
                     info[0] = "Dialog";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3368
                     info[1] = "/dialog.ttf";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3369
                 }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3370
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3371
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3372
        defaultPlatformFont = info;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3373
        return defaultPlatformFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3374
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3375
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3376
    private FontConfigInfo getFontConfigInfo() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3377
         initFontConfigFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3378
         for (int i=0; i<fontConfigFonts.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3379
             if ("sans".equals(fontConfigFonts[i].fcFamily) &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3380
                 0 == fontConfigFonts[i].style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3381
                 return fontConfigFonts[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3382
             }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3383
         }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3384
         return null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3385
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3386
    /*
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3387
     * We need to return a Composite font which has as the font in
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3388
     * its first slot one obtained from fontconfig.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3389
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3390
    private static CompositeFont getFontConfigFont(String name, int style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3391
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3392
        name = name.toLowerCase();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3393
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3394
        initFontConfigFonts();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3395
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3396
        FontConfigInfo fcInfo = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3397
        for (int i=0; i<fontConfigFonts.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3398
            if (name.equals(fontConfigFonts[i].fcFamily) &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3399
                style == fontConfigFonts[i].style) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3400
                fcInfo = fontConfigFonts[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3401
                break;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3402
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3403
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3404
        if (fcInfo == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3405
            fcInfo = fontConfigFonts[0];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3406
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3407
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3408
        if (logging) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3409
            logger.info("FC name=" + name + " style=" + style + " uses " +
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3410
                        fcInfo.familyName + " in file: " + fcInfo.fontFile);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3411
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3412
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3413
        if (fcInfo.compFont != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3414
            return fcInfo.compFont;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3415
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3416
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3417
        /* jdkFont is going to be used for slots 1..N and as a fallback.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3418
         * Slot 0 will be the physical font from fontconfig.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3419
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3420
        CompositeFont jdkFont = (CompositeFont)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3421
            findFont2D(fcInfo.jdkName, style, LOGICAL_FALLBACK);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3422
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3423
        if (fcInfo.familyName == null || fcInfo.fontFile == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3424
            return (fcInfo.compFont = jdkFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3425
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3426
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3427
        /* First, see if the family and exact style is already registered.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3428
         * If it is, use it. If it's not, then try to register it.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3429
         * If that registration fails (signalled by null) just return the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3430
         * regular JDK composite.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3431
         * Algorithmically styled fonts won't match on exact style, so
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3432
         * will fall through this code, but the regisration code will
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3433
         * find that file already registered and return its font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3434
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3435
        FontFamily family = FontFamily.getFamily(fcInfo.familyName);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3436
        PhysicalFont physFont = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3437
        if (family != null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3438
            Font2D f2D = family.getFontWithExactStyleMatch(fcInfo.style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3439
            if (f2D instanceof PhysicalFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3440
                physFont = (PhysicalFont)f2D;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3441
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3442
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3443
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3444
        if (physFont == null || !fcInfo.fontFile.equals(physFont.platName)) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3445
            physFont = registerFromFcInfo(fcInfo);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3446
            if (physFont == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3447
                return (fcInfo.compFont = jdkFont);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3448
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3449
            family = FontFamily.getFamily(physFont.getFamilyName(null));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3450
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3451
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3452
        /* Now register the fonts in the family (the other styles) after
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3453
         * checking that they aren't already registered and are actually in
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3454
         * a different file. They may be the same file in CJK cases.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3455
         * For cases where they are different font files - eg as is common for
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3456
         * Latin fonts, then we rely on fontconfig to report these correctly.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3457
         * Assume that all styles of this font are found by fontconfig,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3458
         * so we can find all the family members which must be registered
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3459
         * together to prevent synthetic styling.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3460
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3461
        for (int i=0; i<fontConfigFonts.length; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3462
            FontConfigInfo fc = fontConfigFonts[i];
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3463
            if (fc != fcInfo &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3464
                physFont.getFamilyName(null).equals(fc.familyName) &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3465
                !fc.fontFile.equals(physFont.platName) &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3466
                family.getFontWithExactStyleMatch(fc.style) == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3467
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3468
                registerFromFcInfo(fontConfigFonts[i]);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3469
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3470
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3471
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3472
        /* Now we have a physical font. We will back this up with the JDK
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3473
         * logical font (sansserif, serif, or monospaced) that corresponds
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3474
         * to the Pango/GTK/FC logical font name.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3475
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3476
        return (fcInfo.compFont = new CompositeFont(physFont, jdkFont));
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3477
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3478
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3479
    /* This is called by Swing passing in a fontconfig family name
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3480
     * such as "sans". In return Swing gets a FontUIResource instance
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3481
     * that has queried fontconfig to resolve the font(s) used for this.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3482
     * Fontconfig will if asked return a list of fonts to give the largest
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3483
     * possible code point coverage.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3484
     * For now we use only the first font returned by fontconfig, and
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3485
     * back it up with the most closely matching JDK logical font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3486
     * Essentially this means pre-pending what we return now with fontconfig's
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3487
     * preferred physical font. This could lead to some duplication in cases,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3488
     * if we already included that font later. We probably should remove such
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3489
     * duplicates, but it is not a significant problem. It can be addressed
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3490
     * later as part of creating a Composite which uses more of the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3491
     * same fonts as fontconfig. At that time we also should pay more
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3492
     * attention to the special rendering instructions fontconfig returns,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3493
     * such as whether we should prefer embedded bitmaps over antialiasing.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3494
     * There's no way to express that via a Font at present.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3495
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3496
    public static FontUIResource getFontConfigFUIR(String fcFamily,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3497
                                                   int style, int size) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3498
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3499
        String mappedName = mapFcName(fcFamily);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3500
        if (mappedName == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3501
            mappedName = "sansserif";
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3502
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3503
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3504
        /* If GTK L&F were to be used on windows, we need to return
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3505
         * something. Since on windows Swing won't have the code to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3506
         * call fontconfig, even if it is present, fcFamily and mapped
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3507
         * name will default to sans and therefore sansserif so this
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3508
         * should be fine.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3509
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3510
        if (isWindows) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3511
            return new FontUIResource(mappedName, style, size);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3512
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3513
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3514
        CompositeFont font2D = getFontConfigFont(fcFamily, style);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3515
        if (font2D == null) { // Not expected, just a precaution.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3516
           return new FontUIResource(mappedName, style, size);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3517
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3518
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3519
        /* The name of the font will be that of the physical font in slot,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3520
         * but by setting the handle to that of the CompositeFont it
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3521
         * renders as that CompositeFont.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3522
         * It also needs to be marked as a created font which is the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3523
         * current mechanism to signal that deriveFont etc must copy
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3524
         * the handle from the original font.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3525
         */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3526
        FontUIResource fuir =
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3527
            new FontUIResource(font2D.getFamilyName(null), style, size);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3528
        setFont2D(fuir, font2D.handle);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3529
        setCreatedFont(fuir);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3530
        return fuir;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3531
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3532
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3533
    /* The following fields and methods which relate to layout
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3534
     * perhaps belong in some other class but FontManager is already
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3535
     * widely used as an entry point for other JDK code that needs
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3536
     * access to the font system internals.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3537
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3538
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3539
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3540
     * Referenced by code in the JDK which wants to test for the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3541
     * minimum char code for which layout may be required.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3542
     * Note that even basic latin text can benefit from ligatures,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3543
     * eg "ffi" but we presently apply those only if explicitly
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3544
     * requested with TextAttribute.LIGATURES_ON.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3545
     * The value here indicates the lowest char code for which failing
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3546
     * to invoke layout would prevent acceptable rendering.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3547
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3548
    public static final int MIN_LAYOUT_CHARCODE = 0x0300;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3549
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3550
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3551
     * Referenced by code in the JDK which wants to test for the
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3552
     * maximum char code for which layout may be required.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3553
     * Note this does not account for supplementary characters
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3554
     * where the caller interprets 'layout' to mean any case where
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3555
     * one 'char' (ie the java type char) does not map to one glyph
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3556
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3557
    public static final int MAX_LAYOUT_CHARCODE = 0x206F;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3558
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3559
    /* If the character code falls into any of a number of unicode ranges
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3560
     * where we know that simple left->right layout mapping chars to glyphs
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3561
     * 1:1 and accumulating advances is going to produce incorrect results,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3562
     * we want to know this so the caller can use a more intelligent layout
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3563
     * approach. A caller who cares about optimum performance may want to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3564
     * check the first case and skip the method call if its in that range.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3565
     * Although there's a lot of tests in here, knowing you can skip
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3566
     * CTL saves a great deal more. The rest of the checks are ordered
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3567
     * so that rather than checking explicitly if (>= start & <= end)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3568
     * which would mean all ranges would need to be checked so be sure
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3569
     * CTL is not needed, the method returns as soon as it recognises
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3570
     * the code point is outside of a CTL ranges.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3571
     * NOTE: Since this method accepts an 'int' it is asssumed to properly
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3572
     * represent a CHARACTER. ie it assumes the caller has already
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3573
     * converted surrogate pairs into supplementary characters, and so
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3574
     * can handle this case and doesn't need to be told such a case is
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3575
     * 'complex'.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3576
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3577
    static boolean isComplexCharCode(int code) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3578
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3579
        if (code < MIN_LAYOUT_CHARCODE || code > MAX_LAYOUT_CHARCODE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3580
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3581
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3582
        else if (code <= 0x036f) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3583
            // Trigger layout for combining diacriticals 0x0300->0x036f
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3584
            return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3585
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3586
        else if (code < 0x0590) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3587
            // No automatic layout for Greek, Cyrillic, Armenian.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3588
             return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3589
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3590
        else if (code <= 0x06ff) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3591
            // Hebrew 0590 - 05ff
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3592
            // Arabic 0600 - 06ff
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3593
            return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3594
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3595
        else if (code < 0x0900) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3596
            return false; // Syriac and Thaana
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3597
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3598
        else if (code <= 0x0e7f) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3599
            // if Indic, assume shaping for conjuncts, reordering:
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3600
            // 0900 - 097F Devanagari
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3601
            // 0980 - 09FF Bengali
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3602
            // 0A00 - 0A7F Gurmukhi
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3603
            // 0A80 - 0AFF Gujarati
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3604
            // 0B00 - 0B7F Oriya
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3605
            // 0B80 - 0BFF Tamil
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3606
            // 0C00 - 0C7F Telugu
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3607
            // 0C80 - 0CFF Kannada
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3608
            // 0D00 - 0D7F Malayalam
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3609
            // 0D80 - 0DFF Sinhala
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3610
            // 0E00 - 0E7F if Thai, assume shaping for vowel, tone marks
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3611
            return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3612
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3613
        else if (code < 0x1780) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3614
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3615
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3616
        else if (code <= 0x17ff) { // 1780 - 17FF Khmer
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3617
            return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3618
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3619
        else if (code < 0x200c) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3620
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3621
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3622
        else if (code <= 0x200d) { //  zwj or zwnj
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3623
            return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3624
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3625
        else if (code >= 0x202a && code <= 0x202e) { // directional control
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3626
            return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3627
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3628
        else if (code >= 0x206a && code <= 0x206f) { // directional control
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3629
            return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3630
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3631
        return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3632
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3633
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3634
    /* This is almost the same as the method above, except it takes a
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3635
     * char which means it may include undecoded surrogate pairs.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3636
     * The distinction is made so that code which needs to identify all
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3637
     * cases in which we do not have a simple mapping from
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3638
     * char->unicode character->glyph can be be identified.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3639
     * For example measurement cannot simply sum advances of 'chars',
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3640
     * the caret in editable text cannot advance one 'char' at a time, etc.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3641
     * These callers really are asking for more than whether 'layout'
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3642
     * needs to be run, they need to know if they can assume 1->1
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3643
     * char->glyph mapping.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3644
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3645
    static boolean isNonSimpleChar(char ch) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3646
        return
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3647
            isComplexCharCode(ch) ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3648
            (ch >= CharToGlyphMapper.HI_SURROGATE_START &&
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3649
             ch <= CharToGlyphMapper.LO_SURROGATE_END);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3650
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3651
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3652
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3653
     * If there is anything in the text which triggers a case
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3654
     * where char->glyph does not map 1:1 in straightforward
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3655
     * left->right ordering, then this method returns true.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3656
     * Scripts which might require it but are not treated as such
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3657
     * due to JDK implementations will not return true.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3658
     * ie a 'true' return is an indication of the treatment by
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3659
     * the implementation.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3660
     * Whether supplementary characters should be considered is dependent
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3661
     * on the needs of the caller. Since this method accepts the 'char' type
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3662
     * then such chars are always represented by a pair. From a rendering
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3663
     * perspective these will all (in the cases I know of) still be one
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3664
     * unicode character -> one glyph. But if a caller is using this to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3665
     * discover any case where it cannot make naive assumptions about
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3666
     * the number of chars, and how to index through them, then it may
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3667
     * need the option to have a 'true' return in such a case.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3668
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3669
    public static boolean isComplexText(char [] chs, int start, int limit) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3670
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3671
        for (int i = start; i < limit; i++) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3672
            if (chs[i] < MIN_LAYOUT_CHARCODE) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3673
                continue;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3674
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3675
            else if (isNonSimpleChar(chs[i])) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3676
                return true;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3677
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3678
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3679
        return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3680
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3681
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3682
    /**
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3683
     * Used by windows printing to assess if a font is likely to
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3684
     * be layout compatible with JDK
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3685
     * TrueType fonts should be, but if they have no GPOS table,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3686
     * but do have a GSUB table, then they are probably older
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3687
     * fonts GDI handles differently.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3688
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3689
    public static boolean textLayoutIsCompatible(Font font) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3690
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3691
        Font2D font2D = FontManager.getFont2D(font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3692
        if (font2D instanceof TrueTypeFont) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3693
            TrueTypeFont ttf = (TrueTypeFont)font2D;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3694
            return
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3695
                ttf.getDirectoryEntry(TrueTypeFont.GSUBTag) == null ||
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3696
                ttf.getDirectoryEntry(TrueTypeFont.GPOSTag) != null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3697
        } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3698
            return false;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3699
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3700
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3701
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3702
    private static FontScaler nullScaler = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3703
    private static Constructor<FontScaler> scalerConstructor = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3704
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3705
    //Find preferred font scaler
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3706
    //
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3707
    //NB: we can allow property based preferences
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3708
    //   (theoretically logic can be font type specific)
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3709
    static {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3710
        Class scalerClass = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3711
        Class arglst[] = new Class[] {Font2D.class, int.class,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3712
        boolean.class, int.class};
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3713
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3714
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3715
            if (SunGraphicsEnvironment.isOpenJDK()) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3716
                scalerClass = Class.forName("sun.font.FreetypeFontScaler");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3717
            } else {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3718
                scalerClass = Class.forName("sun.font.T2KFontScaler");
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3719
            }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3720
        } catch (ClassNotFoundException e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3721
                scalerClass = NullFontScaler.class;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3722
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3723
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3724
        //NB: rewrite using factory? constructor is ugly way
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3725
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3726
            scalerConstructor = scalerClass.getConstructor(arglst);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3727
        } catch (NoSuchMethodException e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3728
            //should not happen
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3729
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3730
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3731
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3732
    /* At the moment it is harmless to create 2 null scalers
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3733
       so, technically, syncronized keyword is not needed.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3734
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3735
       But it is safer to keep it to avoid subtle problems if we will be
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3736
       adding checks like whether scaler is null scaler. */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3737
    public synchronized static FontScaler getNullScaler() {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3738
        if (nullScaler == null) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3739
            nullScaler = new NullFontScaler();
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3740
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3741
        return nullScaler;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3742
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3743
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3744
    /* This is the only place to instantiate new FontScaler.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3745
     * Therefore this is very convinient place to register
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3746
     * scaler with Disposer as well as trigger deregistring bad font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3747
     * in case when scaler reports this.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3748
     */
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3749
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3750
    public static FontScaler getScaler(Font2D font,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3751
                                       int indexInCollection,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3752
                                       boolean supportsCJK,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3753
                                       int filesize) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3754
        FontScaler scaler = null;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3755
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3756
        try {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3757
            Object args[] = new Object[] {font, indexInCollection,
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3758
                                          supportsCJK, filesize};
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3759
            scaler = scalerConstructor.newInstance(args);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3760
            Disposer.addObjectRecord(font, scaler);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3761
        } catch (Throwable e) {
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3762
            scaler = nullScaler;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3763
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3764
            //if we can not instantiate scaler assume bad font
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3765
            //NB: technically it could be also because of internal scaler
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3766
            //    error but here we are assuming scaler is ok.
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3767
            deRegisterBadFont(font);
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3768
        }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3769
        return scaler;
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3770
    }
90ce3da70b43 Initial load
duke
parents:
diff changeset
  3771
}