如何在JavaFX中创建可滚动的组件面板?

7
所以,基本上,我正在尝试实现一个可滚动的组件集,具有间距等功能,并且能够添加更多组件。这些组件的列表是自定义锚点面板组件。
这是一个我已经成功实现的示例: enter image description here 问题在于,它使用了一个网格面板(gridpane)放在滚动窗格(scrollpane)内部,但由于某种原因,网格面板根本不填充滚动窗格的宽度。因此,如果我调整大小,所有内容都会保持原样,而不是在网格面板列中拉伸。另外,如果我坚持使用网格面板(而不是瓷砖面板,后者似乎表现更好,除非组件彼此紧挨着,尽管方向为垂直且prefcolumns为1),那么我该如何添加更多行?这个想法是以一种漂亮、令人愉悦的方式列出github存储库。
感谢您的任何见解。 还有:那些存储库不是我的 - 我没有存储库,一个网站上的人制作了它(它做得不好,所以不要把我和他比较lol)。

2
如何通过使用MediaListCell来丰富您的列表UI?请参考此链接:http://www.guigarage.com/2014/09/enrich-list-ui-using-medialistcell/。如果需要,我们也可以提供一些代码。 - Roland
@Roland - 目前我正在使用场景构建器对所有内容进行原型设计,但我认为我可能不久就要开始使用代码制作自定义组件以获得所需的功能。那个链接很有趣,我会在程序的另一个部分中使用它。现在,我只是在寻找一个纯粹基于FXML的解决方案。 - user3530525
2
看起来你可以在ScrollPane中使用VBox简单地完成这个。对于VBox,设置fillWidth="true",对于ScrollPane,设置fitToWidth="true"。如果你想要一个GridPane,使用columnConstraints来控制宽度。但是,如果你想要更完整的答案,请创建一个简单的示例并发布一些代码。 - James_D
@James_D,你的想法非常好。有没有办法让VBox中的组件(AnchorPanes)自动拉伸以适应VBox的宽度? - user3530525
1
将滚动窗格上的 fitToWidth 设置为 true 应该就足够了。 - James_D
1个回答

9
这看起来像是应该使用一个VBox来容纳您的AnchorPane并将它们放置在ScrollPane中。在ScrollPane上设置fitToWidthtrue,这样就应该强制锚点面板占据滚动面板视口的整个宽度(且不超过),假设您没有从其默认值更改AnchorPanemaxWidth属性。

模拟示例(如果您愿意,可以轻松地在FXML中完成):

import java.util.Random;

import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.Label;
import javafx.scene.control.ScrollPane;
import javafx.scene.layout.AnchorPane;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;

public class ScrollingVBox extends Application {


    @Override
    public void start(Stage primaryStage) {

        final Random rng = new Random();
        VBox content = new VBox(5);
        ScrollPane scroller = new ScrollPane(content);
        scroller.setFitToWidth(true);

        Button addButton = new Button("Add");
        addButton.setOnAction(e -> {
            AnchorPane anchorPane = new AnchorPane();
            String style = String.format("-fx-background: rgb(%d, %d, %d);"+
                    "-fx-background-color: -fx-background;",
                    rng.nextInt(256),
                    rng.nextInt(256),
                    rng.nextInt(256));
            anchorPane.setStyle(style);
            Label label = new Label("Pane "+(content.getChildren().size()+1));
            AnchorPane.setLeftAnchor(label, 5.0);
            AnchorPane.setTopAnchor(label, 5.0);
            Button button = new Button("Remove");
            button.setOnAction(evt -> content.getChildren().remove(anchorPane));
            AnchorPane.setRightAnchor(button, 5.0);
            AnchorPane.setTopAnchor(button, 5.0);
            AnchorPane.setBottomAnchor(button, 5.0);
            anchorPane.getChildren().addAll(label, button);
            content.getChildren().add(anchorPane);
        });

        Scene scene = new Scene(new BorderPane(scroller, null, null, addButton, null), 400, 400);
        primaryStage.setScene(scene);
        primaryStage.show();
    }

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

另一个解决方案可能是使用 ListView。(如果您有许多要显示的项目,这将是更好的选择。)创建一个表示每个 AnchorPane 中显示的项目的类,以及一个自定义列表单元格来显示它们。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接