Die Sprache
Datei
Ereignisse können auch Inline-Skripte ausführen. scriptLanguage: "lua" wählt Lua auf Dateiebene; ohne Angabe gilt JavaScript. Siehe Inline-Skripte.
Eine Datei enthält in beliebiger Zahl und Reihenfolge:
| Oberste Ebene | |
|---|---|
Dialog Name { ... } |
ein Dialog mit eigener Größe (size), die App öffnet den Rahmen |
Screen Name { ... } |
der Inhalt einer Seite; Geometrie und Seite kommen von der App |
component Name : Basistyp { ... } |
ein wiederverwendbares Element |
record Name { typ feld ... } |
ein Datentyp der App, z. B. eine Zeile einer Liste |
- Kommentare:
//und/* */. - Trennung: Anweisungen enden am Zeilenende oder mit
;. Innerhalb von(),[]und? :darf man umbrechen. - Sichtbarkeit: Komponenten und Datensätze gelten für alle Dateien desselben
aura_add_ui(bzw. desselben Loader-Verzeichnisses mit Unterordnern). Die Dateinamen müssen eindeutig sein, auch über Ordner hinweg, weil der erzeugte C++-Code nach ihnen heißt.
Elemente
Typ [id] {
property: wert
Kind { ... }
}
- Typ: ein eingebauter Typ (Tabelle unten), ein Typ der App (
aura-elements.json, siehe unten) oder eine Komponente. id: Name, über den andere Ausdrücke das Element ansprechen und unter dem es im Struct für die App steht. Ohnenamewird die ID auch zumobjectName. Reserviert sindroot,parent,theme,screen,propsundself.- Kinder liegen in der Zeichenreihenfolge über den vorherigen.
| Typ | aura-ui | eigene Properties |
|---|---|---|
Item |
Node |
– |
Rect |
RectNode |
color, radius, corners: topLeft, topRight, bottomRight, bottomLeft, border: breite, farbe, gradient: oben, unten |
Text |
TextNode |
text, font: familie, größe[, gewicht], weight, color, align: left|center|right[, top|center|bottom], wrap: breite[, ausrichtung], fit: true|mindestgröße, lineHeight (QML-Faktor), letterSpacing (px), pixelSize/minimumPixelSize (px, ohne Context::fontSize), underline |
Image |
ImageNode |
source: "name.png" (Context::image) oder image: wert (ein Bild der App, Typ image), fill: stretch|crop|fit|pad, radius, corners |
Svg |
SvgNode |
source: "name.svg", fill: farbe |
Scroll |
ScrollNode |
contentHeight, contentY; mit direction: horizontal waagerecht: contentWidth, contentX. Steckt ein waagerechter in einem senkrechten, entscheidet die Richtung des Fingers |
QrCode |
QrCodeNode |
text (Inhalt), color |
Html |
HtmlNode |
text (HTML wie QML RichText), font: familie, größe, color, lineHeight, margin (documentMargin); ohne height so hoch wie der Text bei seiner Breite |
Column |
ColumnNode |
spacing, padding, align: left|center|right, justify; stapelt die sichtbaren Kinder von oben und wird so hoch wie sie (siehe Layouts) |
Row |
RowNode |
spacing, padding, align: top|center|bottom, justify, wrap: true, direction: leftToRight|rightToLeft; reiht die sichtbaren Kinder von links auf und wird so breit wie sie, bzw. von seinem rechten Rand aus |
Grid |
GridNode |
columns, spacing, padding, cell: breite, höhe; Zellen in der Größe des ersten sichtbaren Kindes (oder cell), wird so hoch wie die Zeilen |
Popover |
PopoverNode |
color, markerPos, unfold (gezeigter Teil der Höhe, 0–1; enter: unfold 0 300 linear klappt es auf); Sprechblase mit Marker oben |
Ripple |
RippleNode |
color (grau), opacity (0,4), size (200 × 200); Rückmeldung seines Elternelements: sitzt beim Drücken am Finger und pulsiert (1 ↔ 1,1, je 500 ms), wächst nach dem Tippen in 500 ms auf das Vierfache, erst dann läuft das onTap des Elternelements (ohne Animator sofort). Als letztes Kind, damit es oben liegt; das Elternelement schneidet seine Kinder ab (clip) |
TextField |
TextFieldNode (aura/ui/text_input.h) |
text (Startwert, siehe Texteingabe), font, weight, color, align, letterSpacing, pixelSize, placeholder, placeholderColor (#cccccc), masked (* je Zeichen), maxLength (Zeichen), characters (die erlaubten Zeichen, z. B. "0123456789*#"), focus: true, onChange: signal, onAccept: signal; eine Zeile mit Schreibmarke, schneidet ab und rollt mit der Schreibmarke |
Keyboard |
KeyboardNode (aura/ui/text_input.h) |
layout: "DE" (CZ, DE, DK, EN, FI, FR, NL, NO, PL, SE, SI, SK, auch klein; "alphanum": 800 × 240, Ziffern und Großbuchstaben, Backspace, OK, Abbrechen), color, radius, border, keyColor, textColor, accentColor (Umschalttasten), okColor, cancelColor, cancelText, okKey: false, onOk: signal, onCancel: signal; Bildschirmtastatur, 960 × 300, auf die eigene Größe skaliert |
Button |
ButtonNode (aura/ui/controls.h) |
text, font, weight, textColor (weiß), color (#404040), pressedColor (sonst color dunkler), radius (8), border; Taste mit Text in der Mitte, Standardgröße 200 × 60 (siehe Bausteine) |
CheckBox |
CheckBoxNode |
text, font, textColor, color (Kästchen), radius, checked, onToggle: signal; ein Tipp schaltet um |
Switch |
SwitchNode |
wie CheckBox, dazu trackColor (aus); Schiebeschalter, color (an) |
RadioButton |
RadioButtonNode |
wie CheckBox, dazu group; ein Tipp wählt ihn und nimmt die Wahl der anderen derselben Gruppe weg (ohne group: seiner Geschwister). onToggle meldet nur der neu gewählte |
ComboBox |
ComboBoxNode |
options (Liste von Texten), index (-1: keiner), placeholder, font, textColor, color, radius, border, listColor, listTextColor, selectedColor, visibleRows (6), onSelect: signal; Auswahlliste: ein Tipp öffnet die Liste darunter über der ganzen Szene (oder darüber, wenn unten kein Platz ist), ein Tipp daneben schließt sie |
Slider |
SliderNode |
value, from (0), to (1), step, color, trackColor, onChange: signal; Ziehen oder Tippen auf die Bahn |
ProgressBar |
ProgressBarNode |
value, from (0), to (1), color, trackColor, radius (halbe Höhe) |
Rive |
RiveNode |
source: "goodbye.riv" (Context::file); spielt die Standard-State-Machine des Standard-Artboards (sonst seine erste Animation) endlos über den Animator, eingepasst wie PreserveAspectFit |
WebView |
aura::webview::WebViewNode (libaura-webview) |
url, script (JavaScript, läuft in jeder Seite vor deren eigenen Skripten); Chromium über CEF, bedienbar per Touch, WebChannel zu C++ (aura.call, aura.on). Nur in Programmen mit AURA_WITH_WEBVIEW, siehe aura-webview.md |
Elementtypen der App: Was eine App selbst zeichnet, beschreibt eine aura-elements.json neben oder über den .aura-Dateien, die es benutzen:
Das folgende Beispiel beschreibt einen von der Anwendung bereitgestellten BadgeNode, keinen eingebauten AURA-Elementtyp.
{
"Badge": {
"type": "BadgeNode",
"header": "widgets/badge_node.h",
"properties": {
"color": {"type": "color"},
"label": {"type": "string", "set": "setLabel()"}
}
}
}
- Properties:
typeistnumber,string,boolodercolor. Der erzeugte Code setzt das Member gleichen Namens bzw. das ausset; endetsetauf(), ruft er die Funktion auf. - Wer sie liest:
aurac(die nächste Datei über jeder.aura-Datei, oder--elements),aura_add_ui(als Abhängigkeit), der Loader (alle im Verzeichnis),aura-viewund die VS-Code-Erweiterung (Prüfung, Vervollständigung). - Dynamischer Modus: Der Loader kennt damit die Properties, erzeugen und setzen kann er den Typ erst, wenn das Programm ihn registriert hat (
aura::ui::registerElementType). Sonst meldet er „not part of this program“ und nimmt die kompilierte Fassung.
Alle Elemente haben außerdem:
| Property | Bedeutung |
|---|---|
name |
objectName (Fernsteuerung, Logs); ohne name gilt die ID |
x, y, width, height, size: w, h |
Geometrie |
place: ... |
Anker, siehe unten |
visible, opacity, rotation, scale, clip, glow |
wie in aura-ui (clip schneidet rechteckig, wie Qt Quick; glow leuchtet weiß, z. B. glow: root.pressed) |
onTap: signal, onTap: signal(args), onTap: ignore |
löst ein Signal aus bzw. schluckt den Tap |
enabled: false |
keine Eingaben für das Element und seine Kinder (QML enabled); Bausteine blenden sich dabei ab |
grow: gewicht |
in einem Column/Row: ein Anteil am freien Platz in Richtung des Layouts (QML Layout.fillHeight/fillWidth) |
stretch: true |
in einem Column/Row: füllt quer zur Richtung (Breite bzw. Höhe), im Grid die Zelle |
minWidth, maxWidth, minHeight, maxHeight |
Grenzen für grow und stretch (0: keine) |
onSettled: signal |
eine Animation des Elements (animate:) ist angekommen, siehe Animationen |
pressSink: versatz, ms |
sinkt beim Drücken ein |
spin: ms |
dreht sich endlos im Uhrzeigersinn, eine Umdrehung in ms |
loop: eigenschaft von bis ms [easing] [pause ms], … |
pendelt endlos zwischen zwei Werten, siehe Animationen |
Text im Detail:
- Schriftfamilie: Ohne
fontgiltaura::ui::TextNode::defaultFamily, das die App beim Start setzt; leer ist es die Standardschrift der Schriftsammlung. - Schriftgröße:
fontundfit: Ngehen durchContext::fontSize()der App (Standard: unverändert).pixelSizesetzt Pixel ohne diesen Weg. - Natürliche Größe: Ein
Textohnewidth/height/sizebekommt die Größe seines Inhalts. Mitwrap: 400ist die Breite 400 und die Höhe ergibt sich aus dem Text. - Rich Text wie QML StyledText:
<b>,<br />und<font color="#rrggbb">.
Anker (place)
place: left 44, below title 30, centerY -20 wird zu aura::ui::place(node).left(44).below(*title, 30).centerY(-20) (siehe graphics.md). Die Reihenfolge zählt.
| Direktive | Bedeutung |
|---|---|
left, right, top, bottom [Abstand] |
zum Rand des Parents |
centerX, centerY [Versatz], center |
im Parent zentriert, gerundet |
below, above, rightOf, leftOf Element [Abstand] |
neben einem Element |
alignLeft, alignTop, alignBottom Element [Versatz] |
an einem Element ausgerichtet |
centerXOn, centerYOn Element |
auf die Mitte eines Elements |
Als Element zählen IDs, die im Quelltext vorher stehen (Geschwister oder Vorfahren), parent und bei wiederholten Elementen id[index], z. B. centerYOn field[0].
Layouts: Column, Row, Grid
Sie ordnen ihre sichtbaren Kinder an, sobald ein Kind hinzukommt. Ändert sich später ein Kind (über eine Bindung oder einen Neuaufbau), ordnen sie neu an. Ihre eigene Größe folgt dem Inhalt (Column: Höhe, Row von links: Breite, Grid: Höhe), sodass andere Elemente sich darauf beziehen können:
Scroll list {
size: parent.width - 4, min(len(lines), 5) * 76
contentHeight: productRows.height // nach dem Bau der Zeilen
Column productRows {
width: parent.width
repeat line, i in lines { CartRow { index: i; line: line } }
}
}
// Header: rechtsbündig
Row buttons { direction: rightToLeft; spacing: 16; size: parent.width, 60 }
// Grid layout
Grid cells { columns: columns; spacing: 10 }
Unsichtbare Kinder belegen keinen Platz. Die Kinder setzen ihre Größe selbst, die Lage in Richtung des Layouts (Column: y, Row: x, Grid: beides) vergibt das Layout.
Flexibel: Mit diesen Properties verteilt ein Layout Platz, statt nur zu stapeln:
Column {
size: 400, parent.height
padding: 20 // 1 Wert, 2 (oben/unten, links/rechts) oder 4 (oben, rechts, unten, links)
spacing: 10
align: center // quer: left, center, right (Row: top, center, bottom)
Text { text: tr("Title", "Titel") }
Scroll { grow: 1 } // nimmt die restliche Höhe
Row {
stretch: true // so breit wie die Column (ohne padding)
height: 60
justify: spaceBetween // start, center, end, spaceBetween, spaceAround, spaceEvenly
DialogButton { text: "Zurück" }
DialogButton { text: "Weiter"; grow: 1; maxWidth: 300 }
}
}
Row tags { width: 500; wrap: true; spacing: 8 } // bricht in Zeilen um (QML Flow), wird so hoch wie sie
- Länge: Hat ein Kind
growoder istjustifygesetzt, behält das Layout seine Höhe (Column) bzw. Breite (Row) und verteilt sie: erst bekommen die Kinder ohnegrowihre Größe und die Abstände, den Rest teilen sich die wachsenden Kinder nach Gewicht (begrenzt durchmin…/max…). Sonst wird es so lang wie sein Inhalt, wie bisher. - Quer: Ohne
align,stretchundpaddingauf dieser Seite behalten die Kinder ihrx(Column) bzw.y(Row), wie bisher. Sonst setzt das Layout es; ein Layout ohne Breite (Höhe) nimmt dann die des breitesten Kindes. - Inhalt folgt: Ändert ein Layout die Größe eines Elements mit
growoderstretch(oder einer Komponenten-Instanz), laufen die Properties seiner Nachfahren erneut (size: parent.width - 4,place: right), danach ordnen die Layouts darin neu an. In C++ setztNode::resize()die Größe und ruftonResized. wrap(nurRowmit Breite): Kinder in Zeilen,spacingauch zwischen den Zeilen;alignundjustifygelten je Zeile.
Ausdrücke
| Werte | Zahlen (intern double, wie in QML), "Text" (mit \n, \t, \b), Farben #rrggbb/#aarrggbb, true/false, Listen [a, b] |
| Operatoren | + - * / %, == != < > <= >=, && || !, a ? b : c; + verbindet auch Texte |
| Namen | IDs (vorher definiert), parent, eigene Geometrie (x, y, width, height, implicitWidth, implicitHeight), Schleifenvariablen, propertys des Dialogs bzw. der Komponente (auch als root.<name>) |
| Element-Werte | id.x, .y, .width, .height, .opacity, .rotation, .scale, .pressed, .implicitWidth/.implicitHeight (Text; Image: Bildgröße; Html: Höhe), .contentHeight (Scroll) |
| Datensätze | zeile.feld, liste[i].feld, root.zeile.feld |
| Listen | liste[i], len(liste), z. B. ["", "ABC", "DEF"][i] |
| Kontext | theme.<name>, screen.width, screen.height, props.bool("ID"), props.int("ID"), props.string("ID") |
| Funktionen | tr("id", "Deutsch"), str(zahl), replace(text, alt, neu), lower(text), upper(text), len(liste|text), fontSize(px) (Context::fontSize), ceil, floor, round, abs, min, max, range(n) |
Typen werden geprüft: Ein Text, wo eine Zahl stehen muss, oder ein Feld, das der Datensatz nicht hat, bricht den Build ab.
Wiederholung und Bedingung
repeat key, index in ["1", "2", "\b"] {
Item keyItem { x: index % 3 * 94; onTap: keyPressed(key) }
}
repeat i in range(6) { Rect field { x: digitsX + i * 54 } }
repeat line, i in lines { CartRow row { line: line } }
if key == "\b" { Svg { ... } } else { Text { ... } }
-
Liste: eine Liste in eckigen Klammern,
range(n), einestrings-Property oder eine Liste von Datensätzen. -
IDs in einer Wiederholung werden im Struct zu Vektoren (
std::vector<aura::ui::RectNode*> field). Außerhalb der Schleife greift man mitfield[0]darauf zu. -
IDs unter
ifsind im Structnullptr, solange der Zweig nicht gebaut ist. Properties, die auf eigene Kinder warten (siehe unten), dürfen keine Kinder unterifnennen. -
Zustand: Hängt die Liste oder die Bedingung vom Zustand ab, wird der Block bei einer Änderung neu gebaut (siehe Neuaufbau).
-
lazy:repeat p, i in photos lazy { … }baut nur die Einträge, die zu sehen sind, für lange Listen (Tausende Fotos eines Telefons):qmlScroll grid { size: parent.width, parent.height contentHeight: cells.height Grid cells { columns: 4 spacing: 10 cell: 240, 180 // Pflicht: jede Zelle gleich groß width: parent.width repeat p, i in photos lazy { PhotoCell cell { photo: p; stretch: true; onTap: pick(i) } } } }- Wo: direkt in einem
Gridmitcell: breite, höhe(für eine Listecolumns: 1), das in einem senkrechtenScrollliegt; ein Element je Eintrag, nicht in einer anderen Wiederholung. - Was gebaut ist: die Zeilen im sichtbaren Teil des
Scrollund je eine davor und danach. Beim Scrollen baut AURA die neuen Einträge und baut die anderen ab (gelöscht vor dem nächsten Bild, ihre Bindungen enden). DasGridsetzt jeden Eintrag in die Zelle seines Index und ist so hoch wie alle Zeilen,contentHeight: cells.heightstimmt also. - IDs:
ui->cellhat einen Eintrag je Listeneintrag,nullptrfür nicht gebaute. Was die App an Zellen hängt (Bilder), hängt sie inui->onRebuiltan die neu gebauten (Zellen ohne ihren Zusatz) und vergisst dabei Zeiger auf abgebaute. - Zustand: wie bei jeder Wiederholung; eine geänderte Liste behält gleiche Einträge, die anderen kommen neu, wenn sie zu sehen sind.
- Wo: direkt in einem
Reihenfolge der Properties
Pro Element gilt diese Reihenfolge, genau wie im früheren handgeschriebenen Code:
- Inhalt (Text, Farben, Schrift, …),
- die natürliche Größe von Texten,
- die Geometrie (
x,y,width,height,size,place,contentHeight) in Quelltext-Reihenfolge.
Deshalb funktioniert height: back.y - 30 - y nach place: left 44, below editBox 30.
Bezug auf eigene Kinder: Eine Property, die eine ID aus dem eigenen Teilbaum nennt, wird erst angewandt, wenn dieses Kind gebaut ist, und zwar direkt danach. Spätere Kinder sehen den Wert schon:
component PriceRow : Rect {
height: topicText.height + 12 // nach topicText
Text topicText { wrap: 290 }
Text { place: right 15, centerY } // sieht die Zeilenhöhe
}
Gedrückt-Zustand
Nennt eine Property id.pressed, wird sie neu ausgewertet, sobald sich der Zustand ändert. Mit ihr laufen alle Nachfahren von id erneut durch, damit Anker mitwandern:
Item keyItem {
onTap: keyPressed(key)
Rect face {
x: keyItem.pressed ? 5 : 0
width: parent.width - (keyItem.pressed ? 8 : 0)
Text { size: parent.width, parent.height } // folgt dem Rect
}
}
id selbst wird dabei nicht neu angeordnet, sonst würde etwa ein pressSink zurückgesetzt. In Komponenten geht auch root.pressed (Taste, Footer-Button).
Texteingabe
TextField code {
font: theme.textFont, 48
placeholder: tr("Voucher_Code", "Gutscheincode")
maxLength: 20
focus: true
size: 400, 60
onChange: codeChanged // signal codeChanged(string text)
onAccept: redeem // Enter
}
Rect ok { onTap: redeem(code.text) }
Keyboard {
layout: props.string("CurrentLanguage") // "de", "EN", ...; unbekannt: DE
place: centerX, bottom 20
onOk: redeem(code.text)
onCancel: close
}
- Fokus: Tasten gehen an das Element mit dem Fokus, sonst wie bisher an
Application::onKey. Ein Tipp auf einTextFieldgibt ihm den Fokus und setzt die Schreibmarke an die Stelle. Ein Tipp anderswo (etwa auf eine Taste der Bildschirmtastatur) lässt ihn, wo er ist.focus: truegibt ihn beim Aufbau,Node::focus()/Node::clearFocus()in C++. Ist das Element unsichtbar oder gelöscht, gehen die Tasten wieder anonKey. - Tasten: Zeichen fügen an der Schreibmarke ein (bis
maxLength), Backspace und Entf löschen, ←/→ bewegen die Schreibmarke, Enter löstonAcceptaus. Escape, Tab, ↑/↓ nimmt das Feld nicht, sie gehen weiter anonKey. Die Quellen sind die Tastatur des Fensters, die Fernsteuerung (Application::injectKey) undKeyboard(aura::ui::sendKey). text: der Startwert. Wertet die Bindung neu aus (eine andere Property des Elements hängt am Zustand), bleibt das Getippte stehen; nur ein geänderter Wert ersetzt es (bindValue). Die App liest den Text mitui->code->value()und setzt ihn mitsetValue()(ohneonChange).id.textgibt in Ausdrücken den aktuellen Text einesTextField(bzw.Text), z. B. als Argument eines Signals. Properties, diefeld.texteinesTextFieldnennen, laufen nach jedem Tippen neu (visible: len(code.text) > 0), wie bei einer Zustands-Property.- Signale:
onChange(nach jeder Änderung durch Tippen) undonAcceptgeben ein Signal mit einemstring-Parameter den Text mit, eines ohne Parameter nichts;onChange: changed(code.text)geht auch.KeyboardhatonOkundonCancel. - Tastatur: Vier Zeilen Zeichentasten mit bis zu acht Belegungen (normal, Shift, Ctrl =
*#+@, Alt =éàóund ihre Kombinationen). Shift, Ctrl und Alt bleiben an, bis man sie noch einmal tippt. Bilder braucht die Tastatur nicht, die Symbole (Backspace, Enter, Shift, Leertaste) zeichnet sie selbst. - Blinken: Die Schreibmarke blinkt im Takt von 500 ms (ohne Animation, die Hauptschleife zeichnet im Leerlauf ohnehin alle 500 ms). Für Bildschirmfotos und Tests stellt
aura::ui::TextFieldNode::blink = falsesie dauerhaft an.
Bausteine
Column {
padding: 24
spacing: 16
CheckBox agb { text: tr("Agb", "AGB gelesen"); checked: accepted; onToggle: accept } // signal accept(bool on)
Slider { from: 0; to: 100; step: 5; value: volume; onChange: setVolume } // signal setVolume(real v)
ProgressBar { value: uploaded; to: total; stretch: true }
Button { text: tr("Next", "Weiter"); color: theme.mainColor; enabled: agb.checked; onTap: next }
}
- Auswahl:
RadioButton { group: "format"; checked: format == "a"; onToggle: chooseA }für wenige, sichtbare Möglichkeiten,ComboBox { options: formats; index: chosen; onSelect: choose }(Signal mitint) für viele. - Zustand:
checked,indexundvaluesind wietextbeimTextFieldStartwerte: Was der Kunde eingestellt hat, bleibt, bis sich der gebundene Wert ändert (bindChecked,bindValue).id.checked,id.index(ComboBox) undid.valuegeben den aktuellen Stand in Ausdrücken; Properties, die sie nennen, folgen jeder Änderung durch den Kunden (enabled: agb.checked,text: str(volume.value)). - Signale:
onTogglegibt einem Signal mit einembool-Parameter den neuen Stand mit,onChangedesSlidereinemreal-Parameter den Wert (nur bei einer Änderung, auch beim Ziehen); ohne Parameter nichts.Buttonhat das gemeinsameonTap. - Aussehen: neutral grau; die App färbt sie über Properties oder eine Komponente, z. B.
component MainButton : Button { color: theme.mainColor; font: theme.textFont, 24 }.Ripple,pressSinkundglowgehen wie bei jedem Element. enabledwirkt auf jedes Element und alle Kinder: keine Taps, kein Ziehen.- Wie es folgt:
TextField,CheckBox,SwitchundSlidermit einer ID melden jede Änderung durch den Kunden (Node::onEdited) unter dem Bindungsschlüssel@id, vor ihrem eigenen Signal. Gilt für einzelne Elemente, nicht für IDs in einemrepeat.
Dialog und Screen
Dialog OrderStatusDialog {
property strings digits // Argument der App (Zustand)
const real digitsX: 140 // Konstante
signal keyPressed(string key)
size: 860, 600
...
}
size: w, h(nur Dialog): Größe des Rahmens. Die App fragt sie mitName::size(ctx, args)ab; Argumente dürfen darin vorkommen.- Screen: hat keine Geometrie. Er darf das Aussehen seiner Seite setzen (
color,border,radius,gradient,opacity), z. B.color: theme.white. signal name/signal name(string key, int index): Ereignisse für die App. Parametertypen sindstring,real,int,boolundcolor;realundintkommen in C++ alsdoublean.property typ name[: Ausdruck]: Argument der App und zugleich veränderbarer Zustand mit Setter, optional mit Standardwert. Sie landet inNameArgsund wird ansize()undbuild()übergeben.const typ name: Ausdruck: Konstante ohne Setter und ohne Argument der Instanz, im ganzen Dialog verwendbar (z. B.const int limit: 5). Das gilt auch in Screens und Komponenten.- Standardwerte: Ein
property-Standardwert wird einmal beim Aufbau ausgewertet, wenn kein Argument übergeben wurde; er ist keine dauerhafte Bindung. Explizite Werte wie0,falseoder""überschreiben ihn. Spätere Änderungen erfolgen über den Setter.
Property-Typen: real, int, bool, string, color, image (ein Bild der App, in C++ sk_sp<SkImage>, leer erlaubt), strings (Liste von Texten, in C++ std::vector<std::string>), ein Datensatz und Datensatz[] (Liste).
Komponenten
component DialogButton : Rect {
property string text // Argument der Instanz (": wert": Standard)
color: theme.mainColor
radius: 4
pressSink: 4, 250
Text {
text: root.text
fit: true
align: center, center
size: parent.width, parent.height
}
}
component LanguageButton : Rect {
property string language
signal select // eigenes Signal der Komponente
onTap: select
...
}
- Basistyp: einer der eingebauten Typen.
property: Argument der Instanz, optional mit Standardwert, und Zustand der Komponente (Setter im Struct).- Signale weiterleiten:
onToggle: toggleContrastan einer Instanz löst beim Komponentensignaltoggledas SignaltoggleContrastdes umgebenden Dialogs aus, mit denselben Parametern.onToggle: picked("x")bzw.onEdit: edit(i)übergibt eigene Argumente. - Reihenfolge bei einer Instanz (
DialogButton noButton { ... }): Zuerst gelten die Properties der Komponentenwurzel, dann die der Instanz (sie gewinnen), erst danach baut die Komponente ihre Kinder. So greifen z. B.size: parent.width, ...in den Kindern auf die Größe der Instanz zu. - Kinder: Eine Instanz hat keine Kinder. Bilder der App kommen als
image-Property; was die App selbst zeichnet (Fotos mit Beschnitt), kommt in ein benanntesItemder Komponente.
docs/aura.md · Markdown herunterladen