90 lines
2.9 KiB
Python
90 lines
2.9 KiB
Python
#!/usr/bin/env python3
|
|
"""Explore the concrete-lining structure drawings (04-004 .. 04-009).
|
|
|
|
Read-only on the source RAG folder. For each DXF prints layers with entity
|
|
counts, INSERT block names, dimension measurements and every text string with
|
|
its position, and writes a JSON dump for later use.
|
|
Usage: explore_lining.py <RAG_04_DIR> <OUT_JSON> [max_texts_per_file]
|
|
"""
|
|
import collections
|
|
import glob
|
|
import json
|
|
import os
|
|
import sys
|
|
|
|
import ezdxf
|
|
from ezdxf import recover
|
|
|
|
RAG_04 = sys.argv[1]
|
|
OUT_JSON = sys.argv[2]
|
|
MAX_TEXT = int(sys.argv[3]) if len(sys.argv) > 3 else 400
|
|
|
|
|
|
def load(path):
|
|
try:
|
|
return ezdxf.readfile(path), None
|
|
except Exception as exc:
|
|
try:
|
|
doc, _ = recover.readfile(path)
|
|
return doc, f"recovered after strict error: {type(exc).__name__}"
|
|
except Exception as exc2:
|
|
return None, f"{type(exc).__name__} | recover: {type(exc2).__name__}: {exc2}"
|
|
|
|
|
|
def explore(path):
|
|
rec = {"file": os.path.basename(path)}
|
|
doc, note = load(path)
|
|
if doc is None:
|
|
rec["error"] = note
|
|
return rec
|
|
rec["note"] = note
|
|
msp = doc.modelspace()
|
|
layers = collections.Counter()
|
|
counts = collections.Counter()
|
|
for e in msp:
|
|
counts[e.dxftype()] += 1
|
|
layers[e.dxf.layer] += 1
|
|
rec["layers"] = dict(layers.most_common())
|
|
rec["entity_counts"] = dict(counts.most_common())
|
|
rec["inserts"] = dict(collections.Counter(e.dxf.name for e in msp if e.dxftype() == "INSERT").most_common(30))
|
|
dims, texts = [], []
|
|
for e in msp:
|
|
t = e.dxftype()
|
|
if t == "DIMENSION":
|
|
try:
|
|
val = round(float(e.get_measurement()), 3)
|
|
except Exception:
|
|
val = None
|
|
dims.append({"layer": e.dxf.layer, "value": val, "text": e.dxf.get("text", "")})
|
|
elif t in ("TEXT", "MTEXT"):
|
|
s = e.dxf.text if t == "TEXT" else e.plain_text()
|
|
if s and s.strip():
|
|
pos = e.dxf.insert
|
|
texts.append({"layer": e.dxf.layer, "x": round(pos.x, 2), "y": round(pos.y, 2),
|
|
"text": s.strip().replace("\n", " | ")[:200]})
|
|
rec["dimensions"] = dims[:200]
|
|
rec["texts_total"] = len(texts)
|
|
rec["texts"] = texts[:MAX_TEXT]
|
|
return rec
|
|
|
|
|
|
def main():
|
|
files = sorted(glob.glob(os.path.join(RAG_04, "C0060304-00[4-9]*.dxf")))
|
|
out = [explore(f) for f in files]
|
|
with open(OUT_JSON, "w", encoding="utf-8") as fh:
|
|
json.dump(out, fh, ensure_ascii=False, indent=1)
|
|
for r in out:
|
|
print("==", r["file"])
|
|
if "error" in r:
|
|
print(" ERROR", r["error"])
|
|
continue
|
|
print(" note:", r["note"])
|
|
print(" entities:", r["entity_counts"])
|
|
print(" layers:", dict(list(r["layers"].items())[:25]))
|
|
print(" inserts:", r["inserts"])
|
|
print(" dims:", len(r["dimensions"]), "texts:", r["texts_total"])
|
|
|
|
|
|
if __name__ == "__main__":
|
|
main()
|