Události¶
Zásuvné moduly reagují na dění v editoru prostřednictvím IEventBus. Události jsou obyčejné
struktury definované v PluginEvents.h:
| Událost | Data |
|---|---|
DocumentOpened |
DocumentId, std::filesystem::path |
DocumentAboutToClose |
DocumentId — uživatel zavírá dokument a zavření je jisté; publikuje se těsně předtím, než zmizí jeho poslední zobrazení, dokud jde dokument ještě celý přečíst. Ne při ukončení programu. Jen nativní moduly; viz níže |
DocumentClosed |
DocumentId |
DocumentSaved |
DocumentId |
DocumentPrinted |
DocumentId, pages — publikuje se poté, co tisková úloha dorazila k zařízení (Soubor ▸ Vytisknout, nebo Tisk uvnitř náhledu); pages počítá vytištěné stránky dokumentu, což je při zvoleném výběru či rozsahu stránek méně, než jich dokument má. Zrušené okno nepublikuje nic. Zatím pouze zásuvné moduly v C++ |
DocumentAboutToSave |
DocumentId, path — synchronní, buffer je stále upravitelný (ořezání bílých znaků, přidání závěrečného konce řádku); žádná okna |
DocumentEncodingChanged |
DocumentId, DocumentEncoding — změnilo se kódování, v němž hostitel dokument zapíše zpět (soubor byl právě rozpoznán, nebo bylo zavoláno setDocumentEncoding) |
DocumentLineEndingChanged |
DocumentId, LineEnding — změnilo se zakončení řádků, které dokument používá (soubor byl právě přečten či znovu načten, při uložení se uplatnilo end_of_line z .editorconfig, nebo bylo zavoláno setLineEnding) |
DocumentModifiedChanged |
DocumentId, modified — přehodil se příznak čistý/změněný (nikoli při každém stisku klávesy) |
TextChanged |
DocumentId, pos, addedBytes, removedBytes |
SelectionChanged |
DocumentId |
ActiveDocumentChanged |
DocumentId |
HostWindowShown |
(žádná) — jednou za běh, poté co je první snímek na obrazovce; naplánujte od ní pomalou práci při spuštění |
SettingsChanged |
scope — "" = v celém editoru, "plugins/<id>" = byla uplatněna stránka tohoto modulu |
WorkspaceRootChanged |
root (prázdné = složka zavřena) — publikuje modul Pracovní prostor |
WorkspaceFilesChanged |
files[] z {path, displayPath} — publikuje modul Pracovní prostor |
ThemeChanged |
variant ("light" / "dark" / "") |
AppAboutToQuit |
(žádná) |
CommandShortcutChanged |
commandId, sequence (nová přenositelná kombinace; "" = bez vazby) |
MarginClicked |
DocumentId, line, margin (EditorMargin::Symbol), modifiers — kliknutí levým tlačítkem do sloupce záložek editoru, při každém takovém kliknutí; viz Značky řádků |
Zásuvné moduly mohou události i publikovat (ctx.events().publish(e)) — právě tak modul Pracovní
prostor rozhlašuje WorkspaceRootChanged / WorkspaceFilesChanged, aby je Najít v souborech a
Paleta příkazů mohly konzumovat.
Jeden dokument, jedno id¶
DocumentId pojmenovává dokument, nikoli panel. Rozdělit dokument ukazuje jeden soubor ve
dvou panelech a oba panely nesou totéž DocumentId, takže:
DocumentOpenedse publikuje jednou na soubor — rozdělení nepublikuje nic;DocumentClosedse publikuje, teprve když se zavře poslední zobrazení dokumentu, takže zavření jednoho panelu nikdy nestrhne stav, který ten druhý ještě potřebuje;activeDocument()odpoví tímto jedním id, ať je vpředu kterýkoli panel, aopenDocuments()dokument vypíše jednou.
Záměrně neexistuje žádná událost na panel ani žádný způsob, jak se zeptat, který panel je aktivní: panely jsou věcí hostitele a vše, co může zásuvný modul pozorovat — text, kurzor, výběr, kódování, konec řádků, stav změněno — patří dokumentu, který panely sdílejí.
DocumentAboutToClose¶
Publikuje se jednou pro každý dokument, bezprostředně předtím, než zmizí jeho
poslední zobrazení, když je zavření jisté — případný dotaz na uložení byl
zodpovězen a nebyl zrušen. Uvnitř obslužné rutiny je dokument ještě celý:
text(), filePath(), caret(), bookmarkedLines() i kódování odpovídají.
Potom následuje úklid a nakonec DocumentClosed. Publikuje ji každý způsob
zavření karty (Zavřít, Zavřít vše, Zavřít ostatní / Zavřít vpravo, kliknutí
prostředním tlačítkem, Zavřít složku, closeDocument() volané modulem),
včetně dokumentů bez názvu; zavření jednoho panelu dokumentu, který je ještě
zobrazen v jiném, ne.
Ukončení programu ji nepublikuje. Aplikace jednou publikuje
AppAboutToQuit, dokud jsou všechny dokumenty ještě otevřené, a žádné
události zavření jednotlivých dokumentů: modul, který si mezi relacemi
uchovává stav dokumentů, projde ve své obslužné rutině AppAboutToQuit
seznam openDocuments(). DocumentAboutToClose proto vždy znamená »tento
dokument se zavírá«, nikdy »program končí«.
Obslužné rutiny běží synchronně, uprostřed zavírání: buďte rychlí, nezobrazujte dialogová okna a s množinou dokumentů zacházejte jen pro čtení — neotevírejte, nezavírejte ani neaktivujte dokumenty a neupravujte text zavíraného dokumentu.
Je záměrně jen nativní: doručení modulům v Pythonu je asynchronní, takže by se tam slib »ještě jde přečíst« nedal dodržet, a událost se jim nenabízí (viz Události v Pythonu).
CommandShortcutChanged¶
CommandShortcutChanged se spustí, když se změní účinná zkratka příkazu — přemapování
uživatelem v Mapování klávesových zkratek, import či obnovení mapy kláves, nebo zapnutí či zrušení
potlačení při konfliktu. Příkazy vázané na nabídku nepotřebují nic (hostitel jejich akci přiřadí
znovu); příkazy registrované se scope = command_scope::kPluginWindow odebírají událost a
posloupnost znovu uplatní na své vlastní widgety (viz Příkazy a nabídky).
Odebírání¶
subscribe je šablona vracející Subscription (RAII). Udržujte odběr naživu jako člen tak
dlouho, jak chcete, aby se zavolání spouštělo; jeho zničením odběr skončí.
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
Každý Subscription držte jako člen modulu, aby se všechna zavolání ve shutdown() strhla
automaticky.