Français
GitHub
Thème

Interface de bureau pour Java

Des applications de bureau en Java, dessinées de zéro.

Limn dessine ses propres pixels. Widgets, mise en page, texte, graphiques, médias et une vue 3D, en une dépendance, sans Swing, sans JavaFX et sans boîte à outils native en dessous.

JDK 17 · Windows, macOS, Linux · Apache-2.0

Construit au grand jour avec Claude Code : Claude l’a écrit, des personnes l’ont dirigé et vérifié. Ce qu’il a coûté à construire est déjà payé : vous n’avez pas à le payer une seconde fois. Comment Limn est fait

L’application de démonstration, rendue par Limn pendant cette compilation.
L’application de démonstration, rendue par Limn pendant cette compilation.
L’application de démonstration, rendue par Limn pendant cette compilation.

Essayez tout de suite

La démo et l’éditeur de thèmes, directement depuis Maven Central. Rien à cloner ; jbang télécharge un JDK si vous n’en avez pas. JBang résout la version la plus récente une seule fois et la conserve : ajoutez --fresh pour en prendre une plus récente.

# la vitrine
jbang demo@limn-toolkit/limn-toolkit
# l’éditeur de thèmes
jbang theme-editor@limn-toolkit/limn-toolkit
# la vitrine
jbang --java-options=-XstartOnFirstThread demo@limn-toolkit/limn-toolkit
# l’éditeur de thèmes
jbang --java-options=-XstartOnFirstThread theme-editor@limn-toolkit/limn-toolkit

Cinq minutes

Une dépendance et une méthode main

Pas de langage de balisage, pas de processeur d’annotations, pas de greffon de build. Ajoutez le backend, qui apporte la boîte à outils avec lui, écrivez du Java ordinaire, et vous avez une fenêtre.

Lire le guide d’installation
build.gradle.kts
dependencies {
    implementation("io.github.limn-toolkit:limn-backend-lwjgl:1.0.0")
}
pom.xml
<dependency>
  <groupId>io.github.limn-toolkit</groupId>
  <artifactId>limn-backend-lwjgl</artifactId>
  <version>1.0.0</version>
</dependency>
Main.java
import limn.backend.Backend;
import limn.backend.NativeWindow;
import limn.backend.WindowConfig;
import limn.backend.lwjgl.LwjglBackend;
import limn.components.Button;
import limn.components.Label;
import limn.scene.Insets;
import limn.scene.Scene;
import limn.scene.layout.Column;
import limn.scene.layout.Padding;

/** A window with a label and a button that closes it. */
public final class HelloWindow {

    public static void main(String[] args) {
        // macOS needs -XstartOnFirstThread on the JVM command line; it is macOS-only and a
        // JVM elsewhere given it will not start.
        try (Backend backend = new LwjglBackend()) {
            NativeWindow window = backend.createWindow(
                    WindowConfig.of("Hello, Limn", 480, 320));

            Column column = new Column();
            column.gap(12);
            column.add(new Label("A window, drawn by Limn."));
            column.add(new Button("Close").onAction(window::requestClose));

            Scene scene = new Scene(new Padding(Insets.all(24), column));
            scene.bind(window);

            backend.runEventLoop();
        }
    }
}

Ce que vous obtenez

Un ensemble de composants que vous n’avez pas à écrire

Boutons, champs, listes, tableaux, arborescences, sélecteurs de date, onglets, menus, boîtes de dialogue, cartes, panneaux divisés, un sélecteur de couleur, des graphiques en barres, en courbes et en anneau, et une liste virtualisée où un million de lignes coûte autant que vingt. Chacun lit sa couleur, sa forme et sa densité dans le thème : rien n’est figé dans le code, et un mode compact tient en une ligne. Au-delà de ses fenêtres, une application imprime sur papier ou en PDF, place une icône dans la zone de notification, met ses menus dans la barre des menus de macOS et échange du contenu avec d’autres programmes par glisser-déposer.

Les voir tous
Button
Button
ComboBox
ComboBox
Slider
Slider
SegmentedControl
SegmentedControl
Checkbox and switch
Checkbox and switch
Spinner
Spinner

Une mise en page qui tient dans la tête

Six widgets et un marqueur : une colonne empile, une rangée répartit, un wrap passe à la ligne quand la largeur manque, une grille aligne les cellules dans les deux sens, une pile superpose, la marge intérieure met en retrait, et Expanded désigne qui prend l’espace restant. Opacity et Transform estompent, déplacent, agrandissent et font pivoter une partie de la fenêtre sans déranger la mise en page autour. Aucun solveur de contraintes à configurer, aucun gestionnaire de mise en page à installer.

Lire le guide de mise en page
Une fenêtre mise en page avec Limn
Une fenêtre mise en page avec Limn
Une fenêtre faite d’une colonne, d’une rangée, d’un séparateur et d’un Expanded.

Des formulaires sans framework

Un champ est un widget, une règle de validation est un écouteur, et soumettre est un appel de méthode. Rien à lier, rien à enregistrer, et des états de validation qui recolorent un champ à l’instant où l’utilisateur le corrige.

Lire le guide des formulaires
Un formulaire construit avec Limn
Un formulaire construit avec Limn
Libellés, validation, un choix et la rangée d’actions.

Tableaux, arbres et dates, déjà construits

Un tableau, ce sont des colonnes typées sur la liste que possède votre application, triée par le toolkit ou par votre serveur, avec un pied qui additionne. Un arbre est un plan sur des enfants que vous fournissez, et une ligne peut promettre des enfants avant de pouvoir les nommer. Un champ de date saisit une date ISO dans le calendrier du lecteur lui-même, et un sélecteur de date ouvre une grille du mois derrière lui.

Lire le guide des listes
Un tableau, un arbre et deux widgets de date dans une fenêtre Limn
Un tableau, un arbre et deux widgets de date dans une fenêtre Limn
Un tableau, un arbre, un champ de date et un sélecteur de date dans une fenêtre.

La vidéo et la 3D sont aussi des widgets

Une vue 3D à matériaux physiquement réalistes et un lecteur vidéo, composés comme des widgets ordinaires : une vue défilante les rogne, une pile dessine par-dessus, et ils participent à la mise en page comme un libellé.

Lire le guide des médias
La vue 3D de Limn
La vue 3D de Limn
La vue 3D, intégrée à une fenêtre ordinaire.

Pour tout le monde

Toutes les langues, et tous les lecteurs d’écran

Dans les langues de vos utilisateurs

Latin, grec, cyrillique et CJC se mêlent dans une même chaîne, et une police est choisie pour chaque segment d’une même écriture. L’arabe, l’hébreu, la devanagari et le thaï sont façonnés correctement — lettres liées, ligatures, diacritiques — et une langue de droite à gauche reflète toute la fenêtre : lignes, marges, barres de défilement, flèches. Les méthodes de saisie composent dans le champ, et l’édition avance par graphème.

Lire le guide du texte
Le même écran capturé en japonais, chinois simplifié, coréen et russe, assemblé en une seule fenêtre.
Le même écran capturé en japonais, chinois simplifié, coréen et russe, assemblé en une seule fenêtre.
Le même écran, capturé en quatre langues pendant cette compilation.

Lu à voix haute, dans ces mêmes langues

Un lecteur d’écran sous Windows, VoiceOver sous macOS et Orca sous Linux lisent une fenêtre Limn par l’API d’accessibilité de chaque plate-forme, sans code de plate-forme dans votre application. Chaque contrôle se décrit avec son rôle, son nom et son état, dans la langue d’affichage de l’interface. Nommer un contrôle, c’est un appel.

Lire le guide d’accessibilité
  1. heading“Create your account”
  2. label“Full name”
  3. text field“Full name”label · focusable, editable, required
  4. label“12 / 40”
  5. label“Email”
  6. text field“Email”label · focusable, editable, invalid, required
  7. label“Enter an address like ada@example.com”
  8. label“Password”
  9. password field“Password”label · focusable, editable, password
  10. label“At least 12 characters”
  11. label“Plan”
  12. combo box“Plan”label · focusable, expandable, has-popup
  13. switch“Email me release notes”focusable, checked
  14. separatorhorizontal
Le formulaire ci-dessus, tel qu’un lecteur d’écran en est informé, capturé pendant cette compilation.

Votre identité, pas celle du toolkit

Votre application doit ressembler à votre produit, pas à la bibliothèque qui l'a produite. Un thème est une donnée brute (chaque couleur, le rayon des angles, le pas de taille dont hérite chaque contrôle), et un appel le remplace à l'exécution. Chargez la police de votre marque depuis un fichier qui vous appartient : il ne reste rien de l'apparence du toolkit.

Comment fonctionne la thématisation
Le même écran dense de contrôles rendu sept fois côte à côte, chaque bande dans une palette, un pas de taille et une police différents.

Les mêmes composants, sept thèmes

Survolez une colonne pour voir son thème sur tout l’écran.Touchez une colonne pour voir son thème ; balayez de côté pour changer.

Un écran, sept thèmes. Le code derrière chaque bande est identique.

Au grand jour

Comment Limn est fait

Le code de Limn est écrit par Claude, le modèle d’Anthropic, dans Claude Code, et il est dirigé et vérifié par des personnes. Nous le disons d’emblée parce que vous voudriez le savoir.

Dirigé signifie que chaque décision de conception est un document écrit dans docs/adr, argumenté et accepté avant le code. Vérifié signifie que chaque modification passe une suite de tests plus volumineuse que le code lui-même ; que l’accessibilité a été écoutée plutôt que supposée, avec un lecteur d’écran sous Windows, VoiceOver sous macOS et Orca sous Linux lisant de vraies fenêtres ; et que le code a traversé des audits répétés de justesse, de performance et de conception d’API.

Arriver jusqu’ici a demandé des milliers d’appels au modèle et des millions de jetons générés. Selon le modèle d’estimation COCOMO II, ses plus de cent mille lignes de code, tests non compris, représentent le travail d’une équipe d’environ vingt personnes pendant plus de deux ans. Ce travail est fait. Vous pouvez bâtir dessus au lieu de le refaire.

Lire les décisions de conception

Une fenêtre à l’écran en cinq minutes

Le guide d’installation se termine par un programme qui tourne. Tout le reste, c’est le guide, la galerie de composants et la référence de l’API.