1 /* 2 * Copyright (c) 1997, 2007, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 27 package javax.swing; 28 29 import java.awt.*; 30 import java.awt.event.*; 31 import java.beans.ConstructorProperties; 32 import java.util.Locale; 33 import java.io.Serializable; 34 import javax.accessibility.*; 35 36 /** 37 * A lightweight container 38 * that uses a BoxLayout object as its layout manager. 39 * Box provides several class methods 40 * that are useful for containers using BoxLayout -- 41 * even non-Box containers. 42 * 43 * <p> 44 * The <code>Box</code> class can create several kinds 45 * of invisible components 46 * that affect layout: 47 * glue, struts, and rigid areas. 48 * If all the components your <code>Box</code> contains 49 * have a fixed size, 50 * you might want to use a glue component 51 * (returned by <code>createGlue</code>) 52 * to control the components' positions. 53 * If you need a fixed amount of space between two components, 54 * try using a strut 55 * (<code>createHorizontalStrut</code> or <code>createVerticalStrut</code>). 56 * If you need an invisible component 57 * that always takes up the same amount of space, 58 * get it by invoking <code>createRigidArea</code>. 59 * <p> 60 * If you are implementing a <code>BoxLayout</code> you 61 * can find further information and examples in 62 * <a 63 href="http://java.sun.com/docs/books/tutorial/uiswing/layout/box.html">How to Use BoxLayout</a>, 64 * a section in <em>The Java Tutorial.</em> 65 * <p> 66 * <strong>Warning:</strong> 67 * Serialized objects of this class will not be compatible with 68 * future Swing releases. The current serialization support is 69 * appropriate for short term storage or RMI between applications running 70 * the same version of Swing. As of 1.4, support for long term storage 71 * of all JavaBeans<sup><font size="-2">TM</font></sup> 72 * has been added to the <code>java.beans</code> package. 73 * Please see {@link java.beans.XMLEncoder}. 74 * 75 * @see BoxLayout 76 * 77 * @author Timothy Prinzing 78 */ 79 @SuppressWarnings("serial") 80 public class Box extends JComponent implements Accessible { 81 82 /** 83 * Creates a <code>Box</code> that displays its components 84 * along the the specified axis. 85 * 86 * @param axis can be {@link BoxLayout#X_AXIS}, 87 * {@link BoxLayout#Y_AXIS}, 88 * {@link BoxLayout#LINE_AXIS} or 89 * {@link BoxLayout#PAGE_AXIS}. 90 * @throws AWTError if the <code>axis</code> is invalid 91 * @see #createHorizontalBox 92 * @see #createVerticalBox 93 */ 94 public Box(int axis) { 95 super(); 96 super.setLayout(new BoxLayout(this, axis)); 97 } 98 99 /** 100 * Creates a <code>Box</code> that displays its components 101 * from left to right. If you want a <code>Box</code> that 102 * respects the component orientation you should create the 103 * <code>Box</code> using the constructor and pass in 104 * <code>BoxLayout.LINE_AXIS</code>, eg: 105 * <pre> 106 * Box lineBox = new Box(BoxLayout.LINE_AXIS); 107 * </pre> 108 * 109 * @return the box 110 */ 111 public static Box createHorizontalBox() { 112 return new Box(BoxLayout.X_AXIS); 113 } 114 115 /** 116 * Creates a <code>Box</code> that displays its components 117 * from top to bottom. If you want a <code>Box</code> that 118 * respects the component orientation you should create the 119 * <code>Box</code> using the constructor and pass in 120 * <code>BoxLayout.PAGE_AXIS</code>, eg: 121 * <pre> 122 * Box lineBox = new Box(BoxLayout.PAGE_AXIS); 123 * </pre> 124 * 125 * @return the box 126 */ 127 public static Box createVerticalBox() { 128 return new Box(BoxLayout.Y_AXIS); 129 } 130 131 /** 132 * Creates an invisible component that's always the specified size. 133 * <!-- WHEN WOULD YOU USE THIS AS OPPOSED TO A STRUT? --> 134 * 135 * @param d the dimensions of the invisible component 136 * @return the component 137 * @see #createGlue 138 * @see #createHorizontalStrut 139 * @see #createVerticalStrut 140 */ 141 public static Component createRigidArea(Dimension d) { 142 return new Filler(d, d, d); 143 } 144 145 /** 146 * Creates an invisible, fixed-width component. 147 * In a horizontal box, 148 * you typically use this method 149 * to force a certain amount of space between two components. 150 * In a vertical box, 151 * you might use this method 152 * to force the box to be at least the specified width. 153 * The invisible component has no height 154 * unless excess space is available, 155 * in which case it takes its share of available space, 156 * just like any other component that has no maximum height. 157 * 158 * @param width the width of the invisible component, in pixels >= 0 159 * @return the component 160 * @see #createVerticalStrut 161 * @see #createGlue 162 * @see #createRigidArea 163 */ 164 public static Component createHorizontalStrut(int width) { 165 return new Filler(new Dimension(width,0), new Dimension(width,0), 166 new Dimension(width, Short.MAX_VALUE)); 167 } 168 169 /** 170 * Creates an invisible, fixed-height component. 171 * In a vertical box, 172 * you typically use this method 173 * to force a certain amount of space between two components. 174 * In a horizontal box, 175 * you might use this method 176 * to force the box to be at least the specified height. 177 * The invisible component has no width 178 * unless excess space is available, 179 * in which case it takes its share of available space, 180 * just like any other component that has no maximum width. 181 * 182 * @param height the height of the invisible component, in pixels >= 0 183 * @return the component 184 * @see #createHorizontalStrut 185 * @see #createGlue 186 * @see #createRigidArea 187 */ 188 public static Component createVerticalStrut(int height) { 189 return new Filler(new Dimension(0,height), new Dimension(0,height), 190 new Dimension(Short.MAX_VALUE, height)); 191 } 192 193 /** 194 * Creates an invisible "glue" component 195 * that can be useful in a Box 196 * whose visible components have a maximum width 197 * (for a horizontal box) 198 * or height (for a vertical box). 199 * You can think of the glue component 200 * as being a gooey substance 201 * that expands as much as necessary 202 * to fill the space between its neighboring components. 203 * 204 * <p> 205 * 206 * For example, suppose you have 207 * a horizontal box that contains two fixed-size components. 208 * If the box gets extra space, 209 * the fixed-size components won't become larger, 210 * so where does the extra space go? 211 * Without glue, 212 * the extra space goes to the right of the second component. 213 * If you put glue between the fixed-size components, 214 * then the extra space goes there. 215 * If you put glue before the first fixed-size component, 216 * the extra space goes there, 217 * and the fixed-size components are shoved against the right 218 * edge of the box. 219 * If you put glue before the first fixed-size component 220 * and after the second fixed-size component, 221 * the fixed-size components are centered in the box. 222 * 223 * <p> 224 * 225 * To use glue, 226 * call <code>Box.createGlue</code> 227 * and add the returned component to a container. 228 * The glue component has no minimum or preferred size, 229 * so it takes no space unless excess space is available. 230 * If excess space is available, 231 * then the glue component takes its share of available 232 * horizontal or vertical space, 233 * just like any other component that has no maximum width or height. 234 * 235 * @return the component 236 */ 237 public static Component createGlue() { 238 return new Filler(new Dimension(0,0), new Dimension(0,0), 239 new Dimension(Short.MAX_VALUE, Short.MAX_VALUE)); 240 } 241 242 /** 243 * Creates a horizontal glue component. 244 * 245 * @return the component 246 */ 247 public static Component createHorizontalGlue() { 248 return new Filler(new Dimension(0,0), new Dimension(0,0), 249 new Dimension(Short.MAX_VALUE, 0)); 250 } 251 252 /** 253 * Creates a vertical glue component. 254 * 255 * @return the component 256 */ 257 public static Component createVerticalGlue() { 258 return new Filler(new Dimension(0,0), new Dimension(0,0), 259 new Dimension(0, Short.MAX_VALUE)); 260 } 261 262 /** 263 * Throws an AWTError, since a Box can use only a BoxLayout. 264 * 265 * @param l the layout manager to use 266 */ 267 public void setLayout(LayoutManager l) { 268 throw new AWTError("Illegal request"); 269 } 270 271 /** 272 * Paints this <code>Box</code>. If this <code>Box</code> has a UI this 273 * method invokes super's implementation, otherwise if this 274 * <code>Box</code> is opaque the <code>Graphics</code> is filled 275 * using the background. 276 * 277 * @param g the <code>Graphics</code> to paint to 278 * @throws NullPointerException if <code>g</code> is null 279 * @since 1.6 280 */ 281 protected void paintComponent(Graphics g) { 282 if (ui != null) { 283 // On the off chance some one created a UI, honor it 284 super.paintComponent(g); 285 } else if (isOpaque()) { 286 g.setColor(getBackground()); 287 g.fillRect(0, 0, getWidth(), getHeight()); 288 } 289 } 290 291 292 /** 293 * An implementation of a lightweight component that participates in 294 * layout but has no view. 295 * <p> 296 * <strong>Warning:</strong> 297 * Serialized objects of this class will not be compatible with 298 * future Swing releases. The current serialization support is 299 * appropriate for short term storage or RMI between applications running 300 * the same version of Swing. As of 1.4, support for long term storage 301 * of all JavaBeans<sup><font size="-2">TM</font></sup> 302 * has been added to the <code>java.beans</code> package. 303 * Please see {@link java.beans.XMLEncoder}. 304 */ 305 @SuppressWarnings("serial") 306 public static class Filler extends JComponent implements Accessible { 307 308 /** 309 * Constructor to create shape with the given size ranges. 310 * 311 * @param min Minimum size 312 * @param pref Preferred size 313 * @param max Maximum size 314 */ 315 @ConstructorProperties({"minimumSize", "preferredSize", "maximumSize"}) 316 public Filler(Dimension min, Dimension pref, Dimension max) { 317 setMinimumSize(min); 318 setPreferredSize(pref); 319 setMaximumSize(max); 320 } 321 322 /** 323 * Change the size requests for this shape. An invalidate() is 324 * propagated upward as a result so that layout will eventually 325 * happen with using the new sizes. 326 * 327 * @param min Value to return for getMinimumSize 328 * @param pref Value to return for getPreferredSize 329 * @param max Value to return for getMaximumSize 330 */ 331 public void changeShape(Dimension min, Dimension pref, Dimension max) { 332 setMinimumSize(min); 333 setPreferredSize(pref); 334 setMaximumSize(max); 335 revalidate(); 336 } 337 338 // ---- Component methods ------------------------------------------ 339 340 /** 341 * Paints this <code>Filler</code>. If this 342 * <code>Filler</code> has a UI this method invokes super's 343 * implementation, otherwise if this <code>Filler</code> is 344 * opaque the <code>Graphics</code> is filled using the 345 * background. 346 * 347 * @param g the <code>Graphics</code> to paint to 348 * @throws NullPointerException if <code>g</code> is null 349 * @since 1.6 350 */ 351 protected void paintComponent(Graphics g) { 352 if (ui != null) { 353 // On the off chance some one created a UI, honor it 354 super.paintComponent(g); 355 } else if (isOpaque()) { 356 g.setColor(getBackground()); 357 g.fillRect(0, 0, getWidth(), getHeight()); 358 } 359 } 360 361 ///////////////// 362 // Accessibility support for Box$Filler 363 //////////////// 364 365 /** 366 * Gets the AccessibleContext associated with this Box.Filler. 367 * For box fillers, the AccessibleContext takes the form of an 368 * AccessibleBoxFiller. 369 * A new AccessibleAWTBoxFiller instance is created if necessary. 370 * 371 * @return an AccessibleBoxFiller that serves as the 372 * AccessibleContext of this Box.Filler. 373 */ 374 public AccessibleContext getAccessibleContext() { 375 if (accessibleContext == null) { 376 accessibleContext = new AccessibleBoxFiller(); 377 } 378 return accessibleContext; 379 } 380 381 /** 382 * This class implements accessibility support for the 383 * <code>Box.Filler</code> class. 384 */ 385 @SuppressWarnings("serial") 386 protected class AccessibleBoxFiller extends AccessibleAWTComponent { 387 // AccessibleContext methods 388 // 389 /** 390 * Gets the role of this object. 391 * 392 * @return an instance of AccessibleRole describing the role of 393 * the object (AccessibleRole.FILLER) 394 * @see AccessibleRole 395 */ 396 public AccessibleRole getAccessibleRole() { 397 return AccessibleRole.FILLER; 398 } 399 } 400 } 401 402 ///////////////// 403 // Accessibility support for Box 404 //////////////// 405 406 /** 407 * Gets the AccessibleContext associated with this Box. 408 * For boxes, the AccessibleContext takes the form of an 409 * AccessibleBox. 410 * A new AccessibleAWTBox instance is created if necessary. 411 * 412 * @return an AccessibleBox that serves as the 413 * AccessibleContext of this Box 414 */ 415 public AccessibleContext getAccessibleContext() { 416 if (accessibleContext == null) { 417 accessibleContext = new AccessibleBox(); 418 } 419 return accessibleContext; 420 } 421 422 /** 423 * This class implements accessibility support for the 424 * <code>Box</code> class. 425 */ 426 @SuppressWarnings("serial") 427 protected class AccessibleBox extends AccessibleAWTContainer { 428 // AccessibleContext methods 429 // 430 /** 431 * Gets the role of this object. 432 * 433 * @return an instance of AccessibleRole describing the role of the 434 * object (AccessibleRole.FILLER) 435 * @see AccessibleRole 436 */ 437 public AccessibleRole getAccessibleRole() { 438 return AccessibleRole.FILLER; 439 } 440 } // inner class AccessibleBox 441 }