尝试使用Task更新JavaFX场景图,在对任务对象外部的事件处理程序调用时出错

时间:2018-02-28 02:53:51

标签: java javafx

我在JavaFX中编写了一个小文件夹/图像浏览器。 (注意 - 我正在使用Java 8)

它目前通过浏览文件夹的内容,查找任何图像,随机挑选其中4个图像,然后显示这些图像以及文件夹名称来显示文件夹。

如果给定的父文件夹中有大量包含大量图像的文件夹,则此过程可能需要相当长的时间。

我正在尝试更改代码,以便在方法完成时一次显示一个文件夹及其选定的图像,而不是在方法完成运行后立即显示。

从我开始研究如何做到这一点,这样的典型方法是将您的代码放入Task对象,然后使用Platform在单独的线程中运行任务.runlater方法在原始FX Application线程上进行对象更新,如:

 final Group group = new Group();
 Task<Void> task = new Task<Void>() {
     @Override protected Void call() throws Exception {
         for (int i=0; i<100; i++) {
             if (isCancelled()) break;
             final Rectangle r = new Rectangle(10, 10);
             r.setX(10 * i);
             Platform.runLater(new Runnable() {
                 @Override public void run() {
                     group.getChildren().add(r);
                 }
             });
         }
         return null;
     }
 };
Thread th = new Thread(task);
th.setDaemon(true);
th.start();

但是,我要更新的代码包含两个setOnMouseClicked事件,imageView.setOnMouseClicked(this :: folderImageClick)和myFolder.setOnMouseClicked(this :: folderClick)。调用在任务之外编写的处理程序。就上面的例子而言,我猜它会是

 final Group group = new Group();
 Task<Void> task = new Task<Void>() {
     @Override protected Void call() throws Exception {
         for (int i=0; i<100; i++) {
             if (isCancelled()) break;
             final Rectangle r = new Rectangle(10, 10);
             r.setX(10 * i);
             r.setOnMouseClicked(this::mouseEventHandler);
             Platform.runLater(new Runnable() {
                 @Override public void run() {
                     group.getChildren().add(r);
                 }
             });
         }
         return null;
     }
 };
Thread th = new Thread(task);
th.setDaemon(true);
th.start();

当我这样做时,我得到了错误

  

Node类型中的方法setOnMouseClicked(EventHandler<? super MouseEvent>)不适用于参数(this::folderImageClick)

  

类型new Task<Void>(){}未定义此处适用的folderImageClick(MouseEvent)

有没有办法修复事件处理程序调用,以便它们在Task内部工作?

1 个答案:

答案 0 :(得分:1)

当从任务的方法中使用时,

this指向Task。显然你的匿名课中没有mouseEventHandler。您需要使用对包含该方法的外部类的引用。假设该类的名称为OuterClass

OuterClass.this::mouseEventHandler