2017-08-16 8 views
0

バックグラウンドスレッドでタスクを実行する方法を学ぶ前に、インターフェイスを使用してコントローラからUIにメッセージを投稿する方法を学びました。インターフェイスを使用すると、どのコントローラでもシステムメッセージを表示できます。タスクからupdateMessageにバインドする方法を理解することはできません。JavaFX並行性:インタフェースを持つコントローラへのメッセージ()の更新方法は?

マイインタフェース:

public interface SystemMessage { 
    void postMessage(String outText); 
} 

マイコントローラ:

public class MainController implements SystemMessage { 
    @FXML 
    public DialogPane systemMessage; 

    @Override 
    public void postMessage(String outText) { 
     systemMessage.setContentText(outText); 
    } 

    //***I have tried the following to bind the dialog pane to the updateMessage 

    systemMessage.contentTextProperty().bind(task.messageProperty()); 

    //***InteliJ tells me that it can not resolve contetTextProperty or task. 
} 

新しいスレッド上のタスクと私のメインクラス。

private SystemMessage mainController; 

FXMLLoader loader = new FXMLLoader(getClass().getResource("fxml/entry.fxml")); 
Parent root = loader.load(); 
this.mainController = (SystemMessage) loader.getController(); 

api = new Api(); 
machineId = new Identity(); 
    db = new SqLite(); 
    //mainController.postMessage(task.messageProperty()).bind(); 
    Thread th = new Thread(task); 
    th.setDaemon(true); 
    th.start(); 

Task<String> task = new Task<String>() { 
    @Override protected String call() throws Exception { 
     checkAsiServer(); 
     updateMessage("API Checked."); 

     checkMachineId(); 
     updateMessage("Machine Id Checked."); 

     checkDb(); 
     updateMessage("Server Checked."); 

     return "done"; 
    } 
}; 

私はでcotrollerの私DialogPaneをバインドしようとしている:

systemMessage.contentTextProperty().bind(task.messageProperty()); 

しかし、それはcontentTextPropertyを解決できないと私はどちらかのタスクオブジェクトについてのコントローラに伝える方法がわかりません。

+0

最後のコードブロックはどこから来たのですか?これはコントローラ内部にありますか?もしそうなら、問題の内容はわかりません。 –

+0

@James_Dいいえ最後のコードブロックは、タスクが実行されているMainにあります。あなたは私がタスクコンポーネントを理解するのを手伝った! Incedentally私はRunLater()でこの作業を行うことができますが、私は私のインターフェイスへのupdateMessageはもっと....エレガントだろうと思っていますか? – silversunhunter

+0

@ James_D ..コントローラにあるsystemMessage ...コードブロックを参照していた場合。 contentTextProprtyまたはtaskは解決できません。 – silversunhunter

答えて

1

私はこの問題を理解しています。コントローラーからプロパティを公開してみませんか?あなたはSystemMessageとしてコントローラの種類を維持したいとpostMessage方法に依存している場合にのみ、あなたは

public class MainController implements SystemMessage { 
    @FXML 
    private DialogPane systemMessage; 

    public StringProperty messageProperty() { 
     return systemMessage.contentTextProperty(); 
    } 

    // ... 
} 

、その後

FXMLLoader loader = new FXMLLoader(getClass().getResource("fxml/entry.fxml")); 
Parent root = loader.load(); 
MainController mainController = loader.getController(); 

Task<String> task = new Task<String>() { /* existing code... */}; 

mainController.messageProperty().bind(task.messageProperty()); 

Thread thread = new Thread(task); 
thread.setDaemon(true); 
thread.start(); 

を行うことができ、その後、明らかにあなたが結合してこれを行うことはできません(あなたはその物件にアクセスする手段がないので)。代わりにリスナーを使用する必要があります。

FXMLLoader loader = new FXMLLoader(getClass().getResource("fxml/entry.fxml")); 
Parent root = loader.load(); 
SystemMessage mainController = loader.getController(); 

Task<String> task = new Task<String>() { /* existing code... */}; 

task.messageProperty().addListener((obs, oldMessage, newMessage) -> 
    mainController.postMessage(newMessage));  

Thread thread = new Thread(task); 
thread.setDaemon(true); 
thread.start(); 
+0

私が最初の解決策を試みるとき、InteliJはmessagePropertyは解決できないと言います。 – silversunhunter

+1

@silversunhunterあなたは私が提案したすべてをしましたか? 'messageProperty()'メソッドをコントローラに追加し、 'mainController'の型を' MainController'に変更しましたか? –

+0

ああ。申し訳ありませんが、タイプをMainControllerに変更しませんでした。私はこれをやりました、そして、私はすべて一緒にインターフェイスを削除しました。私たちが作成したstringPropertyのreturn文でNullPointerExceptionが原因でInvocationExceptionが発生しています。 – silversunhunter

関連する問題