05/26 Fix exported PDF form layout broken
This commit is contained in:
+47
-27
@@ -351,6 +351,7 @@ def _form_fields_section(form_fields, form_data, static_folder):
|
|||||||
if ft in _ALWAYS_SHOW_PRE:
|
if ft in _ALWAYS_SHOW_PRE:
|
||||||
return True
|
return True
|
||||||
if ft == 'rating' and str(v).isdigit() and int(v) > 0: return True
|
if ft == 'rating' and str(v).isdigit() and int(v) > 0: return True
|
||||||
|
if ft == 'pass_fail' and v: return True
|
||||||
if ft == 'checkbox' and v in ('yes','true'): return True
|
if ft == 'checkbox' and v in ('yes','true'): return True
|
||||||
if ft == 'checkbox_group'and isinstance(v, list) and v: return True
|
if ft == 'checkbox_group'and isinstance(v, list) and v: return True
|
||||||
if ft == 'image' and v and os.path.exists(os.path.join(static_folder, v)): return True
|
if ft == 'image' and v and os.path.exists(os.path.join(static_folder, v)): return True
|
||||||
@@ -398,33 +399,13 @@ def _form_fields_section(form_fields, form_data, static_folder):
|
|||||||
# Build one Table row with cells sized by colSpan.
|
# Build one Table row with cells sized by colSpan.
|
||||||
# Fields with no value are skipped unless they are text/textarea/label —
|
# Fields with no value are skipped unless they are text/textarea/label —
|
||||||
# those always appear so free-text notes are never suppressed.
|
# those always appear so free-text notes are never suppressed.
|
||||||
|
# current_col tracks horizontal position (1-based) so gaps between fields
|
||||||
|
# are filled with invisible placeholder cells that preserve column alignment.
|
||||||
cells = []
|
cells = []
|
||||||
col_widths = []
|
col_widths = []
|
||||||
|
has_content = False
|
||||||
|
current_col = 1
|
||||||
|
|
||||||
for field in fields_in_row:
|
|
||||||
ftype = field.get('type', '')
|
|
||||||
col_span = field.get('colSpan', 1)
|
|
||||||
cell_w = UNIT * col_span
|
|
||||||
|
|
||||||
# ── Inline label (free-standing text element) ─────────────────────
|
|
||||||
if ftype == 'label':
|
|
||||||
fs_map = {'small': 8, 'normal': 9, 'large': 11, 'x-large': 13}
|
|
||||||
fs = fs_map.get(field.get('font_size', 'normal'), 9)
|
|
||||||
fw = 'Helvetica-Bold' if field.get('font_weight') == 'bold' else 'Helvetica'
|
|
||||||
p = Paragraph(
|
|
||||||
field.get('text_content', ''),
|
|
||||||
ParagraphStyle('li', fontName=fw, fontSize=fs,
|
|
||||||
textColor=C_DARK, leading=fs + 3),
|
|
||||||
)
|
|
||||||
cells.append(p)
|
|
||||||
col_widths.append(cell_w)
|
|
||||||
continue
|
|
||||||
|
|
||||||
fid = str(field.get('id', ''))
|
|
||||||
val = form_data.get(fid, '')
|
|
||||||
lbl = field.get('label', '')
|
|
||||||
|
|
||||||
# ── Skip fields with no meaningful value ──────────────────────────
|
|
||||||
# Returns True if the field should be hidden from the PDF.
|
# Returns True if the field should be hidden from the PDF.
|
||||||
def _skip(ftype, val):
|
def _skip(ftype, val):
|
||||||
if ftype == 'rating':
|
if ftype == 'rating':
|
||||||
@@ -447,7 +428,43 @@ def _form_fields_section(form_fields, form_data, static_folder):
|
|||||||
# email, radio, select, and any future types)
|
# email, radio, select, and any future types)
|
||||||
return not val
|
return not val
|
||||||
|
|
||||||
|
for field in fields_in_row:
|
||||||
|
ftype = field.get('type', '')
|
||||||
|
col = field.get('col', current_col)
|
||||||
|
col_span = field.get('colSpan', 1)
|
||||||
|
cell_w = UNIT * col_span
|
||||||
|
|
||||||
|
# Fill horizontal gap before this field with an invisible spacer
|
||||||
|
if col > current_col:
|
||||||
|
gap_w = UNIT * (col - current_col)
|
||||||
|
cells.append(Paragraph('', STYLES['FieldValue']))
|
||||||
|
col_widths.append(gap_w)
|
||||||
|
current_col = col + col_span
|
||||||
|
|
||||||
|
# ── Inline label (free-standing text element) ─────────────────────
|
||||||
|
if ftype == 'label':
|
||||||
|
fs_map = {'small': 8, 'normal': 9, 'large': 11, 'x-large': 13}
|
||||||
|
fs = fs_map.get(field.get('font_size', 'normal'), 9)
|
||||||
|
fw = 'Helvetica-Bold' if field.get('font_weight') == 'bold' else 'Helvetica'
|
||||||
|
p = Paragraph(
|
||||||
|
field.get('text_content', ''),
|
||||||
|
ParagraphStyle('li', fontName=fw, fontSize=fs,
|
||||||
|
textColor=C_DARK, leading=fs + 3),
|
||||||
|
)
|
||||||
|
cells.append(p)
|
||||||
|
col_widths.append(cell_w)
|
||||||
|
has_content = True
|
||||||
|
continue
|
||||||
|
|
||||||
|
fid = str(field.get('id', ''))
|
||||||
|
val = form_data.get(fid, '')
|
||||||
|
lbl = field.get('label', '')
|
||||||
|
|
||||||
|
# ── Skip fields with no meaningful value ──────────────────────────
|
||||||
if _skip(ftype, val):
|
if _skip(ftype, val):
|
||||||
|
# Keep a placeholder so subsequent fields stay in column position
|
||||||
|
cells.append(Paragraph('', STYLES['FieldValue']))
|
||||||
|
col_widths.append(cell_w)
|
||||||
continue
|
continue
|
||||||
|
|
||||||
lbl_p = Paragraph(lbl, STYLES['FieldLabel'])
|
lbl_p = Paragraph(lbl, STYLES['FieldLabel'])
|
||||||
@@ -479,7 +496,9 @@ def _form_fields_section(form_fields, form_data, static_folder):
|
|||||||
height=1.0 * inch,
|
height=1.0 * inch,
|
||||||
kind='proportional')
|
kind='proportional')
|
||||||
except Exception:
|
except Exception:
|
||||||
# Could not load image — skip this cell entirely
|
# Could not load image — insert placeholder to preserve column position
|
||||||
|
cells.append(Paragraph('', STYLES['FieldValue']))
|
||||||
|
col_widths.append(cell_w)
|
||||||
continue
|
continue
|
||||||
|
|
||||||
elif ftype == 'signature':
|
elif ftype == 'signature':
|
||||||
@@ -536,9 +555,10 @@ def _form_fields_section(form_fields, form_data, static_folder):
|
|||||||
|
|
||||||
cells.append(box)
|
cells.append(box)
|
||||||
col_widths.append(cell_w)
|
col_widths.append(cell_w)
|
||||||
|
has_content = True
|
||||||
|
|
||||||
# Skip the entire row if nothing made it through the filter
|
# Skip the entire row if no field had meaningful content
|
||||||
if not cells:
|
if not has_content:
|
||||||
continue
|
continue
|
||||||
|
|
||||||
row_tbl = Table([cells], colWidths=col_widths, hAlign='LEFT')
|
row_tbl = Table([cells], colWidths=col_widths, hAlign='LEFT')
|
||||||
|
|||||||
Reference in New Issue
Block a user