source: trunk/src/gcc/libjava/java/awt/FlowLayout.java@ 154

Last change on this file since 154 was 2, checked in by bird, 23 years ago

Initial revision

  • Property cvs2svn:cvs-rev set to 1.1
  • Property svn:eol-style set to native
  • Property svn:executable set to *
File size: 9.5 KB
Line 
1// FlowLayout.java - Grid-based layout engine
2
3/* Copyright (C) 1999, 2000, 2001, 2002 Free Software Foundation
4
5This file is part of GNU Classpath.
6
7GNU Classpath is free software; you can redistribute it and/or modify
8it under the terms of the GNU General Public License as published by
9the Free Software Foundation; either version 2, or (at your option)
10any later version.
11
12GNU Classpath is distributed in the hope that it will be useful, but
13WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15General Public License for more details.
16
17You should have received a copy of the GNU General Public License
18along with GNU Classpath; see the file COPYING. If not, write to the
19Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
2002111-1307 USA.
21
22Linking this library statically or dynamically with other modules is
23making a combined work based on this library. Thus, the terms and
24conditions of the GNU General Public License cover the whole
25combination.
26
27As a special exception, the copyright holders of this library give you
28permission to link this library with independent modules to produce an
29executable, regardless of the license terms of these independent
30modules, and to copy and distribute the resulting executable under
31terms of your choice, provided that you also meet, for each linked
32independent module, the terms and conditions of the license of that
33module. An independent module is a module which is not derived from
34or based on this library. If you modify this library, you may extend
35this exception to your version of the library, but you are not
36obligated to do so. If you do not wish to do so, delete this
37exception statement from your version. */
38
39
40package java.awt;
41
42import java.io.Serializable;
43
44/** This class implements a flow-based layout. Components are laid
45 * out in order from left to right. When a component cannot be placed
46 * without horizontal clipping, a new row is started. This class
47 * supports horizontal and vertical gaps. These are used for spacing
48 * between components.
49 *
50 * @author Tom Tromey <[email protected]>
51 * @author Aaron M. Renn ([email protected])
52 */
53public class FlowLayout implements LayoutManager, Serializable
54{
55 /** Constant that specifies left alignment. */
56 public static final int LEFT = 0;
57 /** Constant that specifies center alignment. */
58 public static final int CENTER = 1;
59 /** Constant that specifies right alignment. */
60 public static final int RIGHT = 2;
61
62 /** Constant that specifies alignment to leading edge of container's
63 * orientation. */
64 public static final int LEADING = 3;
65 /** Constant that specifies alignment to trailing edge of container's
66 * orientation. */
67 public static final int TRAILING = 4;
68
69 // Serialization constant
70 private static final long serialVersionUID = -7262534875583282631L;
71
72 /** Add a new component to the layout. This particular implementation
73 * does nothing.
74 */
75 public void addLayoutComponent (String name, Component comp)
76 {
77 // Nothing.
78 }
79
80 /**
81 * Returns the current justification value for this object.
82 *
83 * @return The current justification value for this object.
84 */
85 public int getAlignment ()
86 {
87 return align;
88 }
89
90 /**
91 * Returns the horizontal gap between components.
92 *
93 * @return The horizontal gap between components.
94 */
95 public int getHgap ()
96 {
97 return hgap;
98 }
99
100 /**
101 * Returns the vertical gap between lines of components.
102 *
103 * @return The vertical gap between lines of components.
104 */
105 public int getVgap ()
106 {
107 return vgap;
108 }
109
110 /**
111 * Initializes a new instance of <code>FlowLayout</code> with a center
112 * justification and a default horizontal and vertical gap of 5.
113 */
114 public FlowLayout ()
115 {
116 this (CENTER, 5, 5);
117 }
118
119 /**
120 * Initializes a new instance of <code>FlowLayout</code> with the specified
121 * justification and a default horizontal and vertical gap of 5.
122 *
123 * @param align The justification setting, which should be one of the
124 * contants in this class.
125 */
126 public FlowLayout (int align)
127 {
128 this (align, 5, 5);
129 }
130
131 /**
132 * Initializes a new instance of <code>FlowLayout</code> with the specified
133 * justification and gap values
134 * @param align Alignment
135 * @param hgap The horizontal gap
136 * @param vgap The vertical gap
137 * @exception IllegalArgumentException If either gap is negative
138 */
139 public FlowLayout (int align, int hgap, int vgap)
140 {
141 // Use methods to set fields so that we can have all the checking
142 // in one place.
143 setVgap (vgap);
144 setHgap (hgap);
145 setAlignment (align);
146 }
147
148 /** Lay out the container's components based on current settings.
149 * @param parent The parent container
150 */
151 public void layoutContainer (Container parent)
152 {
153 int num = parent.getComponentCount ();
154 // This is more efficient than calling getComponents().
155 Component[] comps = parent.component;
156
157 Dimension d = parent.getSize ();
158 Insets ins = parent.getInsets ();
159
160 ComponentOrientation orient = parent.getComponentOrientation ();
161 boolean left_to_right = orient.isLeftToRight ();
162
163 int y = ins.top + vgap;
164 int i = 0;
165 while (i < num)
166 {
167 // Find the components which go in the current row.
168 int new_w = ins.left + hgap + ins.right;
169 int new_h = 0;
170 int j;
171 boolean found_one = false;
172 for (j = i; j < num && ! found_one; ++j)
173 {
174 // Skip invisible items.
175 if (! comps[i].visible)
176 continue;
177
178 Dimension c = comps[i].getPreferredSize ();
179
180 int next_w = new_w + hgap + c.width;
181 if (next_w <= d.width || ! found_one)
182 {
183 new_w = next_w;
184 new_h = Math.max (new_h, c.height);
185 found_one = true;
186 }
187 else
188 {
189 // Must start a new row, and we already found an item
190 break;
191 }
192 }
193
194 // Set the location of each component for this row.
195 int x;
196
197 int myalign = align;
198 if (align == LEADING)
199 myalign = left_to_right ? LEFT : RIGHT;
200 else if (align == TRAILING)
201 myalign = left_to_right ? RIGHT : LEFT;
202
203 if (myalign == LEFT)
204 x = ins.left + hgap;
205 else if (myalign == CENTER)
206 x = (d.width - new_w) / 2;
207 else
208 x = d.width - new_w;
209
210 for (int k = i; k < j; ++k)
211 {
212 if (comps[k].visible)
213 {
214 Dimension c = comps[k].getPreferredSize ();
215 comps[k].setBounds (x, y, c.width, new_h);
216 x += c.width + hgap;
217 }
218 }
219
220 // Advance to next row.
221 i = j;
222 y += new_h + vgap;
223 }
224 }
225
226 /**
227 * Returns the minimum layout size for the specified container using
228 * this layout.
229 * @param cont The parent container
230 * @return The minimum layout size.
231 */
232 public Dimension minimumLayoutSize (Container cont)
233 {
234 return getSize (cont, true);
235 }
236
237 /**
238 * Returns the preferred layout size for the specified container using
239 * this layout.
240 * @param cont The parent container
241 * @return The preferred layout size.
242 */
243 public Dimension preferredLayoutSize (Container cont)
244 {
245 return getSize (cont, false);
246 }
247
248 /** Remove the indicated component from this layout manager.
249 * This particular implementation does nothing.
250 * @param comp The component to remove
251 */
252 public void removeLayoutComponent (Component comp)
253 {
254 // Nothing.
255 }
256
257 /**
258 * Sets the justification value for this object to the specified value.
259 *
260 * @param align The new justification value for this object, which must
261 * be one of the constants in this class.
262 */
263 public void setAlignment (int align)
264 {
265 if (align != LEFT && align != RIGHT && align != CENTER
266 && align != LEADING && align != TRAILING)
267 throw new IllegalArgumentException ("invalid alignment: " + align);
268 this.align = align;
269 }
270
271 /**
272 * Sets the horizontal gap between components to the specified value.
273 *
274 * @param hgap The new horizontal gap between components.
275 */
276 public void setHgap (int hgap)
277 {
278 if (hgap < 0)
279 throw new IllegalArgumentException ("horizontal gap must be nonnegative");
280 this.hgap = hgap;
281 }
282
283 /**
284 * Sets the vertical gap between lines of components to the specified value.
285 *
286 * @param vgap The new vertical gap.
287 */
288 public void setVgap (int vgap)
289 {
290 if (vgap < 0)
291 throw new IllegalArgumentException ("vertical gap must be nonnegative");
292 this.vgap = vgap;
293 }
294
295 /** Return String description of this object.
296 * @return A string representation of this object.
297 */
298 public String toString ()
299 {
300 return ("[" + getClass ().getName () + ",hgap=" + hgap + ",vgap=" + vgap
301 + ",align=" + align + "]");
302 }
303
304 // This method is used to compute the various sizes.
305 private Dimension getSize (Container parent, boolean is_min)
306 {
307 int w, h, num = parent.getComponentCount ();
308 // This is more efficient than calling getComponents().
309 Component[] comps = parent.component;
310
311 w = 0;
312 h = 0;
313 for (int i = 0; i < num; ++i)
314 {
315 if (! comps[i].visible)
316 continue;
317
318 // FIXME: can we just directly read the fields in Component?
319 // Or will that not work with subclassing?
320 Dimension d;
321
322 if (is_min)
323 d = comps[i].getMinimumSize ();
324 else
325 d = comps[i].getPreferredSize ();
326
327 w += d.width;
328 h = Math.max (d.height, h);
329 }
330
331 Insets ins = parent.getInsets ();
332
333 w += (num + 1) * hgap + ins.left + ins.right;
334 h += 2 * vgap + ins.top + ins.bottom;
335
336 return new Dimension (w, h);
337 }
338
339 /**
340 * @serial The justification alignment of the lines of components, which
341 * will be one of the constants defined in this class.
342 */
343 private int align;
344
345 /**
346 * @serial The horizontal gap between components.
347 */
348 private int hgap;
349
350 /**
351 * @serial The vertical gap between lines of components.
352 */
353 private int vgap;
354}
Note: See TracBrowser for help on using the repository browser.