2

Based on this example (Option #1) I am creating a fixed column by using 2 TableViews in a SplitPane. The TableView that shows the other columns (not the fixed one) may get so wide that a ScrollBar is displayed, for which I have to compensate with -fx-padding: 0 0 13px 0; in order to keep the TableRows of both TableViews aligned.

So I have to figure out now whether a ScrollBar is being displayed or not or find a completely different way to ensure the TableRow alignment. The obvious way unfortunately doesn't seem to be working. (The ScrollBar is not null, I just didn't post the code to ensure that)

ScrollBar horizontalScrollBar = (ScrollBar) lookup(".scroll-bar:horizontal");
horizontalScrollBar.visibleProperty().addListener((observable, oldValue, newValue) -> {
    System.out.println(newValueobservableScrollBar);
});

For some reason the Listener is not fired when the ScrollBar appears or disappears.

Samarek
  • 444
  • 1
  • 8
  • 22
  • I guess the `ScrollBar` is completely removed from the scene instead of just made invisible. (Which would be the more efficient approach for layout performance anyways... You could listen to this by adding a listener to the `scene` property and checking for `null`, but the exact way the `ScrollBar` is displayed/hidden is an implementation detail and the code could break any time the java runtime is updated...). – fabian Jun 28 '18 at 09:23
  • So you mean basically just replacing the ```visibleProperty()``` with ```sceneProperty()```? – Samarek Jun 28 '18 at 09:32

1 Answers1

1

So in order to figure out whether a particular scrollbar is visibile I first had to find it, so I looked up all the scrollbars on that particular table.

Set<Node> scrollBars = itemsTableView.lookupAll(".scroll-bar");

Then filter the set in order to retrieve the specific scrollbar I was looking for (horizontal in my case)

Optional<Node> horizontalScrollBar = scrollBars.stream()
          .filter(node ->
            ((ScrollBar) node).getOrientation().equals(Orientation.HORIZONTAL))
          .findAny();

And then attach the listener to the visibility-property of the scrollbar

horizontalScrollBar.ifPresent(node ->
          node.visibleProperty().addListener((observable, oldValue, newValue) -> {
                    if(newValue)
                    {
                        columnTableView.setStyle("-fx-padding: 0 0 13px 0;");
                    } else
                    {
                        columnTableView.setStyle("-fx-padding: 0 0 0 0;");
                    }
              })
        );

Almost looks kinda simply right? Well, it is, as soon as you have figured out that

lookup(".scroll-bar:horizontal");

does NOT return the horizontal scrollbar but the first (vertical) one. And unless you realize that, your Application will behave kinda mysteriously.

Samarek
  • 444
  • 1
  • 8
  • 22