我的 JavaFX GUI 中有两个 TreeView,我动态填充它们。它们可以有很多数据,所以大多数时候,它们是可滚动的。之后,我在两个 TreeView 的 TreeCell 之间创建连接(或者更确切地说是边)。我从源单元格到目标单元格绘制一条线并创建绑定。我的代码如下:
line.startYProperty().bind(Bindings.createDoubleBinding(() -> {
Bounds b = sourceCell.getBoundsInParent();
return b.getMaxY() + b.getHeight() / 2;
}, sourceCell.boundsInParentProperty()));
line.endYProperty().bind(Bindings.createDoubleBinding(() -> {
Bounds b = targetCell.getBoundsInParent();
return b.getMaxY() + b.getHeight() / 2;
}, targetCell.boundsInParentProperty()));
现在,这对我有用,直到我开始滚动其中一个 TreeView。当连接的单元格滚动出树视图的可见区域时,行位置会重置并将其自身连接到不同的单元格。
我认为这是因为绑定到 TreeCell 并且它们可以根据可见数据动态更改它们的值,但是使它起作用的替代方法是什么?
我如何将 Line 绑定到原始 TreeCell 而不会在滚动出并返回视图时发生变化?
我的示例代码:
@Override
public void start(Stage primaryStage) {
try {
AnchorPane root = new AnchorPane();
Scene scene = new Scene(root, 700, 400);
primaryStage.setScene(scene);
primaryStage.show();
TreeItem sourceRoot = new TreeItem("source");
sourceRoot.setExpanded(true);
TreeItem targetRoot = new TreeItem("target");
targetRoot.setExpanded(true);
TreeView<String> source = new TreeView<String>(sourceRoot);
TreeView<String> target = new TreeView<String>(targetRoot);
target.setLayoutX(400.0);
root.getChildren().add(source);
root.getChildren().add(target)
// fill and randomly select two visible cells
for (int i = 0; i < 100; i++) {
sourceRoot.getChildren().add(new TreeItem("ItemS " + i));
targetRoot.getChildren().add(new TreeItem("ItemT " + i));
}
TreeCell<String> sourceCell = (TreeCell<String>) source.lookupAll(".tree-cell").toArray()[2];
TreeCell<String> targetCell = (TreeCell<String>) target.lookupAll(".tree-cell").toArray()[4];
Line line = new Line();
line.setStartX(source.getWidth());
line.startYProperty().bind(Bindings.createDoubleBinding(() -> {
Bounds b = sourceCell.getBoundsInParent();
return b.getMinY() + b.getHeight() / 2;
}, sourceCell.boundsInParentProperty()));
line.setEndX(target.getLayoutX());
line.endYProperty().bind(Bindings.createDoubleBinding(() -> {
Bounds b = targetCell.getBoundsInParent();
return b.getMinY() + b.getHeight() / 2;
}, targetCell.boundsInParentProperty()));
root.getChildren().add(line);
} catch (Exception e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
launch(args);
}