Question

Update:

Still having the same issue, revised source of main app code: http://pastebin.com/fLCwuMVq

There must be something in CoreTest that blocks the UI, but its doing all sorts of stuff (async xmlrpc requests, async http requests, file io etc), i tried putting it all into runLater but it doesnt help.

Update 2:

I verified the code runs and produces output correctly but the UI component cant manage to display it for ages

Update 3:

OK I fixed it. I don't know why, but no guide about JavaFX said this, and its very important:

Always put your program logic in a separate thread from the Java FX thread


I had this working with Swing's JTextArea but for some reason it doesn't work with JavaFX.

I tried debugging and it and doing .getText() after each write returns what seems to be characters written to it properly, but the actual TextArea in GUI shows no text.

Did I forgot to somehow refresh it or something?

TextArea ta = TextAreaBuilder.create()
    .prefWidth(800)
    .prefHeight(600)
    .wrapText(true)
    .build();

Console console = new Console(ta);
PrintStream ps = new PrintStream(console, true);
System.setOut(ps);
System.setErr(ps);

Scene app = new Scene(ta);
primaryStage.setScene(app);
primaryStage.show();

And the Console class:

import java.io.IOException;
import java.io.OutputStream;

import javafx.scene.control.TextArea;

public class Console extends OutputStream
{
    private TextArea    output;

    public Console(TextArea ta)
    {
        this.output = ta;
    }

    @Override
    public void write(int i) throws IOException
    {
        output.appendText(String.valueOf((char) i));
    }

}

Note: this is based on a solution from this answer, I removed bits I didn't care about but unmodified (apart from changing from Swing to JavaFX), it had the same result: data written to the UI element, no data showing on the screen.

Was it helpful?

Solution

Have you tried running it on the UI Thread?

public void write(final int i) throws IOException {
    Platform.runLater(new Runnable() {
        public void run() {
            output.appendText(String.valueOf((char) i));
        }
    });
}

EDIT

I think your problem is that your run some long tasks in the GUI thread, which is going to freeze everything until it completes. I don't know what

CoreTest t = new CoreTest(installPath);
t.perform();

does, but if it takes a few seconds, your GUI won't update during those few seconds. You need to run those tasks in a separate thread.

For the record, this works fine (I have removed the file and CoreTest bits):

public class Main extends Application {

    @Override
    public void start(Stage primaryStage) throws IOException {

        TextArea ta = TextAreaBuilder.create().prefWidth(800).prefHeight(600).wrapText(true).build();
        Console console = new Console(ta);
        PrintStream ps = new PrintStream(console, true);
        System.setOut(ps);
        System.setErr(ps);
        Scene app = new Scene(ta);

        primaryStage.setScene(app);
        primaryStage.show();

        for (char c : "some text".toCharArray()) {
            console.write(c);
        }
        ps.close();
    }

    public static void main(String[] args) {
        launch(args);
    }

    public static class Console extends OutputStream {

        private TextArea output;

        public Console(TextArea ta) {
            this.output = ta;
        }

        @Override
        public void write(int i) throws IOException {
            output.appendText(String.valueOf((char) i));
        }
    }
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top