Skript-Anleitung

Schreib Lua-Skripte, die deine Sprites zeichnen und bearbeiten, führe Bibliotheksskripte und Generatoren aus und füge eigene Fenster und Menübefehle hinzu.

Skripte sind Lua-Programme, die auf dem geöffneten Sprite arbeiten. Sie steuern dieselbe Engine wie der Editor: Alles, was du von Hand an Werkzeugen, Ebenen, Frames, Cels, Tags, Slices, Tiles und Paletteneinträgen ändern kannst, kann ein Skript per Code ändern. Nutze sie, um Kunst zu erzeugen (Bäume, Steine, Texturen, Sternenfelder), um eine mühsame Bearbeitung zu wiederholen oder um den Menüs eigene Befehle hinzuzufügen.

Neu im Scripting? Dein erstes Skript führt dich durch das Schreiben und Ausführen eines Skripts. Diese Seite behandelt alles drumherum.

Das Menü Skripte

EintragFunktion
Skripte > Neues Skript...Benennt ein neues Skript und öffnet es im Bedienfeld Skripte.
Skripte > Mein Skript öffnen...Listet deine Skripte auf: Wähle eines, um es zu öffnen, oder benenne es um oder lösche es. Die letzten fünf, die du geöffnet hast, stehen im Menü darunter.
Skripte > Skriptbibliothek durchsuchen...Die Skriptbibliothek: geteilte Skripte durchsuchen, ausführen, forken und mit Herz markieren, einschließlich der offiziellen Generatoren. Siehe Die Bibliothek.
Skripte > Skriptbefehle...Installiert Menübefehle aus deinen Skripten (unten).
Skripte > Skripting-APIÖffnet die Referenz der Scripting-API in einem neuen Tab.

Jeder davon steht auch in der Befehlspalette (Ctrl+K).

Das Bedienfeld Skripte

Das Bedienfeld Skripte öffnet sich, wenn du ein Skript erstellst oder öffnest (in den Standard-Layouts rechts von der Leinwand angedockt, damit du einem Skript beim Zeichnen zusehen kannst; auf dem Handy davor). Ansicht > Bedienfelder > Skripte blendet es ein und aus, und ein Neuladen öffnet das Skript wieder, das du offen hattest (seinen zuletzt gespeicherten Entwurf). Es hat einen Code-Editor mit Lua-Hervorhebung, Vorschlägen für jede app.-Funktion beim Tippen und einer Beschreibung, wenn du auf eine zeigst. Unter dem Code zeigt ein Ausgabebereich, was das Skript ausgibt, und jeden Fehler.

Das Bedienfeld Skripte mit dem Code eines Skripts, oben die Symbolleiste und darunter die AusgabeDas Bedienfeld Skripte mit dem Code eines Skripts, oben die Symbolleiste und darunter die Ausgabe
Das Bedienfeld Skripte

Oben, von links nach rechts:

  • Der Name des Skripts. Doppelklick darauf, um das Skript umzubenennen. Ein * bedeutet ungespeicherte Änderungen; daneben steht „Entwurf“ für ein Skript, das du nicht veröffentlicht hast, oder die Version, die du bearbeitest („v2“, „v2 · bearbeitet“).
  • Privat oder Geteilt: wer das Skript in der Bibliothek sehen kann. Klick darauf, um es zu ändern.
  • Skript-API-Referenz (das Buch) öffnet die Referenz in einem neuen Tab.
  • Ausführen (die Wiedergabe-Schaltfläche) führt das Skript auf dem aktiven Sprite aus; ein Skript mit einem Konfigurationsformular fragt zuerst nach seinen Werten. Während es läuft, treten die Steuerelemente der Ausführung an seine Stelle (unten).
  • Entwurf speichern (die Diskette) speichert das Skript in diesem Browser.
  • Veröffentlichen fragt nach einem optionalen Versionshinweis, speichert dann das Skript und veröffentlicht es als neue Version.
  • Skripteinstellungen (die Regler) öffnet die Einstellungen des Skripts: seine Tags, wer es sehen kann, sein Konfigurationsformular und seine veröffentlichten Versionen.
  • Bedienfeld ausblenden schließt das Bedienfeld. Das geöffnete Skript bleibt im Menü Datei bei den Sprites aufgelistet: Wähle dort seinen Namen, um das Bedienfeld wieder anzuzeigen.

Das Skript von jemand anderem (mit Code ansehen in der Bibliothek geöffnet) ist schreibgeschützt. Seine Symbolleiste hat Forken statt Entwurf speichern und Veröffentlichen: Das kopiert es in ein neues Skript von dir, das du bearbeiten kannst.

Ausführen, Pausieren und Stoppen

Ein Skript läuft auf dem Sprite, den du gerade ansiehst, und du siehst ihm beim Zeichnen zu. Egal wie viel es ändert, ein Durchlauf ist ein Rückgängig-Schritt: Ctrl+Z nimmt den ganzen Durchlauf zurück.

Skripte haben kein Zeitlimit. Solange eines läuft, kannst du es mit seinen Steuerelementen vorzeitig beenden:

SteuerelementFunktion
Pause / FortsetzenHält das Skript dort an, wo es ist, auch mitten in einer Schleife, und macht später weiter.
StoppBeendet das Skript und behält, was es bisher getan hat.
Stopp & zurücksetzenBeendet das Skript und macht alles rückgängig, was es geändert hat.

Im Bedienfeld Skripte sind das kleine Schaltflächen in der Symbolleiste. Ein Skript, das aus der Bibliothek ausgeführt wird, bedeckt den Editor mit einem Fenster, das seinen Namen, seine Ausgabe und dieselben drei Steuerelemente zeigt, bis es fertig ist.

Wenn ein Skript fehlschlägt, zeigt die Ausgabe den Fehler; im Bedienfeld ist die Zeile hervorgehoben, in der es fehlgeschlagen ist. Ein Skript kann nicht auf einer gesperrten Ebene malen: Der Befehl wird abgelehnt, und das Skript bricht mit einem Fehler ab.

Skripte schreiben

Jede Funktion steckt in der Tabelle app. Die Scripting-API dokumentiert jede einzelne, aus dem Editor selbst erzeugt, in Abschnitten:

Ein paar Dinge, die du wissen solltest:

  • Fang mit print(app.describe()) an. app.describe() liefert die ganze Struktur des Sprites: Ebenen, Frames, Cels, Tags, Slices, die Auswahl und die aktuellen Einstellungen.
  • Einstellungen, die du weglässt, kommen vom Editor. Ein Zeichenbefehl ohne Farbe verwendet die Vordergrundfarbe; ohne Pinsel den aktuellen Pinsel; und so weiter für jede Werkzeugoption.
  • Auswahl und Symmetrie gelten nur, wenn du es verlangst. Übergib respectSelection = true, um weiter innerhalb der Auswahl zu malen, und symmetry = app.getContext().symmetry, um zu spiegeln.
  • Arbeite Pixel für Pixel in einem Image. app.getImage(layer, frame) liest ein Cel in ein Image ein, das im Skript lebt; img:getPixel und img:setPixel sind günstig, also kannst du über beliebig viele Pixel schleifen und es danach einmal mit app.putImage(layer, frame, img) zurückschreiben. Jeder Aufruf von app.* ist ein Weg zum Editor, die Methoden eines Images nicht. Bei indizierten Sprites arbeiten img:getIndex und img:setIndex mit Palettenindizes.
  • Nutze app.random für Zufall. Ein mit app.random.new(seed) erzeugter Generator liefert bei gleichem Seed dieselben Zahlen, sodass sich ein Durchlauf exakt wiederholen lässt. Auch pairs() besucht die Schlüssel einer Tabelle bei jedem Durchlauf in derselben Reihenfolge.
  • Nutze app.color für Farbmathematik. Mischen, Farbreihen und Abstufungen werden in einem wahrnehmungsbasierten Farbraum berechnet, was besser aussieht als das Mitteln von Hex-Werten.
  • Gib etwas aus, um Dinge zu prüfen. print(...) schreibt in den Ausgabebereich; Tabellen werden vollständig ausgegeben.

Dieses Beispiel streut etwa Sterne auf eine neue Ebene; ändere den Seed für einen anderen Himmel:

local layer = app.addLayer("Stars")
local frame = app.getActiveFrameId()

local rng = app.random.new(42)                        -- same seed, same stars
local colors = app.color.ramp({ "#5a6b9e", "#ffffff" }, 4)

local img = app.getImage(layer, frame)                -- the layer's pixels, inside the script
for i = 1, img.width * img.height // 40 do
  img:setPixel(rng:int(0, img.width - 1), rng:int(0, img.height - 1), rng:pick(colors))
end
app.putImage(layer, frame, img)                       -- written back as one change

Konfigurationsformulare

Ein Skript kann vor dem Ausführen nach Einstellungen fragen: Wenn du Ausführen wählst (in der Bibliothek oder im Bedienfeld Skripte), öffnet sich ein Formular mit seinen Feldern (Zahlen, Text, Kontrollkästchen, Auswahlen, Farben sowie ein Pinsel oder eine Palette aus deinen eigenen Bibliotheken), und das Skript liest, was du eingegeben hast, als Tabelle app.config. Felder können je nach früheren Auswahlen angezeigt oder ausgeblendet werden. Zufall würfelt neue Werte innerhalb der vom Autor des Skripts gewählten Bereiche, für schnelle Varianten. Die offiziellen Generatoren funktionieren alle so.

Um einem deiner Skripte ein Formular zu geben, schreib es als JSON in Konfigurationsformular (JSON) in den Einstellungen des Skripts, in der Form, die die Referenz Config forms beschreibt; die Einstellungen sagen dir vor dem Speichern, was daran nicht stimmt. Das Formular ist Teil des Entwurfs und jeder veröffentlichten Version. Ein Skript sollte trotzdem jedes Feld als optional lesen und auf eigene Voreinstellungen zurückfallen. Für Eingaben, während ein Skript läuft, öffne stattdessen ein Skriptfenster.

Skriptfenster

Ein Skript kann mit Dialog{} ein eigenes Fenster öffnen, so gebaut, wie Aseprite-Skripte sie bauen: Beschriftungen, Text- und Zahlenfelder, Regler, Kontrollkästchen, Optionsfelder, Dropdown-Listen, Farbfelder, Reihen von Farbfeldern, Schaltflächen und eine Dateiauswahl (nur kleine Textdateien).

local dlg = Dialog{ title = "Quick Fill" }
dlg:color{ id = "paint", label = "Color", color = "#3a8f4a" }
dlg:button{ id = "fill", text = "Fill layer", onclick = function()
  local layer, frame = app.getActiveLayerId(), app.getActiveFrameId()
  app.floodFill(layer, frame, 0, 0, { color = dlg.data.paint })
end }
dlg:show{ wait = false }
  • dlg:show{ wait = false } öffnet ein schwebendes Fenster, und das Skript wartet untätig, während du weiterzeichnest; jeder Tastendruck oder jede Änderung, auf die es reagiert, ist ein eigener Rückgängig-Schritt. Ohne wait = false ist das Fenster modal: Der Editor ist gesperrt, bis du es schließt.
  • Die Titelleiste des Fensters nennt das Skript und kennzeichnet es als Fenster eines Skripts, und alles darin ist einfacher Text, sodass ein Skript sein Fenster nicht als Teil des Editors ausgeben kann.
  • Das Schließen des Fensters beendet das Skript; das Stoppen des Skripts schließt seine Fenster.

Die Referenz Dialogs and commands enthält jedes Widget mit seinen Optionen.

Skriptbefehle

Ein Skript kann den Menüs des Editors Befehle hinzufügen, genau wie ein Aseprite-Plugin. Definiere eine Funktion init(plugin), die sie mit plugin:newCommand registriert:

local function mirror()
  app.flip("horizontal", app.getActiveLayerId())
end

function init(plugin)
  plugin:newCommand{ id = "mirror", title = "Mirror Layer", group = "layer", onclick = mirror }
end

Speichere das Skript, wähle dann Skripte > Skriptbefehle... und drück neben ihm auf Installieren. Der Befehl erscheint nun:

  • in dem Menü, das sein group nennt (file, file_import, edit, edit_transform, edit_fx, edit_adjustments, sprite, layer, frame, select oder view), angezeigt mit dem Namen des Skripts; ohne Gruppe unter Skripte, in einem Untermenü mit dem Namen des Skripts;
  • in der Befehlspalette;
  • in Einstellungen > Tastenkürzel..., wo du ihm ein Tastenkürzel geben kannst.

Das Ausführen des Befehls führt dein gespeichertes Skript und dann das onclick des Befehls aus, als ein Rückgängig-Schritt. Nachdem du geändert hast, welche Befehle ein Skript registriert, drück auf Neu installieren; Entfernen nimmt sie aus den Menüs. Ein Skript kann bis zu 32 Befehle hinzufügen. Installierte Befehle werden in diesem Browser gespeichert.

Um Befehle aus dem Skript von jemand anderem zu installieren, forke es zuerst in deine Skripte.

Speichern und Veröffentlichen

Deine Skripte werden wie deine Sprites in diesem Browser gespeichert und funktionieren offline. Mit Sync werden sie zusätzlich in deinem Konto und auf deinen anderen Geräten aufbewahrt.

Veröffentlichen teilt ein Skript in der Skriptbibliothek. Jedes Skript beginnt als Privat, sodass nur du es sehen kannst; wähle In der Bibliothek geteilt in seinen Einstellungen (Skripteinstellungen oder das Abzeichen Privat), um es aufzulisten. Dann gilt:

  • Entwurf speichern hält deine Änderungen privat. Wer die Bibliothek nutzt, bekommt immer deine zuletzt veröffentlichte Version, nie den Entwurf.
  • Veröffentlichen speichert den Entwurf und macht ihn mit dem Versionshinweis, den du eintippst (im Versionsverlauf angezeigt), zur nächsten nummerierten Version. Veröffentlichte Versionen ändern sich nie; veröffentliche erneut, um eine neue zu erstellen.
  • Die Einstellungen des Skripts listen jede veröffentlichte Version auf. Code ansehen öffnet eine alte schreibgeschützt, und In meinen Entwurf übernehmen kopiert sie in deinen Entwurf.
  • Ein Skript kann bis zu 3 Tags haben, die Leuten helfen, es in der Bibliothek zu finden.

Zum Veröffentlichen brauchst du ein Konto mit Sync bei pxstud.io. Skripte auszuführen, zu forken und mit Herz zu markieren (mit einem kostenlosen Konto) steht unter Die Bibliothek.

Was Skripte nicht können

Skripte laufen in einer Sandbox, daher ist das Ausführen eines Skripts von jemand anderem sicher:

  • Kein Netzwerk, keine Dateien, kein Nachladen von Code. Ein Skript kann weder das Internet noch deine Dateien erreichen (abgesehen von einer Textdatei, die du in seinem Fenster auswählst) und kann keinen anderen Code laden. Die Lua-Bibliotheken io, os und debug gibt es nicht; string, math, table, utf8 und coroutine schon.
  • Nur der geöffnete Sprite. Ein Skript bearbeitet den Sprite, auf dem du es ausgeführt hast, als ein Rückgängig-Schritt. Es kann keine Sprites öffnen, speichern, exportieren, schließen oder löschen, die Zwischenablage nicht nutzen und weder Ansicht noch Bedienfelder ändern.
  • Deine Bibliotheken nur, wenn du daraus wählst. Ein Skript sieht einen deiner gespeicherten Pinsel oder eine deiner Paletten nur dann, wenn sein Konfigurationsformular danach fragt und du sie auswählst.
  • Ein Speicherbudget. Ein Durchlauf kann nicht mehr als eine bestimmte Menge Speicher belegen: für seine Images, seine Lua-Daten, die Pixel, die er zum Sprite hinzufügt, und den Rückgängig-Schritt, den er aufbaut. Darüber hinaus wird das Skript mit einem Fehler gestoppt, der sagt, welches, und was es bisher getan hat, bleibt als ein Rückgängig-Schritt erhalten, sodass ein außer Kontrolle geratenes Skript weder den Editor zum Absturz bringen noch deine früheren Schritte aus dem Änderungsverlauf verdrängen kann.

Es gibt kein Zeitlimit; ein Skript, das außer Kontrolle gerät, lässt sich immer pausieren oder stoppen.

Die offiziellen Generatoren

Die Skriptbibliothek von pxstud.io hat einen Satz offizieller Skripte, markiert mit Offiziell: Generatoren für Verläufe, Schachbretter, Rausch-Füllungen, Ziegelwände, Kopfsteinpflaster, Holzdielen, Gras- und Wassertexturen, Blitze, Tornados, Regenbögen, Kometen, Galaxien, Planeten, Sterne, Bäume, Büsche und Felsen. Melde dich mit einem kostenlosen Konto an, öffne Skripte > Skriptbibliothek durchsuchen..., wähle Offiziell und drück bei einem auf Ausführen: Füll sein Formular aus (oder drück auf Zufall), und es zeichnet auf deinen Sprite. Fork eines, um zu lesen, wie es gemacht ist, oder um es zu ändern.