K2 für die Bögen werden jetzt richtig gesetzt
This commit is contained in:
+1
-10
@@ -4,7 +4,7 @@ REM ================================================================
|
||||
REM TEST - Umgebungsvariablen Setup
|
||||
REM ================================================================
|
||||
|
||||
echo Setting up environment variables for TEST ...
|
||||
echo Setting up environment variables for DXFMAKROS ...
|
||||
|
||||
REM Basis-Projektpfad (aktueller Ordner)
|
||||
set "DXFMAKRO=%~dp0.."
|
||||
@@ -44,16 +44,7 @@ if not exist "%DXFM_RESULTS%" mkdir "%DXFM_RESULTS%"
|
||||
REM Umgebungsvariablen anzeigen
|
||||
echo.
|
||||
echo ================================================================
|
||||
echo TEST ENVIRONMENT SETUP COMPLETE
|
||||
echo ================================================================
|
||||
echo DXFMAKRO = %DXFMAKRO%
|
||||
echo DXFM_BIN = %DXFM_BIN%
|
||||
echo DXFM_CFG = %DXFM_CFG%
|
||||
echo DXFM_LIB = %DXFM_LIB%
|
||||
echo DXFM_DATA = %DXFM_DATA%
|
||||
echo DXFM_BLOCKS = %DXFM_BLOCKS%
|
||||
echo DXFM_LISP = %DXFM_LISP%
|
||||
echo DXFM_RESULTS = %DXFM_RESULTS%
|
||||
echo PYTHONPATH = %PYTHONPATH%
|
||||
echo ================================================================
|
||||
echo.
|
||||
|
||||
+15
-50
@@ -33,6 +33,7 @@ import ezdxf
|
||||
|
||||
from utils import (
|
||||
ROW_GROUPS, TEXT_HEIGHT, TEXT_MARGIN, CROSS_SIZE, ROW_LABEL_WIDTH,
|
||||
SWITCH_FILTERS,
|
||||
build_row_layout, import_element_as_block, draw_cross,
|
||||
)
|
||||
|
||||
@@ -225,59 +226,23 @@ def horizontal_midpoint_insertion(doc):
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Schalter-Definitionen: (Label, JSON-Datei, Filter, Einfuegepunkt-Funktion)
|
||||
# Filter kommen aus SWITCH_FILTERS in utils.py.
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
_INSERTION_FUNCS = {
|
||||
"boegen": boegen_insertion_point,
|
||||
"weichen45": weichen_insertion_point,
|
||||
"weichen90": weichen_insertion_point,
|
||||
"weichenkoerper": weichenkoerper_insertion_point,
|
||||
"weichen_parallel": weichenkoerper_insertion_point,
|
||||
"sternweiche": horizontal_midpoint_insertion,
|
||||
"delta": horizontal_midpoint_insertion,
|
||||
"dreifachweiche": horizontal_midpoint_insertion,
|
||||
}
|
||||
|
||||
SWITCH_DEFS = {
|
||||
"boegen": (
|
||||
"Boegen",
|
||||
"omniflo_boegen.json",
|
||||
lambda item: True,
|
||||
boegen_insertion_point,
|
||||
),
|
||||
"weichen45": (
|
||||
"Weichen 45 Grad",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["KurvenWinkel"] == 45
|
||||
and item["WeichenTyp"] not in ("Dreifachweiche", "Deltaweiche"),
|
||||
weichen_insertion_point,
|
||||
),
|
||||
"weichen90": (
|
||||
"Weichen 90 Grad",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["KurvenWinkel"] == 90
|
||||
and item["WeichenTyp"] not in ("Dreifachweiche", "Deltaweiche"),
|
||||
weichen_insertion_point,
|
||||
),
|
||||
"weichenkoerper": (
|
||||
"Weichenkoerper",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["KurvenWinkel"] == 22.5,
|
||||
weichenkoerper_insertion_point,
|
||||
),
|
||||
"weichen_parallel": (
|
||||
"Weichen Parallel",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["KurvenWinkel"] == 0 and item["WeichenTyp"] != "Sternweiche",
|
||||
weichenkoerper_insertion_point,
|
||||
),
|
||||
"sternweiche": (
|
||||
"Sternweiche",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["WeichenTyp"] == "Sternweiche",
|
||||
horizontal_midpoint_insertion,
|
||||
),
|
||||
"delta": (
|
||||
"Deltaweichen",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["WeichenTyp"] == "Deltaweiche",
|
||||
horizontal_midpoint_insertion,
|
||||
),
|
||||
"dreifachweiche": (
|
||||
"Dreifachweichen",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["WeichenTyp"] == "Dreifachweiche",
|
||||
horizontal_midpoint_insertion,
|
||||
),
|
||||
key: (*SWITCH_FILTERS[key], _INSERTION_FUNCS[key])
|
||||
for key in SWITCH_FILTERS
|
||||
}
|
||||
|
||||
|
||||
|
||||
+213
-2
@@ -11,7 +11,11 @@ Schalter:
|
||||
Boegen: Beginn der obersten horizontalen Linie,
|
||||
x rechts, y oben, z aus Zeichenebene.
|
||||
Weichen: Beginn der untersten vertikalen Linie,
|
||||
x oben, y rechts, z aus Zeichenebene.
|
||||
x oben, y links, z aus Zeichenebene.
|
||||
--k2set K2 an alle Boegen und Weichen setzen.
|
||||
Boegen: anderes Kettenende, x tangential,
|
||||
y senkrecht, z wie K1.
|
||||
Weichen: noch nicht implementiert (Dummy).
|
||||
--show-omniflo Uebersichts-DXF mit K-Positionen als farbige Kreuze.
|
||||
--test Erzeugt Testdatei mit 4 KOS und verifiziert diese.
|
||||
--number SIVA Nur diese eine 9-stellige Sivasnr verarbeiten.
|
||||
@@ -28,6 +32,7 @@ from ezdxf.math import Matrix44
|
||||
|
||||
from utils import (
|
||||
ROW_GROUPS, TEXT_HEIGHT, TEXT_MARGIN, CROSS_SIZE, ROW_LABEL_WIDTH,
|
||||
SWITCH_FILTERS,
|
||||
load_omniflo_data, build_row_layout, import_element_as_block,
|
||||
draw_cross, is_bogen,
|
||||
)
|
||||
@@ -251,6 +256,150 @@ def k1_point_weiche(doc):
|
||||
return (x, bottom_y, 0), 0, 0, 90
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# K2-Positionsbestimmung (nur Boegen)
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
def k2_point_bogen(doc):
|
||||
"""K2-Position fuer Boegen: anderes Ende der Kette (Gerade-Bogen-Gerade).
|
||||
|
||||
Sucht den Bogen, bestimmt welches Ende zur K1-Seite (oberste H-Linie)
|
||||
gehoert, findet die laengste Linie am anderen Bogenende und setzt K2
|
||||
an deren aeusseres Ende.
|
||||
|
||||
x-Achse tangential zur Linie (Richtung weg vom Bogen),
|
||||
y senkrecht dazu, z aus Zeichenebene (wie K1).
|
||||
Sonderfall 180-Grad-Bogen: x nach rechts (rz=0).
|
||||
"""
|
||||
msp = doc.modelspace()
|
||||
|
||||
# Bogen finden
|
||||
arc = None
|
||||
for e in msp:
|
||||
if e.dxftype() == "ARC":
|
||||
arc = e
|
||||
break
|
||||
if arc is None:
|
||||
return None
|
||||
|
||||
cx, cy = arc.dxf.center[0], arc.dxf.center[1]
|
||||
r = arc.dxf.radius
|
||||
sa, ea = arc.dxf.start_angle, arc.dxf.end_angle
|
||||
|
||||
arc_start = (cx + r * math.cos(math.radians(sa)),
|
||||
cy + r * math.sin(math.radians(sa)))
|
||||
arc_end = (cx + r * math.cos(math.radians(ea)),
|
||||
cy + r * math.sin(math.radians(ea)))
|
||||
|
||||
# K1-Seite = oberste horizontale Linie
|
||||
hline = find_topmost_horizontal_line(doc)
|
||||
if hline is None:
|
||||
return None
|
||||
h_y = hline.dxf.start[1]
|
||||
|
||||
# Welches Bogenende liegt an der K1-H-Linie?
|
||||
tol = 1.0
|
||||
if abs(arc_end[1] - h_y) < tol:
|
||||
k2_junction = arc_start
|
||||
else:
|
||||
k2_junction = arc_end
|
||||
|
||||
# Laengste Linie am K2-Bogenende suchen
|
||||
best_line_len = 0
|
||||
k2_pos = None
|
||||
junc_pt = None
|
||||
for e in msp:
|
||||
if e.dxftype() != "LINE":
|
||||
continue
|
||||
s = (e.dxf.start[0], e.dxf.start[1])
|
||||
end = (e.dxf.end[0], e.dxf.end[1])
|
||||
ds = ((s[0] - k2_junction[0])**2 + (s[1] - k2_junction[1])**2) ** 0.5
|
||||
de = ((end[0] - k2_junction[0])**2 + (end[1] - k2_junction[1])**2) ** 0.5
|
||||
if ds > tol and de > tol:
|
||||
continue
|
||||
ln = ((end[0] - s[0])**2 + (end[1] - s[1])**2) ** 0.5
|
||||
if ln > best_line_len:
|
||||
best_line_len = ln
|
||||
if ds < tol:
|
||||
k2_pos = end
|
||||
junc_pt = s
|
||||
else:
|
||||
k2_pos = s
|
||||
junc_pt = end
|
||||
|
||||
if k2_pos is None:
|
||||
return None
|
||||
|
||||
# Bogenspanne berechnen
|
||||
span = (ea - sa) % 360
|
||||
|
||||
# Tangenten-Richtung: von K2 zur Junction (zur Bogenmitte)
|
||||
dx = junc_pt[0] - k2_pos[0]
|
||||
dy = junc_pt[1] - k2_pos[1]
|
||||
rz = math.degrees(math.atan2(dy, dx))
|
||||
|
||||
# 180-Grad-Sonderfall: x nach rechts, wie K1
|
||||
if abs(span - 180) < 1:
|
||||
rz = 0
|
||||
|
||||
return (k2_pos[0], k2_pos[1], 0), 0, 0, rz
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# K2-Positionsbestimmung Weichen (Dummy-Funktionen)
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
def k2_point_weichen45(doc):
|
||||
"""K2 fuer Weichen 45 Grad – noch nicht implementiert."""
|
||||
return None
|
||||
|
||||
|
||||
def k2_point_weichen90(doc):
|
||||
"""K2 fuer Weichen 90 Grad – noch nicht implementiert."""
|
||||
return None
|
||||
|
||||
|
||||
def k2_point_weichenkoerper(doc):
|
||||
"""K2 fuer Weichenkoerper – noch nicht implementiert."""
|
||||
return None
|
||||
|
||||
|
||||
def k2_point_weichen_parallel(doc):
|
||||
"""K2 fuer Weichen Parallel – noch nicht implementiert."""
|
||||
return None
|
||||
|
||||
|
||||
def k2_point_sternweiche(doc):
|
||||
"""K2 fuer Sternweiche – noch nicht implementiert."""
|
||||
return None
|
||||
|
||||
|
||||
def k2_point_delta(doc):
|
||||
"""K2 fuer Deltaweichen – noch nicht implementiert."""
|
||||
return None
|
||||
|
||||
|
||||
def k2_point_dreifachweiche(doc):
|
||||
"""K2 fuer Dreifachweichen – noch nicht implementiert."""
|
||||
return None
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# K2 Schalter-Zuordnung: SWITCH_FILTERS-Key -> K2-Funktion
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
K2_FUNCS = {
|
||||
"boegen": k2_point_bogen,
|
||||
"weichen45": k2_point_weichen45,
|
||||
"weichen90": k2_point_weichen90,
|
||||
"weichenkoerper": k2_point_weichenkoerper,
|
||||
"weichen_parallel": k2_point_weichen_parallel,
|
||||
"sternweiche": k2_point_sternweiche,
|
||||
"delta": k2_point_delta,
|
||||
"dreifachweiche": k2_point_dreifachweiche,
|
||||
}
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# --k1set
|
||||
# ---------------------------------------------------------------------------
|
||||
@@ -310,6 +459,63 @@ def process_k1set(data_dir, results_dir, number=None):
|
||||
print(f"\nErgebnisse in: {results_dir}")
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# --k2set
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
def process_k2set(data_dir, results_dir, number=None):
|
||||
"""Setzt K2-Block an alle Boegen und Weichen (ueber SWITCH_FILTERS)."""
|
||||
omniflo_dir = os.path.join(data_dir, "omniflo")
|
||||
|
||||
for key, k2_func in K2_FUNCS.items():
|
||||
label, json_file, filter_func = SWITCH_FILTERS[key]
|
||||
|
||||
json_path = os.path.join(data_dir, "json", json_file)
|
||||
if not os.path.exists(json_path):
|
||||
continue
|
||||
with open(json_path, "r", encoding="utf-8") as f:
|
||||
all_items = json.load(f)
|
||||
|
||||
filtered = [item for item in all_items if filter_func(item)]
|
||||
if number:
|
||||
filtered = [item for item in filtered if str(item["Sivasnr"]) == str(number)]
|
||||
if not filtered:
|
||||
continue
|
||||
|
||||
print(f"=== K2 setzen: {label} ===")
|
||||
for item in filtered:
|
||||
sivasnr = str(item["Sivasnr"])
|
||||
dxf_path = os.path.join(results_dir, f"{sivasnr}.dxf")
|
||||
if not os.path.exists(dxf_path):
|
||||
dxf_path = os.path.join(omniflo_dir, f"{sivasnr}.dxf")
|
||||
if not os.path.exists(dxf_path):
|
||||
continue
|
||||
|
||||
doc = ezdxf.readfile(dxf_path)
|
||||
msp = doc.modelspace()
|
||||
|
||||
# Bestehende K2-Referenzen entfernen
|
||||
for entity in list(msp):
|
||||
if entity.dxftype() == "INSERT" and entity.dxf.name == "K2":
|
||||
msp.delete_entity(entity)
|
||||
|
||||
result = k2_func(doc)
|
||||
|
||||
if result is None:
|
||||
print(f" {sivasnr}: K2 nicht bestimmbar (Dummy), ueberspringe.")
|
||||
continue
|
||||
|
||||
point, rx, ry, rz = result
|
||||
insert_ks(msp, "K2", point, rx, ry, rz)
|
||||
|
||||
out_path = os.path.join(results_dir, f"{sivasnr}.dxf")
|
||||
doc.saveas(out_path)
|
||||
print(f" {sivasnr}: K2 at ({point[0]:.2f},{point[1]:.2f},{point[2]:.2f}) "
|
||||
f"rx={rx} ry={ry} rz={rz:.1f} [{item['ProfilTyp']}]")
|
||||
|
||||
print(f"\nErgebnisse in: {results_dir}")
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# --show-omniflo
|
||||
# ---------------------------------------------------------------------------
|
||||
@@ -412,6 +618,8 @@ def main():
|
||||
)
|
||||
parser.add_argument("--k1set", action="store_true",
|
||||
help="K1-Block an alle Boegen und Weichen setzen")
|
||||
parser.add_argument("--k2set", action="store_true",
|
||||
help="K2-Block an alle Boegen setzen (anderes Kettenende)")
|
||||
parser.add_argument("--show-omniflo", action="store_true",
|
||||
help="Uebersichts-DXF mit K-Positionen erzeugen")
|
||||
parser.add_argument("--test", action="store_true",
|
||||
@@ -424,7 +632,7 @@ def main():
|
||||
print("FEHLER: --number muss eine 9-stellige Ganzzahl sein.")
|
||||
sys.exit(1)
|
||||
|
||||
if not args.k1set and not args.show_omniflo and not args.test:
|
||||
if not args.k1set and not args.k2set and not args.show_omniflo and not args.test:
|
||||
parser.print_help()
|
||||
sys.exit(1)
|
||||
|
||||
@@ -448,6 +656,9 @@ def main():
|
||||
if args.k1set:
|
||||
process_k1set(data_dir, results_dir, args.number)
|
||||
|
||||
if args.k2set:
|
||||
process_k2set(data_dir, results_dir, args.number)
|
||||
|
||||
if args.show_omniflo:
|
||||
print("=== Koordinaten Uebersicht ===")
|
||||
show_omniflo(data_dir, results_dir)
|
||||
|
||||
@@ -60,6 +60,57 @@ ROW_GROUPS = [
|
||||
lambda w: w["WeichenTyp"] == "Sternweiche"),
|
||||
]
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# Schalter-Filter: (Label, JSON-Datei, Filter-Funktion)
|
||||
# Gemeinsam genutzt von set_einfuegepkt.py und set_koords.py.
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
SWITCH_FILTERS = {
|
||||
"boegen": (
|
||||
"Boegen",
|
||||
"omniflo_boegen.json",
|
||||
lambda item: True,
|
||||
),
|
||||
"weichen45": (
|
||||
"Weichen 45 Grad",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["KurvenWinkel"] == 45
|
||||
and item["WeichenTyp"] not in ("Dreifachweiche", "Deltaweiche"),
|
||||
),
|
||||
"weichen90": (
|
||||
"Weichen 90 Grad",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["KurvenWinkel"] == 90
|
||||
and item["WeichenTyp"] not in ("Dreifachweiche", "Deltaweiche"),
|
||||
),
|
||||
"weichenkoerper": (
|
||||
"Weichenkoerper",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["KurvenWinkel"] == 22.5,
|
||||
),
|
||||
"weichen_parallel": (
|
||||
"Weichen Parallel",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["KurvenWinkel"] == 0 and item["WeichenTyp"] != "Sternweiche",
|
||||
),
|
||||
"sternweiche": (
|
||||
"Sternweiche",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["WeichenTyp"] == "Sternweiche",
|
||||
),
|
||||
"delta": (
|
||||
"Deltaweichen",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["WeichenTyp"] == "Deltaweiche",
|
||||
),
|
||||
"dreifachweiche": (
|
||||
"Dreifachweichen",
|
||||
"omniflo_weichen.json",
|
||||
lambda item: item["WeichenTyp"] == "Dreifachweiche",
|
||||
),
|
||||
}
|
||||
|
||||
|
||||
PADDING_X = 200
|
||||
PADDING_Y = 400
|
||||
TEXT_HEIGHT = 30
|
||||
|
||||
Reference in New Issue
Block a user