# JavaFX - Binding & Co



## kneitzel (26. Jun 2020)

Hallo zusammen,

ich bin in erster Linie Backend Entwickler, aber man bekommt ja einiges mit und nun möchte ich bezüglich JavaFX mal meine Sichtweise etwas validieren lassen (Ich beschäftige mich da derzeit etwas mit):

Was zumindest ich regelmäßig finde ist:
- fxml mit fx:id
- Im Controller dann alle Controls mit @FXML ControllType fxId
- Dann sehr viel im Code. Wenn Binding, dann wird das im Code gesetzt

Ist das nicht extrem Kontraproduktiv?

Was die Technologie ja bietet, ist das ganze Binding per fxml.

Somit kann ein Software Entwickler dann alles bauen, was fachlich benötigt wird:
- Controller mit diversen Actions - also z.B. sowas wie quitApplicationAction was klar Funktionsbasiert ist (statt sowas wie ein handleQuitButtonAction, was dann Button orientiert ist.)
- Model, welches im Controller referenziert wird und die Daten hält. Der Controller hält diese Daten nur in Form der Modell-Instanz.

Das kann dann aus meiner Sicht gut getestet werden in Unit Tests.
Und die Abhängigkeiten sind dann so aufgebaut, dass der UI Verantwortliche die UI so bauen kann, wie er möchte. Das Beenden der Applikation geht nicht über einen Button sondern dafür gibt es ein eigenes, spezielles ButtonControl? Kein Thema.Oder es gibt gar kein Button? Und das Schließen kann nur/zusätzlich über ein Menü-Punkt erfolgen? Alles kein Thema. Bindings erfolgen im @FXML und können jederzeit (ohne Code neu zu übersetzen) verändert werden.
Ich sehe das als deutlich besseres Design an aber dazu finden sich kaum Seiten und Beschreibungen (oder ich war zu blind, da was zu finden). Und wenn, dann wird es nur leicht angekratzt und es wird fast nur über andere Dinge geredet....

Ursache kann ggf. sein, dass der SceneBuilder mit sowas nicht umgehen kann. Sobald ich da also z.B. in einem Label ein 
`text="${controller.model.greeting}"`
habe, steigt der SceneBuilder mehr oder weniger aus (Text Element wird leer angezeigt aber zumindest bei mir gab es ganz seltsame Verhaltensweisen ... der "Element-Katalog" auf der linken Seite wurde nicht mehr richtig angezeigt und so ... ) Die Code Elemente funktionieren sehr gut, sogar incl. Auswertung des Controllers so dass das Drop Down gefüllt ist.

Somit stellen sich mir die folgenden Fragen:
- Habe ich das mit dem vernünftigen Aufbau einer JavaFX Applikation so erst einmal richtig verstanden? Oder habe ich da jetzt etwas übersehen und es sprechen gute Gründe gegen diese strikte Aufteilung?
- Gibt es bessere GUI Tools anstelle des Scene Builders? Eine Applikation, die ein graphisches Layout incl. Bindings erlaubt?

Vielen Dank schon einmal für eure Sicht / Meinung zu diesen Punkten.


----------



## lam_tr (26. Jun 2020)

JustNobody hat gesagt.:


> Hallo zusammen,
> 
> ich bin in erster Linie Backend Entwickler, aber man bekommt ja einiges mit und nun möchte ich bezüglich JavaFX mal meine Sichtweise etwas validieren lassen (Ich beschäftige mich da derzeit etwas mit):
> 
> ...


Hi @JustNobody ,

an sich würde mich das auch interessieren. Bisher habe ich leider auch noch nicht viel über das Binding im FXML gelesen, was eigentlich sehr schade ist. Ich komme ursprünglich von SWT/XWT, dort kann man UIs auch mit xml deklarieren und direkt im xml data binding benutzen was ziemlich cool ist. 

Aber jetzt zurück zu deiner Frage, ich denke diesen Schritt im FXML haben die Gluon Entwickler noch nicht wirklich Zeit darein gesteckt oder auch darüber nachgedacht. Vielleicht kannst du ein request hier machen https://github.com/gluonhq/scenebuilder und auf Glück warten dass sie es implementieren 

Zur zweiten Frage, ich glaube nicht dass sowas schon gibt. Scene Builder ist schon so ziemlich das einzige UI Builder für JavaFX das ich kenne.

Grüße
lam


----------



## kneitzel (26. Jun 2020)

Danke. Die Problematik ist im SceneBuilder bekannt und wohl nicht so einfach änderbar oder so ... Ich hatte da bereits einen Link dazu. Werde ich noch heraus suchen und bringen.

Aber dann wird es wohl ohne Grafisches Tool gehen müssen. So man entsprechende Panes nutzt, die die Gliederung für einen machen, sollte es kein Problem sein. Bisher hatte ich einfach nur ein paar ganz triviale Dinge gemacht und da habe ich Controls halt mit dem Editor hart plaziert und die Größe gesetzt. Das ist ja eh nicht das Gelbe vom Ei.

Ansonsten nutze ich die Gelegenheit, das auch etwas im Blog nieder zu schreiben um das etwas zu teilen, was ich da so mache und für richtig halte.
Das Binding klappt mit fxml auch super. Meine ersten Tests waren sehr erfolgreich und ich finde es bisher durchaus gelungen. Aber ich will mich da auch nicht zu sehr blamieren - daher frage ich hier auch noch vorsichtshalber nach, ehe ich zu großen Stuss im Blog erzähle ... Wobei auch gilt: Am Ende kann ja auch rauskommen, dass etwas keine gute Idee ist / war  Das ist im Blog auch nicht anders wie bei wissenschaftlichen Arbeiten 

Und was man auch nicht vergessen darf wenn man etwas erstellen möchte: Für viele Bereiche gibt es auch noch Erweiterungen, also z.B. FormsFX, wenn es um Formulare geht. Da wird es dann auch relativ einfach, gewisse Oberflächen zu erstellen.


----------



## lam_tr (26. Jun 2020)

JustNobody hat gesagt.:


> Danke. Die Problematik ist im SceneBuilder bekannt und wohl nicht so einfach änderbar oder so ... Ich hatte da bereits einen Link dazu. Werde ich noch heraus suchen und bringen.
> 
> Aber dann wird es wohl ohne Grafisches Tool gehen müssen. So man entsprechende Panes nutzt, die die Gliederung für einen machen, sollte es kein Problem sein. Bisher hatte ich einfach nur ein paar ganz triviale Dinge gemacht und da habe ich Controls halt mit dem Editor hart plaziert und die Größe gesetzt. Das ist ja eh nicht das Gelbe vom Ei.
> 
> ...


Generell ist Databinding schon ein richtig coole Sache, aber es ist immer morz ein Aufwand das alles einzurichten für die einzelnen Controls, es ist einfach nur übelst Fleißarbeit.

Deshalb habe ich mithilfe von SceneBuilder API ein DatabindingModel -Controller Generator geschrieben, womit ich zum Beispiel alle:
* Labels, Textfields automatisch mit textProperty gebinded wird
* TableView mit ObjectProperty, ObservableList, ...
etc....

Damit spare ich mir sehr viel Tipparbeit. 

Ich freue mich schon auf dein Blog Post. Sag einfach Bescheid wenn du durch bist, blamieren wirst du dich da bestimmt nicht, alleine der Aufwand was du da rein steckst ist schon viel Wert! *daumenhoch*


----------



## kneitzel (26. Jun 2020)

Du findest da eine kleine Serie unter http://blog.kneitzel.de

Ein großes Problem ist aus meiner Sicht, dass man Bidirectional Bindings nicht im XML definieren kann so ich das richtig verstanden habe. Das geht wohl nur in Code.

Da ist meine Lösung ein fx:ccript welches dann javafx.beans.binding.Bindings.bindBidirectional aufruft. Habe noch nicht getestet, ob mit JavaFX 14 das Binding per # statt $ funktioniert oder ob das noch nicht implementiert wurde. Über das bin ich in der Vergangenheit mal gestolpert.


----------



## kneitzel (26. Jun 2020)

lam_tr hat gesagt.:


> Deshalb habe ich mithilfe von SceneBuilder API ein DatabindingModel -Controller Generator geschrieben, womit ich zum Beispiel alle:
> * Labels, Textfields automatisch mit textProperty gebinded wird
> * TableView mit ObjectProperty, ObservableList, ...
> etc....
> ...



Hast / willst / kannst Du das einmal teilen? Das hört sich erst einmal toll an und das würde ich mir gerne einmal anschauen.


----------



## lam_tr (26. Jun 2020)

JustNobody hat gesagt.:


> Hast / willst / kannst Du das einmal teilen? Das hört sich erst einmal toll an und das würde ich mir gerne einmal anschauen.


Nachdem ich dein Post gelesen habe, war ich so motiviert, dass ich jetzt dabei bin, mir ein Eclipse IDE Plugin für das FXML mache. Bin mal gespannt ob das was wird. Ich kanns das Plug-in auf Github verteilen wenn es soweit ist.

Ich hab mal einen kleinen Blick auf deine Seite gemacht, ich schätze deine Arbeit, es macht einfach Spaß sowas zu lesen. Zwei Sachen sind mir da aufgefallen, an sich ist FXML je nachdem wie es aufgebaut ist schon sehr komplex und langsam, wenn ich das noch mit fx:script erweitere, dann wird die FXML  unendlich groß, ist das noch gut zu managen? Und wie du schon sagtest, der SceneBuilder kann das dann auch nicht mehr richtig parsen wenn im FXML fx:script erweitert wird oder? ich rede hier von Performanz, weil ich auch sehr an JavaFX Substrate / Jfxmobile mich interessiere und wenn da etwas ausgebremst wird.

Einer der Hauptgründe warum ich SceneBuilder benutze, ist das ich alles schön und schnell per Editor layouten kann. Wenn ich aber im graphischen Editor das DataBinding nicht machen kann und umgekehrt noch extra Texteditor benötige zum erweitern, schreckt mich das etwas ab. Zumal der TextEditor kein Autocompletion and Syntax Highlighting kann. Und vor allem wird das Debuggen auch viel mehr erschwert sage ich mal.

Ich hatte das früher in XWT sehr bequem und schön Databinden können. Deswegen werde ich das jetzt versuchen für FXML umzusetzen, natürlich nur von der Bedienung her. 

Bitte betrachte es nicht als Kritik, das ist nur meine Meinung zur Databinding im FXML. Und generell liebe ich über jede JavaFX Blog Einträge, leider gibt es zu wenig davon, deswegen würde ich mich noch mehr über deine freuen.

Grüße
lam


----------



## kneitzel (26. Jun 2020)

Ob das am Ende tauglich ist, weiß ich selbst noch nicht. Kann durchaus sein, dass am Ende das Fazit stehen wird: taugt nur sehr begrenzt etwas.

Ob man ohne SceneBuilder auskommen kann, wird sich für mich später zeigen. Ich schaue halt gerade selbst, wie man das mit hbox/vbox und den ganzen Panes gut hin bekommen kann. Klar - am Anfang ist eine GUI einfacher, aber auch bei TeX war meine Erfahrung, dass man da viele Standard Dinge einfacher eben schnell von Hand gemacht hat. War zwar einmal mühsam, sich das zu erarbeiten, aber wenn man das einmal drauf hatte, dann ging es sehr schnell. (Da hatte ich mal die Schnaps-Idee, in TeX Dinge aufzubereiten um dann PDF und HTML zu generieren. Aber das HTML hat sich als annähernd unmöglich herausgestellt. Das war noch zu Zeiten, als ich hier als kneitzel unterwegs war und ich dann so bei einzelnen Fragen das halt generischer ausbauen wollte incl. Blog Eintrag und Post der Antwort hier im Forum. Aber Satz mit X und nach zwei Wochen Fluchen habe ich dann beschlossen, dem TeX doch keine Zeit mehr zu widmen  )

Aber da lernt man schnell, was da alles an Arbeit drinnen steckt. 

Und bei JavaFX fehlt es an Dokumentation / guten Seiten. Ich probiere jetzt derzeit, ob ich nicht einer Property irgendwie eine Property zuweisen kann.
Also ein eigenes Control mit Namen "BidirectionalBinding" und das hat zwei Properties:


```
ObjectProperty<Property<? extends Object>> first = new SimpleObjectProperty<>();
    ObjectProperty<Property<? extends Object>> second = new SimpleObjectProperty<>();
```

Nur wie kann ich dann da die Properties zuweisen? Ich habe also:


```
<TextField fx:id="nameTextField" ... />
<BidirectionalBinding first="..." second="..." />
```
und first soll nun werden $nameTextField.texProperty() und second ${controller.model.nameProperty()} 
nameTextField sieht man ja und controller hat ein model welches dann name als StringProperty hat mit get/set name und nameProperty.

Wenn ich das gesetzt bekomme, dann wäre der Aufruf statt in einem JavaScript in meinem Control (das im Konstruktor die Werte ausliest und dann den Aufruf für das Binding macht...

War das verständlich erläutert?


----------



## lam_tr (26. Jun 2020)

JustNobody hat gesagt.:


> Ob das am Ende tauglich ist, weiß ich selbst noch nicht. Kann durchaus sein, dass am Ende das Fazit stehen wird: taugt nur sehr begrenzt etwas.
> 
> Ob man ohne SceneBuilder auskommen kann, wird sich für mich später zeigen. Ich schaue halt gerade selbst, wie man das mit hbox/vbox und den ganzen Panes gut hin bekommen kann. Klar - am Anfang ist eine GUI einfacher, aber auch bei TeX war meine Erfahrung, dass man da viele Standard Dinge einfacher eben schnell von Hand gemacht hat. War zwar einmal mühsam, sich das zu erarbeiten, aber wenn man das einmal drauf hatte, dann ging es sehr schnell. (Da hatte ich mal die Schnaps-Idee, in TeX Dinge aufzubereiten um dann PDF und HTML zu generieren. Aber das HTML hat sich als annähernd unmöglich herausgestellt. Das war noch zu Zeiten, als ich hier als kneitzel unterwegs war und ich dann so bei einzelnen Fragen das halt generischer ausbauen wollte incl. Blog Eintrag und Post der Antwort hier im Forum. Aber Satz mit X und nach zwei Wochen Fluchen habe ich dann beschlossen, dem TeX doch keine Zeit mehr zu widmen  )
> 
> ...


Ich bin mir nicht ganz sicher ob ich das was du vorhast, verstanden habe. Du willst ein eigenes Control mit zwei Properties haben und die sollen dann über FXML gebindet werden, aber bidirectionalBinding ist doch wenn du am Control oder Model Änderung machst, wird es auf dem anderen aktualisiert und umgekehrt, oder?


----------



## kneitzel (28. Jun 2020)

Sorry, komme jetzt erst dazu, das im Detail zu erläutern.

Derzeit baue ich das Binding ja über ein fx:script Element auf:

```
<TextField fx:id="nameTextField" layoutX="92.0" layoutY="65.0" text="Bitte Namen eingeben." />
      <fx:script>
         javafx.beans.binding.Bindings.bindBidirectional(
               controller.model.nameProperty(),
               nameTextField.textProperty()
         );
      </fx:script>
```
Sprich: Ich habe ein TextField und im Model habe ich dann dazu eine StringProperty.
Und das soll in beide Richtungen gebunden sein.

Meine Überlegung wäre jetzt, dass ich dieses fx:script ersetzen kann über ein eigenes Tag. Ich könnte z.B. ein eigenes "Control" erstellen, welches BidrectionalBinding heisst. Dem müsste ich aber dann ja angeben, welche Properties ich binden möchte.

Also das Ergebnis sollte dann etwas sein wie:


```
<TextField fx:id="nameTextField" layoutX="92.0" layoutY="65.0" text="Bitte Namen eingeben." />
<BidirectionalBinding first="$controller.model.nameProperty" second="$nameTextField.textProperty" />
```

first / second hatte ich dann als ObjectProperty<Property<String>> definiert und so. (Erst einmal konkret für String Properties. Das wäre dann ggf. später erweiterbar auf Property<? extends Object> oder so.

Aber egal, was ich da dann im fxml so angegeben habe: Das hat alles nicht funktioniert. Ich war nicht in der Lage, da eine Property zuzuweisen.

Das BidirectonalBinding ist natürlich ein triviales Control. Es fügt nichts hinzu und ist somit nicht sichtbar. Aber es ruft dann halt
`Bindings.bindBidirectional(first.get(), second.get());`
auf.

Die Kernidee wäre halt, dass man über diesen Umweg auch ohne Scripts im fxml ein Bidirectionales Binding definieren könnte.

Evtl. geht es so auch nicht. Ich war schon etwas am überlegen, ob ich statt dessen einfach 4 Angaben machen könnte:
Control / PropertyName das gebunden werden soll.
Model / PropertyName, das gebunden werden soll.

Aber da beißt sich die Katze in den Schwanz fürchte ich, denn wie gebe ich das Model an? Das könnte natürlich auch wieder eine ObjectProperty sein, aber die müsste ich ja erneut auch angeben ... wenn ich die angegeben bekomme, dann bekomme ich eigentlich auch die konkrete Property im model angegeben... oder die Property des Controls.


----------



## lam_tr (29. Jun 2020)

JustNobody hat gesagt.:


> Sorry, komme jetzt erst dazu, das im Detail zu erläutern.
> 
> Derzeit baue ich das Binding ja über ein fx:script Element auf:
> 
> ...


Okay nach einer ausführlichere Erklärung habe ich dein Vorhaben verstanden. Die Idee ist Klasse, hoffentlich klappt das bei deinem test auch. Dieses Binding würde für einfache StringProperties gehen, aber bei custom Objects, LocalDate, LocalDateTime, etc. würdest du noch einen dritten Parameter benötigen zum Konvertieren.

Eine Sache gefällt mir hier nicht ganz, jedes mal wenn BidirectionalBinding hinzugefügt wird, wird beim Laden der FXML ein separated Object erstellt nur um ein statisches Binding zu machen. Ich finde es irgendwie schöner wenn man für alle <BidirectionalBinding> ein zentrale Klasse hätt. Was meinst du dazu?

Grüße
lam


----------



## kneitzel (29. Jun 2020)

Mein Problem ist, dass ich irgendwie das mit dem Control schon gar nicht erst hin bekomme. Ich habe dazu einmal folgendes gemacht:


```
package de.kneitzel;

import javafx.beans.NamedArg;
import javafx.beans.binding.Bindings;
import javafx.beans.property.ObjectProperty;
import javafx.beans.property.SimpleObjectProperty;
import javafx.beans.property.SimpleStringProperty;
import javafx.beans.property.StringProperty;
import javafx.fxml.Initializable;
import javafx.scene.control.Control;

import java.net.URL;
import java.util.ResourceBundle;

public class BidirectionalBinding extends Control implements Initializable {

    private ObjectProperty<StringProperty> first = new SimpleObjectProperty<>();
    public StringProperty getFist() { return first.getValue(); }
    public void setFirst(final StringProperty value) {
        first.setValue(value);
    }
    public ObjectProperty<StringProperty> firstProperty() { return first; }

    private ObjectProperty<StringProperty> second  = new SimpleObjectProperty<>();
    public StringProperty getSecond() { return second.getValue(); }
    public void setSecond(final StringProperty value) {
        second.setValue(value);
    }
    public ObjectProperty<StringProperty> secondProperty() { return second; }

    public BidirectionalBinding() {}

    public BidirectionalBinding(@NamedArg("first") final StringProperty first, @NamedArg("first") final StringProperty second) {
        setFirst(first);
        setSecond(second);
    }

    @Override
    public void initialize(URL location, ResourceBundle resources) {
        if (first.getValue() == null || second.getValue() == null) {
            System.err.println("A value is null!");
        }
        first.getValue().bindBidirectional(second.getValue());
    }
}
```

Also mal davon abgesehen, dass initialize nicht aufgerufen wird und dass ich die folgende Meldung bekomme:

```
Juni 29, 2020 9:17:06 VORM. javafx.scene.control.Control doProcessCSS
SCHWERWIEGEND: The -fx-skin property has not been defined in CSS for BidirectionalBinding@82e8853 and createDefaultSkin() returned null.
```

Habe ich generell das Problem, dass setFist und setSecond zwar aufgerufen werden aber das nur mit null Werten oder ich kriege eine Exception.

Was habe ich alles probiert:

${controller.model.name} => javafx.fxml.LoadException: Cannot bind to untyped object.
${controller.model.nameProperty} => javafx.fxml.LoadException: Cannot bind to untyped object.
${controller.model.nameProperty()} => javafx.fxml.LoadException: Cannot bind to untyped object.

$controller.model.nameProperty() => null im Aufruf
$controller.model.nameProperty => null im Aufruf
$controller.model.name => java.lang.IllegalArgumentException: Unable to coerce  to class javafx.beans.property.StringProperty.

Also irgendwie habe ich hier gewisse Probleme, so eine Property überhaupt anzugeben.

(Die anderen Probleme weiter oben dürften daher kommen, dass ich das einfach zu sehr vereinfacht habe. Andere CustomControls sind ja mit Controller und so aufgebaut. Aber da ich etwas hatte, das erst einmal geladen werden kann, wollte ich da erst einmal die Angabe von Properties testen.)


----------



## temi (29. Jun 2020)

Ich habe das hier nur überflogen, aber vielleicht kannst du aus diesem Projekt ja etwas Hilfreiches mitnehmen. Falls nicht, so sei es ungeschrieben...


----------



## kneitzel (29. Jun 2020)

Ja, darüber bin ich auch schon gestolpert alleine um zu sehen, ob dies evtl. ein brauchbarer Ansatz zur sauberen Trennung ist. Da werde ich auf jeden Fall noch tiefer eintauchen müssen. Danke auf jeden Fall für den Hinweis!


----------



## temi (29. Jun 2020)

Unter C# hatte ich viel mit XAML und Caliburn Micro gearbeitet. Das war wirklich sehr angenehm. Aber dies nur am Rande. Ich hoffe du findest eine gute Lösung!


----------



## kneitzel (29. Jun 2020)

Ja, C# mit XAML (WPF) habe ich Erfahrungen mit gesammelt. Da ist halt deutlich mehr möglich mit z.B.:
`Text="{Binding Path=SomeSource.SomeValue, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"`

Aber das fxml ist da halt deutlich eingeschränkter. Da scheint es tatsächlich nur den Weg über den Code zu geben.

So wie ich dieses mvvmFX verstehe, hat man da dann im Java Part der View den Code mit den Bindings. Statt also alles in einer fxml Datei zu halten (Die dann nicht mehr mit Tools wie SceneBuilder bearbeitet werden kann), wurden die notwendigen Teile in den "Controller" verschoben, der nun Part der View ist (und auch als View bezeichnet wird).

Mögliche Logik und Co liegt im ViewModel - ist also aus dem Controller raus gewandert, so dass der Controller sozusagen in View umbenannt werden konnte (er kontrolliert nichts mehr! Ich mag es, wenn deutlich wird, dass die Benennung auch direkt Sinn ergibt!).
Hat auf jeden Fall gewisse Vorteile. Aber die View (fxml Part) ist nicht abgegrenzt vom Code editierbar. Wobei das auch bei mir nicht der Fall war - ich hatte den Code ja auch nur in das fxml integriert. Somit sieht das auf jeden Fall wie eine sehr interessante Sache aus.

Und ich kratze ja erst noch an der Oberfläche. Die haben da auch DI verwendet und so (Google Guice, Spring und andere DI Frameworks werden unterstützt wie ich es gesehen habe) und dazu bin ich noch nicht vorgedrungen. Da bin ich mal gespannt, was die da noch für nette Einfälle hatten...


----------



## temi (29. Jun 2020)

JustNobody hat gesagt.:


> So wie ich dieses mvvmFX verstehe, hat man da dann im Java Part der View den Code mit den Bindings. Statt also alles in einer fxml Datei zu halten


Das ist wohl so eine Art "code-behind". Gibt es ja, so ich mich richtig erinnere, auch bei WPF.

EDIT: Aus dem "How-to" von mvvmFX:


> Bei FXML-Basierten Ansichten besteht die konzeptionelle "View" aus 2 Dateien:
> 
> 
> Die FXML-Datei ansich enthält die Struktur und das Layout der Oberfläche. Sie definiert, welche UI-Elemente verwendet werden.
> ...


----------



## mihe7 (29. Jun 2020)

JustNobody hat gesagt.:


> Habe ich generell das Problem, dass setFist und setSecond zwar aufgerufen werden aber das nur mit null Werten oder ich kriege eine Exception.


Keine Ahnung, ob es damit zu tun hat, nur weil es mir gerade auffällt: der Setter ist mit r, der Getter ohne: setFirst vs. getFist

EDIT: kann es sein, dass Getter und Setter hier mit String und nicht StringProperty arbeiten müssen?


----------



## kneitzel (29. Jun 2020)

Ach, Tippfehler. Werde ich morgen noch mal schauen. 

Wobei das Problem schon vorab lag, denn der Setter wurde ja nicht korrekt aufgerufen. Binding scheint nur für Werte zu gehen aber nicht für die eigentlichen Properties wie es scheint.

Der erste Blick auf mvvmFX ist aber sehr vielversprechend finde ich. Das vertiefe ich noch weiter ...

Bin aber generell gespannt, was da noch alles geht. War da ja immer sehr skeptisch, wenn es um Themen wie Multi Plattform Lösungen und so ging. Aber das muss man sich alles mal im Detail ansehen


----------



## Bela B. (30. Jun 2020)

Das hier, ist auch für mich extrem interessant. Bin ebenfalls am Verstehen von mvvmFX und wie man es "richtig" verwendet. Mir fehlt da allerdings einiges an Wissen und so geht es nur schleppend voran bei mir.

Daher @JustNobody bitte dringend mit dem Blog weitermachen und das ganze auch für Einsteiger in JavaFX verständlich erklären, denn genau so etwas fehlt bei JavaFX.

Wie du anfangs schon sagtest, gibt es viele Guides, Tutorials, Videos und Bücher, die JavaFX zum Teil sehr oberflächlich und auch noch sehr "falsch" (damit meine ich sehr unsauber bezüglich Trennung der Zuständigkeiten) zeigen. Da wird oft sehr viel hingerotzt, ohne schönen Code zu produzieren.

Bitte dran bleiben🤩


----------



## kneitzel (30. Jun 2020)

Schreib mir dann auch ruhig Feedback. Was müsste besser gemacht werden? Natürlich auch gerne, was gefällt.

Ich habe ja auch etwas zur aktuellen Planung geschrieben - derzeit ist eine Beispiel-App dran, in der man alles etwas mehr im Zusammenhang sieht. Das fehlt aus meiner Sicht bei den ganz kleinen Beispielen immer ... Aber ich kann auch immer gerne etwas anderes vorziehen oder auch den ganzen Plan über den Haufen werfen wenn notwendig.

Ist halt nicht wirklich eine detaillierte Beschreibung z.B. von MVC sondern nur ein Beispiel, wie ich es sehe ...


----------



## Bela B. (30. Jun 2020)

Bisher schaut dein Plan gut aus, was mir auch bei den bisherigen Beispielen bei mvvmFX fehlt, ist die Erklärung dazu. Bei den Projekten, bei denen dann eine Erklärung dabei ist, ist das Model so verdammt simpel und/oder mit Properties gemacht.

Ich würde mir wünschen, wenn du eine Vorstellung von mvvmFX mit richtiger* Aufteilung nach MVVM-Pattern zeigst, das auf ein komplizierteres Model mit "normalen" Java Datentypen zugreift.

Edit:
Und was mir bisher auch noch nicht so klar ist, welche guten Erweiterungsmodule es für JavaFX alles gibt.

(*: mir ist klar, dass die Aufteilung für jeden Programmierer anders für richtig empfunden wird)


----------



## kneitzel (30. Jun 2020)

Ja, dann wird das, was als nächstes kommt, bestimmt interessant. Da gibt es dann als Beispiel eine Adressverwaltung.
Den Backend-Bereich halte ich natürlich simpel, also keinerlei Laden/Speichern und so, d.h. die Applikation startet mit einer leeren Liste und dann kann man einfache Adressen anlegen, editieren und so weiter.... Aber das its ja ein Bereich, den ich nicht weiter abdecken möchte. Wichtig ist halt für mich, dass es hier einfache Entities gibt: Address, das eine Adresse halten kann und AddressList und eine Reihe von Adressen.

Dabei hat AddressList halt Methoden, wie man sie z.B. bei einem DataLayer finden könnte a.la. findById, findByName, save, delete ...

Das ist halt absichtlich einfach gehalten. Es geht mit halt um:
- den Aufbau mit ViewModel und View. 
- erste einfache Gestaltungsmöglichkeiten

Bezüglich Erweiterungen: Was interessiert Dich da besonders? Derzeit will ich nur auf FormsFX eingehen und mich dann etwas den Multi-Plattform Lösungen mit JavaFX zuwenden.
Es gibt aber natürlich einiges mehr wenn man z.B. auf https://openjfx.io/ unter Community schaut.


----------



## Bela B. (30. Jun 2020)

JustNobody hat gesagt.:


> Das ist halt absichtlich einfach gehalten. Es geht mit halt um:
> - den Aufbau mit ViewModel und View.
> - erste einfache Gestaltungsmöglichkeiten


Ja damit meine ich jetzt auch nicht ein Mords kompliziertes Model, aber bei den meisten Beispielen besteht es nur aus einer Klasse, die sich im Model befindet. In echten Applikationen ist das dann ja doch meist etwas mehr aufgebläht und besser getrennt.

So habe ich z.B. in meiner aktuellen Anwendung mehrere DataLayers die über das Repository-Pattern dem Model einige Methoden anbieten, um diese dann letztendlich zueinander zu vergleichen.



JustNobody hat gesagt.:


> Bezüglich Erweiterungen: Was interessiert Dich da besonders?


Hauptsächlich neben den von dir eh schon geplanten FormsFX die ControlsFX.

Ich will dir damit jetzt nicht zu viel aufhalsen, aber was auch noch mehr als interessant wäre:
TDD mit mvvmFX anhand der Adressverwaltung?

Hoffe, ich gehe dir damit jetzt nur zu sehr auf den S* 😬


----------



## lam_tr (30. Jun 2020)

temi hat gesagt.:


> Ich habe das hier nur überflogen, aber vielleicht kannst du aus diesem Projekt ja etwas Hilfreiches mitnehmen. Falls nicht, so sei es ungeschrieben...



Hallo zusammen,

ich habe das Framework mal angeschaut und bin da leider nicht schlau geworden was man da so wirklich gewinnen kann. Vielleicht denke ich auch zu einfach oder habe es komplett nicht verstanden. Aber eine Aufklärung wäre schon cool 

Grüße
lam


----------



## lam_tr (30. Jun 2020)

Bela B. hat gesagt.:


> Bisher schaut dein Plan gut aus, was mir auch bei den bisherigen Beispielen bei mvvmFX fehlt, ist die Erklärung dazu. Bei den Projekten, bei denen dann eine Erklärung dabei ist, ist das Model so verdammt simpel und/oder mit Properties gemacht.
> 
> Ich würde mir wünschen, wenn du eine Vorstellung von mvvmFX mit richtiger* Aufteilung nach MVVM-Pattern zeigst, das auf ein komplizierteres Model mit "normalen" Java Datentypen zugreift.
> 
> ...


@Bela B.
was meinst du da mit Erweiterungsmodule?

Kann man dich hiermit zufrieden stellen https://github.com/mhrimaz/AwesomeJavaFX es wird fortlaufen geupdatet.


----------



## looparda (30. Jun 2020)

JustNobody hat gesagt.:


> So wie ich dieses mvvmFX verstehe, hat man da dann im Java Part der View den Code mit den Bindings. Statt also alles in einer fxml Datei zu halten (Die dann nicht mehr mit Tools wie SceneBuilder bearbeitet werden kann), wurden die notwendigen Teile in den "Controller" verschoben, der nun Part der View ist (und auch als View bezeichnet wird).


Ich bezeichne diesen Part gern als (View)Controller. Die einzige Zuständigkeit ist das Setzen der Bindings zwischen View und ViewModel und ggf. das kontrollieren aufwändiger Animationen, die nicht einzig in der View definiert werden können. Außerdem werden hier die Actions für Button gesetzt, welche an die angebotenen Commands des ViewModels delegieren. 



lam_tr hat gesagt.:


> Vielleicht denke ich auch zu einfach oder habe es komplett nicht verstanden. Aber eine Aufklärung wäre schon cool


Das ViewModel hat keine Verbindung zur View und ist somit ohne GUI testbar. Du kannst mehrere Views mit einem ViewModel verbinden.


----------



## kneitzel (30. Jun 2020)

lam_tr hat gesagt.:


> Hallo zusammen,
> 
> ich habe das Framework mal angeschaut und bin da leider nicht schlau geworden was man da so wirklich gewinnen kann. Vielleicht denke ich auch zu einfach oder habe es komplett nicht verstanden. Aber eine Aufklärung wäre schon cool
> 
> ...



So wie es schon angeklungen ist: Es geht zum einen darum, dass du möglichst viel mit Unit-Tests testen kannst. Dazu brauchst Du möglichst sauber Abhängigkeiten. Was mich immer wieder massiv stört ist Code, in dem die Abhängigkeiten wild durcheinander gehen. Da hast man dann einen JavaFX Controller, der natürlich massiv abhängig ist zum fxml (weil da ja dann Controls mit fx:id klar so sein müssen). Und dann oft auch noch Business-Logik, die in den Controller wandert (statt in einem Model zu sein) us.w.

Zum anderen sehe ich aber auch Probleme mit der Entwicklung zwischen mehreren Entwicklern. Ich möchte die reine Programierung machen, d.h. am Ende kommen Dinge dabei raus, wie:
- Ich stelle Daten zur Verfügung. (Mit den entsprechenden Pattern wie Observable und so) 
- Ich stelle Aktionen zur Verfügung.

Die, die die GUI bauen, können Ihre GUI direkt bauen indem sie einfach das, was ich später anbiete, modellieren (a.la. Mocking). Sie sind auch komplett frei in Ihrer Wahl von Controls und so. Es ist egal, ob etwas nun ein Button ist oder ein KonradsGeilerKnopf oder einfach ein Label auf den man klicken oder oder oder oder .... Das kommt in meinem Code schlicht nicht vor. Das interessiert mich auch nicht.

Das ist dann auch das, was ich etwas in meinem Blog zu JavaFX MVC darstellen wollte. Führte aber dann dazu, dass auf Grund der Unzulänglichkeiten von fxml eben doch Code notwendig wird ...

Das MVVM Pattern ist ähnlich nur eben sind da die Dinge leicht abgewandelt.

Die View ist (kann) zweiteilig (sein). Du hast das fxml (optional) und ein Java File. Das ist in etwa die View wie beim MVC, nur eben hast Du da den Code sauber in dem "Codebehind" File.
Das ViewModel entspricht dem Model bei MVC. Denn streng genommen war das ja immer ein künstliches Model, denn man musste die Daten ja in entsprechenden Klassen bereit stellen, z.B. die Property oder Oberservable Klassen. Das heisst man hatte zum einen seine Entities, DAL und Co und dann das JavaFX Model.... Nun heisst das JavaFX Model halt ViewModel und Model ist das Model der Applikation, das nun unabhängig von JavaFX ist.

Das sieht für mich relativ gut und brauchbar aus. Die Frage ist nur, was es evtl. noch an Nachteilen gibt. Aber schlecht als die Laufzeit bei den JavaScript Anteilen bei meinem MVC Ansatz kann es eigentlich nicht sein.


----------



## Bela B. (5. Jul 2020)

@JustNobody gibt es eigentlich einen Zeitplan für deinen Blog? Bin schon extrem gespannt auf den nächsten Eintrag🤓


----------



## kneitzel (5. Jul 2020)

Wirklichen Zeitplan nicht, aber ich will das zügig fertig machen.

Es gab jetzt ein paar andere Themen mit höherer Prio, aber ich hoffe, dass ich das die nächste Woche deutlich voran treiben kann.


----------



## lam_tr (20. Jul 2020)

Hi @JustNobody
um auf das Thema zurückzukommen, ich habe mittlerweile einen Renderer für JavaFX geschrieben, womit man Controls anders definieren kann. Zum einen nicht mehr über FXML, da es sehr viel über Reflections geht und zum Anderen in meinem Framework kann man sogar Databinding direkt definiere. 

Hier mal ein kleiner Einblick:
Zum Beispiel für TableView - Defnitiionsdatei





Hier der generierte Model und Controller class


Als Resultat bekommt man über das Framework diese TableView

Natürlich muss noch in der Main klasse die Daten populated werden

Vom Controller aus kommt man mit Hilfe des Models zur Liste der Person, FilteredList und vor allem kommt man dort zur selektierten Zeile.

Gehen wir jetzt nicht von TableView aus sondern ein Formular, kann man dort Binding direkt als Knoten erweitern. Aktuell geht es nur mit TextProperty. Als Zusatzfeature werden Validatoren noch eingebunden, die über Regex gecheckt werden.

Der Boilerplate Code wird an dieser Stelle generiert

Die entsprechende UI sieht so aus

Funktioniert schon wie es dargestellt wird.

Was hälst du von diesem konzept?

Grüße
lam


----------



## kneitzel (20. Jul 2020)

Das sieht sehr interessant aus, aber ich bin leider etwas Land unter was meine Zeit angeht. Aber sobald die aktuelle Situation sich entspannt hat (spätestens in 2 Wochen habe ich Urlaub  ) kann ich endlich auch dieses Ghema voran treiben... sollte ja eigentlich längst erledigt gewesen sein ....


----------



## lam_tr (20. Jul 2020)

JustNobody hat gesagt.:


> Das sieht sehr interessant aus, aber ich bin leider etwas Land unter was meine Zeit angeht. Aber sobald die aktuelle Situation sich entspannt hat (spätestens in 2 Wochen habe ich Urlaub  ) kann ich endlich auch dieses Ghema voran treiben... sollte ja eigentlich längst erledigt gewesen sein ....


Vielleicht nur noch kurz eine Anmerkung, über dieses framework würde man sogar den renderer austauschen können der im controller definiert ist. Somit kann man x beliebige Frontend apis benutzen.

Aber die IDE Unterstützung ist aktuell Javafx lastig.

Vielleicht kann ich bis dahin schon mal eine incubation Version auf github stellen


----------



## Bela B. (22. Okt 2020)

@kneitzel Gibt es denn schon was neues zu den nächsten Blogeinträgen?


----------



## kneitzel (22. Okt 2020)

Danke für Dein Interesse. Es wird dieses Wochenende hoffentlich was neues geben.

Das aktuelle Format / Ergebnis fand ich mangelhaft aber alles komplett ausarbeiten ist schwer. Daher wird es nun einen Versuch geben, das mit Youtube Videos zu verbinden.

Den ersten Teil habe ich soweit aufbereitet. Das Video will ich Samstag final erstellen und dann hochladen. Das ist aber dann erst der erste Schritt, also wahrscheinlich nichts, das Dich interessieren dürfte. Aber mir ist jedes Feedback wichtig um zu sehen, ob das dann vom Prinzip her ok ist oder weitere Veränderungen notwendig sind.

Aber ich melde mich hier, sobald ich das veröffentliche.


----------



## kneitzel (27. Okt 2020)

Am Wochenende wollte ich das erste Video online stellen, aber die Video-Bearbeitung zieht sich extrem hin. Mit dem Klang der Stimme bin ich extrem unzufrieden und da muss ich noch mit der Software mehr spielen.

Und ich werde es in mehrere Videos aufteilen, denn nur die Übersicht über Installation / Tools ist direkt über 40 Minuten geworden - das ist wohl zu viel, oder was meint ihr?

Also von der Arbeit her ist das heftig - hatte ich mir einfacher vorgestellt. Erste Ansätze hatte man ja recht schnell ... aber bis man was zum Hochladen fertig hat ...

BTW: hat da mal einer von euch etwas gemacht? Was für Software könnt Ihr empfehlen? Ich habe für die Aufnahme des Bildschirms jetzt einfach Windows 10 dieses Gaming Center ... und was Software zur Bearbeitung angeht da habe ich bisher nur Magix gefunden als preiswerte Lösung (Video Deluxe, das mir nicht gefällt, aber Magix hat wohl VEGAS übernommen und das Video Studio macht einen guten Eindruck aber erschlägt einen etwas


----------



## mrBrown (27. Okt 2020)

kneitzel hat gesagt.:


> Mit dem Klang der Stimme bin ich extrem unzufrieden und da muss ich noch mit der Software mehr spielen.


Amazon Polly nehmen, dann bist du zwar trotzdem unzufrieden aber es ist immerhin nicht deine eigene Stimme und du kannst ein "Polly wants a cracker" einbauen


----------



## sascha-sphw (27. Okt 2020)

Ich habe die Adobe CC, daher kann ich Premiere für meine Videos nehmen. Ich bin damit ganz zufrieden, ob ich mir das aber für private zwecke zulegen würde kann ich nicht sagen, da ich noch keine andere Video-Software verwendet habe und daher keinen Vergleich habe.


----------



## kneitzel (27. Okt 2020)

mrBrown hat gesagt.:


> Amazon Polly nehmen, dann bist du zwar trotzdem unzufrieden aber es ist immerhin nicht deine eigene Stimme und du kannst ein "Polly wants a cracker" einbauen


Kenne ich bisher nicht, werde ich mir einmal anschauen... Wobei ich ja hoffe, dass ich da mit Equalizer und / oder Filtern irgendwas machen kann ... wobei was machen nicht sein sollte: Audio Spur markieren und löschen 


sascha-sphw hat gesagt.:


> Ich habe die Adobe CC, daher kann ich Premiere für meine Videos nehmen. Ich bin damit ganz zufrieden, ob ich mir das aber für private zwecke zulegen würde kann ich nicht sagen, da ich noch keine andere Video-Software verwendet habe und daher keinen Vergleich habe.


Danke für den Hinweis - werde ich einmal testen. Wobei 25€ / Monat schon eine gewisse Größenordnung ist, die ich eigentlich nicht ausgeben wollte. Denn irgendwie ist meine Erwartungshaltung eher so, dass eine zweistellige Anzahl Follower schon ein unerwarteter Erfolg wäre ... Das Thema, das ich behandle, hat ja nur eine relativ kleine Zielgruppe....


----------



## mrBrown (27. Okt 2020)

kneitzel hat gesagt.:


> Kenne ich bisher nicht, werde ich mir einmal anschauen...


War eigentlich nur Spaß, ist die Text-to-Speech-Engine von Amazon


----------



## kneitzel (27. Okt 2020)

mrBrown hat gesagt.:


> War eigentlich nur Spaß, ist die Text-to-Speech-Engine von Amazon


Die bieten da aber schon einiges - fand ich recht interessant. Aber ich stelle es mir sehr schwer vor, da alles zu synchronisieren. Die Kosten sind auch nicht so wild nach dem was, ich da bisher so gesehen habe.

Und es würde verhindern, dass ich alles wirklich 100 Mal aufnehme ... Irgendwas passiert immer:
- Ich verhaspel mich ... 
- Mein Hund findet etwas zum anbellen ...
- Ein LKW fährt an meinem Arbeitszimmer vorbei ...
- Meine Katze meint, dass sie jetzt auf meiner Tastatur liegen muss ...
- ...

Ich verstehe also, warum es gut schallisolierte Tonstudios gibt und wieso die da dann den Text Karaokemäßig auf Bildschirmen vorspielen ... Ich habe nur einen Monitor und der wird aufgenommen und ich rede frei Schnauze ... und das halt 100 Mal 

Aber ich habe jetzt die Aufteilung des einen Videos in 4 Videos beschlossen und da auch ein erstes Video erstellt mit dem ich jetzt etwas experimentiere ... Musik leise in den Hintergrund könnte es harmonisieren ... und dann halt mal schauen, was für Audio Effekte ich alles anwenden kann


----------



## kneitzel (28. Okt 2020)

Als kleines Update bezüglich dem, was ich so verbreche:





Bezüglich Videoschnitt habe ich mich auf VEGAS Movie Studio festgelegt. Tonbearbeitung habe ich noch keine wirkliche Lösung - da habe ich aber als Option nun das kostenlose Audacity portable und das Sound Forge Audio Studio zur Auswahl. Da habe ich aber noch keine wirkliche Lösung für Rauschen und besser Stimmlage gefunden.

Adobe Premiere war genial - die hatten da paar Checkboxen und da hatte ich dann eine für Rauschen und eine zur Verbesserung der Stimme und schon war alles top .. aber >20€ pro Monat ist mir dann doch erst einmal etwas zu viel - das ist im ersten Jahr das doppelt von dem, was ich jetzt einmalig bezahlt habe.

Feedback evtl. direkt an mich statt hier im Thread. Mir ist vom Inhalt klar: Da ist jetzt noch nichts wirklich enthalten - halt erst einmal die Java Installation (über die ja schon einige stolpern mit 8er JRE und so ...)

Aber das was ich ursprünglich in einem Video haben wollte ist nun auf 3 aufgeteilt - git / gradle / maven kommt als zweites und IntlliJ Einführung als Drittes ... Und dann geht es endlich wirklich mit JavaFX und dem SceneBuilder los!


----------



## kneitzel (28. Nov 2020)

Also das YT-Video aus dem letzten Beitrag werde ich dann in Kürze löschen. Es gibt bereits ein paar andere in dem JavaFX Kanal, wobei ich mit der Qualität bei den vorhandenen Videos immer so meine Probleme hatte ...

Auch wenn es etwas Off Topic ist - es war aber etwas Thema hier und daher gebe ich nur kurz meine Erfahrungen in Kürze zum Besten:

a) Mikrofon: Ich hatte mir eigentlich schon ein recht gutes Mikrofon besorgt, welches mit XLR Stecker daher kommt. Das ist aber ein Kondensator Mikrofon und das will eigentlich mit 48V angesprochen werden. Ansonsten ist es extrem leise und wird dann natürlich verstärkt -> schlechte Qualität, viel Rauschen, .... Was relativ gute Qualität liefert bezüglich Sprache sind die üblichen Headsets. Wenn man es mit Kondensator Mikrofon haben möchte, dann ist das auch kein Thema - dazu gibt es dann Geräte, die auch die 48V geben können. (Ich habe von Steinberg das UR22 mkII besorgt). Die Qualität ist super - ich war positiv überrascht. Da kommt dann auch ein Headset nicht mehr ran finde ich ...
=> Das ist also das, was ich jedem, der an sowas Interesse hat, raten kann.

b) Software: Ich war zuletzt unter Linux unterwegs mit OBS Studio für die Aufnahme, Audacity zur Audio Nachbearbeitung und kdenlive für den Schnitt. Aber mit der besseren Hardware bin ich jetzt auch wieder zurück bei Windows OBS Studio bleibt, Audiobearbeitung und Videoschnitt sind aber jetzt kommerzielle Produkte im Einsatz. Die Open Source Software ist aber auch gut und für die Erstellung von einfachen Videos mehr als ausreichend.

Das einfach nur zu den Meta-Daten, die mich in den letzten Wochen extrem viel beschäftigt haben. Und Danke an alle, die mir mit Tipps und Tricks weiter geholfen haben - auch außerhalb des Forums.

Links zu YT werde ich hier im Dezember posten, wenn da noch etwas mehr zustande gekommen ist - ich hoffe, dass nach der Lösung diverser Probleme nun keine Show Stopper mehr aufkommen ...


----------

