CSV-Export: Nachbarschaftserkennung neu aufgebaut (ohne shapely), Fehlerspalte ergaenzt

Nachbarschaft wird jetzt in drei getrennten Gruppen geprueft statt global
ueber alle Elemente: Kreisel/Eckrad gegeneinander, Kreisel/Eckrad gegen
Gefaellestrecke/Foerderer/Strecke-Modul (diese drei nicht gegeneinander),
und Omniflo-Elemente gegeneinander (rasterbasiert vorgefiltert nach x/y-
Koordinate). Ersetzt die bisherige shapely-STRtree-Loesung durch reines
Python, da die shapely-Abhaengigkeit den regulaeren CSV-Export in der von
BricsCAD genutzten Python-Umgebung brechen konnte.

Neue Spalte "Fehler" markiert Elemente mit zu wenigen Partnern
("unverbunden"/"nur ein Partner") je nach TeileArt-Mindestanzahl.

Ausserdem: SSG_RUN_ALL_TESTS-Absturz nach TEST_KREISEL behoben (ssg-start/
ssg-end nutzten flache globale Variablen statt eines Stacks, wodurch
verschachtelte Aufrufe den *error*-Handler dauerhaft korrumpierten) und
FILEDIA=0 um den DXFOUT-Kommandozeilenaufruf ergaenzt.
This commit is contained in:
2026-07-23 10:13:18 +02:00
parent 6d81b30628
commit ad287b683d
8 changed files with 491 additions and 198 deletions
+85 -18
View File
@@ -13,25 +13,39 @@
;; (ssg-start "Titel" '(("OSMODE") ("ORTHOMODE"))) ;; (ssg-start "Titel" '(("OSMODE") ("ORTHOMODE")))
;; ... Makrocode ... ;; ... Makrocode ...
;; (ssg-end) ;; (ssg-end)
;;
;; Nestbar ueber *ssg-start-stack*: jedes ssg-start legt einen eigenen
;; Frame (vorheriger *error*-Handler + Variablenwerte) oben auf den
;; Stack, ssg-end nimmt genau diesen Frame wieder herunter. Noetig, weil
;; z.B. ein Test-Wrapper (ssg-start "TEST_KREISEL" ...) selbst wieder
;; Makros aufruft, die ihrerseits ssg-start/ssg-end nutzen - mit einer
;; einzelnen globalen Variable statt eines Stacks wuerde der innere
;; Aufruf den *error*-Handler und die CLAYER/CMDECHO/...-Werte des
;; aeusseren Aufrufs ueberschreiben. Ergebnis waere ein *error* wird
;; nach dem aeusseren ssg-end dauerhaft an ssg-errhan haengen bleiben
;; (statt zum urspruenglichen Default-Handler zurueckzukehren) und bei
;; jedem folgenden Fehler faelschlich veraltete CLAYER/CECOLOR-Werte
;; ueber "_LAYER"/"_undo" auf die Kommandozeile schreiben.
;; ------------------------------------------------------------ ;; ------------------------------------------------------------
(defun ssg-start (titel zusatz-vars / xlen xpos xvar) (if (not (boundp '*ssg-start-stack*)) (setq *ssg-start-stack* nil))
(defun ssg-start (titel zusatz-vars / cavar xlen xpos xvar)
;; titel - Anzeigename des Makros ;; titel - Anzeigename des Makros
;; zusatz-vars - Liste zusaetzlicher Variablen z.B. '(("OSMODE")("ORTHOMODE")) ;; zusatz-vars - Liste zusaetzlicher Variablen z.B. '(("OSMODE")("ORTHOMODE"))
;; Immer CLAYER und CMDECHO werden automatisch gesichert. ;; Immer CLAYER und CMDECHO werden automatisch gesichert.
(setq _ssg-olderr *error* (setq cavar (append '(("CLAYER") ("CMDECHO")) zusatz-vars)
*error* (function ssg-errhan) xlen (length cavar)
_ssg-cavar (append '(("CLAYER") ("CMDECHO")) zusatz-vars) xpos 0
xlen (length _ssg-cavar)
xpos 0
) )
(repeat xlen (repeat xlen
(setq xvar (car (nth xpos _ssg-cavar)) (setq xvar (car (nth xpos cavar))
_ssg-cavar (subst (cons xvar (getvar xvar)) cavar (subst (cons xvar (getvar xvar)) (nth xpos cavar) cavar)
(nth xpos _ssg-cavar) _ssg-cavar) xpos (1+ xpos)
xpos (1+ xpos)
) )
) )
(setq *ssg-start-stack* (cons (cons *error* cavar) *ssg-start-stack*))
(setq *error* (function ssg-errhan))
(setvar "CMDECHO" 0) (setvar "CMDECHO" 0)
(command "_undo" "_G") (command "_undo" "_G")
(graphscr) (graphscr)
@@ -39,26 +53,30 @@
(princ) (princ)
) )
(defun ssg-end (/ xpos xlen xvar) (defun ssg-end (/ frame cavar xpos xlen xvar)
(if _ssg-cavar (if *ssg-start-stack*
(progn (progn
(setq frame (car *ssg-start-stack*)
*ssg-start-stack* (cdr *ssg-start-stack*)
cavar (cdr frame)
)
(command) (command)
(command "_undo" "_E") (command "_undo" "_E")
(setq xpos 1 (setq xpos 1
xlen (length _ssg-cavar) xlen (length cavar)
) )
(if (/= (getvar "CLAYER") (caar _ssg-cavar)) (if (/= (getvar "CLAYER") (caar cavar))
(command "_LAYER" "_SE" (cdar _ssg-cavar) "") (command "_LAYER" "_SE" (cdar cavar) "")
) )
(repeat (1- xlen) (repeat (1- xlen)
(setq xvar (nth xpos _ssg-cavar) (setq xvar (nth xpos cavar)
xpos (1+ xpos) xpos (1+ xpos)
) )
(setvar (car xvar) (cdr xvar)) (setvar (car xvar) (cdr xvar))
) )
(setq *error* (car frame))
) )
) )
(if _ssg-olderr (setq *error* _ssg-olderr))
(princ) (princ)
) )
@@ -485,7 +503,56 @@
;; (einsegmentige Gefaellestrecke: 1; Streckengruppe: gezaehlt). ;; (einsegmentige Gefaellestrecke: 1; Streckengruppe: gezaehlt).
(setq *strecke-attr-hinten* (setq *strecke-attr-hinten*
'(("ANZAHL_SEPARATOR" "1") '(("ANZAHL_SEPARATOR" "1")
("ANZAHL_SCANNER" "0"))) ("ANZAHL_SCANNER" "0")
("GERUEST_EINZELMODUL" "0")
("GERUEST_TYP" "Schoenenberger Geruest")))
;; ============================================================
;; GERUESTOPTION - gemeinsame Combobox-Werte fuer Kreisel, Eckrad,
;; VarioFoerderer und Gefaellestrecke (Attribut GERUEST_TYP).
;; Reihenfolge = Reihenfolge in der Dialog-Combobox. Index 2
;; ("Schoenenberger Geruest") ist der Default.
;; ============================================================
(setq *ssg-geruest-optionen*
'("IPE-Geruest abgestuft"
"Obergeruest oben"
"Schoenenberger Geruest"
"nur Doppelrohrtraeger")
)
;; Geruest-Typ (String) -> Combobox-Index. Unbekannter/leerer Wert -> Default (2).
(defun ssg-geruest-typ-to-idx (typ / idx i gefunden)
(setq idx 2 i 0 gefunden nil)
(foreach opt *ssg-geruest-optionen*
(if (and (not gefunden) (equal typ opt))
(progn (setq idx i) (setq gefunden T))
)
(setq i (1+ i))
)
idx
)
;; Combobox-Index -> Geruest-Typ (String).
(defun ssg-geruest-idx-to-typ (idx)
(nth idx *ssg-geruest-optionen*)
)
;; Geruestoption per Kommandozeilen-Menue abfragen (fuer Module ohne DCL-Dialog,
;; z.B. ILS_Eckrad). Rueckgabe: Geruest-Typ-String aus *ssg-geruest-optionen*.
(defun ssg-ask-geruest-typ ( / i opt antwort idx)
(princ (ssg-text "geruest-typ-header"))
(setq i 1)
(foreach opt *ssg-geruest-optionen*
(princ (ssg-textf "geruest-typ-opt" (list i opt)))
(setq i (1+ i))
)
(setq antwort (getint (ssg-textf "geruest-typ-prompt" (list (itoa (1+ (ssg-geruest-typ-to-idx nil)))))))
(if (or (null antwort) (< antwort 1) (> antwort (length *ssg-geruest-optionen*)))
(setq idx (ssg-geruest-typ-to-idx nil))
(setq idx (1- antwort))
)
(ssg-geruest-idx-to-typ idx)
)
;; Geordnete ATTDEF-Definitionsliste fuer einen Strecken-Block-Typ. ;; Geordnete ATTDEF-Definitionsliste fuer einen Strecken-Block-Typ.
;; typ "Gefaellestrecke" -> Vorderteil + Hinterteil (reduziert) ;; typ "Gefaellestrecke" -> Vorderteil + Hinterteil (reduziert)
+31 -3
View File
@@ -31,6 +31,19 @@ pattern_ks_subblocks= KS_EIN, KS_AUS, K1, K2, K3, K4
[Planquadrate] [Planquadrate]
section=Planquadrate_AN section=Planquadrate_AN
# x_origin/y_origin (in m, DXF-Koordinate der Planquadrat-Ecke A/1 bzw. 1/1):
# Der Zeichnungsnullpunkt (0,0) liegt in der Regel NICHT in der Gebaeudeecke -
# Bauteile mit negativer x/y-Koordinate wuerden ohne Offset einen Planquadrat-
# Index <= 0 ergeben und damit ein leeres Label (z.B. "/" oder "A/") liefern.
# Leer lassen/weglassen = automatisch: der Ursprung wird bei jedem Export neu
# auf das jeweils am weitesten links (x_origin) bzw. am weitesten unten
# (y_origin) liegende Element der aktuellen Zeichnung gesetzt, damit gilt
# immer Index 1 = dieses Element. Nur explizit setzen, wenn ein fester
# Bezug zur realen Gebaeudeecke gebraucht wird (z.B. Vergleich ueber
# mehrere Exportlaeufe/Zeichnungen hinweg).
x_origin=
y_origin=
# hier kann man im csv Export aus den Koordinaten der Bauteile die Planquadrate berechnen lassen, in denen sie liegen # hier kann man im csv Export aus den Koordinaten der Bauteile die Planquadrate berechnen lassen, in denen sie liegen
# Zählung ist numerisch oder Alphabetisch möglich, Schrittweite in m (z.B. 2m pro Spalte, 4m pro Zeile) # Zählung ist numerisch oder Alphabetisch möglich, Schrittweite in m (z.B. 2m pro Spalte, 4m pro Zeile)
# liegt man im ersten Quadrat, ist diese A/1, oder 1/1 oder 1/A, je nach Formatierung. Die Zählung beginnt immer bei 1 # liegt man im ersten Quadrat, ist diese A/1, oder 1/1 oder 1/A, je nach Formatierung. Die Zählung beginnt immer bei 1
@@ -61,7 +74,22 @@ format= {x}/{y}
[Nachbarschaft] [Nachbarschaft]
# Toleranz fuer die Nachbarschaftserkennung beim CSV-Export (Spalte "Nachbarn"). # Toleranz fuer die Nachbarschaftserkennung beim CSV-Export (Spalte "Nachbarn").
# Die Bounding-Box jedes Elements wird um die Haelfte dieses Werts nach allen # Die Bounding-Box jedes Elements wird um die Haelfte dieses Werts nach allen
# Seiten erweitert, bevor per STRtree (shapely) auf Ueberschneidung mit anderen # Seiten erweitert, bevor auf Ueberschneidung mit anderen Elementen geprueft
# Elementen geprueft wird - zwei Elemente mit einem Abstand <= toleranz_mm # wird - zwei Elemente mit einem Abstand <= toleranz_mm (z.B. zwei Kreisel)
# (z.B. zwei Kreisel) gelten dann ebenfalls als benachbart. Wert in mm. # gelten dann ebenfalls als benachbart. Wert in mm. Siehe lib/export_neighbors.py.
toleranz_mm=200 toleranz_mm=200
# Rastergroesse (mm) fuer die Omniflo-Nachbarschaftspruefung (Bogen/Weiche/
# Gerade gegen Bogen/Weiche/Gerade). Omniflo-Elemente werden vor dem
# Ueberschneidungstest nach x/y-Koordinate in Quadranten dieser Groesse
# eingeteilt, geprueft wird dann nur innerhalb derselben und der 8
# angrenzenden Zellen (statt jedes Element gegen jedes). Sollte groesser
# als die ueblichen Omniflo-Bauteile sein (AP110-Geraden ca. 2000mm).
omniflo_zellgroesse_mm=3000
[Boundingbox]
# Mindesthoehe (Z-Ausdehnung) der von export.lsp (csv:get-bbox, per
# vla-getboundingbox) ermittelten Bounding-Box. Flache 2D-Bloecke (Draufsicht)
# haben oft dz=0 - wird auf diesen Wert angehoben. Wert in mm. Default 1, falls
# nicht gesetzt.
bb_minimum_height_mm=1
+49 -21
View File
@@ -11,7 +11,7 @@ Aufruf:
python export_csv.py <export_raw.json> <data_dir> <output.csv> python export_csv.py <export_raw.json> <data_dir> <output.csv>
CSV-Format: CSV-Format:
Elementnummer;TeileArt;TeileId;Bezeichnung;Planquadrat;Anzahl;Position;Boundingbox;Nachbarn;Merkmale Elementnummer;TeileArt;TeileId;Bezeichnung;Planquadrat;Anzahl;Position;Boundingbox;Nachbarn;Fehler;Merkmale
Position und Boundingbox stammen aus der von export.lsp (csv:get-bbox, per Position und Boundingbox stammen aus der von export.lsp (csv:get-bbox, per
vla-getboundingbox) ermittelten Bounding-Box je Block: vla-getboundingbox) ermittelten Bounding-Box je Block:
@@ -20,10 +20,21 @@ vla-getboundingbox) ermittelten Bounding-Box je Block:
Planquadrat wird aus der x/y-Koordinate des Blocks berechnet, siehe Planquadrat wird aus der x/y-Koordinate des Blocks berechnet, siehe
export_planquadrat.py ([Planquadrate] in cfg/export.cfg). export_planquadrat.py ([Planquadrate] in cfg/export.cfg).
Nachbarn = kommaseparierte TeileId-Liste ueberschneidender Elemente (Bounding- Nachbarn = kommaseparierte TeileId-Liste ueberschneidender Elemente (Bounding-
Box-Ueberschneidung in der x/y-Ebene per shapely-STRtree, Toleranz konfigurierbar Box-Ueberschneidung in der x/y-Ebene, reines Python ohne externe Abhaengigkeit,
ueber [Nachbarschaft] -> toleranz_mm in cfg/export.cfg), siehe export_neighbors.py. siehe export_neighbors.py). Geprueft wird NICHT global ueber alle Elemente,
Position, Boundingbox, Planquadrat und Nachbarn sind nur fuer EXPORTCSV sondern in drei getrennten Gruppen: 1) Kreisel/Eckrad gegen Kreisel/Eckrad,
vorhanden (nicht EXPORTSIVAS) - siehe csv:run-export. 2) Kreisel/Eckrad gegen Gefaellestrecke/Foerderer/Strecke-Modul (diese drei
nicht gegeneinander), 3) Omniflo-Elemente gegen Omniflo-Elemente (rasterbasiert
vorgefiltert nach x/y-Koordinate). Toleranz und Omniflo-Rastergroesse
konfigurierbar ueber [Nachbarschaft] in cfg/export.cfg.
Fehler = "unverbunden" (keine Partner, aber mindestens einer noetig),
"nur ein Partner" (ein Partner, aber mindestens zwei noetig) oder leer
(Mindestanzahl erreicht bzw. TeileArt wird nicht geprueft). Kreisel/Eckrad/
Omniflo-Elemente brauchen mindestens einen Partner, Gefaellestrecke/
Foerderer/Strecke-Modul mindestens zwei (siehe export_neighbors.py
MIN_PARTNER).
Position, Boundingbox, Planquadrat, Nachbarn und Fehler sind nur fuer
EXPORTCSV vorhanden (nicht EXPORTSIVAS) - siehe csv:run-export.
""" """
import json import json
@@ -31,12 +42,18 @@ import sys
import os import os
from export_blockpatterns import load_patterns, matches_any from export_blockpatterns import load_patterns, matches_any
from export_planquadrat import load_planquadrat_config, compute_planquadrat from export_planquadrat import load_planquadrat_config, resolve_origins, compute_planquadrat
from export_neighbors import load_neighbor_tolerance_mm, compute_neighbor_ids from export_neighbors import (
load_neighbor_tolerance_mm,
load_omniflo_cell_size_mm,
compute_neighbor_ids,
compute_neighbor_errors,
)
BLOCKPATTERNS = load_patterns() BLOCKPATTERNS = load_patterns()
PLANQUADRAT_CFG = load_planquadrat_config() PLANQUADRAT_CFG = load_planquadrat_config()
NEIGHBOR_TOLERANCE_MM = load_neighbor_tolerance_mm() NEIGHBOR_TOLERANCE_MM = load_neighbor_tolerance_mm()
NEIGHBOR_OMNIFLO_CELL_SIZE_MM = load_omniflo_cell_size_mm()
# --------------------------------------------------------------------------- # ---------------------------------------------------------------------------
@@ -258,19 +275,21 @@ def bbox_columns(block):
} }
def planquadrat_column(block): def planquadrat_column(block, planquadrat_cfg):
"""Berechnet das Planquadrat aus x/y des Blocks (siehe export_planquadrat.py). """Berechnet das Planquadrat aus x/y des Blocks (siehe export_planquadrat.py).
planquadrat_cfg = Rueckgabe von resolve_origins() fuer den aktuellen
Exportlauf (x_origin_mm/y_origin_mm bereits aufgeloest).
Leerer String, wenn keine Planquadrat-Konfiguration geladen werden konnte Leerer String, wenn keine Planquadrat-Konfiguration geladen werden konnte
(fehlende/unvollstaendige [Planquadrate]-Sektion in cfg/export.cfg). (fehlende/unvollstaendige [Planquadrate]-Sektion in cfg/export.cfg).
""" """
if PLANQUADRAT_CFG is None: if planquadrat_cfg is None:
return "" return ""
x = block.get("x") x = block.get("x")
y = block.get("y") y = block.get("y")
if x is None or y is None: if x is None or y is None:
return "" return ""
return compute_planquadrat(float(x), float(y), PLANQUADRAT_CFG) return compute_planquadrat(float(x), float(y), planquadrat_cfg)
# --------------------------------------------------------------------------- # ---------------------------------------------------------------------------
@@ -285,6 +304,11 @@ SKIP_BLOCKS = set(BLOCKPATTERNS.get("pattern_ks_subblocks", ["K1", "K2", "K3", "
# --------------------------------------------------------------------------- # ---------------------------------------------------------------------------
def process_blocks(blocks, lookup): def process_blocks(blocks, lookup):
# x_origin_mm/y_origin_mm einmalig fuer diesen Exportlauf aufloesen (siehe
# export_planquadrat.resolve_origins): automatisch aus den Bloecken, falls
# nicht explizit in [Planquadrate] konfiguriert.
planquadrat_cfg = resolve_origins(PLANQUADRAT_CFG, blocks)
items = [] items = []
elem_nr = 0 elem_nr = 0
bogen_count = 0 bogen_count = 0
@@ -322,7 +346,7 @@ def process_blocks(blocks, lookup):
"teileart": "Omniflo Kurve", "teileart": "Omniflo Kurve",
"teileid": shape_id, "teileid": shape_id,
"bezeichnung": f"OFBogen :{bogen_count}", "bezeichnung": f"OFBogen :{bogen_count}",
"planquadrat": planquadrat_column(block), "planquadrat": planquadrat_column(block, planquadrat_cfg),
"merkmale": build_bogen_merkmale(block, eintrag), "merkmale": build_bogen_merkmale(block, eintrag),
**bbox_columns(block), **bbox_columns(block),
}) })
@@ -335,7 +359,7 @@ def process_blocks(blocks, lookup):
"teileart": "Omniflo Weiche", "teileart": "Omniflo Weiche",
"teileid": shape_id, "teileid": shape_id,
"bezeichnung": f"OFWeiche :{weiche_count[wt]}", "bezeichnung": f"OFWeiche :{weiche_count[wt]}",
"planquadrat": planquadrat_column(block), "planquadrat": planquadrat_column(block, planquadrat_cfg),
"merkmale": build_weiche_merkmale(block, eintrag), "merkmale": build_weiche_merkmale(block, eintrag),
**bbox_columns(block), **bbox_columns(block),
}) })
@@ -362,7 +386,7 @@ def process_blocks(blocks, lookup):
"teileart": "Omniflo Gerade", "teileart": "Omniflo Gerade",
"teileid": block.get("attribs", {}).get("ID", "0000"), "teileid": block.get("attribs", {}).get("ID", "0000"),
"bezeichnung": f"OFGerade :{gerade_count}", "bezeichnung": f"OFGerade :{gerade_count}",
"planquadrat": planquadrat_column(block), "planquadrat": planquadrat_column(block, planquadrat_cfg),
"merkmale": build_gerade_merkmale(block), "merkmale": build_gerade_merkmale(block),
**bbox_columns(block), **bbox_columns(block),
}) })
@@ -378,7 +402,7 @@ def process_blocks(blocks, lookup):
"teileart": "ILS 2.0 Strecke", "teileart": "ILS 2.0 Strecke",
"teileid": block.get("attribs", {}).get("ID", "0000"), "teileid": block.get("attribs", {}).get("ID", "0000"),
"bezeichnung": f"VarioFoerderer :{vf_count}", "bezeichnung": f"VarioFoerderer :{vf_count}",
"planquadrat": planquadrat_column(block), "planquadrat": planquadrat_column(block, planquadrat_cfg),
"merkmale": build_variofoerderer_merkmale(block), "merkmale": build_variofoerderer_merkmale(block),
**bbox_columns(block), **bbox_columns(block),
}) })
@@ -393,7 +417,7 @@ def process_blocks(blocks, lookup):
"teileart": "ILS 2.0 Gefaellestrecke", "teileart": "ILS 2.0 Gefaellestrecke",
"teileid": block.get("attribs", {}).get("ID", "0000"), "teileid": block.get("attribs", {}).get("ID", "0000"),
"bezeichnung": f"Gefaellestrecke :{gf_count}", "bezeichnung": f"Gefaellestrecke :{gf_count}",
"planquadrat": planquadrat_column(block), "planquadrat": planquadrat_column(block, planquadrat_cfg),
"merkmale": build_variofoerderer_merkmale(block), "merkmale": build_variofoerderer_merkmale(block),
**bbox_columns(block), **bbox_columns(block),
}) })
@@ -409,7 +433,7 @@ def process_blocks(blocks, lookup):
"teileart": "ILS 2.0 Eckrad", "teileart": "ILS 2.0 Eckrad",
"teileid": block.get("attribs", {}).get("ID", "0000"), "teileid": block.get("attribs", {}).get("ID", "0000"),
"bezeichnung": f"Eckrad :{eckrad_count}", "bezeichnung": f"Eckrad :{eckrad_count}",
"planquadrat": planquadrat_column(block), "planquadrat": planquadrat_column(block, planquadrat_cfg),
"merkmale": build_kreisel_merkmale(block), "merkmale": build_kreisel_merkmale(block),
**bbox_columns(block), **bbox_columns(block),
}) })
@@ -424,7 +448,7 @@ def process_blocks(blocks, lookup):
"teileart": "ILS 2.0 Kreisel", "teileart": "ILS 2.0 Kreisel",
"teileid": block.get("attribs", {}).get("ID", "0000"), "teileid": block.get("attribs", {}).get("ID", "0000"),
"bezeichnung": f"Kreisel :{kreisel_count}", "bezeichnung": f"Kreisel :{kreisel_count}",
"planquadrat": planquadrat_column(block), "planquadrat": planquadrat_column(block, planquadrat_cfg),
"merkmale": build_kreisel_merkmale(block), "merkmale": build_kreisel_merkmale(block),
**bbox_columns(block), **bbox_columns(block),
}) })
@@ -439,7 +463,7 @@ def process_blocks(blocks, lookup):
"teileart": "ILS 2.0 Strecke - Modul", "teileart": "ILS 2.0 Strecke - Modul",
"teileid": block.get("attribs", {}).get("ID", "0000"), "teileid": block.get("attribs", {}).get("ID", "0000"),
"bezeichnung": f"Streckenmodul :{strecke_modul_count}", "bezeichnung": f"Streckenmodul :{strecke_modul_count}",
"planquadrat": planquadrat_column(block), "planquadrat": planquadrat_column(block, planquadrat_cfg),
"merkmale": {"Blockname": bname}, "merkmale": {"Blockname": bname},
**bbox_columns(block), **bbox_columns(block),
}) })
@@ -460,9 +484,12 @@ def process_blocks(blocks, lookup):
"boundingbox": "", "boundingbox": "",
}) })
neighbor_ids = compute_neighbor_ids(items, NEIGHBOR_TOLERANCE_MM) neighbor_ids = compute_neighbor_ids(
for item, nachbarn in zip(items, neighbor_ids): items, NEIGHBOR_TOLERANCE_MM, NEIGHBOR_OMNIFLO_CELL_SIZE_MM)
neighbor_errors = compute_neighbor_errors(items, neighbor_ids)
for item, nachbarn, fehler in zip(items, neighbor_ids, neighbor_errors):
item["nachbarn"] = nachbarn item["nachbarn"] = nachbarn
item["fehler"] = fehler
return items return items
@@ -483,6 +510,7 @@ def format_csv_line(item):
f';"{item["position"]}"' f';"{item["position"]}"'
f';"{item["boundingbox"]}"' f';"{item["boundingbox"]}"'
f';"{item["nachbarn"]}"' f';"{item["nachbarn"]}"'
f';"{item["fehler"]}"'
f';{merkmale_json}' f';{merkmale_json}'
) )
@@ -514,7 +542,7 @@ def main():
items = process_blocks(blocks, lookup) items = process_blocks(blocks, lookup)
header = "Elementnummer;TeileArt;TeileId;Bezeichnung;Planquadrat;Anzahl;Position;Boundingbox;Nachbarn;Merkmale" header = "Elementnummer;TeileArt;TeileId;Bezeichnung;Planquadrat;Anzahl;Position;Boundingbox;Nachbarn;Fehler;Merkmale"
with open(output_csv, "w", encoding="utf-8") as f: with open(output_csv, "w", encoding="utf-8") as f:
f.write(header + "\n") f.write(header + "\n")
for item in items: for item in items:
+195 -41
View File
@@ -1,27 +1,57 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
# -*- coding: utf-8 -*- # -*- coding: utf-8 -*-
""" """
export_neighbors.py - Ermittelt benachbarte Elemente ueber die Bounding-Box (STRtree). export_neighbors.py - Ermittelt benachbarte Elemente ueber Bounding-Box-
Ueberschneidung in der x/y-Ebene (Grundriss, Z/Hoehe wird ignoriert).
Zwei Elemente gelten als benachbart, wenn ihre Bounding-Boxes sich in der Reines Python (keine externe Abhaengigkeit wie shapely) - die Bloecke werden
x/y-Ebene (Grundriss, Z/Hoehe wird ignoriert) ueberschneiden. Um auch nah dazu in drei Gruppen eingeteilt und NUR innerhalb dieser Kombinationen
beieinander liegende, aber nicht direkt beruehrende Elemente (z.B. Kreisel) gegeneinander geprueft (nicht mehr alle Elemente einer Zeichnung gemeinsam):
als benachbart zu erkennen, wird jede Bounding-Box vor der Pruefung um die
Haelfte der konfigurierten Toleranz nach allen Seiten erweitert - zwei 1. Kreisel/Eckrad gegen Kreisel/Eckrad
Elemente mit einem Abstand <= toleranz_mm gelten dann ebenfalls als 2. Kreisel/Eckrad gegen Gefaellestrecke/Foerderer/Strecke-Modul - diese
benachbart. Die Toleranz wird aus cfg/export.cfg ([Nachbarschaft] -> drei Kategorien werden NICHT gegeneinander getestet (nur relevant, wo
toleranz_mm) gelesen. sie an einen Kreisel/Eckrad anschliessen)
3. Omniflo-Elemente (Bogen/Weiche/Gerade) gegen Omniflo-Elemente
Omniflo-Anlagen koennen mehrere hundert Elemente enthalten - ein Test jedes
gegen jedes (O(n^2)) waere dort zu teuer. Die Omniflo-Gruppe wird daher vorab
per Raster (Zellgroesse siehe [Nachbarschaft] -> omniflo_zellgroesse_mm in
cfg/export.cfg) nach x/y-Koordinate in Quadranten/Zellen eingeteilt; jedes
Element wird nur gegen Elemente in derselben und den 8 angrenzenden Zellen
geprueft (3x3-Nachbarschaft, damit auch Elemente knapp jenseits einer
Zellgrenze noch erkannt werden).
Zwei Bounding-Boxes gelten als benachbart, wenn sie sich (nach Erweiterung
um die halbe Toleranz je Seite) in x/y ueberschneiden. Toleranz aus
cfg/export.cfg ([Nachbarschaft] -> toleranz_mm), Wert in mm.
compute_neighbor_errors() prueft zusaetzlich, ob jedes Element die fuer
seine TeileArt noetige Mindestanzahl an Partnern (Nachbarn) hat (siehe
MIN_PARTNER) - Ergebnis ist die CSV-Spalte "Fehler" in export_csv.py.
Nur von export_csv.py genutzt (EXPORTCSV), nicht von export_sivas.py. Nur von export_csv.py genutzt (EXPORTCSV), nicht von export_sivas.py.
""" """
import configparser import configparser
from shapely.geometry import box
from shapely.strtree import STRtree
from export_blockpatterns import cfg_path_from_env from export_blockpatterns import cfg_path_from_env
KREISEL_TEILEARTEN = {"ILS 2.0 Kreisel", "ILS 2.0 Eckrad"}
STRECKEN_TEILEARTEN = {"ILS 2.0 Gefaellestrecke", "ILS 2.0 Strecke", "ILS 2.0 Strecke - Modul"}
OMNIFLO_TEILEARTEN = {"Omniflo Kurve", "Omniflo Weiche", "Omniflo Gerade"}
# Mindestanzahl Partner (Nachbarn) je TeileArt fuer die Fehlerspalte "Fehler"
# (siehe compute_neighbor_errors): Kreisel/Eckrad und Omniflo-Elemente
# brauchen mindestens einen Partner, Gefaellestrecke/Foerderer/Strecke-Modul
# muessen an zwei Seiten anschliessen (mindestens zwei Partner). TeileArten,
# die hier nicht auftauchen (z.B. die synthetische "Omniflo Sum"-Zeile),
# werden nicht geprueft.
MIN_PARTNER = {}
MIN_PARTNER.update({t: 1 for t in KREISEL_TEILEARTEN})
MIN_PARTNER.update({t: 1 for t in OMNIFLO_TEILEARTEN})
MIN_PARTNER.update({t: 2 for t in STRECKEN_TEILEARTEN})
def load_neighbor_tolerance_mm(cfg_path=None): def load_neighbor_tolerance_mm(cfg_path=None):
"""Liest die Nachbarschafts-Toleranz (mm) aus export.cfg. Default: 0.""" """Liest die Nachbarschafts-Toleranz (mm) aus export.cfg. Default: 0."""
@@ -32,41 +62,165 @@ def load_neighbor_tolerance_mm(cfg_path=None):
return parser.getfloat("Nachbarschaft", "toleranz_mm", fallback=0.0) return parser.getfloat("Nachbarschaft", "toleranz_mm", fallback=0.0)
def compute_neighbor_ids(items, tolerance_mm): def load_omniflo_cell_size_mm(cfg_path=None):
"""Ermittelt je Item die IDs (item["teileid"]) ueberschneidender Nachbarn. """Liest die Rastergroesse (mm) fuer die Omniflo-Nachbarschaftspruefung.
items = Liste von dict mit "teileid" und optional "_bbox" Default 3000mm: groesser als die ueblichen Omniflo-Bauteile (AP110-
({"cx","cy","dx","dy",...}, siehe export.lsp csv:get-bbox / export_csv.py Geraden ca. 2000mm), damit ein Element nicht durch ein zu kleines
bbox_columns). Items ohne _bbox (z.B. die synthetische Omniflo-Sum-Zeile) Raster in mehr als eine Zelle ueberlappt.
haben keine Nachbarn. """
if cfg_path is None:
cfg_path = cfg_path_from_env()
parser = configparser.ConfigParser(inline_comment_prefixes=("#",))
parser.read(cfg_path, encoding="utf-8")
return parser.getfloat("Nachbarschaft", "omniflo_zellgroesse_mm", fallback=3000.0)
def _bounds(bbox, half_tol):
"""(minx, maxx, miny, maxy) einer Bounding-Box, je Seite um half_tol erweitert."""
return (
bbox["cx"] - bbox["dx"] / 2.0 - half_tol,
bbox["cx"] + bbox["dx"] / 2.0 + half_tol,
bbox["cy"] - bbox["dy"] / 2.0 - half_tol,
bbox["cy"] + bbox["dy"] / 2.0 + half_tol,
)
def _overlaps(bounds_a, bounds_b):
"""True, wenn sich zwei (minx, maxx, miny, maxy)-Rechtecke in x/y ueberschneiden."""
a_minx, a_maxx, a_miny, a_maxy = bounds_a
b_minx, b_maxx, b_miny, b_maxy = bounds_b
return a_minx <= b_maxx and b_minx <= a_maxx and a_miny <= b_maxy and b_miny <= a_maxy
def _add_neighbor(result, idx_a, idx_b, id_a, id_b):
result[idx_a].append(id_b)
result[idx_b].append(id_a)
def _test_group_pairs(group, result):
"""Alle Paare EINER Gruppe gegeneinander testen (O(n^2) - fuer Kreisel/
Eckrad-Stueckzahlen pro Zeichnung unkritisch)."""
n = len(group)
for a in range(n):
idx_a, bounds_a, id_a = group[a]
for b in range(a + 1, n):
idx_b, bounds_b, id_b = group[b]
if _overlaps(bounds_a, bounds_b):
_add_neighbor(result, idx_a, idx_b, id_a, id_b)
def _test_group_against_group(group_a, group_b, result):
"""Jedes Element aus group_a gegen jedes Element aus group_b testen.
group_b wird NICHT gegen sich selbst getestet (Aufgabe des Aufrufers)."""
for idx_a, bounds_a, id_a in group_a:
for idx_b, bounds_b, id_b in group_b:
if _overlaps(bounds_a, bounds_b):
_add_neighbor(result, idx_a, idx_b, id_a, id_b)
def _grid_cell(bbox, cell_size_mm):
"""Rasterzelle (Quadrant) einer Bounding-Box nach ihrem Mittelpunkt."""
return (int(bbox["cx"] // cell_size_mm), int(bbox["cy"] // cell_size_mm))
def _test_omniflo_grid(group, cell_size_mm, result):
"""Omniflo-Elemente nur gegen Elemente in derselben oder einer der 8
angrenzenden Rasterzellen testen (3x3-Nachbarschaft) statt gegen alle -
haelt den Aufwand bei mehreren hundert Omniflo-Elementen niedrig, ohne
Ueberschneidungen an Zellgrenzen zu verpassen."""
buckets = {}
for entry in group:
idx, bounds, teileid, bbox = entry
buckets.setdefault(_grid_cell(bbox, cell_size_mm), []).append(entry)
checked = set()
for (cx, cy), cell_items in buckets.items():
candidates = []
for dx in (-1, 0, 1):
for dy in (-1, 0, 1):
candidates.extend(buckets.get((cx + dx, cy + dy), []))
for idx_a, bounds_a, id_a, _ in cell_items:
for idx_b, bounds_b, id_b, _ in candidates:
if idx_a >= idx_b:
continue
pair = (idx_a, idx_b)
if pair in checked:
continue
checked.add(pair)
if _overlaps(bounds_a, bounds_b):
_add_neighbor(result, idx_a, idx_b, id_a, id_b)
def compute_neighbor_ids(items, tolerance_mm, omniflo_cell_size_mm=3000.0):
"""Ermittelt je Item die IDs (item["teileid"]) benachbarter Elemente.
items = Liste von dict mit "teileart", "teileid" und optional "_bbox"
({"cx","cy","dx","dy",...}, siehe export_csv.py bbox_columns). Items
ohne _bbox (z.B. die synthetische Omniflo-Sum-Zeile) bleiben ohne
Nachbarn.
Rueckgabe: Liste von kommaseparierten Nachbar-ID-Strings, positionsgleich Rueckgabe: Liste von kommaseparierten Nachbar-ID-Strings, positionsgleich
zu items (nicht ueber die ID dedupliziert, da TeileId nicht zwingend zu items (nicht ueber die ID dedupliziert, da TeileId nicht zwingend
eindeutig ist). eindeutig ist).
""" """
idx_with_bbox = [i for i, it in enumerate(items) if it.get("_bbox")]
result = [""] * len(items)
if len(idx_with_bbox) < 2:
return result
half_tol = tolerance_mm / 2.0 half_tol = tolerance_mm / 2.0
geoms = [] result = [[] for _ in items]
for i in idx_with_bbox:
bb = items[i]["_bbox"]
minx = bb["cx"] - bb["dx"] / 2.0 - half_tol
maxx = bb["cx"] + bb["dx"] / 2.0 + half_tol
miny = bb["cy"] - bb["dy"] / 2.0 - half_tol
maxy = bb["cy"] + bb["dy"] / 2.0 + half_tol
geoms.append(box(minx, miny, maxx, maxy))
tree = STRtree(geoms) kreisel_group = []
for local_i, global_i in enumerate(idx_with_bbox): strecken_group = []
hits = tree.query(geoms[local_i], predicate="intersects") omniflo_group = []
neighbor_ids = [
items[idx_with_bbox[int(local_j)]]["teileid"]
for local_j in hits
if int(local_j) != local_i
]
result[global_i] = ", ".join(neighbor_ids)
return result for idx, item in enumerate(items):
bbox = item.get("_bbox")
if not bbox:
continue
teileart = item.get("teileart", "")
teileid = item.get("teileid", "")
bounds = _bounds(bbox, half_tol)
if teileart in KREISEL_TEILEARTEN:
kreisel_group.append((idx, bounds, teileid))
elif teileart in STRECKEN_TEILEARTEN:
strecken_group.append((idx, bounds, teileid))
elif teileart in OMNIFLO_TEILEARTEN:
omniflo_group.append((idx, bounds, teileid, bbox))
# 1. Kreisel/Eckrad gegen Kreisel/Eckrad
_test_group_pairs(kreisel_group, result)
# 2. Kreisel/Eckrad gegen Gefaellestrecke/Foerderer/Strecke-Modul -
# diese drei Kategorien nicht gegeneinander (siehe Modul-Docstring)
_test_group_against_group(kreisel_group, strecken_group, result)
# 3. Omniflo gegen Omniflo, rasterbasiert vorgefiltert
_test_omniflo_grid(omniflo_group, omniflo_cell_size_mm, result)
return [", ".join(neighbor_ids) for neighbor_ids in result]
def compute_neighbor_errors(items, neighbor_ids):
"""Prueft je Item die Mindestanzahl an Partnern (siehe MIN_PARTNER).
items = dieselbe Liste wie bei compute_neighbor_ids (braucht "teileart").
neighbor_ids = Rueckgabe von compute_neighbor_ids (positionsgleich zu items).
Rueckgabe: Liste von Fehlertexten, positionsgleich zu items:
"unverbunden" - keine Partner, obwohl mindestens einer noetig waere
"nur ein Partner" - genau ein Partner, obwohl mindestens zwei noetig waeren
"" - Mindestanzahl erreicht, oder TeileArt wird nicht geprueft
"""
errors = []
for item, nachbarn in zip(items, neighbor_ids):
min_partner = MIN_PARTNER.get(item.get("teileart", ""))
if min_partner is None:
errors.append("")
continue
anzahl = len([p for p in nachbarn.split(",") if p.strip()])
if anzahl == 0:
errors.append("unverbunden")
elif anzahl == 1 and min_partner >= 2:
errors.append("nur ein Partner")
else:
errors.append("")
return errors
-1
View File
@@ -3,5 +3,4 @@
ezdxf==1.4.1 ezdxf==1.4.1
pytest==9.0.2 pytest==9.0.2
shapely==2.1.2
+109 -109
View File
@@ -1,109 +1,109 @@
Elementnummer;TeileArt;TeileId;Bezeichnung;Planquadrat;Anzahl;Position;Boundingbox;Nachbarn;Merkmale Elementnummer;TeileArt;TeileId;Bezeichnung;Planquadrat;Anzahl;Position;Boundingbox;Nachbarn;Fehler;Merkmale
1;"Omniflo Kurve";"0000";"OFBogen :1";"A/A";1;"";"";"";{"Kurvenwinkel": 22.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104025"} 1;"Omniflo Kurve";"0000";"OFBogen :1";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 22.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104025"}
2;"Omniflo Kurve";"0000";"OFBogen :2";"A/A";1;"";"";"";{"Kurvenwinkel": 22.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104025+0_B10090"} 2;"Omniflo Kurve";"0000";"OFBogen :2";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 22.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104025, 0_B10090"}
3;"Omniflo Kurve";"0000";"OFBogen :3";"A/A";1;"";"";"";{"Kurvenwinkel": 22.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104025+0_B10091"} 3;"Omniflo Kurve";"0000";"OFBogen :3";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 22.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104025, 0_B10091"}
4;"Omniflo Kurve";"0000";"OFBogen :4";"A/A";1;"";"";"";{"Kurvenwinkel": 45.0, "Radius": 400.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104021"} 4;"Omniflo Kurve";"0000";"OFBogen :4";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 45.0, "Radius": 400.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104021"}
5;"Omniflo Kurve";"0000";"OFBogen :5";"A/A";1;"";"";"";{"Kurvenwinkel": 45.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104026"} 5;"Omniflo Kurve";"0000";"OFBogen :5";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 45.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104026"}
6;"Omniflo Kurve";"0000";"OFBogen :6";"A/A";1;"";"";"";{"Kurvenwinkel": 45.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104026+0_B10071"} 6;"Omniflo Kurve";"0000";"OFBogen :6";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 45.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104026, 0_B10071"}
7;"Omniflo Kurve";"0000";"OFBogen :7";"A/A";1;"";"";"";{"Kurvenwinkel": 45.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104037"} 7;"Omniflo Kurve";"0000";"OFBogen :7";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 45.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104037"}
8;"Omniflo Kurve";"0000";"OFBogen :8";"A/A";1;"";"";"";{"Kurvenwinkel": 45.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104029"} 8;"Omniflo Kurve";"0000";"OFBogen :8";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 45.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104029"}
9;"Omniflo Kurve";"0000";"OFBogen :9";"A/A";1;"";"";"";{"Kurvenwinkel": 45.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104031"} 9;"Omniflo Kurve";"0000";"OFBogen :9";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 45.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104031"}
10;"Omniflo Kurve";"0000";"OFBogen :10";"A/A";1;"";"";"";{"Kurvenwinkel": 45.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104031+0_B10060"} 10;"Omniflo Kurve";"0000";"OFBogen :10";"A/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 45.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104031, 0_B10060"}
11;"Omniflo Kurve";"0000";"OFBogen :11";"B/A";1;"";"";"";{"Kurvenwinkel": 45.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104031+0_B10070"} 11;"Omniflo Kurve";"0000";"OFBogen :11";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 45.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104031, 0_B10070"}
12;"Omniflo Kurve";"0000";"OFBogen :12";"B/A";1;"";"";"";{"Kurvenwinkel": 67.5, "Radius": 400.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104024"} 12;"Omniflo Kurve";"0000";"OFBogen :12";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 67.5, "Radius": 400.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104024"}
13;"Omniflo Kurve";"0000";"OFBogen :13";"B/A";1;"";"";"";{"Kurvenwinkel": 67.5, "Radius": 400.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104024+0_B10081"} 13;"Omniflo Kurve";"0000";"OFBogen :13";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 67.5, "Radius": 400.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104024, 0_B10081"}
14;"Omniflo Kurve";"0000";"OFBogen :14";"B/A";1;"";"";"";{"Kurvenwinkel": 67.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104027"} 14;"Omniflo Kurve";"0000";"OFBogen :14";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 67.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104027"}
15;"Omniflo Kurve";"0000";"OFBogen :15";"B/A";1;"";"";"";{"Kurvenwinkel": 67.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104027+0_B10080"} 15;"Omniflo Kurve";"0000";"OFBogen :15";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 67.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104027, 0_B10080"}
16;"Omniflo Kurve";"0000";"OFBogen :16";"B/A";1;"";"";"";{"Kurvenwinkel": 67.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104028"} 16;"Omniflo Kurve";"0000";"OFBogen :16";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 67.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104028"}
17;"Omniflo Kurve";"0000";"OFBogen :17";"B/A";1;"";"";"";{"Kurvenwinkel": 67.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104065"} 17;"Omniflo Kurve";"0000";"OFBogen :17";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 67.5, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104065"}
18;"Omniflo Kurve";"0000";"OFBogen :18";"B/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 400.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104022"} 18;"Omniflo Kurve";"0000";"OFBogen :18";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 400.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104022"}
19;"Omniflo Kurve";"0000";"OFBogen :19";"B/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 500.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104030"} 19;"Omniflo Kurve";"0000";"OFBogen :19";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 500.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104030"}
20;"Omniflo Kurve";"0000";"OFBogen :20";"B/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104033"} 20;"Omniflo Kurve";"0000";"OFBogen :20";"B/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104033"}
21;"Omniflo Kurve";"0000";"OFBogen :21";"C/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104033+0_B10040"} 21;"Omniflo Kurve";"0000";"OFBogen :21";"C/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104033, 0_B10040"}
22;"Omniflo Kurve";"0000";"OFBogen :22";"C/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104033+0_B10050"} 22;"Omniflo Kurve";"0000";"OFBogen :22";"C/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104033, 0_B10050"}
23;"Omniflo Kurve";"0000";"OFBogen :23";"C/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104035"} 23;"Omniflo Kurve";"0000";"OFBogen :23";"C/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104035"}
24;"Omniflo Kurve";"0000";"OFBogen :24";"C/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104041"} 24;"Omniflo Kurve";"0000";"OFBogen :24";"C/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104041"}
25;"Omniflo Kurve";"0000";"OFBogen :25";"C/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104034"} 25;"Omniflo Kurve";"0000";"OFBogen :25";"C/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 630.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104034"}
26;"Omniflo Kurve";"0000";"OFBogen :26";"C/A";1;"";"";"";{"Kurvenwinkel": 90.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104066"} 26;"Omniflo Kurve";"0000";"OFBogen :26";"C/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 90.0, "Radius": 550.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104066"}
27;"Omniflo Kurve";"0000";"OFBogen :27";"C/A";1;"";"";"";{"Kurvenwinkel": 180.0, "Radius": 650.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104043"} 27;"Omniflo Kurve";"0000";"OFBogen :27";"C/A";1;"";"";"";"unverbunden";{"Kurvenwinkel": 180.0, "Radius": 650.0, "Höhe": "2000", "Drehung": 0.0, "SivasNummer": "821104043"}
28;"Omniflo Weiche";"0000";"OFWeiche :1";"C/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342011"} 28;"Omniflo Weiche";"0000";"OFWeiche :1";"C/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342011"}
29;"Omniflo Weiche";"0000";"OFWeiche :2";"C/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342001"} 29;"Omniflo Weiche";"0000";"OFWeiche :2";"C/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342001"}
30;"Omniflo Weiche";"0000";"OFWeiche :3";"C/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342012"} 30;"Omniflo Weiche";"0000";"OFWeiche :3";"C/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342012"}
31;"Omniflo Weiche";"0000";"OFWeiche :4";"D/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342002"} 31;"Omniflo Weiche";"0000";"OFWeiche :4";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342002"}
32;"Omniflo Weiche";"0000";"OFWeiche :1";"D/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342100"} 32;"Omniflo Weiche";"0000";"OFWeiche :1";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342100"}
33;"Omniflo Weiche";"0000";"OFWeiche :2";"D/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342101"} 33;"Omniflo Weiche";"0000";"OFWeiche :2";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342101"}
34;"Omniflo Weiche";"0000";"OFWeiche :1";"D/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342200"} 34;"Omniflo Weiche";"0000";"OFWeiche :1";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342200"}
35;"Omniflo Weiche";"0000";"OFWeiche :2";"D/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342201"} 35;"Omniflo Weiche";"0000";"OFWeiche :2";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 22.5, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834342201"}
36;"Omniflo Weiche";"0000";"OFWeiche :5";"D/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372001"} 36;"Omniflo Weiche";"0000";"OFWeiche :5";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372001"}
37;"Omniflo Weiche";"0000";"OFWeiche :6";"D/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372002"} 37;"Omniflo Weiche";"0000";"OFWeiche :6";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372002"}
38;"Omniflo Weiche";"0000";"OFWeiche :7";"D/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372002+0_BG090090"} 38;"Omniflo Weiche";"0000";"OFWeiche :7";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372002, 0_BG090090"}
39;"Omniflo Weiche";"0000";"OFWeiche :8";"D/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372004"} 39;"Omniflo Weiche";"0000";"OFWeiche :8";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372004"}
40;"Omniflo Weiche";"0000";"OFWeiche :9";"D/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372005"} 40;"Omniflo Weiche";"0000";"OFWeiche :9";"D/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372005"}
41;"Omniflo Weiche";"0000";"OFWeiche :10";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372005+0_BG090090"} 41;"Omniflo Weiche";"0000";"OFWeiche :10";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372005, 0_BG090090"}
42;"Omniflo Weiche";"0000";"OFWeiche :11";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372007"} 42;"Omniflo Weiche";"0000";"OFWeiche :11";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372007"}
43;"Omniflo Weiche";"0000";"OFWeiche :12";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372008"} 43;"Omniflo Weiche";"0000";"OFWeiche :12";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372008"}
44;"Omniflo Weiche";"0000";"OFWeiche :13";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372008+0_BG190090"} 44;"Omniflo Weiche";"0000";"OFWeiche :13";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372008, 0_BG190090"}
45;"Omniflo Weiche";"0000";"OFWeiche :14";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372010"} 45;"Omniflo Weiche";"0000";"OFWeiche :14";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372010"}
46;"Omniflo Weiche";"0000";"OFWeiche :15";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372011"} 46;"Omniflo Weiche";"0000";"OFWeiche :15";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372011"}
47;"Omniflo Weiche";"0000";"OFWeiche :16";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372011+0_BG190090"} 47;"Omniflo Weiche";"0000";"OFWeiche :16";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372011, 0_BG190090"}
48;"Omniflo Weiche";"0000";"OFWeiche :17";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372021"} 48;"Omniflo Weiche";"0000";"OFWeiche :17";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372021"}
49;"Omniflo Weiche";"0000";"OFWeiche :18";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372022"} 49;"Omniflo Weiche";"0000";"OFWeiche :18";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372022"}
50;"Omniflo Weiche";"0000";"OFWeiche :19";"E/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372024"} 50;"Omniflo Weiche";"0000";"OFWeiche :19";"E/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372024"}
51;"Omniflo Weiche";"0000";"OFWeiche :20";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372025"} 51;"Omniflo Weiche";"0000";"OFWeiche :20";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372025"}
52;"Omniflo Weiche";"0000";"OFWeiche :21";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372027"} 52;"Omniflo Weiche";"0000";"OFWeiche :21";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372027"}
53;"Omniflo Weiche";"0000";"OFWeiche :22";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372028"} 53;"Omniflo Weiche";"0000";"OFWeiche :22";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372028"}
54;"Omniflo Weiche";"0000";"OFWeiche :23";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372028+0_BG080090"} 54;"Omniflo Weiche";"0000";"OFWeiche :23";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372028, 0_BG080090"}
55;"Omniflo Weiche";"0000";"OFWeiche :24";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372030"} 55;"Omniflo Weiche";"0000";"OFWeiche :24";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372030"}
56;"Omniflo Weiche";"0000";"OFWeiche :25";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372031"} 56;"Omniflo Weiche";"0000";"OFWeiche :25";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372031"}
57;"Omniflo Weiche";"0000";"OFWeiche :26";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372031+0_BG080090"} 57;"Omniflo Weiche";"0000";"OFWeiche :26";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372031, 0_BG080090"}
58;"Omniflo Weiche";"0000";"OFWeiche :27";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372047"} 58;"Omniflo Weiche";"0000";"OFWeiche :27";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372047"}
59;"Omniflo Weiche";"0000";"OFWeiche :28";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372048"} 59;"Omniflo Weiche";"0000";"OFWeiche :28";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "1", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372048"}
60;"Omniflo Weiche";"0000";"OFWeiche :29";"F/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372050"} 60;"Omniflo Weiche";"0000";"OFWeiche :29";"F/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372050"}
61;"Omniflo Weiche";"0000";"OFWeiche :30";"G/A";1;"";"";"";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372051"} 61;"Omniflo Weiche";"0000";"OFWeiche :30";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Einzelweiche", "Richtung": "2", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372051"}
62;"Omniflo Weiche";"0000";"OFWeiche :3";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372100"} 62;"Omniflo Weiche";"0000";"OFWeiche :3";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372100"}
63;"Omniflo Weiche";"0000";"OFWeiche :4";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372101"} 63;"Omniflo Weiche";"0000";"OFWeiche :4";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372101"}
64;"Omniflo Weiche";"0000";"OFWeiche :5";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG090090+834372101"} 64;"Omniflo Weiche";"0000";"OFWeiche :5";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG090090, 834372101"}
65;"Omniflo Weiche";"0000";"OFWeiche :6";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372101+0_BG090090"} 65;"Omniflo Weiche";"0000";"OFWeiche :6";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372101, 0_BG090090"}
66;"Omniflo Weiche";"0000";"OFWeiche :7";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG090090+834372101+0_BG090090"} 66;"Omniflo Weiche";"0000";"OFWeiche :7";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG090090, 834372101, 0_BG090090"}
67;"Omniflo Weiche";"0000";"OFWeiche :8";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372103"} 67;"Omniflo Weiche";"0000";"OFWeiche :8";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372103"}
68;"Omniflo Weiche";"0000";"OFWeiche :9";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372104"} 68;"Omniflo Weiche";"0000";"OFWeiche :9";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372104"}
69;"Omniflo Weiche";"0000";"OFWeiche :10";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG190090+834372104"} 69;"Omniflo Weiche";"0000";"OFWeiche :10";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG190090, 834372104"}
70;"Omniflo Weiche";"0000";"OFWeiche :11";"G/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372104+0_BG190090"} 70;"Omniflo Weiche";"0000";"OFWeiche :11";"G/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372104, 0_BG190090"}
71;"Omniflo Weiche";"0000";"OFWeiche :12";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG190090+834372104+0_BG190090"} 71;"Omniflo Weiche";"0000";"OFWeiche :12";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG190090, 834372104, 0_BG190090"}
72;"Omniflo Weiche";"0000";"OFWeiche :13";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372106"} 72;"Omniflo Weiche";"0000";"OFWeiche :13";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372106"}
73;"Omniflo Weiche";"0000";"OFWeiche :14";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372107"} 73;"Omniflo Weiche";"0000";"OFWeiche :14";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372107"}
74;"Omniflo Weiche";"0000";"OFWeiche :15";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372109"} 74;"Omniflo Weiche";"0000";"OFWeiche :15";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372109"}
75;"Omniflo Weiche";"0000";"OFWeiche :16";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372110"} 75;"Omniflo Weiche";"0000";"OFWeiche :16";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372110"}
76;"Omniflo Weiche";"0000";"OFWeiche :17";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG080090+834372110"} 76;"Omniflo Weiche";"0000";"OFWeiche :17";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG080090, 834372110"}
77;"Omniflo Weiche";"0000";"OFWeiche :18";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372110+0_BG080090"} 77;"Omniflo Weiche";"0000";"OFWeiche :18";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372110, 0_BG080090"}
78;"Omniflo Weiche";"0000";"OFWeiche :19";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG080090+834372110+0_BG080090"} 78;"Omniflo Weiche";"0000";"OFWeiche :19";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG080090, 834372110, 0_BG080090"}
79;"Omniflo Weiche";"0000";"OFWeiche :20";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372115"} 79;"Omniflo Weiche";"0000";"OFWeiche :20";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372115"}
80;"Omniflo Weiche";"0000";"OFWeiche :21";"H/A";1;"";"";"";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372116"} 80;"Omniflo Weiche";"0000";"OFWeiche :21";"H/A";1;"";"";"";"unverbunden";{"Weichentyp": "Doppelweiche", "Richtung": "3", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372116"}
81;"Omniflo Weiche";"0000";"OFWeiche :3";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372200"} 81;"Omniflo Weiche";"0000";"OFWeiche :3";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372200"}
82;"Omniflo Weiche";"0000";"OFWeiche :4";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372201"} 82;"Omniflo Weiche";"0000";"OFWeiche :4";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372201"}
83;"Omniflo Weiche";"0000";"OFWeiche :5";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG090090+834372201"} 83;"Omniflo Weiche";"0000";"OFWeiche :5";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG090090, 834372201"}
84;"Omniflo Weiche";"0000";"OFWeiche :6";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372201+0_BG090090"} 84;"Omniflo Weiche";"0000";"OFWeiche :6";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372201, 0_BG090090"}
85;"Omniflo Weiche";"0000";"OFWeiche :7";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG090090+834372201+0_BG090090"} 85;"Omniflo Weiche";"0000";"OFWeiche :7";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG090090, 834372201, 0_BG090090"}
86;"Omniflo Weiche";"0000";"OFWeiche :8";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372203"} 86;"Omniflo Weiche";"0000";"OFWeiche :8";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372203"}
87;"Omniflo Weiche";"0000";"OFWeiche :9";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372204"} 87;"Omniflo Weiche";"0000";"OFWeiche :9";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372204"}
88;"Omniflo Weiche";"0000";"OFWeiche :10";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG190090+834372204"} 88;"Omniflo Weiche";"0000";"OFWeiche :10";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG190090, 834372204"}
89;"Omniflo Weiche";"0000";"OFWeiche :11";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372204+0_BG190090"} 89;"Omniflo Weiche";"0000";"OFWeiche :11";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372204, 0_BG190090"}
90;"Omniflo Weiche";"0000";"OFWeiche :12";"I/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG190090+834372204+0_BG190090"} 90;"Omniflo Weiche";"0000";"OFWeiche :12";"I/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 45.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG190090, 834372204, 0_BG190090"}
91;"Omniflo Weiche";"0000";"OFWeiche :13";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372206"} 91;"Omniflo Weiche";"0000";"OFWeiche :13";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372206"}
92;"Omniflo Weiche";"0000";"OFWeiche :14";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372207"} 92;"Omniflo Weiche";"0000";"OFWeiche :14";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372207"}
93;"Omniflo Weiche";"0000";"OFWeiche :15";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372209"} 93;"Omniflo Weiche";"0000";"OFWeiche :15";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372209"}
94;"Omniflo Weiche";"0000";"OFWeiche :16";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372210"} 94;"Omniflo Weiche";"0000";"OFWeiche :16";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372210"}
95;"Omniflo Weiche";"0000";"OFWeiche :17";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG080090+834372210"} 95;"Omniflo Weiche";"0000";"OFWeiche :17";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG080090, 834372210"}
96;"Omniflo Weiche";"0000";"OFWeiche :18";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372210+0_BG080090"} 96;"Omniflo Weiche";"0000";"OFWeiche :18";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372210, 0_BG080090"}
97;"Omniflo Weiche";"0000";"OFWeiche :19";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG080090+834372210+0_BG080090"} 97;"Omniflo Weiche";"0000";"OFWeiche :19";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG080090, 834372210, 0_BG080090"}
98;"Omniflo Weiche";"0000";"OFWeiche :20";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372215"} 98;"Omniflo Weiche";"0000";"OFWeiche :20";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372215"}
99;"Omniflo Weiche";"0000";"OFWeiche :21";"J/A";1;"";"";"";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372216"} 99;"Omniflo Weiche";"0000";"OFWeiche :21";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Dreiwegeweiche", "Richtung": "7", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372216"}
100;"Omniflo Weiche";"0000";"OFWeiche :1";"J/A";1;"";"";"";{"Weichentyp": "Dreifachweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372400"} 100;"Omniflo Weiche";"0000";"OFWeiche :1";"J/A";1;"";"";"";"unverbunden";{"Weichentyp": "Deltaweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372400"}
101;"Omniflo Weiche";"0000";"OFWeiche :2";"K/A";1;"";"";"";{"Weichentyp": "Dreifachweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372403"} 101;"Omniflo Weiche";"0000";"OFWeiche :2";"K/A";1;"";"";"";"unverbunden";{"Weichentyp": "Deltaweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372403"}
102;"Omniflo Weiche";"0000";"OFWeiche :3";"K/A";1;"";"";"";{"Weichentyp": "Dreifachweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372404"} 102;"Omniflo Weiche";"0000";"OFWeiche :3";"K/A";1;"";"";"";"unverbunden";{"Weichentyp": "Deltaweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372404"}
103;"Omniflo Weiche";"0000";"OFWeiche :4";"K/A";1;"";"";"";{"Weichentyp": "Dreifachweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG071090+834372404+0_BG071090"} 103;"Omniflo Weiche";"0000";"OFWeiche :4";"K/A";1;"";"";"";"unverbunden";{"Weichentyp": "Deltaweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG071090, 834372404, 0_BG071090"}
104;"Omniflo Weiche";"0000";"OFWeiche :5";"K/A";1;"";"";"";{"Weichentyp": "Dreifachweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG071090+834372404"} 104;"Omniflo Weiche";"0000";"OFWeiche :5";"K/A";1;"";"";"";"unverbunden";{"Weichentyp": "Deltaweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "0_BG071090, 834372404"}
105;"Omniflo Weiche";"0000";"OFWeiche :6";"K/A";1;"";"";"";{"Weichentyp": "Dreifachweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372404+0_BG071090"} 105;"Omniflo Weiche";"0000";"OFWeiche :6";"K/A";1;"";"";"";"unverbunden";{"Weichentyp": "Deltaweiche", "Richtung": "3", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": true, "SivasNummer": "834372404, 0_BG071090"}
106;"Omniflo Weiche";"0000";"OFWeiche :1";"K/A";1;"";"";"";{"Weichentyp": "Deltaweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372401"} 106;"Omniflo Weiche";"0000";"OFWeiche :7";"K/A";1;"";"";"";"unverbunden";{"Weichentyp": "Deltaweiche", "Richtung": "7", "Weichenwinkel": 90.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372401"}
107;"Omniflo Weiche";"0000";"OFWeiche :1";"K/A";1;"";"";"";{"Weichentyp": "Sternweiche", "Richtung": "3", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372420"} 107;"Omniflo Weiche";"0000";"OFWeiche :1";"K/A";1;"";"";"";"unverbunden";{"Weichentyp": "Sternweiche", "Richtung": "3", "Weichenwinkel": 0.0, "Höhe": "2000", "Drehung": 0.0, "Antrieb Kurve": false, "SivasNummer": "834372420"}
108;"Omniflo Sum";"autogenerated_of_json";"Omniflo sum";"";1;"";"";"";{"Anzahl Bögen": 27, "Anzahl Weichengrundkörper": 0, "Anzahl Einwegweichen": 30, "Anzahl Deltaweichen": 7, "Anzahl Doppelweichen und Dreiwegeweichen": 42, "Anzahl Sternweichen": 1, "Gesamtlänge AP110": 0.0, "Gesamtlänge AP60": 0.0} 108;"Omniflo Sum";"autogenerated_of_json";"Omniflo sum";"";1;"";"";"";"";{"Anzahl Bögen": 27, "Anzahl Weichengrundkörper": 0, "Anzahl Einwegweichen": 30, "Anzahl Deltaweichen": 7, "Anzahl Doppelweichen und Dreiwegeweichen": 42, "Anzahl Sternweichen": 1, "Gesamtlänge AP110": 0.0, "Gesamtlänge AP60": 0.0}
Can't render this file because it contains an unexpected character in line 2 and column 57.
+1 -1
View File
@@ -107,7 +107,7 @@ class TestOmnifloExportUnit:
out_dir = _output_dir() out_dir = _output_dir()
os.makedirs(out_dir, exist_ok=True) os.makedirs(out_dir, exist_ok=True)
csv_path = os.path.join(out_dir, "omniflo_export.csv") csv_path = os.path.join(out_dir, "omniflo_export.csv")
header = "Elementnummer;TeileArt;TeileId;Bezeichnung;Planquadrat;Anzahl;Position;Boundingbox;Nachbarn;Merkmale" header = "Elementnummer;TeileArt;TeileId;Bezeichnung;Planquadrat;Anzahl;Position;Boundingbox;Nachbarn;Fehler;Merkmale"
with open(csv_path, "w", encoding="utf-8") as f: with open(csv_path, "w", encoding="utf-8") as f:
f.write(header + "\n") f.write(header + "\n")
for item in self.items: for item in self.items:
+18 -1
View File
@@ -146,7 +146,7 @@
namen befehl datei export-fn new-doc namen befehl datei export-fn new-doc
out-path dwg-pfad dxf-pfad old-json test-result out-path dwg-pfad dxf-pfad old-json test-result
old-filenames csv-name sivas-name csv-pfad old-filenames csv-name sivas-name csv-pfad
sivas-pfad csv-ok sivas-ok) sivas-pfad csv-ok sivas-ok old-filedia)
(setq tests-pfad (strcat (getenv "DXFMAKRO") "/tests")) (setq tests-pfad (strcat (getenv "DXFMAKRO") "/tests"))
(setq tests-out-dir (strcat tests-pfad "/output")) (setq tests-out-dir (strcat tests-pfad "/output"))
@@ -267,7 +267,15 @@
(princ (strcat "\n DWG gespeichert: " dwg-pfad)) (princ (strcat "\n DWG gespeichert: " dwg-pfad))
) )
((and save-fmt (= (strcase save-fmt) "DXF")) ((and save-fmt (= (strcase save-fmt) "DXF"))
;; FILEDIA=0 erzwingen: sonst oeffnet "_.DXFOUT" den nativen
;; Speichern-Dialog (blockiert im Skriptlauf) statt die
;; Kommandozeilen-Prompts (Dateiname/Genauigkeit) zu nutzen -
;; das brachte den nachfolgenden vla-close aus dem Takt
;; (siehe Kontroll-Modus-Zweig weiter unten fuer Details).
(setq old-filedia (getvar "FILEDIA"))
(setvar "FILEDIA" 0)
(command "_.DXFOUT" out-path 6) (command "_.DXFOUT" out-path 6)
(setvar "FILEDIA" old-filedia)
(princ (strcat "\n DXF gespeichert: " out-path ".dxf")) (princ (strcat "\n DXF gespeichert: " out-path ".dxf"))
) )
(T (T
@@ -343,7 +351,16 @@
(setq dwg-pfad (strcat out-path ".dwg")) (setq dwg-pfad (strcat out-path ".dwg"))
(setq dxf-pfad (strcat out-path ".dxf")) (setq dxf-pfad (strcat out-path ".dxf"))
(vla-saveas new-doc dwg-pfad) (vla-saveas new-doc dwg-pfad)
;; FILEDIA=0 erzwingen: sonst oeffnet "_.DXFOUT" den nativen
;; Speichern-Dialog statt der Kommandozeilen-Prompts - der
;; Skriptlauf haengt dann in einem offenen Dialog fest, und
;; der nachfolgende vla-close (auf dem noch "belegten"
;; Dokument) bricht mit "bad argument type <0>" ab, weil
;; new-doc dabei ungueltig wird.
(setq old-filedia (getvar "FILEDIA"))
(setvar "FILEDIA" 0)
(command "_.DXFOUT" out-path 6) (command "_.DXFOUT" out-path 6)
(setvar "FILEDIA" old-filedia)
(vla-close new-doc :vlax-false) (vla-close new-doc :vlax-false)
(if (findfile dwg-pfad) (vl-file-delete dwg-pfad)) (if (findfile dwg-pfad) (vl-file-delete dwg-pfad))
(setq new-doc (vla-open (vla-get-documents app) dxf-pfad)) (setq new-doc (vla-open (vla-get-documents app) dxf-pfad))