JavaFX和Canvas的快速更新

时间:2016-04-12 13:10:24

标签: java javafx javafx-2 javafx-8 java-canvas

我正在尝试在JavaFX下创建一个自定义Canvas小部件,它从许多不相关的工作线程中收集信息。 "更新"事件可能以各种速率出现,有时太快,有时甚至根本没有,这意味着需要正确地解决过快的更新问题。和空闲时间"需求。更新次数过多,因此每次执行更新时发出 Runnable 都不是一个好方法。

仅仅是为了测试,我的蛮力方法是创建一个 AnimationTimer 来更新Canvas对象的视觉效果。这个解决方案工作正常,但有时候Canvas不需要更新,这使得整个过程效率低下。

我的问题的最接近的答案似乎是this post和一个GUIUpdater助手类,但Canvas似乎没有直接的更新属性。我正试图找到一种方法来插入"插入"带有绑定参数的所需更新功能,但运气好。我甚至试图了解Canvas是否有"更新"事件,但我没有找到它。根据我的理解,我发现的所有其他答案都不符合要求。

提前致谢

修改

以下是我用来确保只有在数据发生变化时才会绘制画布的代码:

new AnimationTimer() {
    @Override
    public void handle(long now) {
        if (needsUpdate.getAndSet(false)) {
            myCustomCanvasRepaint();
        }
    }
}.start();

由以下内容触发:

AtomicBoolean needsUpdate = new AtomicBoolean(true);
...
public void needsUpdate() {
    needsUpdate.set(true);
}

1 个答案:

答案 0 :(得分:0)

这实际上是Throttling javafx gui updates的副本,但您可以

private final AtomicBoolean updated = new AtomicBoolean();

// ...

Thread someBackgroundThread = new Thread(() -> {
    while (true) {
        waitArbitraryTimeForData() ;
        if (updated.getAndSet(false)) {
            updateCanvas();
        }
    }
});

private void updateCanvas() {
    Platform.runLater(() -> {
        updated.set(true);
        // repaint canvas...
    }
}

根据您的更新所依赖的数据,您可能需要在Platform.runLater()的正文周围进行一些额外的数据锁定。或者(可能更好),用不可变类表示累积更新,并用对该类的原子引用替换AtomicBoolean