< prev index next >

modules/javafx.controls/src/main/java/javafx/scene/control/ButtonBar.java

Print this page




  52  * annotations, as well as the overarching
  53  * {@link #buttonOrderProperty() button order} specified for the ButtonBar.
  54  *
  55  * <strong>Uniform button sizing</strong>
  56  * <p>By default all buttons are uniformly sized in a ButtonBar, meaning that all
  57  * buttons take the width of the widest button. It is possible to opt-out of this
  58  * on a per-button basis, but calling the {@link #setButtonUniformSize(Node, boolean)} method with
  59  * a boolean value of false.
  60  *
  61  * <p>If a button is excluded from uniform sizing, it is both excluded from
  62  * being resized away from its preferred size, and also excluded from the
  63  * measuring process, so its size will not influence the maximum size calculated
  64  * for all buttons in the ButtonBar.
  65  *
  66  * <h3>Screenshots</h3>
  67  * <p>Because a ButtonBar comes with built-in support for Windows, Mac OS
  68  * and Linux, there are three screenshots shown below, with the same buttons
  69  * laid out on each of the three operating systems.
  70  *
  71  * <p>
  72  * <strong>Windows:</strong><br/><img src="doc-files/buttonBar-windows.png" /><br>
  73  * <strong>Mac OS:</strong><br/><img src="doc-files/buttonBar-mac.png" /><br>
  74  * <strong>Linux:</strong><br/><img src="doc-files/buttonBar-linux.png" /><br>
  75  *
  76  * <h3>Code Samples</h3>
  77  * <p>Instantiating and using the ButtonBar is simple, simply do the following:
  78  *
  79  * <pre>
  80  * {@code
  81  * // Create the ButtonBar instance
  82  * ButtonBar buttonBar = new ButtonBar();
  83  *
  84  * // Create the buttons to go into the ButtonBar
  85  * Button yesButton = new Button("Yes");
  86  * ButtonBar.setButtonData(yesButton, ButtonData.YES);
  87  *
  88  * Button noButton = new Button("No");
  89  * ButtonBar.setButtonData(noButton, ButtonData.NO);
  90  *
  91  * // Add buttons to the ButtonBar
  92  * buttonBar.getButtons().addAll(yesButton, noButton);
  93  * }</pre>
  94  *
  95  * <p>The code sample above will position the Yes and No buttons relative to the
  96  * users operating system. This means that on Windows and Linux the Yes button
  97  * will come before the No button, whereas on Mac OS it'll be No and then Yes.
  98  *
  99  * <p>In most cases the OS-specific layout is the best choice, but in cases
 100  * where you want a custom layout, this is achieved be modifying the
 101  * {@link #buttonOrderProperty() button order property}. These are cryptic-looking
 102  * strings that are shorthand representations for the button order. The built-in
 103  * orders for Windows, Mac OS and Linux are:
 104  *
 105  * <table border="0">
 106  *   <tr>
 107  *     <td width="75"><strong>Windows:</strong></td>
 108  *     <td>L_E+U+FBXI_YNOCAH_R</td>
 109  *   </tr>
 110  *   <tr>
 111  *     <td><strong>Mac OS:</strong></td>
 112  *     <td>L_HE+U+FBIX_NCYOA_R</td>
 113  *   </tr>
 114  *   <tr>
 115  *     <td><strong>Linux:</strong></td>
 116  *     <td>L_HE+UNYACBXIO_R</td>
 117  *   </tr>
 118  * </table>
 119  *
 120  * <p>You should refer to the {@link ButtonData} enumeration for a description of
 121  * what each of these characters mean. However, if your ButtonBar only consisted
 122  * of {@link ButtonData#YES} and {@link ButtonData#NO} buttons, you always
 123  * wanted the yes buttons before the no buttons, and you wanted the buttons to
 124  * be {@link ButtonData#BIG_GAP right-aligned}, you could do the following:
 125  *
 126  * <pre>
 127  * {@code


 300          *
 301          * <p><strong>Button order code:</strong> _ (underscore)
 302          */
 303         SMALL_GAP("_", false, false); //$NON-NLS-1$
 304 
 305         private final String typeCode;
 306 
 307         private final boolean cancelButton;
 308         private final boolean defaultButton;
 309 
 310         private ButtonData(String type, boolean cancelButton, boolean defaultButton) {
 311             this.typeCode = type;
 312             this.cancelButton = cancelButton;
 313             this.defaultButton = defaultButton;
 314         }
 315 
 316         /**
 317          * Returns the single character code used to represent the ButtonData
 318          * annotation in the {@link ButtonBar#buttonOrderProperty() button order}
 319          * string.


 320          */
 321         public String getTypeCode() {
 322             return typeCode;
 323         }
 324 
 325         /**
 326          * Indicates whether buttons created from the ButtonData enumeration
 327          * should be the 'cancel' button in the user interface. This typically
 328          * means that the button will respond to the escape key press, even if
 329          * the button does not have focus.
 330          *
 331          * <p>ButtonData enumeration values that can be the cancel button have a
 332          * comment stating this in their javadoc.

 333          */
 334         public final boolean isCancelButton() {
 335             return cancelButton;
 336         }
 337 
 338         /**
 339          * Indicates whether buttons created from the ButtonData enumeration
 340          * should be the 'default' button in the user interface. This typically
 341          * means that the button will respond to enter key presses, even if the
 342          * button does not have focus.
 343          *
 344          * <p>ButtonData enumeration values that can be the default button have
 345          * a comment stating this in their javadoc.

 346          */
 347         public final boolean isDefaultButton() {
 348             return defaultButton;
 349         }
 350     }
 351 
 352 
 353     /**
 354      * Sets the given ButtonData on the given button. If this button is
 355      * subsequently placed in a {@link ButtonBar} it will be placed in the
 356      * correct position relative to all other buttons in the bar.
 357      *
 358      * @param button The button to annotate with the given {@link ButtonData} value.
 359      * @param buttonData The ButtonData to designate the button as.
 360      */
 361     public static void setButtonData(Node button, ButtonData buttonData) {
 362         final Map<Object,Object> properties = button.getProperties();
 363         final ObjectProperty<ButtonData> property =
 364                 (ObjectProperty<ButtonData>) properties.getOrDefault(
 365                         Properties.BUTTON_DATA_PROPERTY,
 366                         new SimpleObjectProperty<>(button, "buttonData", buttonData));
 367 
 368         property.set(buttonData);
 369         properties.putIfAbsent(Properties.BUTTON_DATA_PROPERTY, property);
 370     }
 371 
 372     /**
 373      * Returns the previously set ButtonData property on the given button. If this
 374      * was never set, this method will return null.
 375      *
 376      * @param button The button to return the previously set ButtonData for.

 377      */
 378     public static ButtonData getButtonData(Node button) {
 379         final Map<Object,Object> properties = button.getProperties();
 380         if (properties.containsKey(Properties.BUTTON_DATA_PROPERTY)) {
 381             ObjectProperty<ButtonData> property = (ObjectProperty<ButtonData>) properties.get(Properties.BUTTON_DATA_PROPERTY);
 382             return property == null ? null : property.get();
 383         }
 384         return null;
 385     }
 386 
 387     /**
 388      * By default all buttons are uniformly sized in a ButtonBar, meaning that all
 389      * buttons take the width of the widest button. It is possible to opt-out of this
 390      * on a per-button basis, but calling the setButtonUniformSize method with
 391      * a boolean value of false.
 392      *
 393      * <p>If a button is excluded from uniform sizing, it is both excluded from
 394      * being resized away from its preferred size, and also excluded from the
 395      * measuring process, so its size will not influence the maximum size calculated
 396      * for all buttons in the ButtonBar.
 397      *
 398      * @param button The button to include / exclude from uniform sizing.
 399      * @param uniformSize Boolean true to force uniform sizing on the button,
 400      *        false to exclude the button from uniform sizing.
 401      */
 402     public static void setButtonUniformSize(Node button, boolean uniformSize) {
 403         // we store the false, but remove the true (as the isButtonUniformSize
 404         // method returns true by default)
 405         if (uniformSize) {
 406             button.getProperties().remove(Properties.BUTTON_SIZE_INDEPENDENCE);
 407         } else {
 408             button.getProperties().put(Properties.BUTTON_SIZE_INDEPENDENCE, uniformSize);
 409         }
 410     }
 411 
 412     /**
 413      * Returns whether the given node is part of the uniform sizing calculations
 414      * or not. By default all nodes that have not opted out (via
 415      * {@link #setButtonUniformSize(Node, boolean)}) will return true here.


 416      */
 417     public static boolean isButtonUniformSize(Node button) {
 418         return (boolean) button.getProperties().getOrDefault(Properties.BUTTON_SIZE_INDEPENDENCE, true);
 419     }
 420 
 421 
 422 
 423     /**************************************************************************
 424      *
 425      * Private fields
 426      *
 427      **************************************************************************/
 428 
 429     private ObservableList<Node> buttons = FXCollections.<Node>observableArrayList();
 430 
 431 
 432 
 433     /**************************************************************************
 434      *
 435      * Constructors


 502      *      allowing for further buttons to be added or removed.
 503      */
 504     public final ObservableList<Node> getButtons() {
 505         return buttons;
 506     }
 507 
 508 
 509 
 510     /**************************************************************************
 511      *
 512      * Properties
 513      *
 514      **************************************************************************/
 515 
 516     // --- Button order
 517     /**
 518      * The order for the typical buttons in a standard button bar. It is
 519      * one letter per {@link ButtonData} enumeration value. Default button orders
 520      * for operating systems are also available: {@link #BUTTON_ORDER_WINDOWS},
 521      * {@link #BUTTON_ORDER_MAC_OS}, and {@link #BUTTON_ORDER_LINUX}.

 522      */
 523     public final StringProperty buttonOrderProperty() {
 524         return buttonOrderProperty;
 525     }
 526     private final StringProperty buttonOrderProperty =
 527             new SimpleStringProperty(this, "buttonOrder"); //$NON-NLS-1$
 528 
 529     /**
 530      * Sets the {@link #buttonOrderProperty() button order}
 531      * @param buttonOrder The currently set button order, which by default will
 532      *      be the OS-specific button order.
 533      */
 534     public final void setButtonOrder(String buttonOrder) {
 535         buttonOrderProperty.set(buttonOrder);
 536     }
 537 
 538     /**
 539      * Returns the current {@link #buttonOrderProperty() button order}.
 540      * @return The current {@link #buttonOrderProperty() button order}.
 541      */
 542     public final String getButtonOrder() {
 543         return buttonOrderProperty.get();
 544     }
 545 
 546 
 547     // --- button min width
 548     /**
 549      * Specifies the minimum width of all buttons placed in this button bar.

 550      */
 551     public final DoubleProperty buttonMinWidthProperty() {
 552         return buttonMinWidthProperty;
 553     }
 554     private final DoubleProperty buttonMinWidthProperty =
 555             new SimpleDoubleProperty(this, "buttonMinWidthProperty"); //$NON-NLS-1$
 556 
 557     /**
 558      * Sets the minimum width of all buttons placed in this button bar.

 559      */
 560     public final void setButtonMinWidth(double value) {
 561         buttonMinWidthProperty.set(value);
 562     }
 563 
 564     /**
 565      * Returns the minimum width of all buttons placed in this button bar.

 566      */
 567     public final double getButtonMinWidth() {
 568         return buttonMinWidthProperty.get();
 569     }
 570 
 571 
 572 
 573     /**************************************************************************
 574      *
 575      * Implementation
 576      *
 577      **************************************************************************/
 578 
 579     /**
 580      * Returns the initial focus traversable state of this control, for use
 581      * by the JavaFX CSS engine to correctly set its initial value. This method
 582      * is overridden as by default UI controls have focus traversable set to true,
 583      * but that is not appropriate for this control.
 584      *
 585      * @since 9


  52  * annotations, as well as the overarching
  53  * {@link #buttonOrderProperty() button order} specified for the ButtonBar.
  54  *
  55  * <strong>Uniform button sizing</strong>
  56  * <p>By default all buttons are uniformly sized in a ButtonBar, meaning that all
  57  * buttons take the width of the widest button. It is possible to opt-out of this
  58  * on a per-button basis, but calling the {@link #setButtonUniformSize(Node, boolean)} method with
  59  * a boolean value of false.
  60  *
  61  * <p>If a button is excluded from uniform sizing, it is both excluded from
  62  * being resized away from its preferred size, and also excluded from the
  63  * measuring process, so its size will not influence the maximum size calculated
  64  * for all buttons in the ButtonBar.
  65  *
  66  * <h3>Screenshots</h3>
  67  * <p>Because a ButtonBar comes with built-in support for Windows, Mac OS
  68  * and Linux, there are three screenshots shown below, with the same buttons
  69  * laid out on each of the three operating systems.
  70  *
  71  * <p>
  72  * <strong>Windows:</strong><p><img src="doc-files/buttonBar-windows.png" alt=""></p>
  73  * <strong>Mac OS:</strong><p><img src="doc-files/buttonBar-mac.png" alt=""></p>
  74  * <strong>Linux:</strong><p><img src="doc-files/buttonBar-linux.png" alt=""></p>
  75  *
  76  * <h3>Code Samples</h3>
  77  * <p>Instantiating and using the ButtonBar is simple, simply do the following:
  78  *
  79  * <pre>
  80  * {@code
  81  * // Create the ButtonBar instance
  82  * ButtonBar buttonBar = new ButtonBar();
  83  *
  84  * // Create the buttons to go into the ButtonBar
  85  * Button yesButton = new Button("Yes");
  86  * ButtonBar.setButtonData(yesButton, ButtonData.YES);
  87  *
  88  * Button noButton = new Button("No");
  89  * ButtonBar.setButtonData(noButton, ButtonData.NO);
  90  *
  91  * // Add buttons to the ButtonBar
  92  * buttonBar.getButtons().addAll(yesButton, noButton);
  93  * }</pre>
  94  *
  95  * <p>The code sample above will position the Yes and No buttons relative to the
  96  * users operating system. This means that on Windows and Linux the Yes button
  97  * will come before the No button, whereas on Mac OS it'll be No and then Yes.
  98  *
  99  * <p>In most cases the OS-specific layout is the best choice, but in cases
 100  * where you want a custom layout, this is achieved be modifying the
 101  * {@link #buttonOrderProperty() button order property}. These are cryptic-looking
 102  * strings that are shorthand representations for the button order. The built-in
 103  * orders for Windows, Mac OS and Linux are:
 104  *
 105  * <table border="0" summary="">
 106  *   <tr>
 107  *     <td><strong>Windows:</strong></td>
 108  *     <td>L_E+U+FBXI_YNOCAH_R</td>
 109  *   </tr>
 110  *   <tr>
 111  *     <td><strong>Mac OS:</strong></td>
 112  *     <td>L_HE+U+FBIX_NCYOA_R</td>
 113  *   </tr>
 114  *   <tr>
 115  *     <td><strong>Linux:</strong></td>
 116  *     <td>L_HE+UNYACBXIO_R</td>
 117  *   </tr>
 118  * </table>
 119  *
 120  * <p>You should refer to the {@link ButtonData} enumeration for a description of
 121  * what each of these characters mean. However, if your ButtonBar only consisted
 122  * of {@link ButtonData#YES} and {@link ButtonData#NO} buttons, you always
 123  * wanted the yes buttons before the no buttons, and you wanted the buttons to
 124  * be {@link ButtonData#BIG_GAP right-aligned}, you could do the following:
 125  *
 126  * <pre>
 127  * {@code


 300          *
 301          * <p><strong>Button order code:</strong> _ (underscore)
 302          */
 303         SMALL_GAP("_", false, false); //$NON-NLS-1$
 304 
 305         private final String typeCode;
 306 
 307         private final boolean cancelButton;
 308         private final boolean defaultButton;
 309 
 310         private ButtonData(String type, boolean cancelButton, boolean defaultButton) {
 311             this.typeCode = type;
 312             this.cancelButton = cancelButton;
 313             this.defaultButton = defaultButton;
 314         }
 315 
 316         /**
 317          * Returns the single character code used to represent the ButtonData
 318          * annotation in the {@link ButtonBar#buttonOrderProperty() button order}
 319          * string.
 320          * @return the single character code used to represent the ButtonData
 321          * annotation
 322          */
 323         public String getTypeCode() {
 324             return typeCode;
 325         }
 326 
 327         /**
 328          * Indicates whether buttons created from the ButtonData enumeration
 329          * should be the 'cancel' button in the user interface. This typically
 330          * means that the button will respond to the escape key press, even if
 331          * the button does not have focus.
 332          *
 333          * <p>ButtonData enumeration values that can be the cancel button have a
 334          * comment stating this in their javadoc.
 335          * @return true if this is a 'cancel' button
 336          */
 337         public final boolean isCancelButton() {
 338             return cancelButton;
 339         }
 340 
 341         /**
 342          * Indicates whether buttons created from the ButtonData enumeration
 343          * should be the 'default' button in the user interface. This typically
 344          * means that the button will respond to enter key presses, even if the
 345          * button does not have focus.
 346          *
 347          * <p>ButtonData enumeration values that can be the default button have
 348          * a comment stating this in their javadoc.
 349          * @return true if this is a 'default' button
 350          */
 351         public final boolean isDefaultButton() {
 352             return defaultButton;
 353         }
 354     }
 355 
 356 
 357     /**
 358      * Sets the given ButtonData on the given button. If this button is
 359      * subsequently placed in a {@link ButtonBar} it will be placed in the
 360      * correct position relative to all other buttons in the bar.
 361      *
 362      * @param button The button to annotate with the given {@link ButtonData} value.
 363      * @param buttonData The ButtonData to designate the button as.
 364      */
 365     public static void setButtonData(Node button, ButtonData buttonData) {
 366         final Map<Object,Object> properties = button.getProperties();
 367         final ObjectProperty<ButtonData> property =
 368                 (ObjectProperty<ButtonData>) properties.getOrDefault(
 369                         Properties.BUTTON_DATA_PROPERTY,
 370                         new SimpleObjectProperty<>(button, "buttonData", buttonData));
 371 
 372         property.set(buttonData);
 373         properties.putIfAbsent(Properties.BUTTON_DATA_PROPERTY, property);
 374     }
 375 
 376     /**
 377      * Returns the previously set ButtonData property on the given button. If this
 378      * was never set, this method will return null.
 379      *
 380      * @param button The button to return the previously set ButtonData for.
 381      * @return the previously set ButtonData property on the given button
 382      */
 383     public static ButtonData getButtonData(Node button) {
 384         final Map<Object,Object> properties = button.getProperties();
 385         if (properties.containsKey(Properties.BUTTON_DATA_PROPERTY)) {
 386             ObjectProperty<ButtonData> property = (ObjectProperty<ButtonData>) properties.get(Properties.BUTTON_DATA_PROPERTY);
 387             return property == null ? null : property.get();
 388         }
 389         return null;
 390     }
 391 
 392     /**
 393      * By default all buttons are uniformly sized in a ButtonBar, meaning that all
 394      * buttons take the width of the widest button. It is possible to opt-out of this
 395      * on a per-button basis, but calling the setButtonUniformSize method with
 396      * a boolean value of false.
 397      *
 398      * <p>If a button is excluded from uniform sizing, it is both excluded from
 399      * being resized away from its preferred size, and also excluded from the
 400      * measuring process, so its size will not influence the maximum size calculated
 401      * for all buttons in the ButtonBar.
 402      *
 403      * @param button The button to include / exclude from uniform sizing.
 404      * @param uniformSize Boolean true to force uniform sizing on the button,
 405      *        false to exclude the button from uniform sizing.
 406      */
 407     public static void setButtonUniformSize(Node button, boolean uniformSize) {
 408         // we store the false, but remove the true (as the isButtonUniformSize
 409         // method returns true by default)
 410         if (uniformSize) {
 411             button.getProperties().remove(Properties.BUTTON_SIZE_INDEPENDENCE);
 412         } else {
 413             button.getProperties().put(Properties.BUTTON_SIZE_INDEPENDENCE, uniformSize);
 414         }
 415     }
 416 
 417     /**
 418      * Returns whether the given node is part of the uniform sizing calculations
 419      * or not. By default all nodes that have not opted out (via
 420      * {@link #setButtonUniformSize(Node, boolean)}) will return true here.
 421      * @param button the button
 422      * @return true if button is part of the uniform sizing calculations
 423      */
 424     public static boolean isButtonUniformSize(Node button) {
 425         return (boolean) button.getProperties().getOrDefault(Properties.BUTTON_SIZE_INDEPENDENCE, true);
 426     }
 427 
 428 
 429 
 430     /**************************************************************************
 431      *
 432      * Private fields
 433      *
 434      **************************************************************************/
 435 
 436     private ObservableList<Node> buttons = FXCollections.<Node>observableArrayList();
 437 
 438 
 439 
 440     /**************************************************************************
 441      *
 442      * Constructors


 509      *      allowing for further buttons to be added or removed.
 510      */
 511     public final ObservableList<Node> getButtons() {
 512         return buttons;
 513     }
 514 
 515 
 516 
 517     /**************************************************************************
 518      *
 519      * Properties
 520      *
 521      **************************************************************************/
 522 
 523     // --- Button order
 524     /**
 525      * The order for the typical buttons in a standard button bar. It is
 526      * one letter per {@link ButtonData} enumeration value. Default button orders
 527      * for operating systems are also available: {@link #BUTTON_ORDER_WINDOWS},
 528      * {@link #BUTTON_ORDER_MAC_OS}, and {@link #BUTTON_ORDER_LINUX}.
 529      * @return the button order property
 530      */
 531     public final StringProperty buttonOrderProperty() {
 532         return buttonOrderProperty;
 533     }
 534     private final StringProperty buttonOrderProperty =
 535             new SimpleStringProperty(this, "buttonOrder"); //$NON-NLS-1$
 536 
 537     /**
 538      * Sets the {@link #buttonOrderProperty() button order}
 539      * @param buttonOrder The currently set button order, which by default will
 540      *      be the OS-specific button order.
 541      */
 542     public final void setButtonOrder(String buttonOrder) {
 543         buttonOrderProperty.set(buttonOrder);
 544     }
 545 
 546     /**
 547      * Returns the current {@link #buttonOrderProperty() button order}.
 548      * @return The current {@link #buttonOrderProperty() button order}.
 549      */
 550     public final String getButtonOrder() {
 551         return buttonOrderProperty.get();
 552     }
 553 
 554 
 555     // --- button min width
 556     /**
 557      * Specifies the minimum width of all buttons placed in this button bar.
 558      * @return the minimum width property
 559      */
 560     public final DoubleProperty buttonMinWidthProperty() {
 561         return buttonMinWidthProperty;
 562     }
 563     private final DoubleProperty buttonMinWidthProperty =
 564             new SimpleDoubleProperty(this, "buttonMinWidthProperty"); //$NON-NLS-1$
 565 
 566     /**
 567      * Sets the minimum width of all buttons placed in this button bar.
 568      * @param value the minimum width value
 569      */
 570     public final void setButtonMinWidth(double value) {
 571         buttonMinWidthProperty.set(value);
 572     }
 573 
 574     /**
 575      * Returns the minimum width of all buttons placed in this button bar.
 576      * @return the minimum width value
 577      */
 578     public final double getButtonMinWidth() {
 579         return buttonMinWidthProperty.get();
 580     }
 581 
 582 
 583 
 584     /**************************************************************************
 585      *
 586      * Implementation
 587      *
 588      **************************************************************************/
 589 
 590     /**
 591      * Returns the initial focus traversable state of this control, for use
 592      * by the JavaFX CSS engine to correctly set its initial value. This method
 593      * is overridden as by default UI controls have focus traversable set to true,
 594      * but that is not appropriate for this control.
 595      *
 596      * @since 9
< prev index next >