如何将将固定尺寸的Canvas包裹在BorderPane中的ScrollPane居中?

时间:2019-06-18 21:09:47

标签: java javafx javafx-8 scrollpane

在JavaFX应用程序中,我需要将由Canvas然后是StackPane包裹的固定大小的ScrollPaneBorderPane中居中。问题是当我包含ScrollPane时,组件树不再位于BorderPane中心区域的中间。我尝试的一种解决方案是固定ScrollPane的最大大小。这可以起作用(组件变为居中),但是会产生一个不同的问题:当视口区域在任何一个维度(例如宽度)中都不足够时,两个滚动条仍然会出现。由于ScrollPane的大小是有界的,因此滚动条在一个维度上占据的额外空间将导致视口在另一个维度上缩小,居中所需的max size属性将阻止为其留出更多空间。

这是该问题的有效演示:

public final class Minimal extends Application {

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

    @Override
    public void start(Stage stage) {
        Canvas canvas = new Canvas(200,200) {
            @Override
            public boolean isResizable() {
                return false;
            }
        };

        StackPane pane = new StackPane(canvas);
        pane.setStyle("-fx-border-insets: 4; -fx-border-style: solid;");
        ScrollPane scroll = new ScrollPane(pane);
        // scroll.setMaxSize(212, 212); // Imperfect Solution
        BorderPane root = new BorderPane();
        root.setCenter(scroll);
        stage.setScene(new Scene(root));
        stage.show();
    }   
}

注释掉该行,调整大小后,该框架显示为:

enter image description here

如果我确定最大尺寸:那么两个滚动条会同时显示(请注意,垂直滚动条是不必要的:

enter image description here

我找到的最接近的是this question,它实际上没有答案。不幸的是,this solution在Swing中似乎运行良好,但似乎没有任何作用,因为我已经在使用包装器(StackPane),并且没有帮助。我希望有一个解决方案完全依赖于布局,而不必重新编写侦听器来调整大小事件或绑定到size属性等。

1 个答案:

答案 0 :(得分:2)

让StackPane填充整个ScrollPane。然后,StackPane将center the canvas for you

  

堆栈窗格将尝试调整每个子项的大小以填充其内容区域。如果无法调整子级的大小以填充堆栈窗格(由于无法调整大小或限制其最大尺寸),则将使用alignment属性将其在区域内对齐,该属性默认为Pos.CENTER。

因此,您所需要做的就是设置ScrollPane的“ fitTo ...”属性,以便StackPane可以填充它:

scroll.setFitToWidth(true);
scroll.setFitToHeight(true);