I am a new Apn on the Advanced heart failure, and Transplant team. Can you please create a study guide to help me with EKGs and anti-rejection test and treatments as as well as as GDMT for heart failure, patients, etc. please make this easy to understand and comprehend, as I am just starting out in my career
"heart failure" AND "guideline directed medical therapy"
Create a quick reference PDF card (front/back) with EKG findings
ls -la /home/daytona/workspace/ 2>/dev/null || mkdir -p /home/daytona/workspace
mkdir -p /home/daytona/workspace/ekgcard && python3 -c "from reportlab.pdfgen im…
~/ekgcard/build_ekg_card.py
from reportlab.pdfgen import canvas
from reportlab.lib.pagesizes import letter
from reportlab.lib import colors
from reportlab.lib.units import inch
from reportlab.platypus import Table, TableStyle
from reportlab.lib.styles import getSampleStyleSheet
from reportlab.platypus import Paragraph
# ── Palette ──────────────────────────────────────────────────────────────────
NAVY = colors.HexColor("#0A2342")
TEAL = colors.HexColor("#1A6B72")
LIGHT_TEAL = colors.HexColor("#D6F0F2")
RED_ACCENT = colors.HexColor("#C0392B")
AMBER = colors.HexColor("#E67E22")
GREEN = colors.HexColor("#1E8449")
WHITE = colors.white
LIGHT_GRAY = colors.HexColor("#F4F6F8")
MID_GRAY = colors.HexColor("#BDC3C7")
DARK_GRAY = colors.HexColor("#2C3E50")
YELLOW_HI = colors.HexColor("#FDEBD0")
W, H = letter # 8.5 × 11 inches
def header_bar(c, y, text, bg=NAVY, fg=WHITE, fontsize=11):
c.setFillColor(bg)
c.rect(0.35*inch, y, W - 0.7*inch, 0.28*inch, fill=1, stroke=0)
c.setFillColor(fg)
c.setFont("Helvetica-Bold", fontsize)
c.drawCentredString(W/2, y + 0.06*inch, text)
def section_header(c, x, y, w, text, bg=TEAL, fg=WHITE, fontsize=9):
c.setFillColor(bg)
c.rect(x, y, w, 0.22*inch, fill=1, stroke=0)
c.setFillColor(fg)
c.setFont("Helvetica-Bold", fontsize)
c.drawString(x + 0.08*inch, y + 0.05*inch, text)
def bullet(c, x, y, text, fontsize=7.5, color=DARK_GRAY, bold_prefix=None):
c.setFillColor(TEAL)
c.circle(x + 0.04*inch, y + 0.055*inch, 0.025*inch, fill=1, stroke=0)
c.setFillColor(color)
if bold_prefix:
c.setFont("Helvetica-Bold", fontsize)
bw = c.stringWidth(bold_prefix, "Helvetica-Bold", fontsize)
c.drawString(x + 0.13*inch, y + 0.03*inch, bold_prefix)
c.setFont("Helvetica", fontsize)
c.drawString(x + 0.13*inch + bw, y + 0.03*inch, text)
else:
c.setFont("Helvetica", fontsize)
c.drawString(x + 0.13*inch, y + 0.03*inch, text)
def small_text(c, x, y, text, fontsize=7, color=DARK_GRAY, bold=False):
c.setFillColor(color)
c.setFont("Helvetica-Bold" if bold else "Helvetica", fontsize)
c.drawString(x, y, text)
def tag(c, x, y, text, bg=RED_ACCENT, fg=WHITE, fontsize=6.5):
tw = c.stringWidth(text, "Helvetica-Bold", fontsize)
pad = 0.05*inch
c.setFillColor(bg)
c.roundRect(x, y, tw + 2*pad, 0.15*inch, 0.03*inch, fill=1, stroke=0)
c.setFillColor(fg)
c.setFont("Helvetica-Bold", fontsize)
c.drawString(x + pad, y + 0.025*inch, text)
def divider(c, x, y, w, color=MID_GRAY):
c.setStrokeColor(color)
c.setLineWidth(0.4)
c.line(x, y, x+w, y)
def box_outline(c, x, y, w, h, color=MID_GRAY):
c.setStrokeColor(color)
c.setLineWidth(0.5)
c.roundRect(x, y, w, h, 0.05*inch, fill=0, stroke=1)
# ─────────────────────────────────────────────────────────────────────────────
# PAGE 1 — FRONT
# ─────────────────────────────────────────────────────────────────────────────
def draw_front(c):
# Background
c.setFillColor(LIGHT_GRAY)
c.rect(0, 0, W, H, fill=1, stroke=0)
# Top banner
c.setFillColor(NAVY)
c.rect(0, H - 0.75*inch, W, 0.75*inch, fill=1, stroke=0)
c.setFillColor(WHITE)
c.setFont("Helvetica-Bold", 15)
c.drawCentredString(W/2, H - 0.38*inch, "🫀 EKG Quick Reference Card — Advanced HF & Transplant")
c.setFont("Helvetica", 8)
c.setFillColor(LIGHT_TEAL)
c.drawCentredString(W/2, H - 0.60*inch, "FRONT | Systematic Approach · Intervals · Key Patterns | For APN Use")
# Accent stripe
c.setFillColor(TEAL)
c.rect(0, H - 0.78*inch, W, 0.04*inch, fill=1, stroke=0)
# ── COL LEFT x=0.35 w=3.55 ────────────────────────────────────────────
LX = 0.35*inch
LW = 3.55*inch
# 1. SYSTEMATIC APPROACH
cy = H - 1.08*inch
section_header(c, LX, cy, LW, "STEP-BY-STEP SYSTEMATIC APPROACH")
cy -= 0.02*inch
steps = [
("1 RATE", "Count R-R big boxes → 300 ÷ # boxes = rate | Normal: 60–100 bpm"),
("2 RHYTHM", "Regular R-R? P before every QRS? → Sinus if yes"),
("3 AXIS", "Lead I + aVF both upright = normal (−30° to +90°)"),
("4 INTERVALS", "Measure PR, QRS, QTc (see table below)"),
("5 MORPHOLOGY","P shape, Q waves, ST segments, T waves"),
]
row_bg = [LIGHT_TEAL, WHITE, LIGHT_TEAL, WHITE, LIGHT_TEAL]
for i, (label, detail) in enumerate(steps):
cy -= 0.23*inch
c.setFillColor(row_bg[i])
c.rect(LX, cy, LW, 0.22*inch, fill=1, stroke=0)
c.setFillColor(NAVY)
c.setFont("Helvetica-Bold", 7.5)
c.drawString(LX + 0.07*inch, cy + 0.07*inch, label)
lw = c.stringWidth(label, "Helvetica-Bold", 7.5)
c.setFillColor(DARK_GRAY)
c.setFont("Helvetica", 7.2)
c.drawString(LX + 0.12*inch + lw, cy + 0.07*inch, detail)
# 2. NORMAL INTERVALS TABLE
cy -= 0.3*inch
section_header(c, LX, cy, LW, "NORMAL INTERVALS")
cy -= 0.22*inch
rows = [
["Interval", "Normal Range", "Clinical Pearl"],
["PR interval", "0.12 – 0.20 sec\n(3–5 sm boxes)", "Prolonged = heart block\n(common post-transplant)"],
["QRS duration", "< 0.12 sec\n(< 3 sm boxes)", "Wide QRS → BBB or VT\nLBBB + EF≤35% → CRT?"],
["QTc", "♂ < 0.44 s\n♀ < 0.46 s", "Many HF drugs prolong QT\nAmiodarone, azoles, ABX"],
]
col_widths = [0.85*inch, 1.15*inch, 1.55*inch]
table = Table(rows, colWidths=col_widths, rowHeights=[0.2*inch, 0.36*inch, 0.36*inch, 0.36*inch])
table.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1,0), NAVY),
("TEXTCOLOR", (0,0), (-1,0), WHITE),
("FONTNAME", (0,0), (-1,0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1,0), 7.5),
("BACKGROUND", (0,1), (-1,1), LIGHT_TEAL),
("BACKGROUND", (0,2), (-1,2), WHITE),
("BACKGROUND", (0,3), (-1,3), LIGHT_TEAL),
("FONTNAME", (0,1), (-1,-1), "Helvetica"),
("FONTSIZE", (0,1), (-1,-1), 7),
("FONTNAME", (0,1), (0,-1), "Helvetica-Bold"),
("TEXTCOLOR", (0,1), (0,-1), NAVY),
("VALIGN", (0,0), (-1,-1), "MIDDLE"),
("ALIGN", (0,0), (-1,-1), "LEFT"),
("LEFTPADDING", (0,0), (-1,-1), 4),
("RIGHTPADDING", (0,0), (-1,-1), 3),
("GRID", (0,0), (-1,-1), 0.4, MID_GRAY),
("ROWBACKGROUNDS", (0,0), (-1,-1), [None]),
]))
table.wrapOn(c, LW, 2*inch)
table.drawOn(c, LX, cy - 1.08*inch)
cy -= 1.15*inch
# 3. RATE QUICK CALC BOX
cy -= 0.3*inch
section_header(c, LX, cy, LW, "HEART RATE QUICK CALC")
cy -= 0.02*inch
rate_data = [
["# Big Boxes", "1", "2", "3", "4", "5", "6"],
["Heart Rate", "300","150","100","75","60","50"],
]
rt = Table(rate_data, colWidths=[1.05*inch] + [0.41*inch]*6, rowHeights=[0.18*inch, 0.18*inch])
rt.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1,0), TEAL),
("TEXTCOLOR", (0,0), (-1,0), WHITE),
("FONTNAME", (0,0), (-1,0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1,-1), 7.5),
("BACKGROUND", (0,1), (-1,1), LIGHT_TEAL),
("FONTNAME", (0,1), (-1,1), "Helvetica-Bold"),
("TEXTCOLOR", (0,1), (-1,1), NAVY),
("ALIGN", (0,0), (-1,-1), "CENTER"),
("VALIGN", (0,0), (-1,-1), "MIDDLE"),
("GRID", (0,0), (-1,-1), 0.4, MID_GRAY),
]))
rt.wrapOn(c, LW, 0.5*inch)
cy -= 0.38*inch
rt.drawOn(c, LX, cy)
# ── COL RIGHT x=4.15 w=3.95 ───────────────────────────────────────────
RX = 4.15*inch
RW = 4.00*inch
ry = H - 1.08*inch
section_header(c, RX, ry, RW, "KEY EKG PATTERNS")
patterns = [
{
"title": "LBBB — Left Bundle Branch Block",
"color": NAVY,
"tag": "CRT CANDIDATE?",
"tag_bg": AMBER,
"bullets": [
("QRS > 0.12 sec", " (≥ 3 small boxes)"),
("V5–V6:", " broad notched 'M' shape | V1: deep S wave"),
("NEW LBBB + chest pain", " → treat as STEMI"),
("EF ≤ 35% + LBBB + NYHA II–IV", " → refer for CRT"),
]
},
{
"title": "RBBB — Right Bundle Branch Block",
"color": TEAL,
"tag": "NORMAL POST-TRANSPLANT",
"tag_bg": GREEN,
"bullets": [
("V1–V2:", " 'RSR\\'' (rabbit ears) pattern"),
("V5–V6:", " wide slurred S wave"),
("Incomplete RBBB post-transplant", " = expected, not pathologic"),
("Complete RBBB:", " usually benign; evaluate in context"),
]
},
{
"title": "VENTRICULAR TACHYCARDIA (VT)",
"color": RED_ACCENT,
"tag": "HIGH RISK",
"tag_bg": RED_ACCENT,
"bullets": [
("Wide complex tach:", " QRS > 0.12, rate > 100 bpm"),
("NO P waves before QRS", " (or AV dissociation)"),
("Fusion beats", " at start confirm VT"),
("ICD indicated", " if EF ≤ 35% (primary prevention)"),
]
},
{
"title": "ATRIAL FIBRILLATION",
"color": colors.HexColor("#6C3483"),
"tag": "COMMON IN HF",
"tag_bg": colors.HexColor("#6C3483"),
"bullets": [
("Irregularly irregular", " R-R intervals"),
("No clear P waves,", " fibrillatory baseline"),
("Rate control vs. rhythm control", " based on HF severity"),
("Ivabradine does NOT work", " in A-fib (sinus rhythm only)"),
]
},
{
"title": "HEART BLOCK",
"color": colors.HexColor("#784212"),
"tag": "CHECK POST-TRANSPLANT",
"tag_bg": AMBER,
"bullets": [
("1°:", " PR > 0.20 sec, every P conducts"),
("2° Mobitz I:", " progressive PR lengthening → dropped beat"),
("2° Mobitz II:", " fixed PR, sudden dropped QRS → pacemaker likely"),
("3° (complete):", " no P-QRS relationship → urgent pacemaker"),
]
},
]
ry -= 0.02*inch
for pat in patterns:
ry -= 0.23*inch
# Pattern title bar
c.setFillColor(pat["color"])
c.rect(RX, ry, RW, 0.22*inch, fill=1, stroke=0)
c.setFillColor(WHITE)
c.setFont("Helvetica-Bold", 8)
c.drawString(RX + 0.08*inch, ry + 0.06*inch, pat["title"])
# Tag
tag(c, RX + RW - c.stringWidth(pat["tag"], "Helvetica-Bold", 6.5) - 0.18*inch,
ry + 0.035*inch, pat["tag"], bg=pat["tag_bg"])
ry -= 0.01*inch
for b_bold, b_rest in pat["bullets"]:
ry -= 0.135*inch
bullet(c, RX + 0.04*inch, ry, b_rest, fontsize=7, bold_prefix=b_bold)
ry -= 0.03*inch
# ── BOTTOM FULL-WIDTH BAR: TRANSPLANT EKG ALERT ──────────────────────────
alert_y = 0.52*inch
c.setFillColor(colors.HexColor("#FEF9E7"))
c.roundRect(0.35*inch, alert_y, W - 0.7*inch, 0.42*inch, 0.06*inch, fill=1, stroke=0)
c.setStrokeColor(AMBER)
c.setLineWidth(1.2)
c.roundRect(0.35*inch, alert_y, W - 0.7*inch, 0.42*inch, 0.06*inch, fill=0, stroke=1)
c.setFillColor(AMBER)
c.setFont("Helvetica-Bold", 8)
c.drawString(0.5*inch, alert_y + 0.27*inch, "⚠ TRANSPLANT HEART ALERTS:")
c.setFont("Helvetica", 7.2)
c.setFillColor(DARK_GRAY)
alerts = [
"Resting HR 95–110 bpm (no vagal tone) → normal early post-Tx",
"Incomplete RBBB → expected finding",
"Q waves / ST elevation → SIGNIFICANT (silent MI — no chest pain!)",
"Atropine / Glycopyrrolate → USELESS (vagus nerve is cut)",
"Adenosine → use HALF dose (↑ AV block risk)",
]
ax = 0.5*inch
for i, a in enumerate(alerts):
col = ax + (i % 3) * (2.6*inch) if i < 3 else ax + ((i-3) % 3) * (3.9*inch)
row_y = alert_y + 0.22*inch if i < 3 else alert_y + 0.06*inch
c.setFillColor(RED_ACCENT)
c.circle(col + 0.04*inch, row_y + 0.055*inch, 0.022*inch, fill=1, stroke=0)
c.setFillColor(DARK_GRAY)
c.drawString(col + 0.12*inch, row_y + 0.03*inch, a)
# Footer
c.setFillColor(NAVY)
c.rect(0, 0, W, 0.35*inch, fill=1, stroke=0)
c.setFillColor(WHITE)
c.setFont("Helvetica", 6.5)
c.drawCentredString(W/2, 0.13*inch,
"Sources: Braunwald's Heart Disease 11e · Goldman-Cecil Medicine · Rosen's Emergency Medicine | FRONT — See reverse for Transplant EKG & Arrhythmia Drug Guide")
# ─────────────────────────────────────────────────────────────────────────────
# PAGE 2 — BACK
# ─────────────────────────────────────────────────────────────────────────────
def draw_back(c):
# Background
c.setFillColor(LIGHT_GRAY)
c.rect(0, 0, W, H, fill=1, stroke=0)
# Top banner
c.setFillColor(TEAL)
c.rect(0, H - 0.75*inch, W, 0.75*inch, fill=1, stroke=0)
c.setFillColor(WHITE)
c.setFont("Helvetica-Bold", 15)
c.drawCentredString(W/2, H - 0.38*inch, "🫀 EKG Quick Reference Card — Advanced HF & Transplant")
c.setFont("Helvetica", 8)
c.setFillColor(LIGHT_TEAL)
c.drawCentredString(W/2, H - 0.60*inch, "BACK | ST / T-Wave Changes · HF EKG Findings · Arrhythmia Drug Guide · CAV")
c.setFillColor(NAVY)
c.rect(0, H - 0.78*inch, W, 0.04*inch, fill=1, stroke=0)
# ── LEFT COLUMN ──────────────────────────────────────────────────────────
LX = 0.35*inch
LW = 3.55*inch
cy = H - 1.1*inch
# ST / T WAVE CHANGES
section_header(c, LX, cy, LW, "ST SEGMENT & T-WAVE CHANGES")
cy -= 0.03*inch
st_rows = [
["Finding", "Think About", "Action"],
["ST elevation\n(≥1 mm, ≥2 leads)", "STEMI / Pericarditis\nIn Tx pt: CAV, silent MI", "Urgent cardiology consult\nDo NOT delay for biopsy"],
["ST depression", "NSTEMI / Ischemia\nDigoxin effect (scooped)", "Troponin, cardiology"],
["Diffuse saddle-shaped\nST elevation", "Pericarditis", "CRP, echo, NSAIDs\n(if not on anticoag)"],
["Peaked T waves", "Hyperkalemia ⚠", "STAT K⁺ level → treat"],
["Flat/inverted T waves", "Ischemia, LVH,\nelectrolyte imbalance", "Clinical correlation"],
["Prolonged QTc\n(men >0.44, women >0.46)", "Drug toxicity, ↓Mg, ↓K\nAmiodarone, azoles", "Review meds, lytes\nReduce offending drug"],
]
st_col_w = [1.1*inch, 1.35*inch, 1.1*inch]
st_row_h = [0.19*inch] + [0.39*inch]*6
st = Table(st_rows, colWidths=st_col_w, rowHeights=st_row_h)
st.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1,0), NAVY),
("TEXTCOLOR", (0,0), (-1,0), WHITE),
("FONTNAME", (0,0), (-1,0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1,0), 7.5),
("FONTNAME", (0,1), (-1,-1), "Helvetica"),
("FONTNAME", (0,1), (0,-1), "Helvetica-Bold"),
("TEXTCOLOR", (0,1), (0,-1), NAVY),
("FONTSIZE", (0,1), (-1,-1), 6.8),
("BACKGROUND", (0,1), (-1,1), LIGHT_TEAL),
("BACKGROUND", (0,2), (-1,2), WHITE),
("BACKGROUND", (0,3), (-1,3), LIGHT_TEAL),
("BACKGROUND", (0,4), (-1,4), colors.HexColor("#FADBD8")),
("BACKGROUND", (0,5), (-1,5), WHITE),
("BACKGROUND", (0,6), (-1,6), colors.HexColor("#FEF9E7")),
("VALIGN", (0,0), (-1,-1), "MIDDLE"),
("ALIGN", (0,0), (-1,-1), "LEFT"),
("LEFTPADDING", (0,0), (-1,-1), 4),
("GRID", (0,0), (-1,-1), 0.4, MID_GRAY),
]))
st.wrapOn(c, LW, 3*inch)
cy -= 2.73*inch
st.drawOn(c, LX, cy)
# HF-SPECIFIC EKG FINDINGS
cy -= 0.32*inch
section_header(c, LX, cy, LW, "HF-SPECIFIC EKG FINDINGS")
cy -= 0.03*inch
hf_findings = [
("Low voltage throughout all leads", "Cardiac amyloidosis (ATTR-CM)"),
("LBBB + EF ≤ 35%", "CRT candidate — refer"),
("QRS > 150 ms + LBBB", "Strongest CRT benefit"),
("Q waves in transplant patient", "Silent MI → CAV workup (angiogram)"),
("Sinus tach (HR 95–110)", "Normal early post-transplant (denervation)"),
("Abnormal HRV (HR variability)", "Poor prognosis marker in dilated CMP"),
("Nonsustained VT (NSVT) on monitor", "EF ≤ 35% → ICD evaluation"),
]
for i, (finding, meaning) in enumerate(hf_findings):
cy -= 0.19*inch
bg = LIGHT_TEAL if i % 2 == 0 else WHITE
c.setFillColor(bg)
c.rect(LX, cy, LW, 0.18*inch, fill=1, stroke=0)
c.setFillColor(NAVY)
c.setFont("Helvetica-Bold", 7)
c.drawString(LX + 0.07*inch, cy + 0.05*inch, finding)
fw = c.stringWidth(finding, "Helvetica-Bold", 7)
c.setFillColor(colors.HexColor("#555555"))
c.setFont("Helvetica", 7)
c.drawString(LX + 0.1*inch + fw, cy + 0.05*inch, " → " + meaning)
# ── RIGHT COLUMN ─────────────────────────────────────────────────────────
RX = 4.15*inch
RW = 4.00*inch
ry = H - 1.1*inch
# ARRHYTHMIA DRUG GUIDE
section_header(c, RX, ry, RW, "ARRHYTHMIA DRUG GUIDE — HF / TRANSPLANT")
ry -= 0.03*inch
drug_rows = [
["Arrhythmia", "First-Line Rx", "HF / Transplant Notes"],
["A-fib\n(rate control)", "Beta-blocker\nDiltiazem (non-HFrEF)", "Avoid diltiazem if EF↓\nDigoxin adjunct if symptomatic"],
["A-fib\n(rhythm control)", "Amiodarone\nDofetilide", "Amiodarone: ↑ CNI levels in Tx\nDofetilide: QTc monitoring"],
["VT (stable)\nVT storm", "Amiodarone IV\nBeta-blocker IV", "ICD + antiarrhythmic combo\nRule out ischemia / lytes"],
["VF / pulseless VT", "Defibrillation 200J\nAmiodarone 300 mg IV", "Standard ACLS\nNo special Tx rules"],
["SVT\n(transplant heart)", "Adenosine ½ dose\nBeta-blocker / Diltiazem", "Atropine = INEFFECTIVE\nGlycopyrrolate = INEFFECTIVE"],
["Bradycardia\n(transplant heart)", "Isoproterenol / Dopamine\nPacing if refractory", "Atropine = INEFFECTIVE\nDenervated — no vagal response"],
["Torsades de Pointes", "Mg sulfate 2g IV\nStop QT-prolonging drugs", "Correct K⁺ & Mg²⁺\nTemporary pacing if refractory"],
]
dr_col_w = [1.1*inch, 1.3*inch, 1.6*inch]
dr_row_h = [0.19*inch] + [0.42*inch]*7
dr = Table(drug_rows, colWidths=dr_col_w, rowHeights=dr_row_h)
dr.setStyle(TableStyle([
("BACKGROUND", (0,0), (-1,0), NAVY),
("TEXTCOLOR", (0,0), (-1,0), WHITE),
("FONTNAME", (0,0), (-1,0), "Helvetica-Bold"),
("FONTSIZE", (0,0), (-1,0), 7.5),
("FONTNAME", (0,1), (-1,-1), "Helvetica"),
("FONTNAME", (0,1), (0,-1), "Helvetica-Bold"),
("TEXTCOLOR", (0,1), (0,-1), NAVY),
("FONTSIZE", (0,1), (-1,-1), 7),
("BACKGROUND", (0,1), (-1,1), LIGHT_TEAL),
("BACKGROUND", (0,2), (-1,2), WHITE),
("BACKGROUND", (0,3), (-1,3), LIGHT_TEAL),
("BACKGROUND", (0,4), (-1,4), colors.HexColor("#FADBD8")),
("BACKGROUND", (0,5), (-1,5), colors.HexColor("#FEF9E7")),
("BACKGROUND", (0,6), (-1,6), colors.HexColor("#FEF9E7")),
("BACKGROUND", (0,7), (-1,7), WHITE),
("VALIGN", (0,0), (-1,-1), "MIDDLE"),
("ALIGN", (0,0), (-1,-1), "LEFT"),
("LEFTPADDING", (0,0), (-1,-1), 4),
("GRID", (0,0), (-1,-1), 0.4, MID_GRAY),
]))
dr.wrapOn(c, RW, 4*inch)
ry -= 3.38*inch
dr.drawOn(c, RX, ry)
# CAV BOX
ry -= 0.33*inch
c.setFillColor(colors.HexColor("#FADBD8"))
c.roundRect(RX, ry - 1.25*inch, RW, 1.28*inch, 0.06*inch, fill=1, stroke=0)
c.setStrokeColor(RED_ACCENT)
c.setLineWidth(1)
c.roundRect(RX, ry - 1.25*inch, RW, 1.28*inch, 0.06*inch, fill=0, stroke=1)
c.setFillColor(RED_ACCENT)
c.rect(RX, ry - 0.26*inch, RW, 0.28*inch, fill=1, stroke=0)
c.setFillColor(WHITE)
c.setFont("Helvetica-Bold", 8.5)
c.drawCentredString(RX + RW/2, ry - 0.19*inch, "CARDIAC ALLOGRAFT VASCULOPATHY (CAV)")
cav_points = [
("What:", "Diffuse concentric coronary narrowing — the transplant's \"CAD\""),
("Silent:", "No angina (denervated heart) → presents as SCD or silent MI"),
("Diagnose:", "Coronary angiography (gold std); IVUS detects early CAV"),
("EKG clue:", "New Q waves or ST elevation in transplant patient"),
("Prevent:", "Statin therapy for ALL transplant patients; BP / lipid control"),
("Treat:", "Sirolimus/everolimus may slow; severe → retransplantation"),
]
cav_y = ry - 0.28*inch
for label, detail in cav_points:
cav_y -= 0.165*inch
c.setFillColor(RED_ACCENT)
c.setFont("Helvetica-Bold", 7)
c.drawString(RX + 0.1*inch, cav_y, label)
lw = c.stringWidth(label, "Helvetica-Bold", 7)
c.setFillColor(DARK_GRAY)
c.setFont("Helvetica", 7)
c.drawString(RX + 0.13*inch + lw, cav_y, " " + detail)
# NYHA / ICD INDICATIONS MINI BOX — bottom left
bly = 0.52*inch
c.setFillColor(LIGHT_TEAL)
c.roundRect(LX, bly, LW, 0.72*inch, 0.05*inch, fill=1, stroke=0)
c.setStrokeColor(TEAL)
c.setLineWidth(0.8)
c.roundRect(LX, bly, LW, 0.72*inch, 0.05*inch, fill=0, stroke=1)
c.setFillColor(TEAL)
c.setFont("Helvetica-Bold", 8)
c.drawString(LX + 0.1*inch, bly + 0.54*inch, "ICD PRIMARY PREVENTION CRITERIA (ALL 3 must be met):")
icd_items = [
"① EF ≤ 35% (despite ≥ 3 months optimal GDMT)",
"② NYHA functional class II or III",
"③ Life expectancy > 1 year with good functional status",
]
c.setFont("Helvetica", 7.3)
c.setFillColor(DARK_GRAY)
for j, item in enumerate(icd_items):
c.drawString(LX + 0.15*inch, bly + 0.36*inch - j*0.15*inch, item)
# Bottom right mini-box: electrolyte EKG
brx = RX
c.setFillColor(colors.HexColor("#EBF5FB"))
c.roundRect(brx, bly, RW, 0.72*inch, 0.05*inch, fill=1, stroke=0)
c.setStrokeColor(TEAL)
c.setLineWidth(0.8)
c.roundRect(brx, bly, RW, 0.72*inch, 0.05*inch, fill=0, stroke=1)
c.setFillColor(TEAL)
c.setFont("Helvetica-Bold", 8)
c.drawString(brx + 0.1*inch, bly + 0.54*inch, "ELECTROLYTE EKG CHANGES (common in HF/diuretic use):")
elec = [
"Hyperkalemia: Peaked T waves → wide QRS → sine wave → VF",
"Hypokalemia: Flat T waves, U waves (after T wave), QTc prolongation",
"Hypomagnesemia: Torsades de Pointes, ↑ risk with ↓K⁺",
]
c.setFont("Helvetica", 7.1)
c.setFillColor(DARK_GRAY)
for j, item in enumerate(elec):
c.drawString(brx + 0.15*inch, bly + 0.36*inch - j*0.155*inch, item)
# Footer
c.setFillColor(NAVY)
c.rect(0, 0, W, 0.35*inch, fill=1, stroke=0)
c.setFillColor(WHITE)
c.setFont("Helvetica", 6.5)
c.drawCentredString(W/2, 0.13*inch,
"Sources: Braunwald's Heart Disease 11e · Goldman-Cecil Medicine · Rosen's Emergency Medicine | BACK — See front for Systematic Approach & Interval Guide")
# ─────────────────────────────────────────────────────────────────────────────
# BUILD
# ─────────────────────────────────────────────────────────────────────────────
OUTPUT = "/home/daytona/workspace/ekgcard/EKG_Quick_Reference_Card.pdf"
c = canvas.Canvas(OUTPUT, pagesize=letter)
c.setTitle("EKG Quick Reference Card — Advanced HF & Transplant APN")
c.setAuthor("Orris Medical AI")
c.setSubject("EKG Quick Reference for Advanced Heart Failure and Transplant APN")
draw_front(c)
c.showPage()
draw_back(c)
c.save()
print(f"PDF created: {OUTPUT}")