KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > jfree > text > TextLine


1 /* ========================================================================
2  * JCommon : a free general purpose class library for the Java(tm) platform
3  * ========================================================================
4  *
5  * (C) Copyright 2000-2005, by Object Refinery Limited and Contributors.
6  *
7  * Project Info: http://www.jfree.org/jcommon/index.html
8  *
9  * This library is free software; you can redistribute it and/or modify it
10  * under the terms of the GNU Lesser General Public License as published by
11  * the Free Software Foundation; either version 2.1 of the License, or
12  * (at your option) any later version.
13  *
14  * This library is distributed in the hope that it will be useful, but
15  * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
16  * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
17  * License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with this library; if not, write to the Free Software
21  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
22  * USA.
23  *
24  * [Java is a trademark or registered trademark of Sun Microsystems, Inc.
25  * in the United States and other countries.]
26  *
27  * -------------
28  * TextLine.java
29  * -------------
30  * (C) Copyright 2003-2005, by Object Refinery Limited and Contributors.
31  *
32  * Original Author: David Gilbert (for Object Refinery Limited);
33  * Contributor(s): -;
34  *
35  * $Id: TextLine.java,v 1.11 2005/10/18 13:17:16 mungady Exp $
36  *
37  * Changes
38  * -------
39  * 07-Nov-2003 : Version 1 (DG);
40  * 22-Dec-2003 : Added workaround for Java bug 4245442 (DG);
41  * 29-Jan-2004 : Added new constructor (DG);
42  * 22-Mar-2004 : Added equals() method and implemented Serializable (DG);
43  * 01-Apr-2004 : Changed java.awt.geom.Dimension2D to org.jfree.ui.Size2D
44  * because of JDK bug 4976448 which persists on JDK 1.3.1 (DG);
45  * 03-Sep-2004 : Added a method to remove a fragment (DG);
46  * 08-Jul-2005 : Fixed bug in calculateBaselineOffset() (DG);
47  *
48  */

49
50 package org.jfree.text;
51
52 import java.awt.Font JavaDoc;
53 import java.awt.Graphics2D JavaDoc;
54 import java.awt.Paint JavaDoc;
55 import java.io.Serializable JavaDoc;
56 import java.util.Iterator JavaDoc;
57 import java.util.List JavaDoc;
58
59 import org.jfree.ui.Size2D;
60 import org.jfree.ui.TextAnchor;
61 import org.jfree.util.Log;
62 import org.jfree.util.LogContext;
63
64 /**
65  * A sequence of {@link TextFragment} objects that together form a line of
66  * text. A sequence of text lines is managed by the {@link TextBlock} class.
67  *
68  * @author David Gilbert
69  */

70 public class TextLine implements Serializable JavaDoc {
71
72     /** For serialization. */
73     private static final long serialVersionUID = 7100085690160465444L;
74     
75     /** Storage for the text fragments that make up the line. */
76     private List JavaDoc fragments;
77     
78     /** Access to logging facilities. */
79     protected static final LogContext logger
80         = Log.createContext(TextLine.class);
81
82     /**
83      * Creates a new empty line.
84      */

85     public TextLine() {
86         this.fragments = new java.util.ArrayList JavaDoc();
87     }
88     
89     /**
90      * Creates a new text line using the default font.
91      *
92      * @param text the text (<code>null</code> not permitted).
93      */

94     public TextLine(final String JavaDoc text) {
95         this(text, TextFragment.DEFAULT_FONT);
96     }
97     
98     /**
99      * Creates a new text line.
100      *
101      * @param text the text (<code>null</code> not permitted).
102      * @param font the text font (<code>null</code> not permitted).
103      */

104     public TextLine(final String JavaDoc text, final Font JavaDoc font) {
105         this.fragments = new java.util.ArrayList JavaDoc();
106         final TextFragment fragment = new TextFragment(text, font);
107         this.fragments.add(fragment);
108     }
109     
110     /**
111      * Creates a new text line.
112      *
113      * @param text the text (<code>null</code> not permitted).
114      * @param font the text font (<code>null</code> not permitted).
115      * @param paint the text color (<code>null</code> not permitted).
116      */

117     public TextLine(final String JavaDoc text, final Font JavaDoc font, final Paint JavaDoc paint) {
118         if (text == null) {
119             throw new IllegalArgumentException JavaDoc("Null 'text' argument.");
120         }
121         if (font == null) {
122             throw new IllegalArgumentException JavaDoc("Null 'font' argument.");
123         }
124         if (paint == null) {
125             throw new IllegalArgumentException JavaDoc("Null 'paint' argument.");
126         }
127         this.fragments = new java.util.ArrayList JavaDoc();
128         final TextFragment fragment = new TextFragment(text, font, paint);
129         this.fragments.add(fragment);
130     }
131     
132     /**
133      * Adds a text fragment to the text line.
134      *
135      * @param fragment the text fragment (<code>null</code> not permitted).
136      */

137     public void addFragment(final TextFragment fragment) {
138         this.fragments.add(fragment);
139     }
140     
141     /**
142      * Removes a fragment from the line.
143      *
144      * @param fragment the fragment to remove.
145      */

146     public void removeFragment(final TextFragment fragment) {
147         this.fragments.remove(fragment);
148     }
149     
150     /**
151      * Draws the text line.
152      *
153      * @param g2 the graphics device.
154      * @param anchorX the x-coordinate for the anchor point.
155      * @param anchorY the y-coordinate for the anchor point.
156      * @param anchor the point on the text line that is aligned to the anchor
157      * point.
158      * @param rotateX the x-coordinate for the rotation point.
159      * @param rotateY the y-coordinate for the rotation point.
160      * @param angle the rotation angle (in radians).
161      */

162     public void draw(final Graphics2D JavaDoc g2,
163                      final float anchorX, final float anchorY,
164                      final TextAnchor anchor,
165                      final float rotateX, final float rotateY,
166                      final double angle) {
167     
168         float x = anchorX;
169         final float yOffset = calculateBaselineOffset(g2, anchor);
170         final Iterator JavaDoc iterator = this.fragments.iterator();
171         while (iterator.hasNext()) {
172             final TextFragment fragment = (TextFragment) iterator.next();
173             final Size2D d = fragment.calculateDimensions(g2);
174             fragment.draw(
175                 g2, x, anchorY + yOffset, TextAnchor.BASELINE_LEFT,
176                 rotateX, rotateY, angle
177             );
178             x = x + (float) d.getWidth();
179         }
180     
181     }
182     
183     /**
184      * Calculates the width and height of the text line.
185      *
186      * @param g2 the graphics device.
187      *
188      * @return The width and height.
189      */

190     public Size2D calculateDimensions(final Graphics2D JavaDoc g2) {
191         double width = 0.0;
192         double height = 0.0;
193         final Iterator JavaDoc iterator = this.fragments.iterator();
194         while (iterator.hasNext()) {
195             final TextFragment fragment = (TextFragment) iterator.next();
196             final Size2D dimension = fragment.calculateDimensions(g2);
197             width = width + dimension.getWidth();
198             height = Math.max(height, dimension.getHeight());
199             if (logger.isDebugEnabled()) {
200                 logger.debug("width = " + width + ", height = " + height);
201             }
202         }
203         return new Size2D(width, height);
204     }
205     
206     /**
207      * Returns the first text fragment in the line.
208      *
209      * @return The first text fragment in the line.
210      */

211     public TextFragment getFirstTextFragment() {
212         TextFragment result = null;
213         if (this.fragments.size() > 0) {
214             result = (TextFragment) this.fragments.get(0);
215         }
216         return result;
217     }
218     
219     /**
220      * Returns the last text fragment in the line.
221      *
222      * @return The last text fragment in the line.
223      */

224     public TextFragment getLastTextFragment() {
225         TextFragment result = null;
226         if (this.fragments.size() > 0) {
227             result = (TextFragment) this.fragments.get(this.fragments.size()
228                     - 1);
229         }
230         return result;
231     }
232     
233     /**
234      * Calculate the offsets required to translate from the specified anchor
235      * position to the left baseline position.
236      *
237      * @param g2 the graphics device.
238      * @param anchor the anchor position.
239      *
240      * @return The offsets.
241      */

242     private float calculateBaselineOffset(final Graphics2D JavaDoc g2,
243                                           final TextAnchor anchor) {
244         float result = 0.0f;
245         Iterator JavaDoc iterator = this.fragments.iterator();
246         while (iterator.hasNext()) {
247             TextFragment fragment = (TextFragment) iterator.next();
248             result = Math.max(result,
249                     fragment.calculateBaselineOffset(g2, anchor));
250         }
251         return result;
252     }
253     
254     /**
255      * Tests this object for equality with an arbitrary object.
256      *
257      * @param obj the object to test against (<code>null</code> permitted).
258      *
259      * @return A boolean.
260      */

261     public boolean equals(final Object JavaDoc obj) {
262         if (obj == null) {
263             return false;
264         }
265         if (obj == this) {
266             return true;
267         }
268         if (obj instanceof TextLine) {
269             final TextLine line = (TextLine) obj;
270             return this.fragments.equals(line.fragments);
271         }
272         return false;
273     }
274
275     /**
276      * Returns a hash code for this object.
277      *
278      * @return A hash code.
279      */

280     public int hashCode() {
281         return (this.fragments != null ? this.fragments.hashCode() : 0);
282     }
283
284 }
285
Popular Tags