~/stroke-ref/build_pdf.py
from reportlab.lib.pagesizes import A4
from reportlab.lib import colors
from reportlab.lib.units import cm, mm
from reportlab.lib.styles import getSampleStyleSheet, ParagraphStyle
from reportlab.lib.enums import TA_CENTER, TA_LEFT
from reportlab.platypus import (
SimpleDocTemplate, Paragraph, Spacer, Table, TableStyle,
HRFlowable, KeepTogether
)
from reportlab.lib.colors import HexColor
# ── Colour palette ──────────────────────────────────────────────────────────
C_ISCH = HexColor("#1565C0") # deep blue – ischemic
C_ISCH_L = HexColor("#E3F2FD") # light blue
C_HEM = HexColor("#B71C1C") # deep red – hemorrhagic
C_HEM_L = HexColor("#FFEBEE") # light red
C_HEAD = HexColor("#263238") # dark slate – main headings
C_AMBER = HexColor("#E65100") # amber – warnings
C_AMBER_L= HexColor("#FFF3E0")
C_GREEN = HexColor("#1B5E20")
C_GREEN_L= HexColor("#E8F5E9")
C_GREY = HexColor("#ECEFF1")
C_WHITE = colors.white
C_BLACK = colors.black
C_DARK = HexColor("#37474F")
# ── Document ─────────────────────────────────────────────────────────────────
doc = SimpleDocTemplate(
"/home/daytona/workspace/stroke-ref/Stroke_BP_Drug_QuickRef.pdf",
pagesize=A4,
leftMargin=1.5*cm, rightMargin=1.5*cm,
topMargin=1.5*cm, bottomMargin=1.5*cm,
)
W = A4[0] - 3*cm # usable width
# ── Styles ───────────────────────────────────────────────────────────────────
styles = getSampleStyleSheet()
def sty(name, **kw):
return ParagraphStyle(name, **kw)
title_sty = sty("Title2", fontSize=20, textColor=C_WHITE,
fontName="Helvetica-Bold", alignment=TA_CENTER, leading=24)
subtitle_sty = sty("Sub", fontSize=10, textColor=HexColor("#B0BEC5"),
fontName="Helvetica", alignment=TA_CENTER)
sec_isch = sty("SecI", fontSize=12, textColor=C_WHITE,
fontName="Helvetica-Bold", alignment=TA_CENTER, leading=16)
sec_hem = sty("SecH", fontSize=12, textColor=C_WHITE,
fontName="Helvetica-Bold", alignment=TA_CENTER, leading=16)
sec_gen = sty("SecG", fontSize=12, textColor=C_WHITE,
fontName="Helvetica-Bold", alignment=TA_CENTER, leading=16)
cell_bold = sty("CB", fontSize=8.5, fontName="Helvetica-Bold",
textColor=C_DARK, leading=12)
cell_norm = sty("CN", fontSize=8.5, fontName="Helvetica",
textColor=C_DARK, leading=11)
cell_sm = sty("CS", fontSize=7.5, fontName="Helvetica",
textColor=C_DARK, leading=10)
cell_warn = sty("CW", fontSize=8.5, fontName="Helvetica-Bold",
textColor=C_AMBER, leading=11)
cell_white= sty("CWH", fontSize=8.5, fontName="Helvetica-Bold",
textColor=C_WHITE, leading=11)
cell_green= sty("CG", fontSize=8.5, fontName="Helvetica-Bold",
textColor=C_GREEN, leading=11)
note_sty = sty("Note", fontSize=7.5, fontName="Helvetica-Oblique",
textColor=HexColor("#546E7A"), leading=10)
def P(text, style=None): return Paragraph(text, style or cell_norm)
def B(text): return Paragraph(text, cell_bold)
def W_txt(text): return Paragraph(text, cell_warn)
def Wh(text): return Paragraph(text, cell_white)
def Grn(text): return Paragraph(text, cell_green)
def Sm(text): return Paragraph(text, cell_sm)
# ── Section header helper ────────────────────────────────────────────────────
def section_header(text, color):
t = Table([[Paragraph(text, sty("SH", fontSize=12, textColor=C_WHITE,
fontName="Helvetica-Bold", alignment=TA_CENTER, leading=16))]],
colWidths=[W])
t.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1,-1), color),
("ROWBACKGROUNDS", (0,0), (-1,-1), [color]),
("TOPPADDING", (0,0), (-1,-1), 6),
("BOTTOMPADDING",(0,0),(-1,-1), 6),
("LEFTPADDING", (0,0), (-1,-1), 8),
("RIGHTPADDING",(0,0), (-1,-1), 8),
("ROUNDEDCORNERS", [4]),
]))
return t
# ── Subsection label helper ──────────────────────────────────────────────────
def subsec(text, color):
t = Table([[Paragraph(text, sty("SS", fontSize=9, textColor=C_WHITE,
fontName="Helvetica-Bold", leading=13))]],
colWidths=[W])
t.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1,-1), color),
("TOPPADDING",(0,0),(-1,-1), 4),
("BOTTOMPADDING",(0,0),(-1,-1), 4),
("LEFTPADDING",(0,0),(-1,-1), 8),
]))
return t
# ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
# BUILD CONTENT
# ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
story = []
# ── TITLE BANNER ─────────────────────────────────────────────────────────────
title_tbl = Table(
[[Paragraph("STROKE — BP Targets & Drug Doses", title_sty)],
[Paragraph("Quick Reference Card | AHA/ASA Guidelines", subtitle_sty)]],
colWidths=[W]
)
title_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1,-1), C_HEAD),
("TOPPADDING", (0,0), (-1,-1), 10),
("BOTTOMPADDING",(0,0),(-1,-1), 10),
("ROUNDEDCORNERS", [6]),
]))
story.append(title_tbl)
story.append(Spacer(1, 8))
# ── CRITICAL FIRST-STEP BOX ──────────────────────────────────────────────────
warn_tbl = Table(
[[Paragraph("⚠ ALWAYS do CT scan FIRST — Thrombolytics are LIFESAVING in ischemic stroke "
"but LETHAL in hemorrhagic stroke",
sty("W2", fontSize=9, fontName="Helvetica-Bold",
textColor=C_AMBER, alignment=TA_CENTER, leading=13))]],
colWidths=[W]
)
warn_tbl.setStyle(TableStyle([
("BACKGROUND",(0,0),(-1,-1), C_AMBER_L),
("BOX",(0,0),(-1,-1), 1.5, C_AMBER),
("TOPPADDING",(0,0),(-1,-1), 6),
("BOTTOMPADDING",(0,0),(-1,-1), 6),
("ROUNDEDCORNERS",[4]),
]))
story.append(warn_tbl)
story.append(Spacer(1, 10))
# ════════════════════════════════════════════════════════════════
# SECTION 1: ISCHEMIC STROKE
# ════════════════════════════════════════════════════════════════
story.append(section_header("ISCHEMIC STROKE", C_ISCH))
story.append(Spacer(1, 4))
# ── BP TARGETS ──────────────────────────────────────────────────
story.append(subsec("BLOOD PRESSURE TARGETS", C_ISCH))
bp_isch = [
[B("Scenario"), B("BP Target"), B("Key Note")],
[P("No thrombolysis"), B("Treat only if\n>220/120 mmHg"),
P("Reduce by 10–15% only. Elevated BP is often protective.")],
[P("Before giving Alteplase"), B("Must be\n<185/110 mmHg"),
P("Lower BP first, confirm stability, then give tPA.")],
[P("After Alteplase (≥24 h)"), B("Keep\n<180/105 mmHg"),
P("Monitor BP every 15 min × 2 h → 30 min × 6 h → hourly × 16 h.")],
[P("After Thrombectomy"), B("Keep\n<180/105 mmHg"),
P("Same as post-alteplase target.")],
]
bp_isch_tbl = Table(bp_isch, colWidths=[W*0.30, W*0.22, W*0.48])
bp_isch_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1, 0), C_ISCH),
("TEXTCOLOR", (0,0), (-1, 0), C_WHITE),
("FONTNAME", (0,0), (-1, 0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1, 0), 8.5),
("ROWBACKGROUNDS", (0,1), (-1,-1), [C_ISCH_L, C_WHITE]),
("GRID", (0,0), (-1,-1), 0.4, HexColor("#90CAF9")),
("VALIGN", (0,0), (-1,-1), "MIDDLE"),
("TOPPADDING", (0,0), (-1,-1), 5),
("BOTTOMPADDING", (0,0), (-1,-1), 5),
("LEFTPADDING", (0,0), (-1,-1), 6),
("RIGHTPADDING", (0,0), (-1,-1), 6),
("ALIGN", (1,1), (1,-1), "CENTER"),
]))
story.append(bp_isch_tbl)
story.append(Spacer(1, 6))
# ── ALTEPLASE DOSING ────────────────────────────────────────────
story.append(subsec("IV ALTEPLASE (tPA) — DOSING & TIME WINDOWS", C_ISCH))
alt_data = [
[B("Parameter"), B("Details")],
[P("Dose"), P("0.9 mg/kg IV (max 90 mg total)\n"
"→ 10% as IV bolus over 1 min\n"
"→ 90% infused over 60 min")],
[P("Window — 0 to 3 h"), P("Strongly recommended for all eligible patients ≥18 yr")],
[P("Window — 3 to 4.5 h"), P("Recommended if ALL of the following:\n"
"• Age ≤80 yr\n"
"• No history of BOTH diabetes AND prior stroke\n"
"• NIHSS score ≤25\n"
"• Not on oral anticoagulants\n"
"• Ischemic injury <1/3 of MCA territory on imaging")],
[P("Window — >4.5 h"), P("NOT recommended (standard alteplase)")],
[P("Blood glucose"), P("Must be >50 mg/dL (correct hypoglycemia first)")],
]
alt_tbl = Table(alt_data, colWidths=[W*0.30, W*0.70])
alt_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1, 0), C_ISCH),
("TEXTCOLOR", (0,0), (-1, 0), C_WHITE),
("FONTNAME", (0,0), (-1, 0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1, 0), 8.5),
("ROWBACKGROUNDS", (0,1), (-1,-1), [C_ISCH_L, C_WHITE]),
("GRID", (0,0), (-1,-1), 0.4, HexColor("#90CAF9")),
("VALIGN", (0,0), (-1,-1), "TOP"),
("TOPPADDING", (0,0), (-1,-1), 5),
("BOTTOMPADDING", (0,0), (-1,-1), 5),
("LEFTPADDING", (0,0), (-1,-1), 6),
("RIGHTPADDING", (0,0), (-1,-1), 6),
]))
story.append(alt_tbl)
story.append(Spacer(1, 6))
# ── ALTEPLASE CONTRAINDICATIONS ─────────────────────────────────
story.append(subsec("ALTEPLASE — ABSOLUTE CONTRAINDICATIONS", HexColor("#C62828")))
ci_data = [
[B("Contraindication"), B("Contraindication")],
[P("❌ Hemorrhagic stroke on CT"), P("❌ Active internal bleeding")],
[P("❌ BP >185/110 (cannot be lowered)"), P("❌ Intracranial neoplasm / AVM / aneurysm")],
[P("❌ Ischemic stroke or head trauma <3 months"), P("❌ INR >1.7 or aPTT >40 sec (anticoagulated)")],
[P("❌ Prior intracranial hemorrhage"), P("❌ Platelet count <100,000/mm³")],
[P("❌ Recent intracranial/spinal surgery"), P("❌ Blood glucose <50 mg/dL (uncorrected)")],
]
ci_tbl = Table(ci_data, colWidths=[W*0.50, W*0.50])
ci_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1, 0), HexColor("#C62828")),
("TEXTCOLOR", (0,0), (-1, 0), C_WHITE),
("FONTNAME", (0,0), (-1, 0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1, 0), 8.5),
("ROWBACKGROUNDS", (0,1), (-1,-1), [HexColor("#FFEBEE"), C_WHITE]),
("GRID", (0,0), (-1,-1), 0.4, HexColor("#EF9A9A")),
("VALIGN", (0,0), (-1,-1), "MIDDLE"),
("TOPPADDING", (0,0), (-1,-1), 5),
("BOTTOMPADDING", (0,0), (-1,-1), 5),
("LEFTPADDING", (0,0), (-1,-1), 6),
("RIGHTPADDING", (0,0), (-1,-1), 6),
]))
story.append(ci_tbl)
story.append(Spacer(1, 6))
# ── ANTIPLATELET / ANTICOAGULANT ─────────────────────────────────
story.append(subsec("ANTITHROMBOTIC THERAPY — SECONDARY PREVENTION", C_ISCH))
ap_data = [
[B("Stroke Type"), B("Drug"), B("Dose"), B("Notes")],
[P("Non-cardioembolic\n(atherosclerosis/\nsmall vessel)"),
P("Aspirin"), P("160–325 mg load\nthen 75–100 mg/day"),
P("Start within 24–48 h\nNOT within 24 h of alteplase")],
[P(""), P("Clopidogrel"), P("75 mg/day"),
P("Preferred over aspirin alone")],
[P(""), P("Aspirin +\nDipyridamole ER\n(Aggrenox)"),
P("25/200 mg\ntwice daily"),
P("First-line option for\nsecondary prevention")],
[P(""), P("Dual antiplatelet\n(Aspirin + Clopidogrel)"),
P("Short-term\n21–90 days"),
P("Minor stroke/TIA only\nNOT long-term → bleeding risk")],
[P("Cardioembolic\n(Atrial Fibrillation)"),
P("DOAC (apixaban,\nrivaroxaban,\ndabigatran)\nor Warfarin"),
P("Per drug guidelines\nWarfarin: INR 2–3"),
P("Antiplatelets alone\nINADEQUATE for AF")],
]
ap_tbl = Table(ap_data, colWidths=[W*0.20, W*0.22, W*0.22, W*0.36])
ap_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1, 0), C_ISCH),
("TEXTCOLOR", (0,0), (-1, 0), C_WHITE),
("FONTNAME", (0,0), (-1, 0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1, 0), 8.5),
("ROWBACKGROUNDS", (0,1), (-1,-1), [C_ISCH_L, C_WHITE]),
("GRID", (0,0), (-1,-1), 0.4, HexColor("#90CAF9")),
("VALIGN", (0,0), (-1,-1), "TOP"),
("SPAN", (0,1), (0,4)),
("TOPPADDING", (0,0), (-1,-1), 5),
("BOTTOMPADDING", (0,0), (-1,-1), 5),
("LEFTPADDING", (0,0), (-1,-1), 6),
("RIGHTPADDING", (0,0), (-1,-1), 6),
]))
story.append(ap_tbl)
story.append(Spacer(1, 10))
# ════════════════════════════════════════════════════════════════
# SECTION 2: HEMORRHAGIC STROKE
# ════════════════════════════════════════════════════════════════
story.append(section_header("HEMORRHAGIC STROKE (ICH)", C_HEM))
story.append(Spacer(1, 4))
# ── BP TARGETS ICH ──────────────────────────────────────────────
story.append(subsec("BLOOD PRESSURE TARGETS", C_HEM))
bp_ich = [
[B("Target"), B("Value"), B("Note")],
[P("General BP goal"), B("SBP <180\nMAP <130 mmHg"),
P("Treat if BP >180/105 mmHg")],
[P("Ideal BP goal"), B("SBP <160 mmHg"),
P("Rapid lowering safe — does not impair peri-hematomal perfusion")],
[P("SBP <140 target"), B("Still debated"),
P("INTERACT2 & ATACH-II trials showed unclear benefit")],
[P("SAH — before aneurysm secured"), B("Keep SBP <160 mmHg"),
P("After aneurysm treated: do NOT lower BP aggressively")],
]
bp_ich_tbl = Table(bp_ich, colWidths=[W*0.30, W*0.22, W*0.48])
bp_ich_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1, 0), C_HEM),
("TEXTCOLOR", (0,0), (-1, 0), C_WHITE),
("FONTNAME", (0,0), (-1, 0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1, 0), 8.5),
("ROWBACKGROUNDS", (0,1), (-1,-1), [C_HEM_L, C_WHITE]),
("GRID", (0,0), (-1,-1), 0.4, HexColor("#EF9A9A")),
("VALIGN", (0,0), (-1,-1), "MIDDLE"),
("TOPPADDING", (0,0), (-1,-1), 5),
("BOTTOMPADDING", (0,0), (-1,-1), 5),
("LEFTPADDING", (0,0), (-1,-1), 6),
("RIGHTPADDING", (0,0), (-1,-1), 6),
("ALIGN", (1,1), (1,-1), "CENTER"),
]))
story.append(bp_ich_tbl)
story.append(Spacer(1, 6))
# ── IV ANTIHYPERTENSIVE DRUGS ────────────────────────────────────
story.append(subsec("IV ANTIHYPERTENSIVE DRUGS FOR ICH", C_HEM))
drug_data = [
[B("Drug"), B("Class"), B("Dose / Route"), B("Notes")],
[P("Labetalol"), P("α + β blocker"),
P("10–20 mg IV bolus q10–20 min\nOR 1–2 mg/min infusion"),
P("First-line. Smooth, titratable.\nAvoid in asthma/bradycardia")],
[P("Nicardipine"), P("CCB (dihydropyridine)"),
P("5 mg/h IV → titrate\nup by 2.5 mg/h q5 min\n(max 15 mg/h)"),
P("Preferred for continuous\ntitration. No reflex tachycardia")],
[P("Esmolol"), P("β₁-blocker"),
P("500 mcg/kg bolus\nthen 50–200 mcg/kg/min"),
P("Short-acting. Useful peri-op.\nAvoid in severe LV dysfunction")],
[P("Enalaprilat"), P("ACE inhibitor"),
P("0.625 mg IV test dose\nthen 1.25 mg q6h"),
P("Risk of precipitous drop.\nStart with small test dose")],
[P("Sodium Nitroprusside"), P("Vasodilator"),
P("0.3–10 mcg/kg/min infusion"),
P("Reserve for DBP >140 mmHg.\nCan raise ICP — use cautiously")],
[P("Hydralazine\n(for ischemic stroke)"), P("Vasodilator"),
P("10–20 mg IV q20 min"),
P("Used in ischemic stroke\n(not ICH first choice)")],
]
drug_tbl = Table(drug_data, colWidths=[W*0.18, W*0.18, W*0.30, W*0.34])
drug_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1, 0), C_HEM),
("TEXTCOLOR", (0,0), (-1, 0), C_WHITE),
("FONTNAME", (0,0), (-1, 0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1, 0), 8.5),
("ROWBACKGROUNDS", (0,1), (-1,-1), [C_HEM_L, C_WHITE]),
("GRID", (0,0), (-1,-1), 0.4, HexColor("#EF9A9A")),
("VALIGN", (0,0), (-1,-1), "TOP"),
("TOPPADDING", (0,0), (-1,-1), 5),
("BOTTOMPADDING", (0,0), (-1,-1), 5),
("LEFTPADDING", (0,0), (-1,-1), 6),
("RIGHTPADDING", (0,0), (-1,-1), 6),
]))
story.append(drug_tbl)
story.append(Spacer(1, 6))
# ── COAGULOPATHY REVERSAL ─────────────────────────────────────────
story.append(subsec("COAGULOPATHY REVERSAL IN ICH", C_HEM))
coag_data = [
[B("Agent Causing Bleed"), B("Reversal Drug"), B("Dose")],
[P("Warfarin"), P("Vitamin K + 4-factor PCC\n(or FFP if PCC unavailable)"),
P("Vit K: 10 mg IV slow\nPCC: per INR-based dosing\nFFP: 10–15 mL/kg")],
[P("Dabigatran"), P("Idarucizumab (Praxbind)"),
P("5 g IV (two 2.5 g vials)")],
[P("Rivaroxaban / Apixaban\n(Factor Xa inhibitors)"), P("Andexanet alfa\nOR 4-factor PCC"),
P("Andexanet: low/high dose\nper last dose timing")],
[P("Heparin (UFH)"), P("Protamine sulfate"),
P("1 mg per 100 units heparin\ngiven in last 2–3 h (max 50 mg)")],
[P("Thrombolytic-related ICH"), P("Cryoprecipitate\n+ Tranexamic acid"),
P("Cryoprecipitate: 10 units IV\nTXA: 1 g IV\nTarget fibrinogen ≥150 mg/dL")],
[P("Antiplatelet-related ICH"), P("❌ NO platelet transfusion\n(PATCH trial — worsens outcomes)"),
P("Treat thrombocytopenia only\n(platelet <100k → transfuse)")],
]
coag_tbl = Table(coag_data, colWidths=[W*0.30, W*0.38, W*0.32])
coag_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1, 0), C_HEM),
("TEXTCOLOR", (0,0), (-1, 0), C_WHITE),
("FONTNAME", (0,0), (-1, 0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1, 0), 8.5),
("ROWBACKGROUNDS", (0,1), (-1,-1), [C_HEM_L, C_WHITE]),
("GRID", (0,0), (-1,-1), 0.4, HexColor("#EF9A9A")),
("VALIGN", (0,0), (-1,-1), "TOP"),
("TOPPADDING", (0,0), (-1,-1), 5),
("BOTTOMPADDING", (0,0), (-1,-1), 5),
("LEFTPADDING", (0,0), (-1,-1), 6),
("RIGHTPADDING", (0,0), (-1,-1), 6),
]))
story.append(coag_tbl)
story.append(Spacer(1, 10))
# ════════════════════════════════════════════════════════════════
# SECTION 3: SIDE-BY-SIDE SUMMARY
# ════════════════════════════════════════════════════════════════
story.append(section_header("QUICK COMPARISON SUMMARY", C_HEAD))
story.append(Spacer(1, 4))
cmp_data = [
[B("Feature"),
Paragraph("ISCHEMIC STROKE", sty("IH", fontSize=8.5, fontName="Helvetica-Bold",
textColor=C_ISCH, leading=11)),
Paragraph("HEMORRHAGIC (ICH)", sty("HH", fontSize=8.5, fontName="Helvetica-Bold",
textColor=C_HEM, leading=11))],
[P("CT appearance"), P("Dark (hypodense)"), P("Bright white (hyperdense)")],
[P("BP — no specific therapy"), P("Treat only if >220/120"), P("Treat if >180/105")],
[P("BP — thrombolytics"), P("<185/110 before; <180/105 after"), P("N/A — thrombolytics CONTRAINDICATED")],
[P("Ideal target"), P("<180/105 mmHg (post tPA)"), P("SBP <160 mmHg")],
[P("Thrombolytics"), Paragraph("✅ Alteplase — first-line if eligible",
sty("GS", fontSize=8.5, fontName="Helvetica-Bold", textColor=C_GREEN, leading=11)),
Paragraph("❌ Absolutely contraindicated",
sty("RS", fontSize=8.5, fontName="Helvetica-Bold", textColor=C_HEM, leading=11))],
[P("Antiplatelets"), P("✅ Aspirin/clopidogrel within 24–48 h"), P("❌ Avoid (platelet transfusion NOT useful)")],
[P("Anticoagulation"), P("✅ For AF-related stroke (DOACs/warfarin)"), P("❌ Reverse existing anticoagulation ASAP")],
[P("Surgery"), P("Thrombectomy for LVO"), P("For cerebellar ICH >3 cm or herniation")],
[P("DVT prophylaxis"), P("LMWH early (enoxaparin 40 mg OD)"), P("Delay until hemostasis stable")],
[P("30-day mortality"), P("Lower — ~10–20%"), P("High — ~50%")],
]
cmp_tbl = Table(cmp_data, colWidths=[W*0.28, W*0.36, W*0.36])
cmp_tbl.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1, 0), C_HEAD),
("TEXTCOLOR", (0,0), (-1, 0), C_WHITE),
("FONTNAME", (0,0), (-1, 0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1, 0), 8.5),
("ROWBACKGROUNDS", (0,1), (-1,-1), [C_GREY, C_WHITE]),
("GRID", (0,0), (-1,-1), 0.4, HexColor("#B0BEC5")),
("VALIGN", (0,0), (-1,-1), "MIDDLE"),
("TOPPADDING", (0,0), (-1,-1), 5),
("BOTTOMPADDING", (0,0), (-1,-1), 5),
("LEFTPADDING", (0,0), (-1,-1), 6),
("RIGHTPADDING", (0,0), (-1,-1), 6),
]))
story.append(cmp_tbl)
story.append(Spacer(1, 8))
# ── FOOTER ───────────────────────────────────────────────────────
story.append(HRFlowable(width=W, thickness=0.5, color=HexColor("#B0BEC5")))
story.append(Spacer(1, 3))
story.append(Paragraph(
"Sources: Bradley & Daroff's Neurology in Clinical Practice | Rosen's Emergency Medicine 9e | "
"Tintinalli's Emergency Medicine | AHA/ASA 2019 Acute Stroke Guidelines — For clinical use; verify current guidelines.",
sty("FT", fontSize=6.5, fontName="Helvetica-Oblique", textColor=HexColor("#90A4AE"),
alignment=TA_CENTER, leading=9)
))
# ── BUILD ─────────────────────────────────────────────────────────────────────
doc.build(story)
print("PDF created successfully.")