Kotlin DSL
webforJ bietet eine Kotlin Domänenspezifische Sprache, oder DSL, die es Ihnen ermöglicht, UIs mit prägnanter, typsicherer Syntax zu erstellen. Anstelle von imperativem Java-Code schreiben Sie deklarativen Code, der wie eine Beschreibung Ihrer UI-Struktur aussieht.
FlexLayout layout = new FlexLayout();
layout.setDirection(FlexDirection.COLUMN);
layout.setSpacing("10px");
TextField name = new TextField();
name.setLabel("Name");
name.setPlaceholder("Ihr Name");
layout.add(name);
Button submit = new Button("Absenden", ButtonTheme.PRIMARY);
submit.onClick(e -> handleSubmit());
layout.add(submit);
flexLayout {
direction = FlexDirection.COLUMN
styles["gap"] = "10px"
textField("Name", placeholder = "Ihr Name")
button("Absenden", ButtonTheme.PRIMARY) {
onClick { handleSubmit() }
}
}
Die DSL nutzt Kotlin-Erweiterungsfunktionen, Lambdas mit Empfängern und Standardparameter, um eine natürliche Builder-Syntax zu schaffen. Komponenten nisten in einander, die Konfiguration erfolgt in Blöcken, und der Compiler erfasst strukturelle Fehler vor der Laufzeit.
Einrichtung
Es ist keine separate Kotlin-Installation erforderlich. Maven verwaltet die Kompilierung über das Kotlin Maven-Plugin, sodass jedes Projekt, das bereits mit Maven gebaut wird, Kotlin-Unterstützung durch Anpassung der Abhängigkeiten und Plugin-Konfiguration hinzufügen kann.
Abhängigkeiten
Fügen Sie das webforJ Kotlin DSL-Modul und die Kotlin-Standardbibliothek zu Ihrer pom.xml hinzu:
<dependency>
<groupId>com.webforj.kotlin</groupId>
<artifactId>webforj-kotlin</artifactId>
<version>${webforj.version}</version>
</dependency>
<dependency>
<groupId>org.jetbrains.kotlin</groupId>
<artifactId>kotlin-stdlib-jdk8</artifactId>
<version>${kotlin.version}</version>
</dependency>
Wenn Sie planen, Tests in Kotlin zu schreiben, fügen Sie auch die Kotlin-Testabhängigkeit hinzu. Es integriert sich mit JUnit:
<dependency>
<groupId>org.jetbrains.kotlin</groupId>
<artifactId>kotlin-test</artifactId>
<version>${kotlin.version}</version>
<scope>test</scope>
</dependency>
Kotlin Maven-Plugin
Fügen Sie das Kotlin Maven-Plugin hinzu, um sowohl Ihre Kotlin- als auch Ihre Java-Quellen zu kompilieren. Die untenstehende sourceDirs-Konfiguration ermöglicht es, dass Kotlin- und Java-Dateien im selben Projekt coexistieren:
<plugin>
<groupId>org.jetbrains.kotlin</groupId>
<artifactId>kotlin-maven-plugin</artifactId>
<version>${kotlin.version}</version>
<executions>
<execution>
<id>compile</id>
<phase>compile</phase>
<goals>
<goal>compile</goal>
</goals>
<configuration>
<sourceDirs>
<sourceDir>src/main/java</sourceDir>
<sourceDir>target/generated-sources/annotations</sourceDir>
<sourceDir>src/main/kotlin</sourceDir>
</sourceDirs>
</configuration>
</execution>
<execution>
<id>test-compile</id>
<phase>test-compile</phase>
<goals>
<goal>test-compile</goal>
</goals>
<configuration>
<sourceDirs>
<sourceDir>src/test/java</sourceDir>
<sourceDir>target/generated-test-sources/test-annotations</sourceDir>
<sourceDir>src/test/kotlin</sourceDir>
</sourceDirs>
</configuration>
</execution>
</executions>
<configuration>
<jvmTarget>${maven.compiler.target}</jvmTarget>
</configuration>
</plugin>
Mit diesen Ergänzungen kompiliert mvn compile die Kotlin-Quellen neben Java. Kotlin-Dateien können in src/main/kotlin oder src/main/java abgelegt werden, und das Plugin verwaltet beides.
Kotlin wird in JVM-Bytecode kompiliert, sodass es zusammen mit bestehendem Java-Code funktioniert. Sie können von Java-Klassen aus DSL-erstellte Kotlin-Komponenten verwenden, Standard-Java-Komponenten in DSL-Blöcken mit add() einfügen und Kotlin- und Java-Dateien im selben Projekt mischen.
Themen
Die folgenden Themen behandeln die Verwendung der DSL sowie deren Erweiterung um benutzerdefinierte Komponenten oder Kompositionen, die Sie erstellen.
📄️ Using the DSL
Die Kotlin DSL bietet Builder-Funktionen für webforJ-Komponenten. Jede Funktion erstellt eine Komponente, fügt sie einem übergeordneten Container hinzu und führt einen Konfigurationsblock aus. Diese Seite behandelt die Muster und Konventionen, die Sie beim Erstellen von UIs mit der DSL verwenden werden.
📄️ Extending the DSL
Die Kotlin DSL ist erweiterbar und ermöglicht die Hinzufügung von DSL-Funktionen für benutzerdefinierte Komponenten oder Bibliotheken von Drittanbietern. Sie können zusammengesetzte Komponenten erstellen, die die DSL intern verwenden.
Kotlin für Java-Entwickler
Neu in Kotlin? Hier sind einige der wichtigsten Sprachmerkmale, auf die die DSL angewiesen ist.
Nullsicherheit
Kotlin unterscheidet zwischen nullable und non-nullable Typen zur Kompilierzeit:
// Java - jeder Verweis kann null sein
String name = null;
// Kotlin - explizite Nullbarkeit
var name: String? = null // Nullable, kann null sein
var safeName: String = "value" // Non-null, der Compiler erzwingt dies
// Sicherer Aufrufoperator - gibt null zurück, wenn name null ist
println(name?.length)
// Elvis-Operator - bietet Standardwert, wenn null
println(name ?: "Standardwert")
Erweiterungsfunktionen
Kotlin ermöglicht es Ihnen, bestehenden Klassen Methoden ohne Vererbung hinzuzufügen:
// Java-Ansatz - statische Utility-Klasse
public class StringUtils {
public static String addExclamation(String input) {
return input + "!";
}
}
String result = StringUtils.addExclamation("Hallo");
// Kotlin-Ansatz - Erweiterungsfunktion
fun String.addExclamation(): String = this + "!"
val result = "Hallo".addExclamation() // Liest sich wie ein Methodenaufruf
Die DSL verwendet Erweiterungsfunktionen, um Builder-Methoden zu Komponenten hinzuzufügen.
Lambdas und Trailing Lambda-Syntax
Kotlin-Lambdas sind prägnanter als die von Java, und wenn eine Lambda der letzte Parameter ist, kann sie außerhalb der Klammern stehen:
// Java
button.addClickListener(e -> System.out.println("Geklickt"));
// Kotlin - Lambda als letzter Parameter geht außerhalb der Klammern
button.onClick { println("Geklickt") }
// Mit explizitem Parameter
button.onClick { event -> println("Geklickt: $event") }
Diese Trailing Lambda-Syntax macht DSL-Blöcke möglich.
Standardparameter
Kotlin-Funktionen können Standardparameterwerte haben, wodurch die Notwendigkeit für überladene Methoden reduziert wird:
// Java - mehrere Konstruktoren benötigt
public Button() {}
public Button(String text) {}
public Button(String text, ButtonTheme theme) {}
// Kotlin - eine Funktion mit Standardwerten
fun button(
text: String = "",
theme: ButtonTheme = ButtonTheme.DEFAULT,
block: Button.() -> Unit = {}
): Button