当前位置: 首页 > 知识库问答 >
问题:

如何在javafx中操纵未来的结果

易招
2023-03-14

这是我的JavaFX控制器

public class MainController {
   private Future<Graph> operation;
   private ExecutorService executor = Executors.newSingleThreadExecutor();

   @FXML
   private void createSession() { //invoked by a button click in the view
      //GraphCreationSession implements Callable<Graph>
      GraphCreationSession graphSession = new GraphCreationSession();

      if (operation != null && !operation.isDone()) {
         //cancel previous session
         operation.cancel(true);
      }
      operation = executor.submit(graphSession);
      ???
    }
 }

所以我的问题是,在javaFX上下文中,处理<code>未来</code>结果的习惯用法是什么?

我知道我可以做operation.get(),线程将阻塞,直到操作完成,但我会阻塞Application线程。我正在考虑在Callable完成时进行回调,我发现了CompletableFuture,哪种类型通过thenAccep执行此操作,但基于此答案,线程仍将被阻塞,这违反了Future的要点,就像答案中提到的那样。

在我的例子中,可调用的结果(在我的例子中是Graph)包含一个结果,当操作完成时,我想在面板中显示这个结果。

共有1个答案

姬歌者
2023-03-14

最简单的方法是更改< code > GraphCreationSession ,使其成为< code>Task的子类

public class GraphCreationSession extends Task<Graph> {

    @Override
    public Graph call() throws Exception {
        // implementation as before...
    }
}

然后你可以做

public class MainController {
   private ExecutorService executor = Executors.newSingleThreadExecutor();
   private GraphCreationSession graphSession ;

   @FXML
   private void createSession() { //invoked by a button click in the view

      if (graphSession != null && !graphSession.getState()==Worker.State.RUNNING) {
         //cancel previous session
         graphSession.cancel(true);
      }
      graphSession = new GraphCreationSession();
      graphSession.setOnSucceeded(event -> {
          Graph graph = graphSession.getValue();
          // update UI...
      });
      executor.execute(graphSession);
    }
 }

如果您无法更改<code>GraphCreationSession,或者希望它独立于JavaFXAPI,那么只需将其包装在一个简单的<code>任务

public class MainController {

    private Task<Graph> graphSession ;
    // ...

    @FXML
    public void createSession() {

        // ...

        graphSession = new Task<Graph>() {
            @Override
            public Graph call() throws Exception {
                return new GraphCreationSession().call();
            }
        };

        graphSession.setOnSucceeded(...);
        executor.execute(graphSession);
   }
}
 类似资料:
  • 我用JavaFX做了一个国际象棋棋盘,并把所有的方格设置为GridPane的子方格,有没有办法用GridPane索引来访问这些方格并改变它们的属性? 我尝试通过磁贴矩阵访问一个磁贴来更改磁贴的颜色属性,但它不会更改 GridPane 中显示的磁贴。 的。getChildren()方法返回一个节点列表,一旦tile对象成为节点,我就无法访问它的方法。 这是我的磁贴类: } 这是我的董事会课:

  • 为了简化我的问题,假设我想用有效负载中的'd'替换所有'b'字符。 有没有一种方法可以让我原生地处理JSON数据,而不是首先将数据转换为XML? 我试图构建一个自定义的类中介来放入OutSequence中,但由于我只能访问MessageContext,它将有效负载视为XML,所以我遇到了问题。 以在正常情况下传递内容(否则将在XML到JSON处理步骤中失败)。但必须有一种方法让我将数据操作为原生J

  • 问题内容: 我想使用Node Http模块直接调用服务器以设置我的量角器测试。Http基于回调,我想将其变为promise。 例如,我想让这个函数返回promise: 因此,问题是:我需要什么并代替“以某种方式创造承诺”才能使之起作用? 问题答案: 量角器使用WebDriver的承诺,并在“量角器”上全局公开该API。所以你应该能够做 有关完整的WebDriverJS Promise API,请参

  • 问题内容: 在操纵up中按Enter似乎没有任何效果。但是,当我按其他键时,它会执行应有的操作。这有效: 这不是: 这是输入的样子: 有任何想法吗? 编辑:我也尝试过page.keyboard.down&page.keyboard.up来确保。 问题答案: 使用该站点时,我注意到有调度和事件,但没有。这可能是一个错误,但是幸运的是,发送回车键码(13)似乎可以正常工作,因此我们现在可以解决它。

  • 我正在使用junit运行一些单元测试。其中一个调用了一个对象中的方法,我使用mockito-like模拟该对象; 然后我设置mockito做一些类似的事情 现在myClass.foo实际上以我的另一个类(比如类Person)作为参数,我想做的是这样的事情 这当然是伪代码,但我希望它说明了我正在尝试做什么。这可能吗?

  • AFAIK将/提交到是我想并行执行资源密集型代码的方法。因此,我的方法结构: 我在上面的代码中标记了两个可能发生故障的点。对于这两种情况,可用于错误处理的选项非常不同。 在提交任务之前,可能会出现一些问题,例如参数无效,一些可能失败的快速预处理代码。 我在这里看到了几种表示失败的方式: 如果提供给的无效立即返回null。在这种情况下,我必须检查每次调用时是否返回null。 抛出检查过的异常而不是上