3
votes

would really appreciate some help with my problem.

I'm using JavaFX and the NetBeans IDE. I am making a very simple launch window for a desktop client. The window currently looks like this image.

Current Look:

current look

Wanted Look (editted with paint):

wanted look

In other words, I want the buttons to be:

  1. centered underneath the 'Welcome' text
  2. maintain their current width

My current setup is:

I have a GridPane acting as the root. Not sure why JavaFX chose to use (col,row), but that's how I'll represent my setup in the following:

  • @GridPane(0,0) -> 'Welcome' Text
  • @GridPane(0,1) -> VBox (this VBox contains the 2 buttons shown in above image)

The relevant code (or what I think is relevant, please correct me if I am wrong) is below:

//adds GridPane to Scene
GridPane grid = new GridPane();
RowConstraints row1 = new RowConstraints();
row1.setPercentHeight(25);
grid.getRowConstraints().add(row1);
grid.setAlignment(Pos.CENTER);
Scene scene = new Scene(grid, 400, 300,Color.WHITESMOKE);

//Create welcome message and add it to grid, and align it to the center
Text sceneTitle = new Text("Welcome");
grid.add(sceneTitle,0,0);
GridPane.setHalignment(sceneTitle,HPos.CENTER);

//Create buttons and fix their widths
Button newBtn = new Button("Create New Project");
Button loadBtn = new Button("Load Existing Project");
newBtn.setMaxWidth(150);
loadBtn.setMaxWidth(150);

//Create a VBox, add children to it, and then add it to the grid
VBox vBtns = new VBox();
vBtns.setSpacing(5);
vBtns.getChildren().addAll(newBtn,loadBtn);
grid.add(vBtns,0,1);

I've tried a lot of different things.. to mention some of the more 'logical' ones:

//1. Center the VBox within its current GridPane cell
GridPane.setHalignment(vBtns,HPos.CENTER);

//2. Center the buttons within the VBox 
newBtn.setAlignment(Pos.CENTER);
loadBtn.setAlignment(Pos.CENTER);

I've never been good at GUI programming. It's very discouraging when something that should be so simple takes so long to figure out. Are there any developers out there who can help me find a solution?

1
don't try to fight it in the GridPane. Instead, wrap your stuff in yet another VBox, make that 100% width, and make it's contents centered. Then your inner contents will be in the center of that VBox. JavaFX/FXML is all about nesting elements in other elements to get the style you desire. (also, you should really check out FXML instead of hand coding this gui, JavaFX really benefits from FXML, and you can then use SceneBuilder to Drag-n-Drop your GUI elements and get them all lined up, etc..). - SnakeDoc
Or, just put all three things in a single VBox. Or a single GridPane. But there's no obvious need for two layout panes here at all. - James_D
@SnakeDoc Hi! Yeah I have the Scene Builder plugin installed.. I wasn't happy with how nested elements weren't centering the way I wanted them to so I went back to code. - Henry Lin
@HenryLin Using FXML instead of hand-coding all of your UI will make things a bit more "manageable", although there is obviously a learning curve. SceneBuilder can do everything you can do with code, so if it wasn't working the way you wanted, it's probably because you didn't checkbox the right option or something. It's definitely worth learning, and will save you considerable time down the road. - SnakeDoc
@James_D I tried putting them all into one VBox earlier, but I switched back to a GridPane because I want to add a small icon to be displayed to the left of 'Welcome' text. Unfortunately I had to take it out because I couldn't get the text to center properly with the ImageView included. - Henry Lin

1 Answers

1
votes

To fix it with your current setup, you just need:

vBtns.setAlignment(Pos.CENTER);

However, this just seems overly complex. Why not just do

import javafx.application.Application;
import javafx.geometry.HPos;
import javafx.geometry.Pos;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.layout.ColumnConstraints;
import javafx.scene.layout.GridPane;
import javafx.scene.layout.RowConstraints;
import javafx.scene.paint.Color;
import javafx.scene.text.Text;
import javafx.stage.Stage;

public class LayoutTest extends Application {

    @Override
    public void start(Stage primaryStage) {
        GridPane grid = new GridPane();
        RowConstraints row1 = new RowConstraints();
        row1.setPercentHeight(25);
        grid.getRowConstraints().add(row1);

        ColumnConstraints colConstraints = new ColumnConstraints();
        colConstraints.setHalignment(HPos.CENTER);
        grid.getColumnConstraints().add(colConstraints);

        grid.setAlignment(Pos.CENTER);
        Scene scene = new Scene(grid, 400, 300,Color.WHITESMOKE);

        //Create welcome message and add it to grid, and align it to the center
        Text sceneTitle = new Text("Welcome");
        sceneTitle.setStyle("-fx-font-size:48;");
        grid.add(sceneTitle,0,0);

        //Create buttons and fix their widths
        Button newBtn = new Button("Create New Project");
        Button loadBtn = new Button("Load Existing Project");
        newBtn.setMaxWidth(150);
        loadBtn.setMaxWidth(150);

        grid.add(newBtn, 0, 1);

        GridPane.setMargin(loadBtn, new Insets(5, 0, 5, 0));
        grid.add(loadBtn, 0, 2);

        primaryStage.setScene(scene);
        primaryStage.show();
    }

    public static void main(String[] args) {
        launch(args);
    }
}