jdk/src/share/classes/java/awt/font/GlyphMetrics.java
changeset 2 90ce3da70b43
child 5506 202f599c92aa
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/share/classes/java/awt/font/GlyphMetrics.java	Sat Dec 01 00:00:00 2007 +0000
@@ -0,0 +1,324 @@
+/*
+ * Copyright 1997-2006 Sun Microsystems, Inc.  All Rights Reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Sun designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Sun in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
+ * CA 95054 USA or visit www.sun.com if you need additional information or
+ * have any questions.
+ */
+
+/*
+ * (C) Copyright Taligent, Inc. 1996 - 1997, All Rights Reserved
+ * (C) Copyright IBM Corp. 1996 - 1998, All Rights Reserved
+ *
+ * The original version of this source code and documentation is
+ * copyrighted and owned by Taligent, Inc., a wholly-owned subsidiary
+ * of IBM. These materials are provided under terms of a License
+ * Agreement between Taligent and Sun. This technology is protected
+ * by multiple US and International patents.
+ *
+ * This notice and attribution to Taligent may not be removed.
+ * Taligent is a registered trademark of Taligent, Inc.
+ *
+ */
+
+package java.awt.font;
+
+import java.awt.geom.Rectangle2D;
+
+/**
+ * The <code>GlyphMetrics</code> class represents infomation for a
+ * single glyph.   A glyph is the visual representation of one or more
+ * characters.  Many different glyphs can be used to represent a single
+ * character or combination of characters.  <code>GlyphMetrics</code>
+ * instances are produced by {@link java.awt.Font Font} and are applicable
+ * to a specific glyph in a particular <code>Font</code>.
+ * <p>
+ * Glyphs are either STANDARD, LIGATURE, COMBINING, or COMPONENT.
+ * <ul>
+ * <li>STANDARD glyphs are commonly used to represent single characters.
+ * <li>LIGATURE glyphs are used to represent sequences of characters.
+ * <li>COMPONENT glyphs in a {@link GlyphVector} do not correspond to a
+ * particular character in a text model. Instead, COMPONENT glyphs are
+ * added for typographical reasons, such as Arabic justification.
+ * <li>COMBINING glyphs embellish STANDARD or LIGATURE glyphs, such
+ * as accent marks.  Carets do not appear before COMBINING glyphs.
+ * </ul>
+ * <p>
+ * Other metrics available through <code>GlyphMetrics</code> are the
+ * components of the advance, the visual bounds, and the left and right
+ * side bearings.
+ * <p>
+ * Glyphs for a rotated font, or obtained from a <code>GlyphVector</code>
+ * which has applied a rotation to the glyph, can have advances that
+ * contain both X and Y components.  Usually the advance only has one
+ * component.
+ * <p>
+ * The advance of a glyph is the distance from the glyph's origin to the
+ * origin of the next glyph along the baseline, which is either vertical
+ * or horizontal.  Note that, in a <code>GlyphVector</code>,
+ * the distance from a glyph to its following glyph might not be the
+ * glyph's advance, because of kerning or other positioning adjustments.
+ * <p>
+ * The bounds is the smallest rectangle that completely contains the
+ * outline of the glyph.  The bounds rectangle is relative to the
+ * glyph's origin.  The left-side bearing is the distance from the glyph
+ * origin to the left of its bounds rectangle. If the left-side bearing is
+ * negative, part of the glyph is drawn to the left of its origin.  The
+ * right-side bearing is the distance from the right side of the bounds
+ * rectangle to the next glyph origin (the origin plus the advance).  If
+ * negative, part of the glyph is drawn to the right of the next glyph's
+ * origin.  Note that the bounds does not necessarily enclose all the pixels
+ * affected when rendering the glyph, because of rasterization and pixel
+ * adjustment effects.
+ * <p>
+ * Although instances of <code>GlyphMetrics</code> can be directly
+ * constructed, they are almost always obtained from a
+ * <code>GlyphVector</code>.  Once constructed, <code>GlyphMetrics</code>
+ * objects are immutable.
+ * <p>
+ * <strong>Example</strong>:<p>
+ * Querying a <code>Font</code> for glyph information
+ * <blockquote><pre>
+ * Font font = ...;
+ * int glyphIndex = ...;
+ * GlyphMetrics metrics = GlyphVector.getGlyphMetrics(glyphIndex);
+ * int isStandard = metrics.isStandard();
+ * float glyphAdvance = metrics.getAdvance();
+ * </pre></blockquote>
+ * @see java.awt.Font
+ * @see GlyphVector
+ */
+
+public final class GlyphMetrics {
+    /**
+     * Indicates whether the metrics are for a horizontal or vertical baseline.
+     */
+    private boolean horizontal;
+
+    /**
+     * The x-component of the advance.
+     */
+    private float advanceX;
+
+    /**
+     * The y-component of the advance.
+     */
+    private float advanceY;
+
+    /**
+     * The bounds of the associated glyph.
+     */
+    private Rectangle2D.Float bounds;
+
+    /**
+     * Additional information about the glyph encoded as a byte.
+     */
+    private byte glyphType;
+
+    /**
+     * Indicates a glyph that represents a single standard
+     * character.
+     */
+    public static final byte STANDARD = 0;
+
+    /**
+     * Indicates a glyph that represents multiple characters
+     * as a ligature, for example 'fi' or 'ffi'.  It is followed by
+     * filler glyphs for the remaining characters. Filler and combining
+     * glyphs can be intermixed to control positioning of accent marks
+     * on the logically preceeding ligature.
+     */
+    public static final byte LIGATURE = 1;
+
+    /**
+     * Indicates a glyph that represents a combining character,
+     * such as an umlaut.  There is no caret position between this glyph
+     * and the preceeding glyph.
+     */
+    public static final byte COMBINING = 2;
+
+    /**
+     * Indicates a glyph with no corresponding character in the
+     * backing store.  The glyph is associated with the character
+     * represented by the logicaly preceeding non-component glyph.  This
+     * is used for kashida justification or other visual modifications to
+     * existing glyphs.  There is no caret position between this glyph
+     * and the preceeding glyph.
+     */
+    public static final byte COMPONENT = 3;
+
+    /**
+     * Indicates a glyph with no visual representation. It can
+     * be added to the other code values to indicate an invisible glyph.
+     */
+    public static final byte WHITESPACE = 4;
+
+    /**
+     * Constructs a <code>GlyphMetrics</code> object.
+     * @param advance the advance width of the glyph
+     * @param bounds the black box bounds of the glyph
+     * @param glyphType the type of the glyph
+     */
+    public GlyphMetrics(float advance, Rectangle2D bounds, byte glyphType) {
+        this.horizontal = true;
+        this.advanceX = advance;
+        this.advanceY = 0;
+        this.bounds = new Rectangle2D.Float();
+        this.bounds.setRect(bounds);
+        this.glyphType = glyphType;
+    }
+
+    /**
+     * Constructs a <code>GlyphMetrics</code> object.
+     * @param horizontal if true, metrics are for a horizontal baseline,
+     *   otherwise they are for a vertical baseline
+     * @param advanceX the X-component of the glyph's advance
+     * @param advanceY the Y-component of the glyph's advance
+     * @param bounds the visual bounds of the glyph
+     * @param glyphType the type of the glyph
+     * @since 1.4
+     */
+    public GlyphMetrics(boolean horizontal, float advanceX, float advanceY,
+                        Rectangle2D bounds, byte glyphType) {
+
+        this.horizontal = horizontal;
+        this.advanceX = advanceX;
+        this.advanceY = advanceY;
+        this.bounds = new Rectangle2D.Float();
+        this.bounds.setRect(bounds);
+        this.glyphType = glyphType;
+    }
+
+    /**
+     * Returns the advance of the glyph along the baseline (either
+     * horizontal or vertical).
+     * @return the advance of the glyph
+     */
+    public float getAdvance() {
+        return horizontal ? advanceX : advanceY;
+    }
+
+    /**
+     * Returns the x-component of the advance of the glyph.
+     * @return the x-component of the advance of the glyph
+     * @since 1.4
+     */
+    public float getAdvanceX() {
+        return advanceX;
+    }
+
+    /**
+     * Returns the y-component of the advance of the glyph.
+     * @return the y-component of the advance of the glyph
+     * @since 1.4
+     */
+    public float getAdvanceY() {
+        return advanceY;
+    }
+
+    /**
+     * Returns the bounds of the glyph. This is the bounding box of the glyph outline.
+     * Because of rasterization and pixel alignment effects, it does not necessarily
+     * enclose the pixels that are affected when rendering the glyph.
+     * @return a {@link Rectangle2D} that is the bounds of the glyph.
+     */
+    public Rectangle2D getBounds2D() {
+        return new Rectangle2D.Float(bounds.x, bounds.y, bounds.width, bounds.height);
+    }
+
+    /**
+     * Returns the left (top) side bearing of the glyph.
+     * <p>
+     * This is the distance from 0,&nbsp;0 to the left (top) of the glyph
+     * bounds.  If the bounds of the glyph is to the left of (above) the
+     * origin, the LSB is negative.
+     * @return the left side bearing of the glyph.
+     */
+    public float getLSB() {
+        return horizontal ? bounds.x : bounds.y;
+    }
+
+    /**
+     * Returns the right (bottom) side bearing of the glyph.
+     * <p>
+     * This is the distance from the right (bottom) of the glyph bounds to
+     * the advance. If the bounds of the glyph is to the right of (below)
+     * the advance, the RSB is negative.
+     * @return the right side bearing of the glyph.
+     */
+    public float getRSB() {
+        return horizontal ?
+            advanceX - bounds.x - bounds.width :
+            advanceY - bounds.y - bounds.height;
+    }
+
+    /**
+     * Returns the raw glyph type code.
+     * @return the raw glyph type code.
+     */
+    public int getType() {
+        return glyphType;
+    }
+
+    /**
+     * Returns <code>true</code> if this is a standard glyph.
+     * @return <code>true</code> if this is a standard glyph;
+     *          <code>false</code> otherwise.
+     */
+    public boolean isStandard() {
+        return (glyphType & 0x3) == STANDARD;
+    }
+
+    /**
+     * Returns <code>true</code> if this is a ligature glyph.
+     * @return <code>true</code> if this is a ligature glyph;
+     *          <code>false</code> otherwise.
+     */
+    public boolean isLigature() {
+        return (glyphType & 0x3) == LIGATURE;
+    }
+
+    /**
+     * Returns <code>true</code> if this is a combining glyph.
+     * @return <code>true</code> if this is a combining glyph;
+     *          <code>false</code> otherwise.
+     */
+    public boolean isCombining() {
+        return (glyphType & 0x3) == COMBINING;
+    }
+
+    /**
+     * Returns <code>true</code> if this is a component glyph.
+     * @return <code>true</code> if this is a component glyph;
+     *          <code>false</code> otherwise.
+     */
+    public boolean isComponent() {
+        return (glyphType & 0x3) == COMPONENT;
+    }
+
+    /**
+     * Returns <code>true</code> if this is a whitespace glyph.
+     * @return <code>true</code> if this is a whitespace glyph;
+     *          <code>false</code> otherwise.
+     */
+    public boolean isWhitespace() {
+        return (glyphType & 0x4) == WHITESPACE;
+    }
+}