具有固定视图y轴的Java FX滚动窗格折线图 [英] Scrollpane line chart with fixed view y axis JavaFX

查看:182
本文介绍了具有固定视图y轴的Java FX滚动窗格折线图的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试制作一个可滚动的图表,其中无论滚动条中的光标位置如何,Y轴都停留在视图中(默认情况下,由于Y轴信息位于视图的末尾,因此您只会看到它滚动到足以看到结尾的地方

I'm trying to make a scrollable chart where the Y-axis stays in view regardless of the cursor position in the scrollbar (by default since the Y-axis informations is at the end of the view, you would only see it after you scroll enough to see the end)

以下是我要完成的示例:

Here is an example what Im trying to accomplish:

请注意,即使滚动条位于中间位置,Y轴文本(价格)仍会保留在视图中

Notice that even though the scrollbar position is midway-through, the Y-axis text(price) still remains in view

我环顾了网上,只能找到一个类似示例的一个示例,但是它似乎无法与scrollPane内的折线图一起使用.

I looked around the web and was only able to find a single example of something similar but it does not appear to work with a line chart inside the scrollPane.

在以下位置滚动锚定节点时始终可见Java FX 2.0?

以上内容适用于Circle对象,但会更改为折线图 在异常:无法设置绑定值"中,因为在滚动窗格内使用折线图时,它似乎会自动调用集合布局.

The above works with a Circle object but changing to a Line Chart will result in "Exception:A bound value cannot be set" as it seems to automatically call set layout when using Line chart inside a scrollpane

public class FancyScrollPane extends Application {
private LineChart<String, Number> qChart;
@Override
public void start(Stage primaryStage) {
    ScrollPane scrollPane = new ScrollPane();
    Pane content = new Pane();
    final CategoryAxis xAxis = new CategoryAxis();
    final NumberAxis yAxis = new NumberAxis(12, 20, 1);
    yAxis.setSide(Side.RIGHT);
    qChart=new LineChart<String,Number>(xAxis, yAxis);
    qChart.setPrefSize(3000, 250);
    content.getChildren().add(qChart);
    scrollPane.setContent(content);


   Circle immovableObject = new Circle(30, Color.RED);
    content.getChildren().add(immovableObject);

    primaryStage.setScene(new Scene(scrollPane, 300, 300));
    primaryStage.show();

    yAxis.layoutXProperty().bind(
            scrollPane.hvalueProperty()
                .multiply(
                    content.widthProperty()
                        .subtract(
                            new ScrollPaneViewPortWidthBinding(scrollPane))));
}

// we need this class because Bounds object doesn't support binding 
private static class ScrollPaneViewPortWidthBinding extends DoubleBinding {

    private final ScrollPane root;

    public ScrollPaneViewPortWidthBinding(ScrollPane root) {
        this.root = root;
        super.bind(root.viewportBoundsProperty());
    }

    @Override
    protected double computeValue() {
        return root.getViewportBounds().getWidth();
    }
}

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

有什么想法可以解决上述问题,或者有更好的方法来解决此问题?

Any ideas to get around the above issue or a better way to accomplish this ?

谢谢

推荐答案

这是一个小小的修改,它使用setTranslateX方法而不是layoutXProperty使用滚动条移动yAxis和圆.

Here is a little modification that moves the yAxis and the circle with the scroll bar using the setTranslateX method rather than the layoutXProperty.

import javafx.application.Application;
import javafx.beans.binding.DoubleBinding;
import javafx.scene.Scene;
import javafx.scene.control.ScrollPane;
import javafx.scene.layout.Pane;
import javafx.scene.paint.Color;
import javafx.scene.shape.Circle;
import javafx.scene.shape.Rectangle;
import javafx.stage.Stage;

public class FancyScrollPane extends Application {

    @Override
    public void start(Stage primaryStage) {
        ScrollPane scrollPane = new ScrollPane();
        Pane content = new Pane();
        scrollPane.setContent(content);

        // adding background
        content.getChildren().add(new Rectangle(500, 500, Color.GREEN));

        Circle immovableObject = new Circle(30, Color.RED);
        content.getChildren().add(immovableObject);

        primaryStage.setScene(new Scene(scrollPane, 300, 300));
        primaryStage.show();

        immovableObject.layoutXProperty().bind(
                scrollPane.hvalueProperty()
                        .multiply(
                                content.widthProperty()
                                        .subtract(
                                                new ScrollPaneViewPortWidthBinding(scrollPane))));
    }

    // we need this class because Bounds object doesn't support binding
    private static class ScrollPaneViewPortHeightBinding extends DoubleBinding {

        private final ScrollPane root;

        public ScrollPaneViewPortHeightBinding(ScrollPane root) {
            this.root = root;
            super.bind(root.viewportBoundsProperty());
        }

        @Override
        protected double computeValue() {
            return root.getViewportBounds().getHeight();
        }
    }
    // we need this class because Bounds object doesn't support binding
    private static class ScrollPaneViewPortWidthBinding extends DoubleBinding {

        private final ScrollPane root;

        public ScrollPaneViewPortWidthBinding(ScrollPane root) {
            this.root = root;
            super.bind(root.viewportBoundsProperty());
        }

        @Override
        protected double computeValue() {
            return root.getViewportBounds().getWidth();
        }
    }
    public static void main(String[] args) { launch(); }
}

这篇关于具有固定视图y轴的Java FX滚动窗格折线图的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆