blob: 8354e2593ae0088184ed1766534708217245f704 [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* @author Ilya S. Okomin
* @version $Revision$
*/
package org.apache.harmony.awt.gl.font;
import java.awt.Font;
import java.awt.peer.FontPeer;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.lang.ref.ReferenceQueue;
import java.lang.ref.SoftReference;
import java.util.Enumeration;
import java.util.Hashtable;
import java.util.Locale;
import java.util.Properties;
import java.util.Vector;
import org.apache.harmony.awt.gl.CommonGraphics2DFactory;
import org.apache.harmony.luni.util.NotImplementedException;
public abstract class FontManager {
//???AWT
boolean NOT_IMP = false;
/**
* array of font families names
*/
public String[] allFamilies;
public static final String DEFAULT_NAME = "Default"; /* Default font name */ //$NON-NLS-1$
public static final String DIALOG_NAME = "Dialog"; /* Dialog font name */ //$NON-NLS-1$
/**
* Set of constants applicable to the TrueType 'name' table.
*/
public static final byte FAMILY_NAME_ID = 1; /* Family name identifier */
public static final byte FONT_NAME_ID = 4; /* Full font name identifier */
public static final byte POSTSCRIPT_NAME_ID = 6; /* PostScript name identifier */
public static final short ENGLISH_LANGID = 0x0409; /* English (United States)language identifier */
/**
* Set of constants describing font type.
*/
public static final byte FONT_TYPE_TT = 4; /* TrueType type (TRUETYPE_FONTTYPE) */
public static final byte FONT_TYPE_T1 = 2; /* Type1 type (DEVICE_FONTTYPE) */
public static final byte FONT_TYPE_UNDEF = 0; /* Undefined type */
// logical family types (indices in FontManager.LOGICAL_FONT_NAMES)
static final int DIALOG = 3; // FF_SWISS
static final int SANSSERIF = 1; // FF_SWISS
static final int DIALOGINPUT = 4; // FF_MODERN
static final int MONOSPACED = 2; // FF_MODERN
static final int SERIF = 0; // FF_ROMAN
/**
* FontProperty related constants.
*/
public static final String PLATFORM_FONT_NAME = "PlatformFontName"; //$NON-NLS-1$
public static final String LOGICAL_FONT_NAME = "LogicalFontName"; //$NON-NLS-1$
public static final String COMPONENT_INDEX = "ComponentIndex"; //$NON-NLS-1$
public static final String STYLE_INDEX = "StyleIndex"; //$NON-NLS-1$
public static final String[] FONT_MAPPING_KEYS = {
"LogicalFontName.StyleName.ComponentIndex", "LogicalFontName.ComponentIndex" //$NON-NLS-1$ //$NON-NLS-2$
};
public static final String FONT_CHARACTER_ENCODING = "fontcharset.LogicalFontName.ComponentIndex"; //$NON-NLS-1$
public static final String EXCLUSION_RANGES = "exclusion.LogicalFontName.ComponentIndex"; //$NON-NLS-1$
public static final String FONT_FILE_NAME = "filename.PlatformFontName"; //$NON-NLS-1$
/**
* Available logical font families names.
*/
public static final String[] LOGICAL_FONT_FAMILIES = {
"Serif", "SansSerif", "Monospaced", "Dialog", "DialogInput" //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
};
/**
* Available logical font names.
*/
public static final String[] LOGICAL_FONT_NAMES = {
"serif", "serif.plain", "serif.bold", "serif.italic", "serif.bolditalic", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"sansserif", "sansserif.plain", "sansserif.bold", "sansserif.italic", "sansserif.bolditalic", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"monospaced", "monospaced.plain", "monospaced.bold", "monospaced.italic", "monospaced.bolditalic", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"dialog", "dialog.plain", "dialog.bold", "dialog.italic", "dialog.bolditalic", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"dialoginput", "dialoginput.plain", "dialoginput.bold", "dialoginput.italic", "dialoginput.bolditalic" //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
};
/**
* Available logical font face names.
*/
public static final String[] LOGICAL_FONT_FACES = {
"Serif", "Serif.plain", "Serif.bold", "Serif.italic", "Serif.bolditalic", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"Sansserif", "Sansserif.plain", "Sansserif.bold", "Sansserif.italic", "Sansserif.bolditalic", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"Monospaced", "Monospaced.plain", "Monospaced.bold", "Monospaced.italic", "Monospaced.bolditalic", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"Dialog", "Dialog.plain", "Dialog.bold", "Dialog.italic", "Dialog.bolditalic", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"Dialoginput", "Dialoginput.plain", "Dialoginput.bold", "Dialoginput.italic", "Dialoginput.bolditalic" //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
};
/**
* Set of font style names.
* Font.getStyle() corresponds to indexes in STYLE_NAMES array.
*/
public static final String[] STYLE_NAMES = {
"plain", "bold", "italic", "bolditalic" //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$
};
/**
* Logical font styles names table where font styles names used
* as the key and the value is the index of this style name.
*/
private static final Hashtable<String, Integer> style_keys = new Hashtable<String, Integer>(4);
/**
* Initialize font styles keys table.
*/
static {
for (int i = 0; i < STYLE_NAMES.length; i++){
style_keys.put(STYLE_NAMES[i], Integer.valueOf(i));
}
}
/**
* Return font style from the logical style name.
*
* @param lName style name of the logical face
*/
public static int getLogicalStyle(String lName){
Integer value = style_keys.get(lName);
return value != null ? value.intValue(): -1;
}
/**
* Set of possible "os" property values.
*/
public static final String[] OS_VALUES = {
"NT", "98", "2000", "Me", "XP", // For Windows //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$
"Redhat", "Turbo", "SuSE" // For Linux //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
};
/**
* Set of possible font.property file names.
* Language, Country, Encoding, OS, Version should be replaced with
* the values from current configuration.
*/
public static final String[] FP_FILE_NAMES = {
"/lib/font.properties.Language_Country_Encoding.OSVersion", //$NON-NLS-1$
"/lib/font.properties.Language_Country_Encoding.OS", //$NON-NLS-1$
"/lib/font.properties.Language_Country_Encoding.Version", //$NON-NLS-1$
"/lib/font.properties.Language_Country_Encoding", //$NON-NLS-1$
"/lib/font.properties.Language_Country.OSVersion", //$NON-NLS-1$
"/lib/font.properties.Language_Country.OS", //$NON-NLS-1$
"/lib/font.properties.Language_Country.Version", //$NON-NLS-1$
"/lib/font.properties.Language_Country", //$NON-NLS-1$
"/lib/font.properties.Language_Encoding.OSVersion", //$NON-NLS-1$
"/lib/font.properties.Language_Encoding.OS", //$NON-NLS-1$
"/lib/font.properties.Language_Encoding.Version", //$NON-NLS-1$
"/lib/font.properties.Language_Encoding", //$NON-NLS-1$
"/lib/font.properties.Language.OSVersion", //$NON-NLS-1$
"/lib/font.properties.Language.OS", //$NON-NLS-1$
"/lib/font.properties.Language.Version", //$NON-NLS-1$
"/lib/font.properties.Language", //$NON-NLS-1$
"/lib/font.properties.Encoding.OSVersion", //$NON-NLS-1$
"/lib/font.properties.Encoding.OS", //$NON-NLS-1$
"/lib/font.properties.Encoding.Version", //$NON-NLS-1$
"/lib/font.properties.Encoding", //$NON-NLS-1$
"/lib/font.properties.OSVersion", //$NON-NLS-1$
"/lib/font.properties.OS", //$NON-NLS-1$
"/lib/font.properties.Version", //$NON-NLS-1$
"/lib/font.properties" //$NON-NLS-1$
};
/**
* Table with all available font properties corresponding
* to the current system configuration.
*/
public Hashtable<String, Vector<FontProperty>> fProperties = new Hashtable<String, Vector<FontProperty>>();
public FontManager(){
allFamilies = getAllFamilies();
/*
* Creating and registering shutdown hook to free resources
* before object is destroyed.
*/
//???AWT
//DisposeNativeHook shutdownHook = new DisposeNativeHook();
//Runtime.getRuntime().addShutdownHook(shutdownHook);
}
/**
* Maximum number of unreferenced font peers to keep.
*/
public static final int EMPTY_FONTS_CAPACITY = 10;
/**
* Locale - Language ID hash table.
*/
Hashtable<String, Short> tableLCID = new Hashtable<String, Short>();
/**
* Hash table that contains FontPeers instances.
*/
public Hashtable<String, HashMapReference> fontsTable = new Hashtable<String, HashMapReference>();
/**
* ReferenceQueue for HashMapReference objects to check
* if they were collected by garbage collector.
*/
public ReferenceQueue<FontPeer> queue = new ReferenceQueue<FontPeer>();
/**
* Singleton instance
*/
public final static FontManager inst = CommonGraphics2DFactory.inst.getFontManager();
/**
* Gets singleton instance of FontManager
*
* @return instance of FontManager implementation
*/
public static FontManager getInstance() {
return inst;
}
/**
* Returns platform-dependent Font peer created from the specified
* Font object from the table with cached FontPeers instances.
*
* Note, this method checks whether FontPeer with specified parameters
* exists in the table with cached FontPeers' instances. If there is no needed
* instance - it is created and cached.
*
* @param fontName name of the font
* @param _fontStyle style of the font
* @param size font size
*
* @return platform dependent FontPeer implementation created from
* the specified parameters
*/
public FontPeer getFontPeer(String fontName, int _fontStyle, int size) {
updateFontsTable();
FontPeer peer = null;
String key;
String name;
int fontStyle = _fontStyle;
int logicalIndex = getLogicalFaceIndex(fontName);
if (logicalIndex != -1){
name = getLogicalFaceFromFont(fontStyle, logicalIndex);
fontStyle = getStyleFromLogicalFace(name);
key = name.concat(String.valueOf(size));
} else {
name = fontName;
key = name.concat(String.valueOf(fontStyle)).
concat(String.valueOf(size));
}
HashMapReference hmr = fontsTable.get(key);
if (hmr != null) {
peer = hmr.get();
}
if (peer == null) {
peer = createFontPeer(name, fontStyle, size, logicalIndex);
if (peer == null){
peer = getFontPeer(DIALOG_NAME, fontStyle, size);
}
fontsTable.put(key, new HashMapReference(key, peer, queue));
}
return peer;
}
/**
* Returns instance of font peer (logical or physical) according to the
* specified parameters.
*
* @param name font face name
* @param style style of the font
* @param size size of the font
* @param logicalIndex index of the logical face name in LOGICAL_FONT_FACES
* array or -1 if desired font peer is not logical.
*/
private FontPeer createFontPeer(String name, int style, int size, int logicalIndex){
FontPeer peer;
if (logicalIndex != -1){
peer = createLogicalFontPeer(name, style, size);
}else {
peer = createPhysicalFontPeer(name, style, size);
}
return peer;
}
/**
* Returns family name for logical face names as a parameter.
*
* @param faceName logical font face name
*/
public String getFamilyFromLogicalFace(String faceName){
int pos = faceName.indexOf("."); //$NON-NLS-1$
if (pos == -1){
return faceName;
}
return faceName.substring(0, pos);
}
/**
* Returns new logical font peer for the parameters specified using font
* properties.
*
* @param faceName face name of the logical font
* @param style style of the font
* @param size font size
*
*/
private FontPeer createLogicalFontPeer(String faceName, int style, int size){
String family = getFamilyFromLogicalFace(faceName);
FontProperty[] fps = getFontProperties(family.toLowerCase() + "." + style); //$NON-NLS-1$
if (fps != null){
int numFonts = fps.length;
FontPeerImpl[] physicalFonts = new FontPeerImpl[numFonts];
for (int i = 0; i < numFonts; i++){
FontProperty fp = fps[i];
String name = fp.getName();
int fpStyle = fp.getStyle();
String key = name.concat(String.valueOf(fpStyle)).
concat(String.valueOf(size));
HashMapReference hmr = fontsTable.get(key);
if (hmr != null) {
physicalFonts[i] = (FontPeerImpl)hmr.get();
}
if (physicalFonts[i] == null){
physicalFonts[i] = (FontPeerImpl)createPhysicalFontPeer(name, fpStyle, size);
fontsTable.put(key, new HashMapReference(key, physicalFonts[i], queue));
}
if (physicalFonts[i] == null){
physicalFonts[i] = (FontPeerImpl)getDefaultFont(style, size);
}
}
return new CompositeFont(family, faceName, style, size, fps, physicalFonts);
}
// if there is no property for this logical font - default font is to be
// created
FontPeerImpl peer = (FontPeerImpl)getDefaultFont(style, size);
return peer;
}
/**
* Returns new physical font peer for the parameters specified using font properties
* This method must be overridden by subclasses implementations.
*
* @param faceName face name or family name of the font
* @param style style of the font
* @param size font size
*
*/
public abstract FontPeer createPhysicalFontPeer(String name, int style, int size);
/**
* Returns default font peer class with "Default" name that is usually
* used when font with specified font names and style doesn't exsist
* on a system.
*
* @param style style of the font
* @param size size of the font
*/
public FontPeer getDefaultFont(int style, int size){
updateFontsTable();
FontPeer peer = null;
String key = DEFAULT_NAME.concat(String.valueOf(style)).
concat(String.valueOf(size));
HashMapReference hmr = fontsTable.get(key);
if (hmr != null) {
peer = hmr.get();
}
if (peer == null) {
peer = createDefaultFont(style, size);
((FontPeerImpl)peer).setFamily(DEFAULT_NAME);
((FontPeerImpl)peer).setPSName(DEFAULT_NAME);
((FontPeerImpl)peer).setFontName(DEFAULT_NAME);
fontsTable.put(key, new HashMapReference(key, peer, queue));
}
return peer;
}
/**
*
* Returns new default font peer with "Default" name for the parameters
* specified. This method must be overridden by subclasses implementations.
*
* @param style style of the font
* @param size size of the font
*/
public abstract FontPeer createDefaultFont(int style, int size);
/**
* Returns face name of the logical font, which is the result
* of specified font style and face style union.
*
* @param fontStyle specified style of the font
* @param logicalIndex index of the specified face from the
* LOGICAL_FONT_FACES array
* @return resulting face name
*/
public String getLogicalFaceFromFont(int fontStyle, int logicalIndex){
int style = 0;
String name = LOGICAL_FONT_FACES[logicalIndex];
int pos = name.indexOf("."); //$NON-NLS-1$
if (pos == -1){
return createLogicalFace(name, fontStyle);
}
String styleName = name.substring(pos+1);
name = name.substring(0, pos);
// appending font style to the face style
style = fontStyle | getLogicalStyle(styleName);
return createLogicalFace(name, style);
}
/**
* Function returns style value from logical face name.
*
* @param name face name
* @return font style
*/
public int getStyleFromLogicalFace(String name){
int style;
int pos = name.indexOf("."); //$NON-NLS-1$
if (pos == -1){
return Font.PLAIN;
}
String styleName = name.substring(pos+1);
style = getLogicalStyle(styleName);
return style;
}
/**
* Returns logical face name corresponding to the logical
* family name and style of the font.
*
* @param family font family
* @param styleIndex index of the style name from the STYLE_NAMES array
*/
public String createLogicalFace(String family, int styleIndex){
return family + "." + STYLE_NAMES[styleIndex]; //$NON-NLS-1$
}
/**
* Return language Id from LCID hash corresponding to the specified locale
*
* @param l specified locale
*/
public Short getLCID(Locale l){
if (this.tableLCID.size() == 0){
initLCIDTable();
}
return tableLCID.get(l.toString());
}
/**
* Platform-dependent LCID table init.
*/
public abstract void initLCIDTable();
/**
* Freeing native resources. This hook is used to avoid
* sudden application exit and to free resources created in native code.
*/
private class DisposeNativeHook extends Thread {
@Override
public void run() {
try{
/* Disposing native font peer's resources */
Enumeration<String> kEnum = fontsTable.keys();
while(kEnum.hasMoreElements()){
Object key = kEnum.nextElement();
HashMapReference hmr = fontsTable.remove(key);
FontPeerImpl delPeer = (FontPeerImpl)hmr.get();
if ((delPeer != null) && (delPeer.getClass() != CompositeFont.class)){
// there's nothing to dispose in CompositeFont objects
delPeer.dispose();
}
}
} catch (Throwable t){
throw new RuntimeException(t);
}
}
}
/**
* Returns File object, created in a directory
* according to the System, where JVM is being ran.
*
* In Linux case we use ".fonts" directory (for fontconfig purpose),
* where font file from the stream will be stored, hence in LinuxFontManager this
* method is overridden.
* In Windows case we use Windows temp directory (default implementation)
*
*/
public File getTempFontFile()throws IOException{
//???AWT
/*
File fontFile = File.createTempFile("jFont", ".ttf"); //$NON-NLS-1$ //$NON-NLS-2$
fontFile.deleteOnExit();
return fontFile;
*/
if(NOT_IMP)
throw new NotImplementedException("getTempFontFile not Implemented");
return null;
}
/**
* Returns File object with font properties. It's name obtained using current
* system configuration properties and locale settings. If no appropriate
* file is found method returns null.
*/
public static File getFontPropertyFile(){
File file = null;
String javaHome = System.getProperty("java.home"); //$NON-NLS-1$
Locale l = Locale.getDefault();
String language = l.getLanguage();
String country = l.getCountry();
String fileEncoding = System.getProperty("file.encoding"); //$NON-NLS-1$
String os = System.getProperty("os.name"); //$NON-NLS-1$
int i = 0;
// OS names from system properties don't match
// OS identifiers used in font.property files
for (; i < OS_VALUES.length; i++){
if (os.endsWith(OS_VALUES[i])){
os = OS_VALUES[i];
break;
}
}
if (i == OS_VALUES.length){
os = null;
}
String version = System.getProperty("os.version"); //$NON-NLS-1$
String pathname;
for (i = 0; i < FP_FILE_NAMES.length; i++){
pathname = FP_FILE_NAMES[i];
if (os != null){
pathname = pathname.replaceFirst("OS", os); //$NON-NLS-1$
}
pathname = javaHome + pathname;
pathname = pathname.replaceAll("Language", language). //$NON-NLS-1$
replaceAll("Country", country). //$NON-NLS-1$
replaceAll("Encoding", fileEncoding). //$NON-NLS-1$
replaceAll("Version", version); //$NON-NLS-1$
file = new File(pathname);
if (file.exists()){
break;
}
}
return file.exists() ? file : null;
}
/**
* Returns an array of integer range values
* if the parameter exclusionString has format:
* Range
* Range [, exclusionString]
*
* Range:
* Char-Char
*
* Char:
* HexDigit HexDigit HexDigit HexDigit
*
* Method returns null if the specified string is null.
*
* @param exclusionString string parameter in specified format
*/
public static int[] parseIntervals(String exclusionString){
int[] results = null;
if (exclusionString == null){
return null;
}
String[] intervals = exclusionString.split(","); //$NON-NLS-1$
if (intervals != null){
int num = intervals.length;
if (num > 0){
results = new int[intervals.length << 1];
for (int i = 0; i < intervals.length; i++){
String ranges[] = intervals[i].split("-"); //$NON-NLS-1$
results[i*2] = Integer.parseInt(ranges[0], 16);
results[i*2+1] = Integer.parseInt(ranges[1], 16);
}
}
}
return results;
}
/**
* Returns Properties from the properties file or null if
* there is an error with FileInputStream processing.
*
* @param file File object containing properties
*/
public static Properties getProperties(File file){
Properties props = null;
FileInputStream fis = null;
try{
fis = new FileInputStream(file);
props = new Properties();
props.load(fis);
} catch (Exception e){
System.out.println(e);
}
return props;
}
/**
* Returns an array of FontProperties from the properties file
* with the specified property name "logical face.style". E.g.
* "dialog.2" corresponds to the font family Dialog with bold style.
*
* @param fpName key of the font properties in the properties set
*/
public FontProperty[] getFontProperties(String fpName){
Vector<FontProperty> props = fProperties.get(fpName);
if (props == null){
return null;
}
int size = props.size();
if (size == 0){
return null;
}
FontProperty[] fps = new FontProperty[size];
for (int i=0; i < fps.length; i++){
fps[i] = props.elementAt(i);
}
return fps;
}
/**
* Returns index of the font name in array of font names or -1 if
* this font is not logical.
*
* @param fontName specified font name
*/
public static int getLogicalFaceIndex(String fontName){
for (int i=0; i<LOGICAL_FONT_NAMES.length; i++ ){
if (LOGICAL_FONT_NAMES[i].equalsIgnoreCase(fontName)){
return i;
}
}
return -1;
}
/**
* Returns true if specified family name is available in this
* GraphicsEnvironment.
*
* @param familyName the specified font family name
*/
public boolean isFamilyExist(String familyName){
return (getFamilyIndex(familyName) != -1);
}
/**
* Returns index of family name from the array of family names available in
* this GraphicsEnvironment or -1 if no family name was found.
*
* @param familyName specified font family name
*/
public int getFamilyIndex(String familyName){
for (int i=0; i<allFamilies.length; i++ ){
if (familyName.equalsIgnoreCase(allFamilies[i])){
return i;
}
}
return -1;
}
/**
* Returns family with index specified from the array of family names available in
* this GraphicsEnvironment.
*
* @param index index of the family in families names array
*/
public String getFamily(int index){
return allFamilies[index];
}
/**
* Returns index of face name from the array of face names available in
* this GraphicsEnvironment or -1 if no face name was found. Default return
* value is -1, method must be overridden by FontManager implementation.
*
* @param faceName font face name which index is to be searched
*/
public int getFaceIndex(String faceName){
return -1;
}
public abstract String[] getAllFamilies();
public abstract Font[] getAllFonts();
/**
* Class contains SoftReference instance that can be stored in the
* Hashtable by means of key field corresponding to it.
*/
private class HashMapReference extends SoftReference<FontPeer> {
/**
* The key for Hashtable.
*/
private final String key;
/**
* Creates a new soft reference with the key specified and
* adding this reference in the reference queue specified.
*
* @param key the key in Hashtable
* @param value object that corresponds to the key
* @param queue reference queue where reference is to be added
*/
public HashMapReference(final String key, final FontPeer value,
final ReferenceQueue<FontPeer> queue) {
super(value, queue);
this.key = key;
}
/**
* Returns the key that corresponds to the SoftReference instance
*
* @return the key in Hashtable with cached references
*/
public Object getKey() {
return key;
}
}
/**
* Removes keys from the Hashtable with font peers which corresponding
* HashMapReference objects were garbage collected.
*/
private void updateFontsTable() {
HashMapReference r;
//???AWT
//while ((r = (HashMapReference)queue.poll()) != null) {
// fontsTable.remove(r.getKey());
//}
}
}