Keine Zentrierung für Tätigkeiten. Doppeltes Datum anzeigen.

This commit is contained in:
Rob committed 2026-06-30 10:52:45 +02:00
1 parent 87f8150bd3
commit 8fde588b8f
3 files changed
+68 -73

No files matched your search

+68 -73
View File
@@ -102,10 +102,10 @@ def _scan_template_fields(
template_path: Path,
mapping: list[OutputMapping],
fontsize: float,
) -> dict[str, dict]:
) -> dict[str, list[dict]]:
"""
Scannt ALLE Seiten des PDF-Templates nach _Field-Platzhaltern.
Rückgabe: dict[pdf_field] → {source_field, page_num, rect, fontsize, fontname, ...}
Rückgabe: dict[pdf_field] → Liste von {source_field, page_num, rect, fontsize, fontname, ...}
Felder mit pdf_field=None werden übersprungen.
"""
doc = fitz.open(template_path)
@@ -116,26 +116,23 @@ def _scan_template_fields(
if m.pdf_field is not None:
pdf_to_source[m.pdf_field] = m.source_field
field_info: dict[str, dict] = {}
field_info: dict[str, list[dict]] = {}
# Per search_for die Rechtecke aller PDF-Feld-Marker finden (alle Seiten)
# Alle Vorkommen aller PDF-Feld-Marker finden (alle Seiten)
for pdf_field, source_field in pdf_to_source.items():
found_any = False
occurrences: list[dict] = []
for page_num in range(doc.page_count):
page = doc[page_num]
found = page.search_for(pdf_field)
if found:
field_info[pdf_field] = {
for rect in found:
occurrences.append({
"source_field": source_field,
"page_num": page_num,
"rect": found[0],
"rect": rect,
"fontsize": fontsize,
"fontname": "helv",
}
found_any = True
break # erstes Vorkommen (seitenübergreifend)
if not found_any:
field_info[pdf_field] = None # nicht gefunden
})
field_info[pdf_field] = occurrences
doc.close()
return field_info
@@ -150,7 +147,7 @@ def _fill_pdf_pages(
record: EmployeeRecord,
employee_name: str,
mapping: list[OutputMapping],
field_info: dict[str, dict],
field_info: dict[str, list[dict]],
fontsize: float,
) -> None:
"""Befüllt alle Template-Seiten: redacted _Field-Platzhalter und fügt echte Daten ein."""
@@ -162,76 +159,74 @@ def _fill_pdf_pages(
if m.pdf_field is None:
continue
info = field_info.get(m.pdf_field)
if info is None:
occurrences = field_info.get(m.pdf_field, [])
if not occurrences:
continue # Feld nicht im Template gefunden
page_num = info["page_num"]
if page_num >= len(pages):
continue
page = pages[page_num]
rect = info["rect"]
value = _get_field_value(record, employee_name, m.source_field)
formatted = _format_value(value, m.format)
# Platzhalter immer redacten, auch wenn kein Wert zum Einsetzen da ist
page.add_redact_annot(rect)
page.apply_redactions()
if not formatted:
continue
# Mehrzeilige Felder: Zeilenweise per insert_text schreiben
if m.pdf_field in MULTILINE_FIELDS:
# Doppelte Leerzeilen entfernen
clean_text = "\n".join(
line for line in formatted.split("\n") if line.strip()
)
if not clean_text:
# Jedes Vorkommen des Feldes im PDF befüllen
for info in occurrences:
page_num = info["page_num"]
if page_num >= len(pages):
continue
# Zeilenweise mit automatischem Umbruch schreiben
lines = clean_text.split("\n")
line_spacing = fontsize * 1.2 # Zeilenabstand
page = pages[page_num]
rect = info["rect"]
# Zuerst alle Ausgabezeilen sammeln, um Gesamthöhe zu berechnen
output_lines: list[str] = []
for line in lines:
max_width = TEXTBOX_WIDTH_PT
words = line.split(" ")
current_line = ""
for word in words:
test_line = current_line + (" " if current_line else "") + word
text_width = fitz.get_text_length(test_line, fontname="helv", fontsize=fontsize)
if text_width <= max_width or not current_line:
current_line = test_line
else:
output_lines.append(current_line)
current_line = word
if current_line:
output_lines.append(current_line)
# Platzhalter redacten
page.add_redact_annot(rect)
page.apply_redactions()
# Textblock oben beginnend schreiben
y = rect.y0 + fontsize
if not formatted:
continue
for current_line in output_lines:
page.insert_text(
(rect.x0, y), current_line,
fontname="helv", fontsize=fontsize,
# Mehrzeilige Felder: Zeilenweise per insert_text schreiben
if m.pdf_field in MULTILINE_FIELDS:
# ... (unverändert)
clean_text = "\n".join(
line for line in formatted.split("\n") if line.strip()
)
if not clean_text:
continue
lines = clean_text.split("\n")
line_spacing = fontsize * 1.2
output_lines: list[str] = []
for line in lines:
max_width = TEXTBOX_WIDTH_PT
words = line.split(" ")
current_line = ""
for word in words:
test_line = current_line + (" " if current_line else "") + word
text_width = fitz.get_text_length(test_line, fontname="helv", fontsize=fontsize)
if text_width <= max_width or not current_line:
current_line = test_line
else:
output_lines.append(current_line)
current_line = word
if current_line:
output_lines.append(current_line)
y = rect.y0 + fontsize
for current_line in output_lines:
page.insert_text(
(rect.x0, y), current_line,
fontname="helv", fontsize=fontsize,
)
y += line_spacing
else:
# Einzeilige Felder: vertikal zentriert platzieren
mid_y = (rect.y0 + rect.y1) / 2
baseline_y = mid_y + fontsize * 0.35
page.insert_text(
(rect.x0, baseline_y),
formatted,
fontname="helv",
fontsize=fontsize,
)
y += line_spacing
else:
# Einzeilige Felder: vertikal zentriert platzieren
mid_y = (rect.y0 + rect.y1) / 2
baseline_y = mid_y + fontsize * 0.35
page.insert_text(
(rect.x0, baseline_y),
formatted,
fontname="helv",
fontsize=fontsize,
)
# ─────────────────────────────────────────────
Binary file not shown.
Binary file not shown.