Hallo zusammen,
ich versuche mich gerade in JavFX einzuarbeiten um meine Applikation die auf Java Swing basiert in JavaFX zu implemntieren. Ich versuche dabei auch das MVC Pattern zu realisieren. Das GUI habe ich mit Hilfe des Scenebuilder realisiert und aufgebaut.
Hier nun mein Problem:
Ich habe eine TextArea in der ich Meldungen ausgeben möchte die z.B. auch in der Model Class entstehen. Ich versuche nun beim drücken eines Button in einem extra Thread, da das UI nicht beeinträchtigt werden soll. eine Aktion durchzuführen. In Java Swing habe ich das mit ProcessWorker realisiert. Mir fehlt nun die richtige Implemntierung für JavaFX. Nachdem ich nun einiges gelesen habe war dies mein erster Versuch:
Der Code der im Controller beim drücken des Button ausgeführt wird:
Die Model Class ist folgendermaßen implementiert:
Wenn ich die Applikation starte und den Button drücke wird auf der Konsole die Ausgabe "Value:1" bis "Value 100" gemacht, in der Message Area kommen ungefähr die Ausgaben bis Value: 4 und es wird eine Exception ausgegeben:
Frage:
Kann mir jemand helfen bei der korrekten Implementierung eines Worker Threads mit JavaFX und MVC Pattern?
LG
Ralf
ich versuche mich gerade in JavFX einzuarbeiten um meine Applikation die auf Java Swing basiert in JavaFX zu implemntieren. Ich versuche dabei auch das MVC Pattern zu realisieren. Das GUI habe ich mit Hilfe des Scenebuilder realisiert und aufgebaut.
Hier nun mein Problem:
Ich habe eine TextArea in der ich Meldungen ausgeben möchte die z.B. auch in der Model Class entstehen. Ich versuche nun beim drücken eines Button in einem extra Thread, da das UI nicht beeinträchtigt werden soll. eine Aktion durchzuführen. In Java Swing habe ich das mit ProcessWorker realisiert. Mir fehlt nun die richtige Implemntierung für JavaFX. Nachdem ich nun einiges gelesen habe war dies mein erster Versuch:
Der Code der im Controller beim drücken des Button ausgeführt wird:
Java:
public void checkConnectDBButtonTapped() {
//statusIndicator.setVisible(true);
//statusIndicator.setImage(statusInProgress);
messageTextArea.appendText("DB hostname/address: " + dbHostNameAddress.getText() + "\n");
messageTextArea.appendText("Listener Port: " + listenerPort.getText() + "\n");
messageTextArea.appendText("DB SID: " + dbSid.getText() + "\n");
messageTextArea.appendText("DB User Name: " + dbUserName.getText() + "\n");
messageTextArea.appendText("DB User Password: " + dbUserPassword.getText() + "\n" );
messageTextArea.appendText("DB sys User Password: " + dbSysUserPassword.getText() + "\n");
messageTextArea.appendText("TNS Names Directory: " + tnsnamesDir.getText() + "\n");
messageTextArea.appendText("TNS Service Name: " + tnsamesServiceName.getText() + "\n");
Model model = new Model(messageTextArea);
new Thread(model.task).start();
//statusIndicator.setImage(statusOK);
}
Die Model Class ist folgendermaßen implementiert:
Java:
package application;
import javafx.concurrent.Task;
import javafx.scene.control.ProgressBar;
import javafx.scene.control.TextArea;
public class Model {
// Fields
TextArea messageTextArea;
ProgressBar bar;
// Constructors
public Model() {
}
public Model(TextArea messageTextArea, ProgressBar bar) {
super();
this.messageTextArea = messageTextArea;
this.bar = bar;
}
public Model(TextArea messageTextArea) {
super();
this.messageTextArea = messageTextArea;
}
// Methods
Task task = new Task<Void>() {
@Override
public void run() {
final int max = 100;
for (int i = 1; i <= max; i++) {
updateProgress(i, max);
System.out.println("Value: " + i);
messageTextArea.appendText("Value: " + i + "\n");
}
}
@Override
protected Void call() throws Exception {
// TODO Auto-generated method stub
return null;
}
};
}
Wenn ich die Applikation starte und den Button drücke wird auf der Konsole die Ausgabe "Value:1" bis "Value 100" gemacht, in der Message Area kommen ungefähr die Ausgaben bis Value: 4 und es wird eine Exception ausgegeben:
Code:
Value: 1
Exception in thread "JavaFX Application Thread" Value: 2
Value: 3
Value: 4
Value: 5
Value: 6
Value: 7
Value: 8
Value: 9
Value: 10
Value: 11
Value: 12
Value: 13
Value: 14
Value: 15
Value: 16
Value: 17
Value: 18
Value: 19
Value: 20
Value: 21
Value: 22
java.lang.NullPointerException
at com.sun.javafx.text.PrismTextLayout.addTextRun(PrismTextLayout.java:755)
at com.sun.javafx.text.GlyphLayout.addTextRun(GlyphLayout.java:140)
at com.sun.javafx.text.GlyphLayout.breakRuns(GlyphLayout.java:210)
at com.sun.javafx.text.PrismTextLayout.buildRuns(PrismTextLayout.java:770)
at com.sun.javafx.text.PrismTextLayout.layout(PrismTextLayout.java:1021)
at com.sun.javafx.text.PrismTextLayout.ensureLayout(PrismTextLayout.java:223)
at com.sun.javafx.text.PrismTextLayout.getBounds(PrismTextLayout.java:246)
at javafx.scene.text.Text.getLogicalBounds(Text.java:358)
at javafx.scene.text.Text.impl_computeGeomBounds(Text.java:1168)
at javafx.scene.Node.updateGeomBounds(Node.java:3579)
at javafx.scene.Node.getGeomBounds(Node.java:3532)
at javafx.scene.Node.getLocalBounds(Node.java:3480)
at javafx.scene.Node$MiscProperties$2.computeBounds(Node.java:6474)
at javafx.scene.Node$LazyBoundsProperty.get(Node.java:9308)
at javafx.scene.Node$LazyBoundsProperty.get(Node.java:9278)
at javafx.scene.Node.getBoundsInLocal(Node.java:3158)
at com.sun.javafx.scene.control.skin.TextAreaSkin$ContentView.layoutChildren(TextAreaSkin.java:207)
at javafx.scene.Parent.layout(Parent.java:1087)
at javafx.scene.Parent.layout(Parent.java:1093)
at javafx.scene.Parent.layout(Parent.java:1093)
at javafx.scene.Parent.layout(Parent.java:1093)
at javafx.scene.Parent.layout(Parent.java:1093)
at javafx.scene.Parent.layout(Parent.java:1093)
at javafx.scene.Parent.layout(Parent.java:1093)
at javafx.scene.Scene.doLayoutPass(Scene.java:552)
at javafx.scene.Scene$ScenePulseListener.pulse(Scene.java:2397)
at com.sun.javafx.tk.Toolkit.lambda$runPulse$30(Toolkit.java:355)
at java.security.AccessController.doPrivileged(Native Method)
at com.sun.javafx.tk.Toolkit.runPulse(Toolkit.java:354)
at com.sun.javafx.tk.Toolkit.firePulse(Toolkit.java:381)
at com.sun.javafx.tk.quantum.QuantumToolkit.pulse(QuantumToolkit.java:510)
at com.sun.javafx.tk.quantum.QuantumToolkit.pulse(QuantumToolkit.java:490)
at com.sun.javafx.tk.quantum.QuantumToolkit.lambda$runToolkit$404(QuantumToolkit.java:319)
at com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:95)
at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
at com.sun.glass.ui.win.WinApplication.lambda$null$148(WinApplication.java:191)
at java.lang.Thread.run(Unknown Source)
Value: 23
Value: 24
Value: 25
Value: 26
Value: 27
Value: 28
Value: 29
Value: 30
Value: 31
Value: 32
Value: 33
Value: 34
Value: 35
Value: 36
Value: 37
Value: 38
Value: 39
Value: 40
Value: 41
Value: 42
Value: 43
Value: 44
Value: 45
Value: 46
Value: 47
Value: 48
Value: 49
Value: 50
Value: 51
Value: 52
Value: 53
Value: 54
Value: 55
Value: 56
Value: 57
Value: 58
Value: 59
Value: 60
Value: 61
Value: 62
Exception in thread "JavaFX Application Thread" java.lang.NullPointerException
at com.sun.javafx.text.PrismTextLayout.addTextRun(PrismTextLayout.java:755)
at com.sun.javafx.text.GlyphLayout.addTextRun(GlyphLayout.java:140)
at com.sun.javafx.text.GlyphLayout.breakRuns(GlyphLayout.java:210)
at com.sun.javafx.text.PrismTextLayout.buildRuns(PrismTextLayout.java:770)
at com.sun.javafx.text.PrismTextLayout.layout(PrismTextLayout.java:1021)
at com.sun.javafx.text.PrismTextLayout.ensureLayout(PrismTextLayout.java:223)
at com.sun.javafx.text.PrismTextLayout.getBounds(PrismTextLayout.java:246)
at javafx.scene.text.Text.getLogicalBounds(Text.java:358)
at javafx.scene.text.Text.impl_computeGeomBounds(Text.java:1168)
at javafx.scene.Node.updateGeomBounds(Node.java:3579)
at javafx.scene.Node.getGeomBounds(Node.java:3532)
at javafx.scene.Node.getLocalBounds(Node.java:3480)
at javafx.scene.Node.updateTxBounds(Node.java:3643)
at javafx.scene.Node.getTransformedBounds(Node.java:3426)
at javafx.scene.Node.updateBounds(Node.java:559)
at javafx.scene.Parent.updateBounds(Parent.java:1717)
at javafx.scene.Parent.updateBounds(Parent.java:1717)
at javafx.scene.Parent.updateBounds(Parent.java:1717)
at javafx.scene.Parent.updateBounds(Parent.java:1717)
at javafx.scene.Parent.updateBounds(Parent.java:1717)
at javafx.scene.Parent.updateBounds(Parent.java:1717)
at javafx.scene.Parent.updateBounds(Parent.java:1717)
at javafx.scene.Parent.updateBounds(Parent.java:1717)
at javafx.scene.Scene$ScenePulseListener.pulse(Scene.java:2404)
at com.sun.javafx.tk.Toolkit.lambda$runPulse$30(Toolkit.java:355)
at java.security.AccessController.doPrivileged(Native Method)
at com.sun.javafx.tk.Toolkit.runPulse(Toolkit.java:354)
at com.sun.javafx.tk.Toolkit.firePulse(Toolkit.java:381)
at com.sun.javafx.tk.quantum.QuantumToolkit.pulse(QuantumToolkit.java:510)
at com.sun.javafx.tk.quantum.QuantumToolkit.pulse(QuantumToolkit.java:490)
at com.sun.javafx.tk.quantum.QuantumToolkit.lambda$runToolkit$404(QuantumToolkit.java:319)
at com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:95)
at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
at com.sun.glass.ui.win.WinApplication.lambda$null$148(WinApplication.java:191)
at java.lang.Thread.run(Unknown Source)
Value: 63
Value: 64
Value: 65
Value: 66
Value: 67
Value: 68
Value: 69
Value: 70
Value: 71
Value: 72
Value: 73
Value: 74
Value: 75
Value: 76
Value: 77
Value: 78
Value: 79
Value: 80
Value: 81
Value: 82
Value: 83
Value: 84
Value: 85
Value: 86
Value: 87
Value: 88
Value: 89
Value: 90
Value: 91
Value: 92
Value: 93
Value: 94
Value: 95
Value: 96
Value: 97
Value: 98
Value: 99
Value: 100
Frage:
Kann mir jemand helfen bei der korrekten Implementierung eines Worker Threads mit JavaFX und MVC Pattern?
LG
Ralf