1. /*
  2. * @(#)GlyphMetrics.java 1.39 03/01/23
  3. *
  4. * Copyright 2003 Sun Microsystems, Inc. All rights reserved.
  5. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
  6. */
  7. /*
  8. * (C) Copyright Taligent, Inc. 1996 - 1997, All Rights Reserved
  9. * (C) Copyright IBM Corp. 1996 - 1998, All Rights Reserved
  10. *
  11. * The original version of this source code and documentation is
  12. * copyrighted and owned by Taligent, Inc., a wholly-owned subsidiary
  13. * of IBM. These materials are provided under terms of a License
  14. * Agreement between Taligent and Sun. This technology is protected
  15. * by multiple US and International patents.
  16. *
  17. * This notice and attribution to Taligent may not be removed.
  18. * Taligent is a registered trademark of Taligent, Inc.
  19. *
  20. */
  21. package java.awt.font;
  22. import java.awt.geom.Rectangle2D;
  23. /**
  24. * The <code>GlyphMetrics</code> class represents infomation for a
  25. * single glyph. A glyph is the visual representation of one or more
  26. * characters. Many different glyphs can be used to represent a single
  27. * character or combination of characters. <code>GlyphMetrics</code>
  28. * instances are produced by {@link java.awt.Font Font} and are applicable
  29. * to a specific glyph in a particular <code>Font</code>.
  30. * <p>
  31. * Glyphs are either STANDARD, LIGATURE, COMBINING, or COMPONENT.
  32. * <ul>
  33. * <li>STANDARD glyphs are commonly used to represent single characters.
  34. * <li>LIGATURE glyphs are used to represent sequences of characters.
  35. * <li>COMPONENT glyphs in a {@link GlyphVector} do not correspond to a
  36. * particular character in a text model. Instead, COMPONENT glyphs are
  37. * added for typographical reasons, such as Arabic justification.
  38. * <li>COMBINING glyphs embellish STANDARD or LIGATURE glyphs, such
  39. * as accent marks. Carets do not appear before COMBINING glyphs.
  40. * </ul>
  41. * <p>
  42. * Other metrics available through <code>GlyphMetrics</code> are the
  43. * components of the advance, the visual bounds, and the left and right
  44. * side bearings.
  45. * <p>
  46. * Glyphs for a rotated font, or obtained from a <code>GlyphVector</code>
  47. * which has applied a rotation to the glyph, can have advances that
  48. * contain both X and Y components. Usually the advance only has one
  49. * component.
  50. * <p>
  51. * The advance of a glyph is the distance from the glyph's origin to the
  52. * origin of the next glyph along the baseline, which is either vertical
  53. * or horizontal. Note that, in a <code>GlyphVector</code>,
  54. * the distance from a glyph to its following glyph might not be the
  55. * glyph's advance, because of kerning or other positioning adjustments.
  56. * <p>
  57. * The bounds is the smallest rectangle that completely contains the
  58. * outline of the glyph. The bounds rectangle is relative to the
  59. * glyph's origin. The left-side bearing is the distance from the glyph
  60. * origin to the left of its bounds rectangle. If the left-side bearing is
  61. * negative, part of the glyph is drawn to the left of its origin. The
  62. * right-side bearing is the distance from the right side of the bounds
  63. * rectangle to the next glyph origin (the origin plus the advance). If
  64. * negative, part of the glyph is drawn to the right of the next glyph's
  65. * origin. Note that the bounds does not necessarily enclose all the pixels
  66. * affected when rendering the glyph, because of rasterization and pixel
  67. * adjustment effects.
  68. * <p>
  69. * Although instances of <code>GlyphMetrics</code> can be directly
  70. * constructed, they are almost always obtained from a
  71. * <code>GlyphVector</code>. Once constructed, <code>GlyphMetrics</code>
  72. * objects are immutable.
  73. * <p>
  74. * <strong>Example</strong>:<p>
  75. * Querying a <code>Font</code> for glyph information
  76. * <blockquote><pre>
  77. * Font font = ...;
  78. * int glyphIndex = ...;
  79. * GlyphMetrics metrics = GlyphVector.getGlyphMetrics(glyphIndex);
  80. * int isStandard = metrics.isStandard();
  81. * float glyphAdvance = metrics.getAdvance();
  82. * </pre></blockquote>
  83. * @see java.awt.Font
  84. * @see GlyphVector
  85. */
  86. public final class GlyphMetrics {
  87. /**
  88. * Indicates whether the metrics are for a horizontal or vertical baseline.
  89. */
  90. private boolean horizontal;
  91. /**
  92. * The x-component of the advance.
  93. */
  94. private float advanceX;
  95. /**
  96. * The y-component of the advance.
  97. */
  98. private float advanceY;
  99. /**
  100. * The bounds of the associated glyph.
  101. */
  102. private Rectangle2D.Float bounds;
  103. /**
  104. * Additional information about the glyph encoded as a byte.
  105. */
  106. private byte glyphType;
  107. /**
  108. * Indicates a glyph that represents a single standard
  109. * character.
  110. */
  111. public static final byte STANDARD = 0;
  112. /**
  113. * Indicates a glyph that represents multiple characters
  114. * as a ligature, for example 'fi' or 'ffi'. It is followed by
  115. * filler glyphs for the remaining characters. Filler and combining
  116. * glyphs can be intermixed to control positioning of accent marks
  117. * on the logically preceeding ligature.
  118. */
  119. public static final byte LIGATURE = 1;
  120. /**
  121. * Indicates a glyph that represents a combining character,
  122. * such as an umlaut. There is no caret position between this glyph
  123. * and the preceeding glyph.
  124. */
  125. public static final byte COMBINING = 2;
  126. /**
  127. * Indicates a glyph with no corresponding character in the
  128. * backing store. The glyph is associated with the character
  129. * represented by the logicaly preceeding non-component glyph. This
  130. * is used for kashida justification or other visual modifications to
  131. * existing glyphs. There is no caret position between this glyph
  132. * and the preceeding glyph.
  133. */
  134. public static final byte COMPONENT = 3;
  135. /**
  136. * Indicates a glyph with no visual representation. It can
  137. * be added to the other code values to indicate an invisible glyph.
  138. */
  139. public static final byte WHITESPACE = 4;
  140. /**
  141. * Constructs a <code>GlyphMetrics</code> object.
  142. * @param advance the advance width of the glyph
  143. * @param bounds the black box bounds of the glyph
  144. * @param glyphType the type of the glyph
  145. */
  146. public GlyphMetrics(float advance, Rectangle2D bounds, byte glyphType) {
  147. this.horizontal = true;
  148. this.advanceX = advance;
  149. this.advanceY = 0;
  150. this.bounds = new Rectangle2D.Float();
  151. this.bounds.setRect(bounds);
  152. this.glyphType = glyphType;
  153. }
  154. /**
  155. * Constructs a <code>GlyphMetrics</code> object.
  156. * @param horizontal if true, metrics are for a horizontal baseline,
  157. * otherwise they are for a vertical baseline
  158. * @param advanceX the X-component of the glyph's advance
  159. * @param advanceY the Y-component of the glyph's advance
  160. * @param bounds the visual bounds of the glyph
  161. * @param glyphType the type of the glyph
  162. */
  163. public GlyphMetrics(boolean horizontal, float advanceX, float advanceY,
  164. Rectangle2D bounds, byte glyphType) {
  165. this.horizontal = horizontal;
  166. this.advanceX = advanceX;
  167. this.advanceY = advanceY;
  168. this.bounds = new Rectangle2D.Float();
  169. this.bounds.setRect(bounds);
  170. this.glyphType = glyphType;
  171. }
  172. /**
  173. * Returns the advance of the glyph along the baseline (either
  174. * horizontal or vertical).
  175. * @return the advance of the glyph
  176. */
  177. public float getAdvance() {
  178. return horizontal ? advanceX : advanceY;
  179. }
  180. /**
  181. * Returns the x-component of the advance of the glyph.
  182. * @return the x-component of the advance of the glyph
  183. */
  184. public float getAdvanceX() {
  185. return advanceX;
  186. }
  187. /**
  188. * Returns the y-component of the advance of the glyph.
  189. * @return the y-component of the advance of the glyph
  190. */
  191. public float getAdvanceY() {
  192. return advanceY;
  193. }
  194. /**
  195. * Returns the bounds of the glyph. This is the bounding box of the glyph outline.
  196. * Because of rasterization and pixel alignment effects, it does not necessarily
  197. * enclose the pixels that are affected when rendering the glyph.
  198. * @return a {@link Rectangle2D} that is the bounds of the glyph.
  199. */
  200. public Rectangle2D getBounds2D() {
  201. return new Rectangle2D.Float(bounds.x, bounds.y, bounds.width, bounds.height);
  202. }
  203. /**
  204. * Returns the left (top) side bearing of the glyph.
  205. * <p>
  206. * This is the distance from 0, 0 to the left (top) of the glyph
  207. * bounds. If the bounds of the glyph is to the left of (above) the
  208. * origin, the LSB is negative.
  209. * @return the left side bearing of the glyph.
  210. */
  211. public float getLSB() {
  212. return horizontal ? bounds.x : bounds.y;
  213. }
  214. /**
  215. * Returns the right (bottom) side bearing of the glyph.
  216. * <p>
  217. * This is the distance from the right (bottom) of the glyph bounds to
  218. * the advance. If the bounds of the glyph is to the right of (below)
  219. * the advance, the RSB is negative.
  220. * @return the right side bearing of the glyph.
  221. */
  222. public float getRSB() {
  223. return horizontal ?
  224. advanceX - bounds.x - bounds.width :
  225. advanceY - bounds.y - bounds.height;
  226. }
  227. /**
  228. * Returns the raw glyph type code.
  229. * @return the raw glyph type code.
  230. */
  231. public int getType() {
  232. return glyphType;
  233. }
  234. /**
  235. * Returns <code>true</code> if this is a standard glyph.
  236. * @return <code>true</code> if this is a standard glyph;
  237. * <code>false</code> otherwise.
  238. */
  239. public boolean isStandard() {
  240. return (glyphType & 0x3) == STANDARD;
  241. }
  242. /**
  243. * Returns <code>true</code> if this is a ligature glyph.
  244. * @return <code>true</code> if this is a ligature glyph;
  245. * <code>false</code> otherwise.
  246. */
  247. public boolean isLigature() {
  248. return (glyphType & 0x3) == LIGATURE;
  249. }
  250. /**
  251. * Returns <code>true</code> if this is a combining glyph.
  252. * @return <code>true</code> if this is a combining glyph;
  253. * <code>false</code> otherwise.
  254. */
  255. public boolean isCombining() {
  256. return (glyphType & 0x3) == COMBINING;
  257. }
  258. /**
  259. * Returns <code>true</code> if this is a component glyph.
  260. * @return <code>true</code> if this is a component glyph;
  261. * <code>false</code> otherwise.
  262. */
  263. public boolean isComponent() {
  264. return (glyphType & 0x3) == COMPONENT;
  265. }
  266. /**
  267. * Returns <code>true</code> if this is a whitespace glyph.
  268. * @return <code>true</code> if this is a whitespace glyph;
  269. * <code>false</code> otherwise.
  270. */
  271. public boolean isWhitespace() {
  272. return (glyphType & 0x4) == WHITESPACE;
  273. }
  274. }