Aller au contenu

Événements

Les plugins réagissent à l'activité de l'éditeur via IEventBus. Les événements sont de simples structs définis dans PluginEvents.h :

Événement Charge utile
DocumentOpened DocumentId, std::filesystem::path
DocumentAboutToClose DocumentId — l'utilisateur ferme le document et la fermeture est certaine ; publié juste avant la disparition de sa dernière vue, tant qu'il est encore entièrement lisible. Pas à la sortie du programme. Plugins natifs uniquement ; voir plus bas
DocumentClosed DocumentId
DocumentSaved DocumentId
DocumentPrinted DocumentId, pages — publié une fois qu'un travail d'impression a atteint le périphérique (Fichier ▸ Imprimer, ou Imprimer depuis l'aperçu) ; pages compte les pages du document imprimées, moins que le document n'en a lorsqu'une sélection ou une plage de pages a été choisie. Une boîte de dialogue annulée ne publie rien. Extensions C++ uniquement pour l'instant
DocumentAboutToSave DocumentId, path — synchrone, tampon encore modifiable (rogner les espaces, ajouter la dernière ligne) ; pas de dialogues
DocumentEncodingChanged DocumentId, DocumentEncoding — l'encodage dans lequel l'hôte réécrira le document a changé (fichier tout juste identifié, ou setDocumentEncoding appelé)
DocumentLineEndingChanged DocumentId, LineEnding — la fin de ligne utilisée par le document a changé (fichier tout juste lu ou rechargé, end_of_line d'un .editorconfig appliqué à l'enregistrement, ou setLineEnding appelé)
DocumentModifiedChanged DocumentId, modified — le drapeau propre/modifié a basculé (pas à chaque frappe)
TextChanged DocumentId, pos, addedBytes, removedBytes
SelectionChanged DocumentId
ActiveDocumentChanged DocumentId
HostWindowShown (aucune) — une fois par exécution, après la première image à l'écran ; planifiez ici le travail de démarrage lent
SettingsChanged scope — "" = tout l'éditeur, "plugins/<id>" = la page de cette extension a été appliquée
WorkspaceRootChanged root (vide = dossier fermé) — publié par l'extension Espace de travail
WorkspaceFilesChanged files[] de {path, displayPath} — publié par l'extension Espace de travail
ThemeChanged variant ("light" / "dark" / "")
AppAboutToQuit (aucune)
CommandShortcutChanged commandId, sequence (nouvelle combinaison portable ; "" = non lié)
MarginClicked DocumentId, line, margin (EditorMargin::Symbol), modifiers — un clic gauche dans la colonne des signets d'un éditeur, à chaque clic de ce type ; voir Marqueurs de ligne

Les extensions peuvent aussi publier des événements (ctx.events().publish(e)) — c'est ainsi que l'extension Espace de travail diffuse WorkspaceRootChanged / WorkspaceFilesChanged pour Rechercher dans les fichiers et la palette de commandes.

Un document, un identifiant

Un DocumentId désigne un document, pas un volet. Diviser le document affiche un même fichier dans deux volets, et les deux portent le même DocumentId, donc :

  • DocumentOpened est publié une fois par fichier — la division ne publie rien ;
  • DocumentClosed n'est publié que lorsque la dernière vue du document se ferme : fermer un volet ne démonte jamais un état dont l'autre a encore besoin ;
  • activeDocument() répond avec cet identifiant unique quel que soit le volet au premier plan, et openDocuments() liste le document une seule fois.

Il n'existe volontairement aucun événement par volet ni moyen de demander quel volet est actif : les volets relèvent de l'hôte, et tout ce qu'une extension peut observer — texte, curseur, sélection, encodage, fin de ligne, état modifié — appartient au document, que les volets partagent.

DocumentAboutToClose

Publié une fois par document, immédiatement avant la disparition de sa dernière vue, lorsque la fermeture est certaine — une éventuelle demande d'enregistrement a reçu une réponse et n'a pas été annulée. Dans le gestionnaire, le document est encore entier : text(), filePath(), caret(), bookmarkedLines() et l'encodage répondent tous. Le démontage suit, puis DocumentClosed. Toute manière de fermer un onglet le publie (Fermer, Tout fermer, Fermer les autres / Fermer à droite, un clic milieu, Fermer le dossier, le closeDocument() d'un plugin), documents sans titre compris ; fermer un volet d'un document encore affiché dans un autre ne le publie pas.

Quitter le programme ne le publie pas. L'application publie AppAboutToQuit une seule fois, alors que tous les documents sont encore ouverts, et aucun événement de fermeture par document : un plugin qui conserve un état par document d'une session à l'autre parcourt openDocuments() dans son gestionnaire d'AppAboutToQuit. DocumentAboutToClose signifie donc toujours « ce document est en cours de fermeture », jamais « le programme se termine ».

Les gestionnaires s'exécutent de manière synchrone, au cœur de la fermeture : soyez rapide, n'affichez aucune boîte de dialogue et traitez l'ensemble des documents en lecture seule — n'ouvrez, ne fermez ni n'activez aucun document, et ne modifiez pas le texte du document en cours de fermeture.

Il est natif uniquement, par conception : la livraison aux plugins Python est asynchrone, la promesse « encore lisible » ne pourrait donc pas y être tenue, et l'événement ne leur est pas proposé (voir Événements Python).

CommandShortcutChanged

CommandShortcutChanged se déclenche quand le raccourci effectif d'une commande change — un remappage par l'utilisateur dans le mappeur de raccourcis, un import/une réinitialisation de keymap, ou une suppression de conflit qui s'active/se lève. Les commandes liées à un menu n'ont besoin de rien (l'hôte relie leur action) ; les commandes enregistrées avec scope = command_scope::kPluginWindow s'abonnent et réappliquent la séquence à leurs propres widgets (voir Commandes et menus).

S'abonner

subscribe est un template qui renvoie une Subscription (RAII). Gardez l'abonnement vivant comme membre aussi longtemps que vous voulez que le callback se déclenche ; sa destruction vous désabonne.

m_sub = ctx.events().subscribe<MTE::plugin::DocumentSaved>(
    [this](const MTE::plugin::DocumentSaved& e) {
        // react to e.id ...
    });
class IEventBus {
public:
    template <class Event>
    Subscription subscribe(std::function<void(const Event&)> cb);
    // Forwards to a type-erased subscribeRaw(std::type_index, ...) internally.
};

Tip

Conservez chaque Subscription comme membre du plugin afin que tous les callbacks soient démontés automatiquement dans shutdown().