使用ScheduledExecutorService查看不会更新

时间:2019-04-27 09:37:05

标签: java javafx java-8

我无法让ScheduledExecutorService正常工作。

这是我正在调用的方法, 可以工作 ,如果我不计划它就调用它。

但是,如果我通过ScheduledExecutorService调用它,但我的屏幕不会更新,它也只能运行一次,所以我猜有一个异常被抛出,但是服务器或客户端上都没有异常。

private void getNextRoundFromServer() throws IOException{
    try{
        if(!this.connected) return;
        this.dos.writeByte(2);
        this.dos.flush(); // Send data
        this.grid = (Grid) this.ois.readObject(); //i have checked, i do recieve this object
        setMainPane(render.render(this.grid)); //this renders the view
    } catch(ClassNotFoundException ex){
        ex.printStackTrace();
    }
}

这就是我的实现方式。

continuousPlayButton.setOnMouseClicked(e -> {
    try{
        Runnable scheduledRound = () -> {
            try {
                getNextRoundFromServer();
            } catch (IOException ex) {
                ex.printStackTrace();
            }
        };
        ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);
        scheduler.scheduleAtFixedRate(scheduledRound, 1, 5, TimeUnit.SECONDS);
    }catch(Exception ex){
        ex.printStackTrace();
    }
});

为什么我的视图没有更新?

更新

解决方案:

如用户tjanu所述:我忘记在计划的任务上致电Platform.runLater。我没有计划就调用它时已经做了...

3 个答案:

答案 0 :(得分:2)

您需要在JavaFX应用程序线程上进行UI更新。

这就是Platform::runLater的作用。

-编辑 根据要求,此代码需要进行更改:

private void getNextRoundFromServer() throws IOException{
    try{
        if(!this.connected) return;
        this.dos.writeByte(2);
        this.dos.flush(); // Send data
        this.grid = (Grid) this.ois.readObject(); //i have checked, i do recieve this object
        // This is the needed change
        Platform.runLater(() -> setMainPane(render.render(this.grid))); //this renders the view
    } catch(ClassNotFoundException ex){
        ex.printStackTrace();
    }
}

答案 1 :(得分:0)

不是您问题的完整答案,而是一个建议。也许您可以尝试覆盖run()方法。

Runnable scheduledRound = new Runnable() {
    @Override
    public void run() {
        try {
            getNextRoundFromServer();
        } catch (IOException ex) {
            ex.printStackTrace();
        }
    }
};

答案 2 :(得分:0)

您在getNextRoundFromServer()方法中引用实例变量,现在从一个新的(匿名)Runnable实例中调用该方法,因此您对“ this”的引用可能无法解析为您认为的位置解决。

也许传递了对原始实例的引用?

private void getNextRoundFromServer(YourObjectClass instance) throws IOException{
    try{
        if(!instance.connected) return;
        instance.dos.writeByte(2);
        instance.dos.flush(); // Send data
        instance.grid = (Grid) instance.ois.readObject(); //i have checked, i do recieve this object
        setMainPane(render.render(instance.grid)); //this renders the view
    } catch(ClassNotFoundException ex){
        ex.printStackTrace();
    }
}


continuousPlayButton.setOnMouseClicked(e -> {
    try {
        final instanceRef = getReferenceToYourOriginalInstance();  
        Runnable scheduledRound = () -> {
            try {
                getNextRoundFromServer( instanceRef );
            } catch (IOException ex) {
                ex.printStackTrace();
            }
        };
        ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);
        scheduler.scheduleAtFixedRate(scheduledRound, 1, 5, TimeUnit.SECONDS);
    }catch(Exception ex){
        ex.printStackTrace();
    }
});