If the JavaFX screen size is below a certain level, a scroll bar will be displayed, and if it is above a certain level, the node inside will be maximized as much as possible.

This goal

I used ListView when creating a GUI application using JavaFx, but I received the following requests.

  1. I want to display the ListView as large as possible -→ The size changes automatically according to the size of the window
  2. If the window size falls below a certain level, I want to stop resizing the ListView and scroll the window.

I had a hard time meeting such a request, so I made a note of the result.

The final move I aimed for was like this. The blue frame is ListView, and when the screen size is smaller than the position where the button is located, a scroll bar appears to indicate that there is a part next to it. 目指す姿fxml.gif


java1.8 JavaFX Scene Builder 2.0

First from the result

The final component configuration was realized as follows.

スクリーンショット 2020-07-09 13.20.23.png

Setting points of each part

ScrollPane -- Properties --``` Hbar / Vbar Policy``` is set to ```AS_NEEDED```. --``` Layout``` --``Fit To Width / Height``` is set to true (: heavy_check_mark :).

AnchorPane -- Layout --` Min Width / Height is set to the window size where you want to start displaying the scroll bar.

ListView -- Layout --`` Anchor Pane Constrains``` Set all four sides as fixed values.

The road to realization Step by step

ListView settings linked to Window size

By the following combination, "the size of ListView changes according to the window size" can be realized.

AnchorPane and ListView

We use Anchor Pane. anchorpaneWhat is

AnchorPane allows the edges of child nodes to be anchored to an offset from the anchor pane's edges.

Regarding the node included in it, it is possible to fix the distance from the end of the parent Anchor Pane.

When I add Control to the child element of Anchor Pane in SceneBulider, Anchor Pane Constraints is displayed in Layout. スクリーンショット 2020-07-09 12.58.15.png

The end of the individual element and the end of the Anchor Pane are fixed by the value (distance) entered in these four text boxes. This is the fixed value only below. 下のみ固定.gif

If only one side is fixed, the size of the control is not changed and the display position is changed.

This is the one that fixed the top and bottom. 上下固定.gif

When the top and bottom are fixed, the distance from the top and bottom is prioritized over the size of the control, and it can be seen that the size of the control expands and contracts.

This time, in order to display the size of ListView as large as possible, it was found that the ListView included in AnchorPane should have fixed values for all four sides of Anchor Pane Constraints.

Anchor Pane in Scroll Pane

ScrollPane has FitTo [Width | Height] Property. In SceneBuilder, this property layoutoffit to widthWhenfit to heightSet with.

If you check the meaning of this Fit To Width / Height in the document

public final BooleanProperty fitToWidthProperty

If true and if the contained node is a Resizable, then the node will be kept resized to match the width of the ScrollPane's viewport. If the contained node is not a Resizable, this value is ignored.

(Appropriate translation) When> true, if the node contained in it is Risizable, the size of the node changes according to the width of the viewport of the ScrollPane. This value is ignored unless the contained node is Resizable.

So, by putting AnchorPane in ScrollPane and setting `` Fit To Width / Height``` to `true```, the size of ScrollPane (Window size in this case) is changed. The size of Anchor Pane now changes in conjunction with. (AnchorPane, or rather, all JavaFX controls are Resizeable)

Measures when the size of the window is less than a certain level

Next is "Display a scroll bar when the size of the window becomes smaller than a certain width".

ScrollPaneFitTo[Width|Height]PropertyTotrueとした場合、内部のnodeの大きさはScrollPane大きさに連動して変化するが、内部のnodeのMin [Width|Height]Max [Width|Height]To超えては大きさは変化しない様子。

So, I set the size of `Min Width` of Anchor Pane in ScrollPane so that `` `Button``` is not hidden, and it was done.

The resulting fxml

Aiming figure.fxml

<?xml version="1.0" encoding="UTF-8"?>

<?import java.lang.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>

<ScrollPane fitToHeight="true" fitToWidth="true" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" xmlns:fx="http://javafx.com/fxml/1" xmlns="http://javafx.com/javafx/8">
    <AnchorPane minHeight="0.0" minWidth="0.0" prefHeight="343.0" prefWidth="486.0">
            <TextField layoutX="14.0" layoutY="7.0" prefHeight="27.0" prefWidth="247.0" />
            <ListView layoutX="-4.0" layoutY="41.0" prefHeight="357.0" prefWidth="598.0" AnchorPane.bottomAnchor="0.0" AnchorPane.leftAnchor="0.0" AnchorPane.rightAnchor="0.0" AnchorPane.topAnchor="40.0" />
            <Button layoutX="272.0" layoutY="7.0" mnemonicParsing="false" text="Button" />

Recommended Posts

If the JavaFX screen size is below a certain level, a scroll bar will be displayed, and if it is above a certain level, the node inside will be maximized as much as possible.