JavaFX 2 buttons size fill width and are each same width?

后端 未结 2 1255
伪装坚强ぢ
伪装坚强ぢ 2021-01-04 12:32

Working in Java FX 2.2. The Scene has a horizontal width that is fixed but is unknown at compile time. I want to place 2 or more buttons in a horizontal row that completel

相关标签:
2条回答
  • 2021-01-04 13:05

    A bit cleaner solution with property binding:

        HBox buttonLayout = new HBox();
        buttonLayout.getChildren().add(button1);
        buttonLayout.getChildren().add(button2);
    
        int btnCount = buttonLayout.getChildren().size();
        button1.prefWidthProperty().bind(buttonLayout.widthProperty().divide(btnCount));
        button2.prefWidthProperty().bind(buttonLayout.widthProperty().divide(btnCount));
    
    0 讨论(0)
  • 2021-01-04 13:11

    This code from the HBox javadoc will almost do what you want, except that "buttons themselves are different sizes based on the text contained in the button - wider text causes wider buttons".

    HBox hbox = new HBox();
    Button button1 = new Button("Add");
    Button button2 = new Button("Remove");
    HBox.setHgrow(button1, Priority.ALWAYS);
    HBox.setHgrow(button2, Priority.ALWAYS);
    button1.setMaxWidth(Double.MAX_VALUE);
    button2.setMaxWidth(Double.MAX_VALUE);
    hbox.getChildren().addAll(button1, button2);
    

    By creating a custom layout pane based on HBox and overriding it's layout method, you can get exactly the behaviour you describe.

    import javafx.application.Application;
    import javafx.collections.ObservableList;
    import javafx.event.*;
    import javafx.scene.*;
    import javafx.scene.control.Button;
    import javafx.scene.layout.*;
    import javafx.stage.Stage;
    
    // displays equal width buttons which fill a layout region's width.
    // http://stackoverflow.com/questions/12830402/javafx-2-buttons-size-fill-width-and-are-each-same-width
    public class HorizontallyTiledButtons extends Application {
      public static void main(String[] args) { launch(args); }
      @Override public void start(Stage stage) {
        final Button addButton    = new Button("Add");
        final Button removeButton = new Button("Remove");
        final Button extraButton  = new Button("The wizard of Frobozz is watching");
    
        final ButtonBar buttonBar = new ButtonBar(5, addButton, removeButton);
    
        addButton.setOnAction(new EventHandler<ActionEvent>() {
          @Override public void handle(ActionEvent event) {
            buttonBar.addButton(extraButton);
          }
        });
    
        removeButton.setOnAction(new EventHandler<ActionEvent>() {
          @Override public void handle(ActionEvent event) {
            buttonBar.removeButton(extraButton);
          }
        });
    
        VBox layout = new VBox(10);
        layout.getChildren().addAll(buttonBar);
        layout.setStyle("-fx-background-color: cornsilk; -fx-padding: 10;");
    
        stage.setScene(new Scene(layout));
        stage.setWidth(800);
        stage.show();
      }
    
      class ButtonBar extends HBox {
        ButtonBar(double spacing, Button... buttons) {
          super(spacing);
          getChildren().addAll(buttons);
          for (Button b: buttons) {
            HBox.setHgrow(b, Priority.ALWAYS);
            b.setMaxWidth(Double.MAX_VALUE);
          }
        }
    
        public void addButton(Button button) {
          HBox.setHgrow(button, Priority.ALWAYS);
          button.setMaxWidth(Double.MAX_VALUE);
          ObservableList<Node> buttons = getChildren();
          if (!buttons.contains(button)) {
            buttons.add(button);
          }
        }
    
        public void removeButton(Button button) {
          getChildren().remove(button);
        }
    
        @Override protected void layoutChildren() {
          double minPrefWidth = calculatePrefChildWidth();
          for (Node n: getChildren()) {
            if (n instanceof Button) {
              ((Button) n).setMinWidth(minPrefWidth);
            }
          }
          super.layoutChildren();
        }
    
        private double calculatePrefChildWidth() {
          double minPrefWidth = 0;
          for (Node n: getChildren()) {
            minPrefWidth = Math.max(minPrefWidth, n.prefWidth(-1));
          }
          return minPrefWidth;
        }
      }
    }
    

    Sample program output: twobuttons threebuttons

    0 讨论(0)
提交回复
热议问题