fix: berechne-alle-winkel Signatur-Nachzug (schon-flach) + HundM05-Menu-Fix nachgezogen

Lisp/vf_standard.lsp: berechne-alle-winkel um Parameter schon-flach
erweitert (Fussabdruck-Korrektur, wenn ein Frame flach statt bei 3 Grad
ankommt) - vf_linienzug.lsp rief die Funktion bereits mit diesem 5.
Argument auf, dieser Commit fehlte im letzten Commit und liess den
Zwischenstand mit Argumentzahl-Mismatch zurueck. tests/test_foerderer.lsp
und tests/test_mubea.lsp ziehen dieselbe Signatur nach (inkl.
berechne-horizontale-mitte, das schon-flach bereits erwartete).
tests/testdata/linienzug_tests*.json aktualisiert passend zum echten
Bau-Ablauf. menu/SSG_LIB.mnu/.cui: TEST_LINIENZUG_STUFE2 im Testmenue
ergaenzt.

Lisp/vf_spec.lsp + lib/vf_spec_export.py: *vsp-menu-start* auf die aktuelle
6-Optionen-Kettenanfang-Zuordnung umgestellt (vorher noch 4 Optionen) -
vsp-journal replayt gegen den LEBENDEN vf-linienzug-modus. Python-Tabelle
bewusst NICHT umgestellt (dekodiert eine eingefrorene Alt-Aufzeichnung).
TEST_HUNDM05 schlaegt trotzdem weiterhin fehl (separates, ungeloestes
Problem - siehe naechster Absatz).

Bekannter offener Fehler: TEST_HUNDM05 baut nach wie vor nicht korrekt -
der Menu-Code-Fix allein reicht nicht. Root Cause nicht abschliessend
geklaert, Uebergabe an Kollegen fuer Logik-Review vorgesehen.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
Yuelin Wang
2026-09-14 08:43:54 +02:00
co-authored by Claude Sonnet 5
parent 1b49bd3c3b
commit 4418840d5e
9 changed files with 832 additions and 738 deletions
+64 -11
View File
@@ -65,10 +65,21 @@
(setq *vsp-tab-ende2* '(("ja-mit-es" . "1") ("nein" . "2")))
;; Glied -> Menue-Code. Der Code haengt am Frame: die ERSTE Sektion laeuft
;; ohne Frame und bekommt 4 Optionen (kein GF-Bogen - es gibt noch keine
;; Richtung, an die er anschliessen koennte), jede spaetere 5.
(setq *vsp-menu-start* '(("Linie-GF" . "1") ("Linie-VF" . "2")
("Horizontal-VF" . "3") ("Linie" . "4")))
;; ohne Frame (Kettenanfang) und bekommt 6 Optionen - GF-Bogen UND Vario-Kurve
;; sind seit der "Fortsetzung einer bestehenden Teilkette"-Erweiterung
;; (vf_linienzug.lsp, vfl-naechstes-element-header-Zweig ohne frame) AUCH am
;; Kettenanfang waehlbar (Referenzrichtung kommt dann aus einem KS_AUS am
;; Startpunkt statt aus einem Frame) - NICHT mehr nur 4 Optionen wie fruecher.
;; Jede spaetere Sektion (Frame existiert bereits) hat weiterhin 5 Optionen
;; (GF-Bogen ist dort IMMER Option 1, kein Vario-Kurve-Sonderfall noetig - eine
;; Vario-Kurve wird dort ueber die VF-Einheit selbst erreicht). Beide Tabellen
;; MUESSEN exakt zur Options-Reihenfolge in vf-linienzug-modus passen (siehe
;; dortiger Kommentar "Kettenanfang: 6 Optionen statt 4") - ein Regressions-Fund
;; 2026-09-12 (TEST_HUNDM05 baute "GF-Bogen" statt "Linie-GF" als erstes Glied,
;; weil diese Tabelle noch die alte 4-Optionen-Zuordnung hatte).
(setq *vsp-menu-start* '(("GF-Bogen" . "1") ("Vario-Kurve" . "2")
("Linie-GF" . "3") ("Linie-VF" . "4")
("Horizontal-VF" . "5") ("Linie" . "6")))
(setq *vsp-menu-weiter* '(("GF-Bogen" . "1") ("Linie-GF" . "2")
("Linie-VF" . "3") ("Horizontal-VF" . "4")
("Linie" . "5")))
@@ -88,6 +99,10 @@
;; darum in vsp-bau-aus-spec und nicht einmal aussen: der Abbruch-Handler in
;; vf-linienzug-modus setzt *ssg-ils-dim* zurueck.
(if (not (boundp '*vsp-dim-override*)) (setq *vsp-dim-override* nil))
;; Ausgabe-Flag von vsp-sektion (siehe dort): T, wenn eine "Linie-GF"-Sektion
;; mit ende="ja-mit-es" die NAECHSTE Sektion (das ES-Glied) bereits inline
;; mitverarbeitet hat - vsp-journal ueberspringt sie dann beim Weiterzaehlen.
(if (not (boundp '*vsp-es-verbraucht*)) (setq *vsp-es-verbraucht* nil))
;; Fehler sammeln (aeltester zuerst) statt beim ersten abzubrechen: eine
;; handgeschriebene Spec hat selten genau einen Tippfehler.
@@ -234,7 +249,13 @@
(vsp-wert-str (ssg-val kopf "as_winkel") "as_winkel")
(vsp-code-raus *vsp-tab-seite* (ssg-val kopf "as_seite") "as_seite"))))
(defun vsp-sektion (sek subs erster / label tab code art modus smodus)
;; naechste: Felder der NAECHSTEN Top-Level-Sektion (oder nil) - wird nur fuer
;; "Linie-GF" gebraucht (siehe dort). *vsp-es-verbraucht* (Ausgabe-Flag, vom
;; Aufrufer vsp-journal gelesen): T, wenn diese Sektion die naechste (das
;; ES-Glied) bereits mitverarbeitet hat - der Aufrufer muss sie dann beim
;; Weiterzaehlen ueberspringen.
(defun vsp-sektion (sek subs erster naechste / label tab code art modus smodus ende-wert)
(setq *vsp-es-verbraucht* nil)
(setq label (ssg-val sek "glied"))
(setq *vsp-wo* (strcat "Sektion " (if label label "(ohne glied)")))
(cond
@@ -277,6 +298,31 @@
(setq modus (ssg-val sek "laenge_modus"))
(if (null modus) (setq modus "endpunkt"))
(vsp-code-raus *vsp-tab-gf-laenge-modus* modus "laenge_modus")
;; NEU (2026-09-12): "Ist das Kettenende?" wird im Bau-Ablauf jetzt
;; SOFORT nach der Laenge-Modus-Wahl gefragt (vor Separator/
;; Gefaelle) - vorher lief die Frage erst nach dem Bau. Bei
;; "ja-mit-es" fragt vf-linienzug-modus DIREKT im Anschluss auch
;; ES-Winkel/-Seite (damit deren Fussabdruck schon in die
;; Laengenberechnung eingeht) - die Spec beschreibt das ES-Element
;; aber weiterhin als EIGENE, nachfolgende Sektion (glied="ES",
;; siehe dort) fuer bessere Lesbarkeit. vsp-journal muss die beiden
;; Tokengruppen daher HIER zusammenziehen: "ende" + (bei ja-mit-es)
;; die Winkel/Seite-Tokens der naechsten Sektion, vorgezogen. Die
;; eigentliche ES-Sektion wird dadurch bereits vollstaendig
;; verbraucht - vsp-journal ueberspringt sie danach (siehe
;; *vsp-es-verbraucht*), sonst kaemen ihre Tokens ein zweites Mal.
(setq ende-wert (ssg-val sek "ende"))
(vsp-code-raus *vsp-tab-ende3* ende-wert "ende")
(if (= ende-wert "ja-mit-es")
(cond
((null naechste)
(vsp-fehler "ende=\"ja-mit-es\", aber keine folgende ES-Sektion vorhanden"))
((/= (ssg-val naechste "glied") "ES")
(vsp-fehler "ende=\"ja-mit-es\" erwartet eine direkt folgende Sektion mit glied=\"ES\""))
(T
(vsp-wert-str (ssg-val naechste "winkel") "winkel (ES, vorgezogen)")
(vsp-code-raus *vsp-tab-seite* (ssg-val naechste "seite") "seite (ES, vorgezogen)")
(setq *vsp-es-verbraucht* T))))
(cond
((= modus "steigend")
(setq smodus (ssg-val sek "steigend_modus"))
@@ -304,7 +350,7 @@
(vsp-zahl "REAL" (ssg-val sek "hoehe") "hoehe")
(vsp-zahl "REAL" (ssg-val sek "winkel") "winkel")))
)
(vsp-code-raus *vsp-tab-ende3* (ssg-val sek "ende") "ende"))
)
((= label "Linie-VF")
(vsp-linie sek)
@@ -424,17 +470,24 @@
;; Spec -> Vorwaerts-Journal. Rueckgabe: Journal, oder nil wenn die Spec
;; Fehler hat (dann stehen sie in *vsp-fehler*).
(defun vsp-journal (spec / sektionen i)
;; Index-basierte Schleife (statt foreach) - noetig, damit "Linie-GF" bei
;; ende="ja-mit-es" die naechste Sektion (das ES-Glied) vorziehen UND danach
;; ueberspringen kann (siehe vsp-sektion/*vsp-es-verbraucht*).
(defun vsp-journal (spec / sektionen n i s naechste)
(setq *vsp-fehler* nil *vsp-tok* nil *vsp-erster-dl* T *vsp-wo* "Spec")
(cond
((null (vsp-kopf spec)) (vsp-fehler "Kopf-Objekt fehlt") nil)
(T
(vsp-praeambel (vsp-kopf spec))
(setq sektionen (vsp-sektionen spec) i 0)
(setq sektionen (vsp-sektionen spec))
(setq n (length sektionen))
(if (null sektionen) (vsp-fehler "Spec hat keine Sektionen"))
(foreach s sektionen
(setq i (1+ i))
(vsp-sektion (vsp-sek-felder s) (vsp-sek-subs s) (= i 1)))
(setq i 0)
(while (< i n)
(setq s (nth i sektionen))
(setq naechste (if (< (1+ i) n) (vsp-sek-felder (nth (1+ i) sektionen)) nil))
(vsp-sektion (vsp-sek-felder s) (vsp-sek-subs s) (= i 0) naechste)
(setq i (+ i (if *vsp-es-verbraucht* 2 1))))
(if *vsp-fehler* nil (reverse *vsp-tok*)))))
;; Nur pruefen, nichts bauen: liefert die Fehlerliste (nil = Spec in