diff --git a/PLAN.md b/PLAN.md index 4a9ba6c..3e7e026 100644 --- a/PLAN.md +++ b/PLAN.md @@ -54,22 +54,22 @@ Wiki-Referenzen zur QB/PDS-Familie, zeitgenössische Artikel, Screenshots). Emulator-Sessions nur noch als Rückfallebene für Detailfragen, die die Dokumentation nicht beantwortet. -- [~] Sprachreferenz zusammentragen: Anweisungen, Funktionen, Operatoren, - Typsystem (INTEGER, LONG, SINGLE, DOUBLE, STRING, CURRENCY, - feste Strings, `TYPE…END TYPE`), Typ-Suffixe (`% & ! # $ @`), - `DEFINT`-Familie, Sichtbarkeitsregeln (`SHARED`, `COMMON`, `STATIC`) - → Grundgerüst in [docs/sprachreferenz.md](docs/sprachreferenz.md); - Detailfragen (exaktes Verhalten) werden dort als TODO markiert -- [~] Forms-/Steuerelemente-Referenz: Steuerelementtypen, Eigenschaften, - Methoden, Ereignisse, Standardwerte, Fokus- und Z-Reihenfolge - → Grundgerüst in [docs/forms-referenz.md](docs/forms-referenz.md) -- [~] Dateiformate dokumentieren: Quelltext (`.BAS`), Formulare (`.FRM`, - Textformat mit `VERSION`/`Begin…End`-Blöcken), Projekt (`.MAK`) - → [docs/dateiformate.md](docs/dateiformate.md) -- [x] Laufzeitfehler-Katalog (Codes + Meldungstexte) erfasst und als - `tb_runtime::errors` implementiert (inkl. Tests) -- [~] IDE-UX-Referenz: Menüstruktur, Fensterverwaltung, Farbschema, - Tastenbelegung, Editor-Verhalten des Vorbilds +- [x] Sprachreferenz zusammengetragen und gegen die Original-Hilfe des + Vorbilds (dos-help.soulsphere.org, README der Professional Edition) + verifiziert → [docs/sprachreferenz.md](docs/sprachreferenz.md); + Rest-TODOs dort markiert (SINGLE/DOUBLE-Literalschwelle, + `PRINT USING`-Überlaufverhalten, `KEY n`-Makros) +- [x] Forms-/Steuerelemente-Referenz aus Original-Hilfe, CONSTANT.BI und + Programm-Stringtabellen rekonstruiert (alle 16 Steuerelemente mit + Eigenschaften/Methoden/Ereignissen, Defaults, SCREEN-Objekt, + Modalität, Menüsystem) → [docs/forms-referenz.md](docs/forms-referenz.md) +- [~] Dateiformate dokumentieren → [docs/dateiformate.md](docs/dateiformate.md); + offen: exakte Text-`.FRM`-Serialisierung (kein Original-Beispiel + auffindbar — wir definieren nach Windows-1.0-Schema und dokumentieren) +- [x] Laufzeitfehler-Katalog vollständig (1–76, ISAM 80–89, Forms 260–480) + als `tb_runtime::errors` implementiert (inkl. Tests) +- [x] IDE-UX-Referenz: Menüstruktur, Fensterverwaltung, Farbschema, + Tastenbelegung, Editor-Verhalten aus Original-Hilfe und Screenshots → [docs/ide-referenz.md](docs/ide-referenz.md) - [~] Testkorpus aufbauen: kleine Referenzprogramme, deren erwartete Ausgabe dokumentiert ist → erste Programme in `tests/compat/`, Harness folgt diff --git a/crates/tb-runtime/src/errors.rs b/crates/tb-runtime/src/errors.rs index 7aa91be..57d6f71 100644 --- a/crates/tb-runtime/src/errors.rs +++ b/crates/tb-runtime/src/errors.rs @@ -1,13 +1,15 @@ //! Laufzeitfehler: Codes und Meldungstexte kompatibel zum Vorbild. //! -//! Die Codes und (englischen) Meldungstexte entsprechen dem klassischen -//! DOS-BASIC-Katalog; Programme prüfen `ERR` gegen diese Nummern, daher -//! sind sie Teil des Kompatibilitätsvertrags. Nicht belegte Nummern -//! liefern "Unprintable error" (wie im Vorbild bei `ERROR n`). +//! Die Codes und (englischen) Meldungstexte entsprechen dem Katalog des +//! Vorbilds (Original-Hilfe, Topic „Run-Time Error Codes"): klassische +//! Codes 1–76 (QB-Erbe), 80–89 (ISAM), 260–480 (Forms). Programme prüfen +//! `ERR` gegen diese Nummern, daher sind sie Teil des Kompatibilitäts- +//! vertrags. Nicht belegte Nummern liefern "Unprintable error" (wie im +//! Vorbild bei `ERROR n`); Nummer 105 ist im Vorbild intern reserviert. /// Ein Laufzeitfehler des Dialekts, identifiziert durch seinen klassischen Code. #[derive(Debug, Clone, Copy, PartialEq, Eq)] -pub struct RuntimeError(pub u8); +pub struct RuntimeError(pub u16); impl RuntimeError { pub const NEXT_WITHOUT_FOR: Self = Self(1); @@ -64,9 +66,15 @@ impl RuntimeError { pub const RENAME_ACROSS_DISKS: Self = Self(74); pub const PATH_FILE_ACCESS_ERROR: Self = Self(75); pub const PATH_NOT_FOUND: Self = Self(76); + // Forms-Fehler (Auswahl mit benannten Konstanten; vollständige Texte in message()): + pub const INVALID_SCREEN_MODE: Self = Self(271); + pub const INVALID_WHEN_FORMS_SHOWING: Self = Self(272); + pub const INVALID_PROPERTY_VALUE: Self = Self(380); + pub const NO_ACTIVE_CONTROL: Self = Self(430); + pub const NO_ACTIVE_FORM: Self = Self(431); /// Klassischer Fehlercode für `ERR`. - pub fn code(self) -> u8 { + pub fn code(self) -> u16 { self.0 } @@ -124,9 +132,59 @@ impl RuntimeError { 71 => "Disk not ready", 72 => "Disk-media error", 73 => "Feature unavailable", - 74 => "Rename across disks", + 74 => "Can't rename with different drive", 75 => "Path/File access error", 76 => "Path not found", + // ISAM (PDS-Erbe) — Terminal Basic implementiert ISAM nicht, + // die Codes/Texte gehören aber zum Kompatibilitätsvertrag. + 80 => "Feature removed", + 81 => "ISAM - Invalid name", + 82 => "ISAM - Table not found", + 83 => "ISAM - Index not found", + 84 => "ISAM - Invalid column", + 85 => "ISAM - No current record", + 86 => "ISAM - Duplicate value for unique index", + 87 => "ISAM - Invalid operation on NULL index", + 88 => "ISAM - Database inconsistent", + 89 => "ISAM - Insufficient ISAM buffers", + // Forms-Fehler des Vorbilds + 260 => "No timer available", + 271 => "Invalid screen mode", + 272 => "Invalid when forms are showing", + 340 => "Control array element does not exist", + 341 => "Invalid object array index", + 342 => "Not enough room to allocate control array", + 343 => "Object not an array", + 344 => "Must specify index for object array", + 345 => "Reached limit: cannot create any more controls for this form", + 360 => "Object already loaded", + 361 => "Can't load or unload this object", + 362 => "Can't unload controls created at design time", + 363 => "Custom control not found", + 364 => "Object was unloaded", + 365 => "Unable to unload within this context", + 380 => "Invalid property value", + 381 => "Invalid property array index", + 382 => "Property can't be set at run time", + 383 => "Property is read-only", + 384 => "Property can't be modified when form is minimized or maximized", + 385 => "Must specify index when using property array", + 386 => "Property not available at run time", + 387 => "Property can't be set on this control", + 400 => "Form already displayed; can't show form modally", + 401 => "Can't show non-modal form when a modal form is being displayed", + 402 => "Must close or hide topmost modal form first", + 403 => "MDI form cannot be shown modally", + 410 => "Property can't be modified on MDI form", + 420 => "Invalid object reference", + 421 => "Method not applicable for this object", + 422 => "Property not found", + 423 => "Property or control not found", + 424 => "Object required", + 425 => "Invalid object use", + 430 => "No currently active control", + 431 => "No currently active form", + 480 => "Can't create AutoRedraw image", _ => "Unprintable error", } } @@ -153,9 +211,22 @@ mod tests { assert_eq!(RuntimeError::FEATURE_UNAVAILABLE.code(), 73); } + #[test] + fn forms_und_isam_codes() { + assert_eq!(RuntimeError(80).message(), "Feature removed"); + assert_eq!( + RuntimeError::INVALID_WHEN_FORMS_SHOWING.message(), + "Invalid when forms are showing" + ); + assert_eq!(RuntimeError::NO_ACTIVE_FORM.code(), 431); + assert_eq!(RuntimeError(403).message(), "MDI form cannot be shown modally"); + } + #[test] fn unbelegte_codes_sind_unprintable() { assert_eq!(RuntimeError(15).message(), "Unprintable error"); + assert_eq!(RuntimeError(105).message(), "Unprintable error"); // intern reserviert assert_eq!(RuntimeError(200).message(), "Unprintable error"); + assert_eq!(RuntimeError(500).message(), "Unprintable error"); } } diff --git a/docs/dateiformate.md b/docs/dateiformate.md index 0b4bb12..3bfdfb2 100644 --- a/docs/dateiformate.md +++ b/docs/dateiformate.md @@ -12,7 +12,17 @@ Metabefehle in Kommentaren: `'$INCLUDE: 'datei.bi'`, `'$STATIC`, `'$DYNAMIC`. ## Formular: `.FRM` -Textformat, zwei Abschnitte: Formular-Beschreibung, dann Code. +Das Vorbild kannte zwei Speicherformate: **binär** („Fast load and save", +Standard) und **Text** („Readable by other programs"). Terminal Basic +implementiert nur das Textformat; das Binärformat ist Nicht-Ziel (FT.EXE +des Vorbilds konvertierte zwischen beiden). + +Textformat, zwei Abschnitte: Formular-Beschreibung, dann Code. Schema wie +beim Windows-Schwesterprodukt: `VERSION`-Zeile, verschachtelte +`Begin … End`-Blöcke (Klassennamen siehe +forms-referenz.md), `Eigenschaft = Wert`-Zeilen. Der Parser des Vorbilds +akzeptiert Version 1.00 und 2.00 (Import aus dem Windows-Produkt via +Übersetzer). ``` VERSION 1.00 @@ -39,14 +49,17 @@ END SUB - `VERSION`-Zeile, dann verschachtelte `Begin … End`-Blöcke mit `Eigenschaft = Wert`-Zeilen (Strings in `"…"`). - Danach normaler BASIC-Code des Formular-Moduls. -- TODO: exakte Eigenschaftsnamen/-reihenfolge und Einrückung des Vorbilds - an Originaldateien verifizieren (Ziel: Roundtrip-Kompatibilität). +- TODO: Ein wörtliches Original-Beispiel einer Text-`.FRM` war online nicht + auffindbar (Beispieldateien des Originalpakets liegen alle binär vor). + Exakte Serialisierung (Kopfzeile, Einrückung, welche Eigenschaften + geschrieben werden) ist daher festzulegen: wir folgen dem + Windows-1.0-Schema und dokumentieren unsere Fassung als Referenz. ## Projekt: `.MAK` -Zeilenweise Liste der Projektdateien (`.BAS`, `.FRM`, `.BI`), TODO: -Optionszeilen des Vorbilds prüfen. Terminal Basic akzeptiert zusätzlich -Kommentarzeilen mit `'`. +Reine Textdatei ohne Kopfzeile, **eine Projektdatei pro Zeile** +(`.BAS`/`.FRM`; belegt durch die Originalbeispiele). Terminal Basic +akzeptiert zusätzlich Kommentarzeilen mit `'`. ## Kompilat: `.tbc` (neu, eigenes Format) diff --git a/docs/forms-referenz.md b/docs/forms-referenz.md index b670845..e931b8a 100644 --- a/docs/forms-referenz.md +++ b/docs/forms-referenz.md @@ -1,85 +1,181 @@ # Forms-Referenz Terminal Basic -Rekonstruierte Referenz der Forms-Engine des Vorbilds (textbasierte, -ereignisgesteuerte Oberflächen). Grundlage für `tb-ui::forms` und den -Formular-Designer der IDE. Unklare Punkte sind mit `TODO` markiert. +Rekonstruierte Referenz der Forms-Engine des Vorbilds (VBDOS 1.0) — +Grundlage für `tb-ui::forms` und den Formular-Designer. Primärquellen: +Original-Hilfedatei (dekodiert), `CONSTANT.BI`, Stringtabellen der +Original-Programme, Beispielprojekte. Aussagen ohne TODO sind daraus belegt. ## Koordinatenmodell -Alle Maße in **Textzellen** (Zeilen/Spalten), Ursprung links oben. -Formulare liegen auf dem 80×25-Bildschirm; Steuerelemente relativ zum -Formular-Innenbereich. Eigenschaften `Top`, `Left`, `Height`, `Width`. +Einheit ist durchgängig die **Textzelle** (Spalte/Zeile), keine Twips. +`Left`/`Top` relativ zum Container, gültiger Bereich 0–254; `Height`/`Width` +für Controls 1–254, für Formulare bis Bildschirmgröße. `ScaleHeight`/ +`ScaleWidth` (nur Form/PictureBox, read-only) = Innenmaß ohne Rahmen/Menü. +Maus-Koordinaten in Ereignissen sind SINGLE, aber in Zellen. -## Steuerelemente (Übersicht) +## Steuerelemente (exakte Klassennamen) -| Steuerelement | Zweck | Schlüssel-Ereignisse | +`CheckBox, ComboBox, CommandButton, DirListBox, DriveListBox, FileListBox, +Frame, HScrollBar, Label, ListBox, Menu, OptionButton, PictureBox, TextBox, +Timer, VScrollBar` — alle außer `Menu` über die Toolbox platzierbar +(Menüs entstehen im Menu Design Window). Default-Namen: `Check1`, `Combo1`, +`Command1`, `Dir1`, `Drive1`, `File1`, `Frame1`, `HScroll1`, `Label1`, +`List1`, `Option1`, `Picture1`, `Text1`, `Timer1`, `VScroll1`. + +## Eigenschaften/Methoden/Ereignisse je Steuerelement + +**Form** — Ereignisse: Click, DblClick, DragDrop, DragOver, GotFocus, +KeyDown, KeyPress, KeyUp, Load, LostFocus, MouseDown, MouseMove, MouseUp, +Paint, Resize, Unload. Methoden: CLS, DRAG, HIDE, LOAD, MOVE, PRINT, +PRINTFORM, REFRESH, SHOW, TEXTHEIGHT, TEXTWIDTH, UNLOAD. Eigenschaften: +AutoRedraw, BackColor, BorderStyle, Caption, ControlBox, CurrentX, CurrentY, +DragMode, Enabled, ForeColor, FormName, FormType, Height, Left, MaxButton, +MinButton, MousePointer, Parent, ScaleHeight, ScaleWidth, Tag, Top, +Visible, Width, WindowState. + +**CommandButton** — Ereignisse: Click, DragDrop, DragOver, GotFocus, +KeyDown, KeyPress, KeyUp, LostFocus. Methoden: DRAG, MOVE, REFRESH, +SETFOCUS. Eigenschaften: BackColor, Cancel, Caption, CtlName, Default, +DragMode, Enabled, Height, Index, Left, MousePointer, Parent, TabIndex, +TabStop, Tag, Top, Value, Visible, Width. Darstellung nach Höhe: +1 = ``, 2 = einzeiliger Rahmen, ≥3 = Kasten; Mindestgröße 1×3. + +**TextBox** — Ereignisse: Change, DragDrop, DragOver, GotFocus, KeyDown, +KeyPress, KeyUp, LostFocus. Methoden: DRAG, MOVE, REFRESH, SETFOCUS. +Eigenschaften: BackColor, BorderStyle, CtlName, DragMode, Enabled, +ForeColor, Height, Index, Left, MousePointer, MultiLine, Parent, +ScrollBars, SelLength, SelStart, SelText, TabIndex, TabStop, Tag, Text, +Top, Visible, Width. + +**ListBox** — Ereignisse: Click, DblClick, DragDrop, DragOver, GotFocus, +Key*, LostFocus, Mouse*. Methoden: ADDITEM, DRAG, MOVE, REFRESH, +REMOVEITEM, SETFOCUS. Eigenschaften: BackColor, CtlName, DragMode, Enabled, +ForeColor, Height, Index, Left, List, ListCount, ListIndex, MousePointer, +Parent, Sorted, TabIndex, TabStop, Tag, Text, Top, Visible, Width. + +**ComboBox** — wie ListBox plus Change, DropDown (Ereignisse), SelLength/ +SelStart/SelText/Style/Text (Eigenschaften). + +**CheckBox / OptionButton** — Ereignisse: Click (Option auch DblClick), +Drag*, GotFocus, Key*, LostFocus. Methoden: DRAG, MOVE, REFRESH, SETFOCUS. +Eigenschaften: BackColor, Caption, CtlName, DragMode, Enabled, ForeColor, +Height, Index, Left, MousePointer, Parent, TabIndex, TabStop, Tag, Top, +Value, Visible, Width. + +**Frame** — nur DragDrop/DragOver; DRAG, MOVE, REFRESH (kein SetFocus); +Container für Gruppierung (OptionButton-Gruppen). + +**Label** — Ereignisse: Change, Click, DblClick, Drag*, Mouse*. Methoden: +DRAG, MOVE, REFRESH. Eigenschaften: zusätzlich Alignment, AutoSize, +BorderStyle. + +**HScrollBar/VScrollBar** — Ereignisse: Change, Drag*, GotFocus, Key*, +LostFocus (**kein** separates Scroll-Ereignis). Eigenschaften: zusätzlich +Attached (VBDOS-Spezifikum: am Formularrand angedockt; Laufzeit read-only), +LargeChange, Min, Max, SmallChange, Value. + +**PictureBox** — Text-Zeichenfläche (PRINT/CLS aufs Control) und Container +für OptionButton-Gruppen. Ereignisse: Click, DblClick, Drag*, GotFocus, +Key*, LostFocus, Mouse*, Paint. Methoden: CLS, DRAG, MOVE, PRINT, REFRESH, +SETFOCUS, TEXTHEIGHT, TEXTWIDTH. Eigenschaften: zusätzlich AutoRedraw, +CurrentX, CurrentY, ScaleHeight, ScaleWidth. + +**Timer** — Ereignis Timer, keine Methoden; Eigenschaften: CtlName, Enabled, +Index, Interval (0 = aus … 65 535 ms), Parent, Tag. + +**Menu** — Ereignis Click; Eigenschaften Caption, Checked, CtlName, Enabled, +Index, Parent, Separator, Tag, Visible (Shortcut nur zur Entwurfszeit). + +**DirListBox/DriveListBox/FileListBox** — Datei-Browser-Controls +(Path/Drive/FileName/Pattern/Archive/Hidden/Normal/ReadOnly/System; +Ereignisse u. a. Change, PathChange, PatternChange). Terminal Basic bildet +sie plattformneutral nach (Laufwerksliste → Wurzeln/Mounts). + +## Standardwerte und Wertebereiche + +| Eigenschaft | Bereich | Default | |---|---|---| -| Form | Fenster (mit/ohne Rahmen, Titel, verschiebbar) | Load, Unload, Activate, Deactivate, Resize, Paint, Click, KeyPress | -| Label | statischer Text | Click | -| TextBox | ein-/mehrzeilige Texteingabe | Change, KeyPress, GotFocus, LostFocus | -| CommandButton | Schaltfläche | Click | -| CheckBox | Mehrfachauswahl (Value 0/1/2) | Click | -| OptionButton | Einfachauswahl in Gruppe (Value TRUE/FALSE) | Click | -| Frame | Gruppierungsrahmen (Container) | — | -| ListBox | Liste (List, ListCount, ListIndex, AddItem/RemoveItem) | Click, DblClick | -| ComboBox | Eingabe + Liste (Style 0/1/2) | Change, Click, DblClick | -| HScrollBar / VScrollBar | Bildlauf (Min, Max, Value, SmallChange, LargeChange) | Change, Scroll | -| PictureBox | Text-Zeichenfläche (PRINT/CLS auf Steuerelement) | Click, Paint | -| Timer | unsichtbar; Interval in ms (Vorbild: 55-ms-Ticks) | Timer | -| Menu | Menüleiste/-einträge (Designer-definiert) | Click | +| CheckBox.Value | 0 Unchecked · 1 Checked · 2 Grayed | 0 | +| OptionButton.Value | 0/−1 | 0 | +| CommandButton.Value | True löst Click aus | False | +| ComboBox.Style | 0 Dropdown · 1 Simple · 2 Dropdown List | 0 | +| BorderStyle (Form) | 0 None · 1 Fixed Single · 2 Sizable Single · 3 Fixed Double · 4 Sizable Double · 5 Fixed Solid · 6 Sizable Solid | 2 | +| BorderStyle (Control) | 0 None · 1 Single · 2 Double (nur Label/PictureBox) | Label 0; TextBox/PictureBox 1 | +| WindowState | 0 Normal · 1 Minimized · 2 Maximized | 0 | +| FormType | 0 Normal · 1 MDI-Container | 0 | +| Timer.Interval | 0–65 535 ms | 0 | +| ScrollBar Min/Max | −32 768…32 767 | 0 / 32 767 | +| Small-/LargeChange | 1…32 767 | 1 | +| TextBox.ScrollBars | 0 None · 1 H · 2 V · 3 Both | 0 | +| MultiLine/Sorted/Attached | Boolean, Laufzeit read-only | False | +| Alignment (Label) | 0 Left · 1 Right · 2 Center | 0 | +| DragMode | 0 Manual · 1 Automatic | 0 | +| MousePointer | 0–12 (Default, Block, Cross, I-Beam, …) | 0 | +| ForeColor/BackColor | 0–15 | 0 / 7 | +| Text (TextBox/ComboBox) | — | Entwurfszeit = CtlName | +| ListIndex | −1 = keine Auswahl | −1 | -## Gemeinsame Eigenschaften +**Keine Default-Eigenschaften:** `Text1 = "x"` gibt es nicht — Zugriff +immer explizit (`Text1.Text`). „Default" ist nur die CommandButton- +Eigenschaft (Enter-Taste); „Cancel" analog für Esc. -`Name` (Entwurfszeit), `Caption`/`Text`, `Top`/`Left`/`Height`/`Width`, -`Visible`, `Enabled`, `TabIndex`, `TabStop`, `Tag`, `Index` (Steuerelement- -Arrays), `ForeColor`/`BackColor` (0–15 bzw. 0–7), `MousePointer` (TODO). -Zugriff zur Laufzeit: `form.eigenschaft`, `form!element.eigenschaft`; -Standard-Eigenschaft (z. B. `Text` bei TextBox, `Caption` bei Label) bei -Zuweisung ohne Eigenschaftsname. TODO: exakte Standard-Eigenschaften prüfen. +## Ereignis-Signaturen -## Gemeinsame Methoden +```basic +SUB Form_KeyDown (KeyCode AS INTEGER, Shift AS INTEGER) +SUB ctl_KeyPress ([Index AS INTEGER,] KeyAscii AS INTEGER) +SUB Form_MouseDown (Button AS INTEGER, Shift AS INTEGER, X AS SINGLE, Y AS SINGLE) +SUB Form_DragDrop (Source AS CONTROL, X AS SINGLE, Y AS SINGLE) +SUB Form_DragOver (Source AS CONTROL, X AS SINGLE, Y AS SINGLE, State AS INTEGER) +SUB Form_Unload (Cancel AS INTEGER) ' Cancel <> 0 verhindert Entladen +``` -`Move top, left [, height, width]` · `SetFocus` · `Refresh` · `Drag` (Nicht- -Ziel?) · Form zusätzlich: `Show [modal]`, `Hide`, `Cls`, `Print`, `Line` -(Textmodus-Variante? TODO). ListBox/ComboBox: `AddItem text$ [, index]`, -`RemoveItem index`, `Clear` (TODO: hieß es `Clear`?). +Shift-Bitfeld 1 Shift · 2 Ctrl · 4 Alt; Button 1 links · 2 rechts; +DragOver-State 0 Enter · 1 Leave · 2 Over. Bei Steuerelement-Arrays steht +`Index AS INTEGER` immer vorn. KeyAscii ist bei uns ein Unicode-Codepoint +(UTF-8-Abweichung); klassische KeyCode-Konstanten bleiben gültig +(Vorbild-Eigenheit: Entf = 127). -## Ereignismodell +## SCREEN-Objekt -- Ereignisprozeduren heißen `SUB elementname_Ereignis (argumente)` und liegen - im Formular-Modul. -- Tastatur: `KeyDown(KeyCode%, Shift%)`, `KeyPress(KeyAscii%)`, `KeyUp` — - KeyAscii ist bei uns ein Unicode-Codepoint (Abweichung UTF-8). -- Maus: `MouseDown/MouseMove/MouseUp(Button%, Shift%, X!, Y!)` in Zellen. -- Fokusreihenfolge über `TabIndex`; Tab/Shift+Tab wechseln, Access-Keys per - `&` im Caption (z. B. `"&OK"` → Alt+O). -- Zentrale Schleife: Ereignisse werden nur bei `DOEVENTS`, `SLEEP`, `INPUT`- - artigen Wartezuständen oder nach Ende einer Ereignisprozedur zugestellt - (kooperativ, wie im Vorbild — keine Präemption). +Eigenschaften: ActiveControl, ActiveForm, AutoRedraw, ControlPanel, +Height, Width (Zeichen, read-only), MousePointer. Methoden: HIDE, SHOW +(alle sichtbaren Formulare ein-/ausblenden). `SCREEN.ControlPanel(0–17)` +konfiguriert Systemfarben/-effekte (AccessKey-/Desktop-/Menü-/Titel- +Farben, Schatten, 3D-Effekte, Desktop-Füllzeichen) — Konstanten in der +Konstanten-Include-Datei. -## Globale Objekte und Funktionen +## Show/Hide/Load/Unload und Modalität -- `SCREEN`-Objekt: `SCREEN.ActiveForm`, `SCREEN.ActiveControl`, - `SCREEN.Height`/`Width` (25/80), `SCREEN.MousePointer` (TODO: Umfang). -- `MSGBOX(text$ [, typ% [, titel$]])` als Anweisung und Funktion - (Rückgabe: gedrückte Schaltfläche), `INPUTBOX$(prompt$ [, titel$ - [, standard$ [, spalte%, zeile%]]])`. -- `LOAD form` (Load-Ereignis, unsichtbar), `UNLOAD form` (Unload-Ereignis), - Formular-Referenzen sind statisch (keine Instanziierung wie in späteren - Nachfolgern). +`form.SHOW [style%]`: **0 = modeless (Standard), 1 = modal**; lädt bei +Bedarf. Bei modal läuft der Code nach `SHOW` erst nach Schließen weiter. +Modal-Stacking-Regeln → Fehler 400–403 (u. a. „MDI form cannot be shown +modally"). `HIDE` setzt nur `Visible = False`; `LOAD`/`UNLOAD` mit +Load-/Unload-Ereignis (Cancel-Parameter). `LOAD/UNLOAD ctl(index%)` für +Steuerelement-Arrays (Entwurfszeit-Elemente sind nicht entladbar, +Fehler 362). -## Farben und Zeichensatz +## Menüsystem -Rahmen, Schatten und Bedienelemente werden mit Unicode-Box-Drawing gezeichnet -(Abweichung: UTF-8 statt CP437, identische Optik). Standard-Farbschema des -Vorbilds (grauer Dialog, schwarze Schrift, weiße Akzente) wird als Default -nachgebildet. TODO: exakte Attributtabelle je Steuerelement-Zustand -(normal/fokussiert/deaktiviert) aus Screenshots/Emulator ableiten. +Definition pro Formular im **Menu Design Window**, bis zu 6 Ebenen. +Felder: Caption (`&` Access-Key, `-` Separator), CtlName, Tag, Index, +Checked/Enabled/Visible/Separator, Shortcut-Dropdown. Regeln: Separatoren +nicht checked/disabled/mit Shortcut; Menütitel ohne Shortcut. +Menü-Steuerelement-Arrays sind möglich. -## Offene Detailfragen (per Emulator-Session zu klären) +## Steuerelement-Arrays, Drag & Drop, Custom Controls -- Exakte Standardwerte aller Eigenschaften je Steuerelement -- Z-Reihenfolge/Überlappung von Steuerelementen und Formularen -- Verhalten `Show 1` (modal): welche Ereignisse laufen weiter? -- Timer-Auflösung und -Reihenfolge bei mehreren Timern -- Genauer Umfang von PictureBox im Textmodus +- **Control-Arrays:** gleiche CtlName + Index; Laufzeit-Erzeugung per + `LOAD ctl(index%)`. +- **Drag & Drop:** DragMode 0/1, Methode `DRAG action%` (0 Cancel · + 1 Begin · 2 Drop), Ereignisse DragDrop/DragOver mit `Source AS CONTROL`. +- **Custom Controls:** das Vorbild lud sie aus Quick-Libraries; für + Terminal Basic ist ein natives Erweiterungsmodell **Stufe 2** (PLAN.md). + +## Offene Detailfragen + +- Exakte Optik je Steuerelement-Zustand (normal/fokussiert/deaktiviert): + aus den Original-Screenshots ableiten (Phase 4) +- Z-Reihenfolge/Überlappung: Verhalten bei überlappenden Controls +- Timer-Reihenfolge bei mehreren gleichzeitig fälligen Timern +- `.FRM`-Textformat: exakte Serialisierung (siehe dateiformate.md) \ No newline at end of file diff --git a/docs/ide-referenz.md b/docs/ide-referenz.md new file mode 100644 index 0000000..e9d4d29 --- /dev/null +++ b/docs/ide-referenz.md @@ -0,0 +1,167 @@ +# IDE-Referenz Terminal Basic + +Rekonstruierte UX-Spezifikation der IDE des Vorbilds (VBDOS 1.0, 1992) — +Grundlage für `tb-ide` (Phase 5). Quellen: Original-Hilfedatei (dekodiert), +README des Originalpakets, Screenshots (Pixelanalyse), Sekundärliteratur. +Konfidenz je Abschnitt vermerkt; `TODO` = offen. + +Die IDE besteht im Vorbild aus zwei Programmen: der **Programmierumgebung** +und dem separaten **Form Designer** (eigene Menüleiste, Wechsel über +„Event Procedures"/F12 bzw. View→Form). Terminal Basic bildet beides in +**einem** Prozess ab, behält aber die zwei Modi mit identischer Bedienung. + +## 1. Menüstruktur (Konfidenz: sicher) + +Menüleiste der Umgebung: **File Edit View Search Run Debug Options Window**, +**Help** rechtsbündig. Form-Designer-Modus: **File Edit View Tools Options +Window Help**. `───` = Separator, `•` = Toggle-Markierung. + +- **File (Alt+F):** New Project / Open Project… / Save Project ─── New Form / + New Module… / Add File… / Remove File… / Save File / Save File As… ─── + Load Text… / Save Text… ─── Print… / Shell ─── Exit **Alt+F4** +- **Edit (Alt+E):** Undo **Ctrl+Z** ─── Cut **Ctrl+X** / Copy **Ctrl+C** / + Paste **Ctrl+V** / Clear **Del** ─── New Sub… / New Function… / + Event Procedures… **F12** +- **View (Alt+V):** Code… **F2** / Form… **Shift+F12** ─── Next Statement / + Output Screen **F4** ─── Included File / •Included Lines + *(Designer-Modus: … ─ Menu Bar **F10** / Grid Lines)* +- **Search (Alt+S):** Find… / Selected Text **Ctrl+\\** / Repeat Last Find + **F3** / Change… +- **Run (Alt+R):** Start **Shift+F5** / Restart / Continue **F5** / + Modify COMMAND$… ─── Make EXE File… / Make Library… ─── Set Start-up File… +- **Debug (Alt+D):** Add Watch… / Instant Watch… **Shift+F9** / Watchpoint… / + Delete Watch… / Delete All Watch ─── •Trace On / •History On ─── + Toggle Breakpoint **F9** / Clear All Breakpoints / •Break on Errors / + Set Next Statement +- **Options (Alt+O):** Display… / Set Paths… / Right Mouse… / Save… / + •Syntax Checking (Einstellungen persistent) +- **Window (Alt+W):** New Window / Arrange All ─── Calls / Debug / Help / + Immediate / Output / Project ─── Liste offener Code-Fenster (• = aktiv) + *(Designer-Modus: Color Palette / Menu Design Window / Toolbox / Help / + •Form: … )* +- **Help (Alt+H):** Index / Contents ─── Keyboard ─── Topic: **F1** / + Using Help **Shift+F1** / Tutorial ─── About… + +Bedienung: **Alt** (oder F11) aktiviert die Menüleiste, hervorgehobene +Buchstaben wählen, Esc bricht ab, „…" kündigt Dialog an. + +## 2. Fensterverwaltung (Konfidenz: sicher) + +- MDI-artig: alle Fenster/Dialoge sind Kinder der IDE-Fläche. Titelleiste + mit Control-Menü-Box links, Minimieren/Maximieren rechts, Rahmen, + Scrollbalken; Code-Fenster nummeriert („[1] Untitled"). +- Tasten: **F6/Ctrl+F6** nächstes, **Shift+F6** vorheriges Fenster, + **Ctrl+F4** schließen, **Ctrl+F7** verschieben, **Ctrl+F8** Größe, + **Ctrl+F9** minimieren, **Ctrl+F10** maximieren, **Ctrl+F5** + wiederherstellen, **Alt+Minus** Control-Menü; „Arrange All" kachelt. +- **Project Window** (Start: rechts angedockt): Buttons „Form"/„Code" + (Enter öffnet, „Form" wechselt in den Designer) + Modulliste (.FRM/.BAS). +- **Immediate Window** über Alt+W,I — nicht permanent sichtbar (anders als QB). +- **Debug Window** (read-only: Watches/Watchpoints), **Output Window** + (Ausgabebildschirm als Fenster; **F4** = echter Vollbild-Output), + **Calls**- und **Help**-Fenster. + +## 3. Form Designer (Konfidenz: sicher) + +- **Toolbox** links; Einträge: Check Box, Combo Box, Command Button, + Dir List, Drive List, File List, Frame, HScrollBar, Label, List Box, + Option Button, Picture Box, Text Box, Timer, VScrollBar (identisch als + Tools-Menü). +- Platzieren: Doppelklick auf Toolbox-Eintrag oder Tool wählen + auf der + Form aufziehen; **Sizing Handles** (■ an den Ecken); Verschieben per Drag. + Tastatur: Pfeile = 1 Zelle verschieben, **Ctrl+Pfeile** = 5 Zellen, + **Shift+Pfeile** = Größe, **Tab/Shift+Tab** = Control-Wechsel; + Mehrfachauswahl mit Strg+Klick (nur Maus). Raster: View→Grid Lines. +- **Properties Bar oben** statt Eigenschaftsfenster: + `Property: [Caption]↓ Value: […]↓ │ Spalte,Zeile │ BxH`. + **F2** springt in die Value-Box; **F10** toggelt Menüleiste ↔ Properties + Bar (nur eine sichtbar). Keine Statuszeile im Designer. +- **Menu Design Window** (Alt+W,M): Caption (`&` = Access-Key, `-` = + Separator), CtlName, Tag, Index; Checked/Enabled/Visible/Separator; + Shortcut-Dropdown; Outlining-Buttons (Ebene/Reihenfolge, Einfügen, + Löschen, Done). +- **Color Palette** (Alt+W,C): ForeColor/BackColor wählen, Farbe per Drag + auf die Form ziehen. + +## 4. Farbschema (Konfidenz: sicher für belegte Elemente) + +| Element | Farben (DOS-Palette) | +|---|---| +| Menüleiste | Schwarz (0) auf Hellgrau (7) | +| Desktop | Füllzeichen ▒, Hellgrau (7) auf Schwarz (0); Füllzeichen einstellbar | +| Code-Fenster | Hellgrau/Weiß auf **Blau (1)** | +| Titelleiste aktiv | **Weiß (15) auf Magenta (5)** — VBDOS-Spezifikum | +| Rahmen/Scrollbalken | Schwarz auf Hellgrau (7) | +| Project Window/Dialoge | Schwarz auf Hellgrau (7); Fokus-Button mit weißem Doppelrahmen; Deaktiviertes Dunkelgrau (8); Listenauswahl Weiß auf Schwarz | +| Statuszeile | Schwarz auf **Cyan (3)** | + +Alles über **Options→Display** je „User-Interface Element" umkonfigurierbar +(Fore-/Background aus 16 Farben, Desktop-Füllzeichen, Tabweite). +Laufzeit-Defaults kompilierter Programme weichen ab (Titel Weiß auf Schwarz). + +## 5. Editor-Verhalten (Konfidenz: sicher; Keyword-Großschreibung: wahrscheinlich) + +- **Syntax Checking** (Toggle, Standard an): beim Verlassen der Zeile wird + geprüft (Fehlerdialog), formatiert (Leerzeichen, Keywords groß) und die + Zeile sofort in ausführbare Form übersetzt. Für Terminal Basic heißt das: + zeilenweise Inkrementalübersetzung ist Teil des Editors (passt zur + Instant-Compile-Anforderung). +- **DECLARE**-Prototypen werden beim Speichern automatisch erzeugt; + DEFtype-Zeilen werden automatisch in neue Prozeduren übernommen. +- Tastatur: CUA (Ctrl+X/C/V/Z, Einfg, Pos1/Ende) **plus** WordStar-Chords + (Ctrl+Q…, Ctrl+Y Zeile löschen, Bookmarks Ctrl+K,0–3 / Ctrl+Q,0–3). + Prozedurnavigation **Shift+F2/Ctrl+F2**. + +## 6. Run/Debug-Tasten (Konfidenz: sicher) + +**Shift+F5** Start · **F5** Continue · **F4** Output-Screen-Toggle · +**F7** bis Cursor · **F8** Single Step · **F10** Procedure Step · +**F9** Breakpoint · **Shift+F9** Instant Watch · **Shift+F8/Shift+F10** +History rückwärts/vorwärts (bei History On) · **F12** Event Procedures. +Break-Modus: Immediate Window akzeptiert `PRINT`, Zuweisungen, +Prozeduraufrufe, `ERROR n`; „Set Next Statement" verlegt die Ausführung. +„Break on Errors" stoppt im Fehlerhandler. + +## 7. Hilfe (Konfidenz: sicher) + +**F1** kontextsensitiv (auch rechte Maustaste, konfigurierbar), +**Shift+F1** Using Help. Hyperlinks als ◄Thema►, Tab/Shift+Tab springt, +Enter folgt, **Alt+F1** zurück (20 Ebenen), Ctrl+F1 nächstes Topic, +Esc schließt. Hilfe im eigenen Fenster; Index, Contents, Keyboard-Guide, +Tutorial. → Terminal Basic: eigenes Hilfeformat, gleiche Navigation. + +## 8. Statuszeile (Konfidenz: sicher; Caps/Num: unklar) + +Unterste Zeile, Schwarz auf Cyan. Links kontextabhängige Shortcuts in +spitzen Klammern (` +`), per Mausklick auslösbar. Rechts `Zeile:Spalte` +(`00001:001`). TODO: Caps/Num-Anzeige. + +## 9. Start (Konfidenz: wahrscheinlich) + +„Log-On Screen" (Begrüßung, Version, Copyright), danach leeres Projekt: +Code-Fenster „[1] Untitled", Project Window „Untitled". Kein +Survival-Guide-Dialog, kein Easy/Full-Menüs-Konzept. TODO: Splash vs. Dialog. + +## 10. Interpreter vs. Compiler (Konfidenz: sicher) + +Die Umgebung führt P-Code-übersetzte Zeilen sofort aus; der separate +Compiler erzeugt native EXEs (wahlweise standalone oder mit Runtime-Modul). +Nur die Umgebung hat: Immediate Window, Watches/Watchpoints, Breakpoints, +Stepping, History-Trace, Set Next Statement, automatische Bereichs-/ +Überlaufprüfungen. → Terminal Basic: `tbdos` (IDE) und `tbdosc` +(Standalone-Compiler) teilen sich dieselbe TBVM, damit es — anders als im +Vorbild — **keine** Verhaltensunterschiede zwischen IDE-Lauf und +kompiliertem Programm gibt (dokumentierte Abweichung, gewollt). + +## Übernahme-Entscheidungen für Terminal Basic + +1. Menüstruktur, Tastenbelegung, Fensterverwaltung und Farbschema werden + originalgetreu übernommen (inkl. Magenta-Titelleiste, Options→Display). +2. Umgebung und Form Designer werden ein Prozess mit zwei Modi; der + F12/Shift+F12-Wechsel bleibt erhalten. +3. Zeilenweises Syntax-Checking mit Formatierung/Normalisierung ist + Editor-Standard (abschaltbar wie im Vorbild). +4. IDE-Lauf und `tbdosc`-Kompilat verhalten sich identisch (gleiche TBVM). +5. MS-DOS-spezifische Toolbox-Controls (Dir/Drive/File List) werden als + plattformneutrale Datei-Browser-Controls nachgebildet. diff --git a/docs/sprachreferenz.md b/docs/sprachreferenz.md index 3d3d9cc..a3a7352 100644 --- a/docs/sprachreferenz.md +++ b/docs/sprachreferenz.md @@ -5,6 +5,12 @@ BASIC-Familie mit Forms-Erweiterung). Dieses Dokument ist die verbindliche Grundlage für Frontend und Runtime. Unklare Detailfragen sind mit `TODO` markiert und werden per Testkorpus geklärt bzw. entschieden. +**Primärquellen:** Original-Hilfedateien des Vorbilds als HTML unter +https://dos-help.soulsphere.org/ (`qck.hlp` Quick Reference, `advr.hlp` +Details, `ener.hlp` Fehlermeldungen; Vergleich PDS 7.1: `bas7qck.hlp`) +sowie das Original-README der Professional Edition. Aussagen ohne +TODO-Markierung sind daraus belegt. + **Bewusste Abweichungen vom Vorbild** stehen am Ende des Dokuments. --- @@ -12,24 +18,32 @@ markiert und werden per Testkorpus geklärt bzw. entschieden. ## 1. Lexik - **Zeilenorientiert.** Eine logische Zeile enthält eine oder mehrere - Anweisungen, getrennt durch `:`. Keine Zeilenfortsetzung im Vorbild - (`_` ist eine spätere Erfindung) — TODO: als Erweiterung erlauben? + Anweisungen, getrennt durch `:`. **Zeilenfortsetzung:** `_` als letztes + Zeichen (mit vorangehendem Leerzeichen/Tab) setzt die Zeile fort — im + Vorbild für extern erstellten Code gedacht (der IDE-Editor fügt + fortgesetzte Zeilen beim Laden zusammen); Terminal Basic akzeptiert es + überall. - **Zeilennummern** sind optional und wirken als Labels. Alphanumerische **Labels** enden mit `:` am Zeilenanfang (`Fehler:`). - **Kommentare:** `REM` (ganze Anweisung) und `'` (bis Zeilenende). `REM`/`'` am Zeilenanfang mit `$STATIC`/`$DYNAMIC`/`$INCLUDE: 'datei'` sind **Metabefehle**. -- **Bezeichner:** Buchstabe, dann Buchstaben/Ziffern/`.`, max. 40 Zeichen, - case-insensitiv. Optionales Typ-Suffix als letztes Zeichen. +- **Bezeichner:** Buchstabe, dann Buchstaben/Ziffern/`.`/`_`, max. 40 + Zeichen, case-insensitiv. Optionales Typ-Suffix als letztes Zeichen. + (`_` in Bezeichnern ist eine dokumentierte Neuerung des Vorbilds.) - **Typ-Suffixe:** `%` INTEGER · `&` LONG · `!` SINGLE · `#` DOUBLE · `$` STRING · `@` CURRENCY. `name`, `name%`, `name$` sind **verschiedene Variablen**. - **Keywords** sind reserviert und case-insensitiv; die IDE normalisiert auf Großschreibung. - **Numerische Literale:** dezimal (`123`, `1.5`, `1.5E3`, `1D3` für DOUBLE), - hexadezimal `&HFF`, oktal `&O777`; Suffixe wie bei Variablen (`10%`, `10&`, - `1.5#`, `2.5@`). Ohne Suffix: kleinster passender Typ (Ganzzahl → INTEGER, - sonst SINGLE/DOUBLE je nach Präzision; TODO: exakte Regel testen). + hexadezimal `&HFF`, oktal `&O777`; Suffixe erzwingen den Typ (`10%`, `10&`, + `1.5!`, `1.5#`, `2.5@`). Ohne Suffix gilt: Ganzzahl im INTEGER-Bereich → + INTEGER; Hex/Oktal ohne `&`-Suffix → 16 Bit (INTEGER), mit `&` → LONG; + `E`-Exponent → SINGLE, `D`-Exponent → DOUBLE; Dezimalpunkt-Wert → + SINGLE, bei mehr als 15 Stellen DOUBLE (TODO: exakte Schwelle — Quelle + an der Stelle widersprüchlich); Ganzzahl außerhalb des LONG-Bereichs + wird Gleitkommawert (kein Fehler). - **String-Literale:** `"…"`; doppeltes `""` ergibt ein Anführungszeichen. ## 2. Typsystem @@ -51,13 +65,16 @@ markiert und werden per Testkorpus geklärt bzw. entschieden. Suffix gilt der Standardtyp SINGLE, änderbar per `DEFINT/DEFLNG/DEFSNG/DEFDBL/DEFSTR/DEFCUR a–z` (buchstabenbereichsweise, wirkt pro Modul/Prozedur ab Deklaration). -- `OPTION EXPLICIT` gibt es im Vorbild **nicht** — TODO: als opt-in - Erweiterung anbieten? +- `OPTION EXPLICIT` **existiert** (Neuerung des Vorbilds gegenüber der + QB/PDS-Familie): erzwingt Deklaration aller Variablen (über COMMON, + CONST, DEF FN, DIM, FUNCTION, REDIM, SHARED, STATIC oder SUB); gilt + auch für das Direktfenster. - **Arrays:** `DIM a(10)`, `DIM a(1 TO 10, 0 TO 5)`. Untergrenze standardmäßig 0, per `OPTION BASE 1` änderbar. `$STATIC`/`$DYNAMIC` bzw. Kontext bestimmen statisch/dynamisch; `REDIM` (dynamisch, löscht Inhalt), `ERASE` - (reinitialisiert statisch / gibt dynamisch frei). Max. 8 Dimensionen - (TODO: prüfen). `LBOUND`/`UBOUND` liefern Grenzen. + (reinitialisiert statisch / gibt dynamisch frei). Max. **60 Dimensionen**, + Indizes −32 767 … 32 767 (mit `TO`). `LBOUND`/`UBOUND` liefern Grenzen. + (DOS-Speichergrenzen der Arrays — 64K/128K-Regeln — übernehmen wir nicht.) - **Konvertierung:** implizit zwischen numerischen Typen mit Rundung (Banker's Rounding bei `CINT`/`CLNG` und Zuweisung an Ganzzahl); Überlauf → Fehler 6. Keine implizite Konvertierung Zahl ↔ String (Fehler 13, @@ -125,38 +142,47 @@ INTEGER −1 (wahr) / 0 (falsch). externe Routinen (entfällt bei uns; TODO: `BYVAL` allgemein erlauben?). - Arrays werden mit `name()` übergeben, TYPEs BYREF. - Rekursion erlaubt (außer bei `STATIC`-Semantik-Konflikten). -- `DEF FNname (args) = ausdruck` und Block-`DEF FN … END DEF`; Aufruf - `FNname(…)`. Modulweit, kein eigener Namensraum. +- `DEF FNname (args) = ausdruck` und Block-`DEF FN … END DEF` (mit + `EXIT DEF`); Aufruf `FNname(…)`. Nur auf Modulebene definier- und + nutzbar, **nicht rekursiv**, Argumente by value, keine Arrays/Records/ + Fixed-Strings als Argumente. ## 7. Fehlerbehandlung -- `ON ERROR GOTO label` (aktiviert Handler), `ON ERROR GOTO 0` (deaktiviert; - in einem aktiven Handler: Fehler weiterreichen → Programmabbruch), - `ON ERROR RESUME NEXT` — TODO: prüfen, ob das Vorbild das kennt - (QB-Familie: nein; Forms-Dialekt: ja?). +- Vollständige Syntax: `ON [LOCAL] ERROR {GOTO zeile/label | RESUME NEXT | + GOTO 0}`. `LOCAL` installiert einen **prozedurlokalen** Handler; + ohne `LOCAL` gilt der Handler modulweit. `GOTO 0` deaktiviert (in einem + aktiven Handler: Fehler weiterreichen → Programmabbruch). - Im Handler: `RESUME` (fehlerauslösende Anweisung wiederholen), - `RESUME NEXT`, `RESUME label`. + `RESUME NEXT`, `RESUME zeile/label`. - `ERR` (Code), `ERL` (Zeilennummer, nur numerische Zeilennummern!), - `ERROR n` (Fehler auslösen). + `ERROR n` (Fehler auslösen). Fehlernummer 105 ist im Vorbild intern + reserviert und sollte nicht via `ERROR n` verwendet werden. - Fehler im aktiven Handler → sofortiger Abbruch. Fehler ohne Handler → Abbruch mit Meldung „Fehlertext in Zeile n" bzw. Debugger in der IDE. -- Fehlerkatalog: siehe `tb-runtime/src/errors.rs` (implementiert). +- Fehlerkatalog: klassische Codes 1–76, ISAM-Codes 80–89, Forms-Codes + 260–480 — vollständig implementiert in `tb-runtime/src/errors.rs`. ## 8. Ereignis-Traps (klassisch, ohne Forms) -`ON TIMER(n) GOSUB label` + `TIMER ON/OFF/STOP`; analog `ON KEY(n)`, -`ON PLAY`, `ON COM(n)`, `ON PEN`, `ON STRIG(n)`. Für Terminal Basic relevant: -`TIMER` und `KEY`; Rest: Nicht-Ziel (siehe Abweichungen). +Vorhanden im Vorbild: `ON COM/KEY/PEN/PLAY/STRIG/TIMER/UEVENT(…) GOSUB label` +mit Steueranweisungen `… ON/OFF/STOP`, dazu das `EVENT`-Statement (auch für +Forms-Ereignisse) und `SetUEvent`. Timer-Events und Trapping sind ausgesetzt, +solange ein Menü-Control den Fokus hat. Für Terminal Basic relevant: +`TIMER`, `KEY`, `UEVENT`; `COM/PEN/PLAY/STRIG`: Nicht-Ziel (Fehler 73). ## 9. Konsolen-E/A - `PRINT [#n,] liste` — Trennzeichen `;` (direkt anschließend) und `,` (nächste 14-Zeichen-Druckzone). Zahlen: führendes Leerzeichen bzw. `-`, nachgestelltes Leerzeichen. Abschluss ohne `;`/`,` → Zeilenumbruch. -- `PRINT USING "format"; liste` — Formatzeichen: `#` Ziffer, `.` Dezimalpunkt, - `,` Tausendertrennung, `+`/`-` Vorzeichen, `$$` Währung, `**` Füllsterne, - `^^^^` Exponent, `&` String ganz, `!` erstes Zeichen, `\ \` n Zeichen, - `_` Literal-Escape. +- `PRINT USING "format"; liste` — Formatzeichen (offizielle Liste): + numerisch `#` Ziffer, `.` Dezimalpunkt, `,` Tausendertrennung, `+` Vorzeichen- + position, `-` nachgestelltes Minus, `$$` führendes $, `**` Füllsterne, + `**$` kombiniert, `^^^^` Exponent; String `&` ganz, `!` erstes Zeichen, + `\ \` n Zeichen (Leerzeichen + 2); `_` Literal-Escape; alle anderen + Zeichen literal. TODO: `%`-Präfix bei Feldüberlauf (QB-Verhalten) in der + Vorbild-Hilfe nicht gelistet — per Test klären, wir übernehmen es vorerst. - `INPUT ["prompt"{;|,}] var, …` (mit `;` vor Prompt: kein „? "); `LINE INPUT` (ganze Zeile in String). - `INKEY$` (nicht blockierend; "" wenn leer; erweiterte Tasten: @@ -199,7 +225,11 @@ INTEGER −1 (wahr) / 0 (falsch). (kompatibler PRNG! → Testkorpus), `CINT`, `CLNG`, `CSNG`, `CDBL`, `CCUR`. **Datum/Zeit:** `DATE$` (Funktion und Anweisung — Setzen: Nicht-Ziel), -`TIME$`, `TIMER` (Sekunden seit Mitternacht, SINGLE). +`TIME$`, `TIMER` (Sekunden seit Mitternacht, SINGLE); dazu die nativen +Schlüsselwörter des Vorbilds (Neuerung ggü. QB/PDS): `NOW`, `DATESERIAL`, +`DATEVALUE`, `TIMESERIAL`, `TIMEVALUE`, `DAY`, `MONTH`, `YEAR`, `WEEKDAY`, +`HOUR`, `MINUTE`, `SECOND` (serielle Datumswerte als DOUBLE) sowie +`FORMAT$` (Zahlen-, Datums-/Zeitformatierung). **Sonstiges:** `LBOUND`, `UBOUND`, `FRE(…)` (freier Speicher — liefert bei uns Pseudowerte), `VARPTR`/`VARSEG`/`SADD`/`PEEK`/`POKE` → Nicht-Ziel @@ -211,8 +241,20 @@ uns Pseudowerte), `VARPTR`/`VARSEG`/`SADD`/`PEEK`/`POKE` → Nicht-Ziel `form.eigenschaft = wert`, `form!steuerelement.eigenschaft`, Ereignisprozeduren `SUB name_Ereignis (…)`, `LOAD`/`UNLOAD form`, -`form.SHOW [modal]`, `form.HIDE`, `MSGBOX`/`INPUTBOX$`-Funktionen, -`DOEVENTS`, `SCREEN`-Objekt (aktives Formular/Steuerelement). +`form.SHOW [style%]` (0 = modeless, Standard; 1 = modal), `form.HIDE`, +`DOEVENTS()`, `SCREEN`-Objekt, Datentypen `FORM`/`CONTROL`, `IF TYPEOF`, +`$FORM`-Metabefehl, Include-Dateien (Konstanten-`.BI`). + +Dialoge: +- `MSGBOX msg$ [,type% [,title$]]` (Anweisung) bzw. Funktion → INTEGER. + `type%` = Buttons (0 OK · 1 OK/Cancel · 2 Abort/Retry/Ignore · + 3 Yes/No/Cancel · 4 Yes/No · 5 Retry/Cancel) + Default-Button + (0/256/512). Rückgabe 1 OK · 2 Cancel/Esc · 3 Abort · 4 Retry · + 5 Ignore · 6 Yes · 7 No. Keine Icon-Flags (Textmodus). msg$ max. 1024 + Zeichen, modal. +- `INPUTBOX$(prompt$ [,title$ [,default$ [,xpos%, ypos%]]])` → STRING; + Cancel liefert `""`; Position in **Zeichen**, sonst zentriert; Dialog + fest 46×16 Zeichen; prompt$ max. 255 Zeichen. --- @@ -234,7 +276,10 @@ Ereignisprozeduren `SUB name_Ereignis (…)`, `LOAD`/`UNLOAD form`, TODO. 4. **Kein `CHAIN`/Overlay-Mechanismus**; `SHELL` startet die System-Shell. 5. **Grafik-Anweisungen** (`SCREEN n>0`, `PSET`, `LINE`, `CIRCLE`, `PAINT`, - `DRAW`) sind Nicht-Ziel (Fehler 73) — das Vorbild war im Forms-Modus - ebenfalls textonly. + `DRAW`, Grafik-`GET`/`PUT`, `PALETTE`, `WINDOW`/`VIEW`, `PMAP`, `PCOPY`) + sind Nicht-Ziel (Fehler 73). Hinweis: das Vorbild **hatte** die + Grafikmodi 0–13, aber nicht gleichzeitig mit Forms (dort Fehler 272 + „Invalid when forms are showing") — wir übernehmen nur den + Forms-/Textmodus-Zweig. 6. **`PLAY`/`SOUND`**: `BEEP` = Terminal-Bell; Rest Nicht-Ziel (Fehler 73). 7. **`WIDTH 40`** wird nicht unterstützt (nur 80×25).