Pathophysiology of ckd , bilateral small kidney with grade 2 rpc
"chronic kidney disease" AND "pathophysiology" AND "small kidney"
"chronic kidney disease" AND pathophysiology
bilateral small kidneys grade 2 RPC renal parenchymal changes CKD ultrasound pathophysiology
https://radiologykey.com/diffuse-renal-parenchymal-diseases
| Grade | Echogenicity | Corticomedullary Differentiation | Size |
|---|---|---|---|
| Grade 0 (Normal) | Equal to or less than liver/spleen | Preserved | Normal (9-14 cm) |
| Grade 1 | Mildly increased | Slightly reduced | Normal or mildly reduced |
| Grade 2 | Moderately increased (equal to liver) | Reduced/indistinct | Reduced |
| Grade 3 | Markedly increased (greater than liver) | Lost | Small/shrunken |
Initial nephron loss
↓
Compensatory hyperfiltration + glomerular hypertension
↓
Podocyte injury → Proteinuria
↓
Tubular protein overload → Inflammation + TIF
↓
Peritubular capillary loss → Tubular ischemia
↓
Glomerulosclerosis → Further nephron loss
↓
(cycle repeats, accelerating)
| Factor | Mechanism |
|---|---|
| Oxidative stress | Excess ROS from hypoxic tubules activates NF-kB, drives TGF-beta, damages DNA |
| Metabolic acidosis | Increases ammonia production (which activates complement), upregulates ET-1, accelerates fibrosis |
| Hypertension (systemic) | Incompletely buffered by autoregulation in damaged kidneys; transmitted to glomeruli |
| Anemia | Tubulointerstitial hypoxia from loss of EPO-producing cortical cells; further capillary dropout |
| Hyperphosphatemia | Vascular calcification, FGF-23 elevation (cardiotoxic), secondary hyperparathyroidism |
| Hyperuricemia | Activates NLRP3 inflammasome, induces arteriolopathy in afferent arterioles |
| Lipid accumulation | Lipotoxicity in proximal tubule cells; foam cell formation in interstitium |
| Superimposed AKI episodes | Each episode accelerates nephron loss beyond what recovers |
| Ultrasound Feature | Pathological Correlate |
|---|---|
| Increased echogenicity (Grade 2 = liver echogenicity) | Fibrosis replacing normal parenchyma; loss of normal medullary pyramids |
| Reduced corticomedullary differentiation | Cortical fibrosis making cortex as echogenic as medulla |
| Small kidney size | Nephron dropout, glomerulosclerosis, tubular atrophy |
| Smooth contour | Diffuse atrophy (not focal scarring) - suggests DM/HT/GN |
| Renal sinus fat prominence | Compensatory lipomatosis from parenchymal volume loss |
Make a presentation on CKD pathophysiology and renoprotective strategies
mkdir -p /tmp/workspace/ckd-presentation
~/ckd-presentation/create_ckd_pptx.py
from pptx import Presentation
from pptx.util import Inches, Pt, Emu
from pptx.dml.color import RGBColor
from pptx.enum.text import PP_ALIGN, MSO_ANCHOR
from pptx.oxml.ns import qn
from lxml import etree
from io import BytesIO
# ── Palette ───────────────────────────────────────────────
NAVY = RGBColor(0x0D, 0x2B, 0x55) # dark navy
TEAL = RGBColor(0x00, 0x84, 0x8A) # accent teal
ORANGE = RGBColor(0xE8, 0x6A, 0x1B) # warm accent
LIGHT_BG = RGBColor(0xF2, 0xF6, 0xFA) # very light blue-grey
WHITE = RGBColor(0xFF, 0xFF, 0xFF)
MID_GREY = RGBColor(0x55, 0x65, 0x78)
LIGHT_TEAL= RGBColor(0xE0, 0xF4, 0xF5)
LIGHT_ORG = RGBColor(0xFD, 0xF0, 0xE6)
DARK_TEXT = RGBColor(0x1A, 0x1A, 0x2E)
RED_WARN = RGBColor(0xC0, 0x39, 0x2B)
def new_prs():
prs = Presentation()
prs.slide_width = Inches(13.333)
prs.slide_height = Inches(7.5)
return prs
def blank_slide(prs):
return prs.slides.add_slide(prs.slide_layouts[6])
def fill_shape(shape, rgb):
sp = shape._element
spPr = sp.find(qn('p:spPr'))
if spPr is None:
spPr = etree.SubElement(sp, qn('p:spPr'))
solidFill = etree.SubElement(spPr, qn('a:solidFill'))
srgbClr = etree.SubElement(solidFill, qn('a:srgbClr'))
srgbClr.set('val', f'{rgb[0]:02X}{rgb[1]:02X}{rgb[2]:02X}')
def add_rect(slide, x, y, w, h, rgb):
shape = slide.shapes.add_shape(1, Inches(x), Inches(y), Inches(w), Inches(h))
shape.line.fill.background()
fill_shape(shape, rgb)
return shape
def add_textbox(slide, x, y, w, h, text, size, bold=False, color=DARK_TEXT,
align=PP_ALIGN.LEFT, wrap=True, italic=False, font="Calibri"):
tb = slide.shapes.add_textbox(Inches(x), Inches(y), Inches(w), Inches(h))
tf = tb.text_frame
tf.word_wrap = wrap
tf.margin_left = 0; tf.margin_right = 0
tf.margin_top = 0; tf.margin_bottom = 0
p = tf.paragraphs[0]
p.alignment = align
run = p.add_run()
run.text = text
run.font.name = font
run.font.size = Pt(size)
run.font.bold = bold
run.font.italic = italic
run.font.color.rgb = color
return tf
def add_para(tf, text, size, bold=False, color=DARK_TEXT,
align=PP_ALIGN.LEFT, italic=False, space_before=0, font="Calibri"):
p = tf.add_paragraph()
p.alignment = align
if space_before:
p.space_before = Pt(space_before)
run = p.add_run()
run.text = text
run.font.name = font
run.font.size = Pt(size)
run.font.bold = bold
run.font.italic = italic
run.font.color.rgb = color
return p
def add_bullet(tf, text, size=14, color=DARK_TEXT, indent=0, bold=False):
p = tf.add_paragraph()
p.level = indent
run = p.add_run()
bullet = "• " if indent == 0 else " – "
run.text = bullet + text
run.font.name = "Calibri"
run.font.size = Pt(size)
run.font.bold = bold
run.font.color.rgb = color
def slide_header(slide, title, subtitle=None):
"""Navy top bar with white title"""
add_rect(slide, 0, 0, 13.333, 1.1, NAVY)
add_textbox(slide, 0.4, 0.12, 12, 0.6, title,
size=26, bold=True, color=WHITE, align=PP_ALIGN.LEFT)
if subtitle:
add_textbox(slide, 0.4, 0.68, 12, 0.38, subtitle,
size=13, bold=False, color=RGBColor(0xB0,0xD0,0xE8),
align=PP_ALIGN.LEFT)
def teal_box(slide, x, y, w, h, title, bullets, title_size=14, bullet_size=12.5):
add_rect(slide, x, y, w, 0.42, TEAL)
add_textbox(slide, x+0.1, y+0.05, w-0.2, 0.35, title,
size=title_size, bold=True, color=WHITE)
tb = slide.shapes.add_textbox(Inches(x), Inches(y+0.42),
Inches(w), Inches(h-0.42))
tf = tb.text_frame
tf.word_wrap = True
tf.margin_left = Inches(0.1); tf.margin_right = Inches(0.05)
tf.margin_top = Inches(0.05)
for i, b in enumerate(bullets):
if i == 0:
p = tf.paragraphs[0]
else:
p = tf.add_paragraph()
run = p.add_run()
run.text = "• " + b
run.font.name = "Calibri"
run.font.size = Pt(bullet_size)
run.font.color.rgb = DARK_TEXT
def orange_box(slide, x, y, w, h, title, bullets, title_size=14, bullet_size=12.5):
add_rect(slide, x, y, w, 0.42, ORANGE)
add_textbox(slide, x+0.1, y+0.05, w-0.2, 0.35, title,
size=title_size, bold=True, color=WHITE)
tb = slide.shapes.add_textbox(Inches(x), Inches(y+0.42),
Inches(w), Inches(h-0.42))
tf = tb.text_frame
tf.word_wrap = True
tf.margin_left = Inches(0.1); tf.margin_right = Inches(0.05)
tf.margin_top = Inches(0.05)
for i, b in enumerate(bullets):
if i == 0:
p = tf.paragraphs[0]
else:
p = tf.add_paragraph()
run = p.add_run()
run.text = "• " + b
run.font.name = "Calibri"
run.font.size = Pt(bullet_size)
run.font.color.rgb = DARK_TEXT
# ═══════════════════════════════════════════════════════════
# Build presentation
# ═══════════════════════════════════════════════════════════
prs = new_prs()
# ── SLIDE 1: Title ─────────────────────────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, NAVY)
# Diagonal accent stripe
accent = slide.shapes.add_shape(1, Inches(8.5), Inches(0), Inches(5), Inches(7.5))
fill_shape(accent, TEAL)
accent.line.fill.background()
# Overlap with lighter shade
accent2 = slide.shapes.add_shape(1, Inches(9.5), Inches(0), Inches(3.833), Inches(7.5))
fill_shape(accent2, RGBColor(0x00,0x6A,0x70))
accent2.line.fill.background()
add_textbox(slide, 0.6, 1.4, 8.5, 0.8, "CHRONIC KIDNEY DISEASE",
size=36, bold=True, color=TEAL, font="Calibri")
add_textbox(slide, 0.6, 2.1, 8.5, 1.1,
"Pathophysiology & Renoprotective Strategies",
size=28, bold=True, color=WHITE, font="Calibri")
add_textbox(slide, 0.6, 3.2, 8.0, 0.4,
"From Nephron Loss to End-Stage Kidney Disease",
size=15, bold=False, color=RGBColor(0xB0,0xD0,0xE8), italic=True)
add_textbox(slide, 0.6, 5.8, 8.0, 0.35,
"Based on Brenner & Rector's The Kidney | Harrison's Principles of Internal Medicine",
size=11, color=RGBColor(0x80,0xA0,0xC0))
add_textbox(slide, 0.6, 6.2, 8.0, 0.35,
"Goldman-Cecil Medicine | Grainger & Allison's Diagnostic Radiology",
size=11, color=RGBColor(0x80,0xA0,0xC0))
# ── SLIDE 2: Overview / Agenda ─────────────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Presentation Overview",
"A structured journey through CKD mechanisms and management")
items = [
("1", "Definition & Epidemiology", "What is CKD? Global burden, staging (KDIGO G & A categories)"),
("2", "Intact Nephron Hypothesis", "Bricker's hypothesis: hyperfunctioning nephron pool"),
("3", "Glomerular Hemodynamics", "Brenner hypothesis: hyperfiltration & glomerular capillary HTN"),
("4", "Proteinuria & Tubular Injury", "Filtered proteins as mediators of tubulointerstitial damage"),
("5", "Fibrosis & Sclerosis", "TGF-β1, EMT, glomerulosclerosis – the final common endpoint"),
("6", "Amplifying Factors", "Oxidative stress, acidosis, anemia, hyperuricemia, lipotoxicity"),
("7", "Bilateral Small Kidneys", "Radiological-pathological correlates; RPC grading"),
("8", "Renoprotective Strategies", "RAAS, SGLT2i, Finerenone, Sparsentan, lifestyle"),
("9", "Summary", "Key take-home points and clinical pearls"),
]
cols = [(0.3, 6.3), (6.8, 6.3)]
for i, (num, title, desc) in enumerate(items):
col = 0 if i < 5 else 1
cx, cw = cols[col]
row = i if col == 0 else i - 5
y = 1.25 + row * 1.18
add_rect(slide, cx, y, 0.5, 0.55, TEAL)
add_textbox(slide, cx+0.05, y+0.06, 0.4, 0.45, num,
size=18, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
add_textbox(slide, cx+0.6, y, cw-0.65, 0.32, title,
size=13, bold=True, color=NAVY)
add_textbox(slide, cx+0.6, y+0.3, cw-0.65, 0.3, desc,
size=10.5, color=MID_GREY)
# ── SLIDE 3: Definition & Epidemiology ────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "CKD: Definition & Epidemiology",
"KDIGO 2012 criteria remain the global standard")
add_rect(slide, 0.3, 1.25, 6.0, 2.35, WHITE)
tf = add_textbox(slide, 0.5, 1.35, 5.6, 0.38, "KDIGO Definition of CKD",
size=14, bold=True, color=NAVY)
tb = slide.shapes.add_textbox(Inches(0.5), Inches(1.75), Inches(5.6), Inches(1.7))
tf2 = tb.text_frame; tf2.word_wrap = True
for b in [
"Abnormalities of kidney structure OR function",
"Present for > 3 months",
"With implications for health",
"Markers: GFR <60 mL/min/1.73m² OR albuminuria (ACR ≥30 mg/g)",
"Structural markers: small kidneys, cysts, histological abnormalities",
]:
p = tf2.add_paragraph() if b != "Abnormalities of kidney structure OR function" else tf2.paragraphs[0]
run = p.add_run()
run.text = "✓ " + b
run.font.name = "Calibri"; run.font.size = Pt(12); run.font.color.rgb = DARK_TEXT
add_rect(slide, 0.3, 3.75, 6.0, 1.05, TEAL)
add_textbox(slide, 0.5, 3.82, 5.6, 0.38, "KDIGO GFR Categories (G1–G5)",
size=13, bold=True, color=WHITE)
cats = [("G1", ">90"), ("G2", "60–89"), ("G3a", "45–59"), ("G3b", "30–44"), ("G4", "15–29"), ("G5", "<15")]
for j, (g, val) in enumerate(cats):
x = 0.35 + j*1.0
add_rect(slide, x, 4.2, 0.92, 0.5, NAVY if j == 5 else (TEAL if j >= 3 else RGBColor(0x1A,0x7A,0x80)))
add_textbox(slide, x+0.03, 4.22, 0.88, 0.25, g, size=11, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
add_textbox(slide, x+0.03, 4.46, 0.88, 0.22, val, size=9.5, color=WHITE, align=PP_ALIGN.CENTER)
add_rect(slide, 6.55, 1.25, 6.5, 5.1, WHITE)
add_textbox(slide, 6.7, 1.35, 6.1, 0.38, "Global Burden",
size=14, bold=True, color=NAVY)
epi_data = [
("~850 million", "people affected worldwide", TEAL),
("~10%", "of the global adult population", ORANGE),
("2–3 million", "deaths/year from kidney failure", RED_WARN),
("Top 5", "cause of years of life lost globally", NAVY),
("DM & HTN", "account for 50–60% of all CKD cases", TEAL),
("ESKD", "~180,000 new cases/year in the USA", ORANGE),
]
for k, (stat, label, color) in enumerate(epi_data):
y_pos = 1.85 + k*0.72
add_rect(slide, 6.7, y_pos, 2.0, 0.5, color)
add_textbox(slide, 6.75, y_pos+0.04, 1.9, 0.28, stat,
size=15, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
add_textbox(slide, 6.75, y_pos+0.3, 1.9, 0.18, label,
size=9, color=WHITE, align=PP_ALIGN.CENTER)
add_textbox(slide, 8.85, y_pos+0.05, 4.0, 0.4, label,
size=12, color=DARK_TEXT)
# ── SLIDE 4: Intact Nephron Hypothesis ────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "The Intact Nephron Hypothesis (Bricker)",
"Remaining nephrons hypertrophy and hyperfunction to compensate for lost nephrons")
add_rect(slide, 0.3, 1.25, 6.1, 5.75, WHITE)
add_textbox(slide, 0.5, 1.35, 5.7, 0.38, "Core Concept",
size=14, bold=True, color=NAVY)
tb = slide.shapes.add_textbox(Inches(0.5), Inches(1.8), Inches(5.7), Inches(4.8))
tf = tb.text_frame; tf.word_wrap = True
for b in [
"Kidney function is maintained by a diminishing pool of hyperfunctioning nephrons",
"Rather than a constant number of nephrons with diminishing function",
"Glomerulotubular balance preserved until terminal CKD",
"GFR falls only when nephron loss is substantial (>75%)",
"",
"Once GFR falls below a critical threshold → relentless progression",
"Rate of GFR decline is LINEAR and characteristic of the individual patient",
"Not the disease → implies a final COMMON PATHWAY",
"",
"Adaptive hypertrophy is driven by:",
" – Increased tubular workload per remaining nephron",
" – Hormonal signals: angiotensin II, IGF-1, EGF",
" – Hemodynamic: increased single-nephron GFR (SNGFR)",
"",
"Initially protective → ultimately MALADAPTIVE",
]:
if b == "Core Concept" or b == "":
p = tf.add_paragraph()
p.add_run().text = b
continue
p = tf.add_paragraph()
run = p.add_run()
run.text = b
run.font.name = "Calibri"; run.font.size = Pt(12.5)
run.font.color.rgb = DARK_TEXT
if b.startswith(" –"):
run.font.color.rgb = MID_GREY
add_rect(slide, 6.7, 1.25, 6.3, 5.75, LIGHT_TEAL)
add_textbox(slide, 6.9, 1.35, 5.9, 0.38, "Experimental Evidence",
size=14, bold=True, color=NAVY)
# Diagram: boxes and arrows
boxes = [
(7.1, 2.05, 5.7, 0.55, "Normal: 2 kidneys, ~2 million nephrons", NAVY, WHITE),
(7.1, 2.85, 5.7, 0.55, "Nephron loss (disease / nephrectomy)", RED_WARN, WHITE),
(7.1, 3.65, 5.7, 0.55, "Remaining nephrons: hypertrophy & ↑SNGFR", TEAL, WHITE),
(7.1, 4.45, 5.7, 0.55, "GFR maintained (initially)", RGBColor(0x27,0xAE,0x60), WHITE),
(7.1, 5.25, 5.7, 0.55, "Maladaptation → glomerulosclerosis, fibrosis", ORANGE, WHITE),
(7.1, 6.05, 5.7, 0.55, "Progressive nephron loss → ESKD", RED_WARN, WHITE),
]
for bx, by, bw, bh, btext, bcol, tcol in boxes:
add_rect(slide, bx, by, bw, bh, bcol)
add_textbox(slide, bx+0.1, by+0.1, bw-0.2, bh-0.1, btext,
size=12.5, bold=True, color=tcol, align=PP_ALIGN.CENTER)
if by < 6.05:
add_textbox(slide, 9.3, by+0.55, 0.5, 0.3, "▼",
size=14, bold=True, color=NAVY, align=PP_ALIGN.CENTER)
# ── SLIDE 5: Glomerular Hemodynamics ──────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Glomerular Hemodynamic Adaptations – The Brenner Hypothesis",
"Glomerular capillary hypertension is the primary driver of progressive nephron injury")
# Left column
add_rect(slide, 0.3, 1.25, 6.0, 5.75, WHITE)
add_textbox(slide, 0.5, 1.35, 5.7, 0.38, "Mechanism of Glomerular Hypertension",
size=13.5, bold=True, color=NAVY)
tb = slide.shapes.add_textbox(Inches(0.5), Inches(1.8), Inches(5.7), Inches(4.5))
tf = tb.text_frame; tf.word_wrap = True
bullets_hem = [
"Nephron loss → compensatory afferent arteriolar DILATION",
"Increased glomerular plasma flow rate (Qα ↑)",
"Efferent arteriolar constriction (angiotensin II mediated)",
"Net effect: ↑ intraglomerular hydraulic pressure (Pgc)",
"↑ Pgc → glomerular capillary HYPERTENSION",
"",
"In 5/6 nephrectomy rat model:",
" – 300% ↑ in SNGFR at 16 days post-op",
" – Direct measurement: Pgc elevated by 15–20 mmHg",
"",
"It is CAPILLARY HYPERTENSION (not hyperfiltration per se)",
"that drives injury – key distinction for therapy",
"",
"Evidence (strong):",
" – RAAS inhibitors ↓ Pgc → renoprotection",
" – SGLT2 inhibitors ↓ Pgc via TGF → renoprotection",
" – Both act by different mechanisms yet same endpoint",
]
for i, b in enumerate(bullets_hem):
p = tf.paragraphs[0] if i == 0 else tf.add_paragraph()
run = p.add_run()
run.text = b
run.font.name = "Calibri"
run.font.size = Pt(12.5)
run.font.color.rgb = MID_GREY if b.startswith(" –") or b == "" else (NAVY if "Evidence" in b or "RAAS" in b or "SGLT2" in b else DARK_TEXT)
run.font.bold = ("CAPILLARY HYPERTENSION" in b or b.startswith("Evidence"))
# Right: diagram
add_rect(slide, 6.6, 1.25, 6.4, 5.75, LIGHT_TEAL)
add_textbox(slide, 6.8, 1.35, 6.0, 0.38, "Glomerular Hemodynamic Changes",
size=13.5, bold=True, color=NAVY)
params = [
("Renal Blood Flow (RBF)", "↑ Initially", TEAL),
("Glomerular Plasma Flow (Qα)", "↑↑", TEAL),
("Afferent Arteriole Tone", "↓ (dilated)", TEAL),
("Efferent Arteriole Tone", "↑ (AngII)", ORANGE),
("Intraglomerular Pressure (Pgc)", "↑↑ KEY DRIVER", RED_WARN),
("Single-Nephron GFR (SNGFR)", "↑↑↑", TEAL),
("Total GFR (initially)", "Maintained", RGBColor(0x27,0xAE,0x60)),
("Ultrafiltration Coefficient (Kf)", "↓ Late", ORANGE),
]
for j, (param, val, col) in enumerate(params):
y_pos = 1.85 + j*0.58
add_rect(slide, 6.8, y_pos, 3.8, 0.45, WHITE)
add_textbox(slide, 6.9, y_pos+0.06, 3.6, 0.35, param, size=11.5, color=DARK_TEXT)
add_rect(slide, 10.7, y_pos, 2.1, 0.45, col)
add_textbox(slide, 10.75, y_pos+0.06, 2.0, 0.35, val,
size=11.5, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
add_textbox(slide, 6.8, 6.5, 6.0, 0.45,
"★ ACE inhibitor/ARB: ↑ efferent dilation → ↓ Pgc | SGLT2i: ↑ TGF → ↑ afferent tone → ↓ Pgc",
size=11, bold=True, color=NAVY)
# ── SLIDE 6: Proteinuria & Tubular Injury ─────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Proteinuria as a Mediator of Tubular Injury",
"Filtered proteins are not innocent bystanders – they are active mediators of CKD progression")
teal_box(slide, 0.3, 1.25, 4.1, 3.0, "How Proteinuria Causes Tubular Damage", [
"Disrupted filtration barrier → protein enters tubular lumen",
"Proximal tubule cells reabsorb excess protein via endocytosis",
"Protein overload triggers oxidative stress (ROS generation)",
"Activates NF-κB → pro-inflammatory cytokine cascade",
"Upregulates MCP-1, RANTES, osteopontin, ET-1",
"Recruits macrophages/monocytes to interstitium",
"Tubular cell apoptosis & interstitial inflammation",
])
orange_box(slide, 0.3, 4.4, 4.1, 2.6, "Key Inflammatory Mediators", [
"TGF-β1: activates myofibroblasts, drives collagen deposition",
"MCP-1 (CCL2): macrophage chemoattractant",
"PDGF: fibroblast proliferation",
"Angiotensin II: local amplifier of TGF-β1 production",
"ET-1: vasoconstriction + pro-fibrotic",
"Complement (C3a, C5a): interstitial macrophage activation",
])
teal_box(slide, 4.7, 1.25, 4.0, 3.0, "Progression of Tubular Injury", [
"Stage 1: Protein overload → tubular cell stress",
"Stage 2: NF-κB activation, cytokine release",
"Stage 3: Macrophage infiltration, fibroblast activation",
"Stage 4: EMT – tubular cells become myofibroblasts",
"Stage 5: Extracellular matrix deposition (collagen I, III, IV)",
"Stage 6: Tubular atrophy, loss of function",
"Stage 7: Peritubular capillary rarefaction → ischaemia",
])
orange_box(slide, 4.7, 4.4, 4.0, 2.6, "Clinical Implications", [
"Proteinuria grade correlates with rate of GFR decline",
"Reducing proteinuria is a validated surrogate endpoint",
"Target: ACR <30 mg/g (ideally <10 mg/g)",
"Each 50% proteinuria reduction = ~30% less risk of ESKD",
"Combined RAAS blockade → additive proteinuria reduction",
])
add_rect(slide, 9.0, 1.25, 4.0, 5.75, LIGHT_TEAL)
add_textbox(slide, 9.15, 1.35, 3.7, 0.38, "Downstream Consequences",
size=13.5, bold=True, color=NAVY)
conseqs = [
("Tubulointerstitial Fibrosis", "TGF-β1 → myofibroblast activation → collagen deposition", TEAL),
("Tubular Atrophy", "Cell death → tubular dropout → loss of concentrating ability", ORANGE),
("Capillary Rarefaction", "Loss of peritubular capillaries → chronic hypoxia", RED_WARN),
("Interstitial Inflammation", "Macrophage infiltration → perpetuation of injury cycle", NAVY),
("Glomerulosclerosis", "Retrograde pressure from scarred tubules → glomerular collapse", ORANGE),
]
for k, (title_c, desc_c, col) in enumerate(conseqs):
y_pos = 1.85 + k * 0.96
add_rect(slide, 9.15, y_pos, 0.4, 0.72, col)
add_textbox(slide, 9.65, y_pos, 3.2, 0.32, title_c, size=12, bold=True, color=DARK_TEXT)
add_textbox(slide, 9.65, y_pos+0.32, 3.2, 0.38, desc_c, size=10.5, color=MID_GREY)
# ── SLIDE 7: Fibrosis & Glomerulosclerosis ────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Tubulointerstitial Fibrosis & Glomerulosclerosis",
"The final common histopathological endpoint of all causes of CKD")
# TIF section
add_rect(slide, 0.3, 1.25, 6.1, 2.7, WHITE)
add_textbox(slide, 0.5, 1.35, 5.7, 0.38, "Tubulointerstitial Fibrosis (TIF)",
size=14, bold=True, color=NAVY)
tb = slide.shapes.add_textbox(Inches(0.5), Inches(1.8), Inches(5.7), Inches(2.0))
tf = tb.text_frame; tf.word_wrap = True
tif_bullets = [
"Best histological predictor of GFR decline (stronger than glomerular changes)",
"Key driver: TGF-β1 from injured tubular cells and macrophages",
"EMT: tubular epithelial cells transdifferentiate into myofibroblasts",
"Myofibroblasts secrete collagen I, III, IV → permanent matrix deposition",
"HIF-1α (hypoxia-inducible factor) amplifies TGF-β1 in hypoxic tubules",
"Net: interstitial volume expands, tubules compress, nephrons drop out",
]
for i, b in enumerate(tif_bullets):
p = tf.paragraphs[0] if i == 0 else tf.add_paragraph()
run = p.add_run()
run.text = "• " + b
run.font.name = "Calibri"; run.font.size = Pt(12)
run.font.color.rgb = DARK_TEXT
# GS section
add_rect(slide, 0.3, 4.1, 6.1, 2.7, WHITE)
add_textbox(slide, 0.5, 4.2, 5.7, 0.38, "Glomerulosclerosis",
size=14, bold=True, color=NAVY)
tb2 = slide.shapes.add_textbox(Inches(0.5), Inches(4.65), Inches(5.7), Inches(2.0))
tf2 = tb2.text_frame; tf2.word_wrap = True
gs_bullets = [
"Podocyte loss: podocytes cannot regenerate; loss = permanent",
"Denuded GBM → mesangial expansion into capillary loops",
"FSGS morphology: final common pattern regardless of initial disease",
"Segmental sclerosis → segmental → global glomerulosclerosis",
"Tubular injury (above) feeds back: obstructed tubules → glomerular atrophy",
"Each sclerosed glomerulus = permanent, irreversible nephron loss",
]
for i, b in enumerate(gs_bullets):
p = tf2.paragraphs[0] if i == 0 else tf2.add_paragraph()
run = p.add_run()
run.text = "• " + b
run.font.name = "Calibri"; run.font.size = Pt(12)
run.font.color.rgb = DARK_TEXT
# Right: Vicious cycle
add_rect(slide, 6.7, 1.25, 6.3, 5.75, LIGHT_TEAL)
add_textbox(slide, 6.9, 1.35, 5.9, 0.38, "The Vicious Cycle of CKD Progression",
size=13.5, bold=True, color=NAVY)
cycle_steps = [
("Initial Nephron Loss", NAVY),
("Compensatory Hyperfiltration\n+ Glomerular Hypertension", TEAL),
("Podocyte Injury\n→ Proteinuria", ORANGE),
("Tubular Protein Overload\n→ Inflammation + TIF", RED_WARN),
("Capillary Rarefaction\n→ Tubular Ischaemia", ORANGE),
("Glomerulosclerosis\n→ Further Nephron Loss", RED_WARN),
]
for k, (label, col) in enumerate(cycle_steps):
y_pos = 1.85 + k * 0.78
add_rect(slide, 7.0, y_pos, 5.7, 0.6, col)
add_textbox(slide, 7.05, y_pos+0.05, 5.6, 0.52, label,
size=12, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
if k < 5:
add_textbox(slide, 9.5, y_pos+0.6, 0.7, 0.2, "▼",
size=13, bold=True, color=NAVY, align=PP_ALIGN.CENTER)
add_rect(slide, 7.0, 6.5, 5.7, 0.4, NAVY)
add_textbox(slide, 7.05, 6.52, 5.6, 0.35,
"↩ Cycle repeats — accelerating with each iteration",
size=12, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
# ── SLIDE 8: Amplifying Factors ───────────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Non-Hemodynamic Amplifying Factors",
"Multiple concurrent mechanisms accelerate nephron loss beyond hemodynamics alone")
factors = [
("Oxidative Stress", [
"NADPH oxidase → ↑ ROS in ischaemic tubules",
"ROS activates NF-κB → TGF-β1, MCP-1 upregulation",
"Mitochondrial dysfunction in podocytes and tubular cells",
"Therapeutic target: finerenone (MRA) reduces OS",
], TEAL),
("Metabolic Acidosis", [
"↑ Ammonia production per nephron → complement activation",
"ET-1 upregulation → vasoconstriction + fibrosis",
"Accelerates tubular injury independent of GFR",
"NaHCO₃ supplementation slows CKD progression",
], ORANGE),
("RAAS Overactivation", [
"AngII: pro-fibrotic (TGF-β1 induction) beyond BP effects",
"Aldosterone: tubular inflammation, podocyte toxicity",
"Intrarenal RAAS amplified in CKD independently of systemic BP",
"Finerenone: non-steroidal MRA; renal + CV benefits",
], NAVY),
("Hyperphosphatemia & FGF-23", [
"Phosphate retention → secondary HPT → vascular calcification",
"FGF-23 rises early in CKD → direct cardiotoxic effect on LV",
"FGF-23 also suppresses 1α-hydroxylase → ↓ calcitriol",
"Target: dietary phosphate restriction, binders",
], TEAL),
("Anemia of CKD", [
"Loss of cortical EPO-producing cells → absolute EPO deficiency",
"Chronic inflammation → functional iron deficiency (hepcidin ↑)",
"Anaemia → ↓ O₂ delivery → tubular ischaemia → fibrosis",
"ESA + IV iron correct anaemia; SGLT2i modestly raise Hb",
], ORANGE),
("Superimposed AKI Episodes", [
"Each AKI episode accelerates irreversible nephron loss",
"Incomplete tubular repair → maladaptive fibrosis",
"AKI-to-CKD transition via HIF, TGF-β1, pericyte activation",
"Prevent: avoid nephrotoxins, adequate hydration, prompt Rx",
], RED_WARN),
]
positions = [
(0.3, 1.25), (4.55, 1.25), (8.8, 1.25),
(0.3, 4.05), (4.55, 4.05), (8.8, 4.05),
]
for (x, y), (title_f, blist, col) in zip(positions, factors):
teal_box(slide, x, y, 4.0, 2.65, title_f, blist, title_size=13, bullet_size=11.5) if col == TEAL else \
orange_box(slide, x, y, 4.0, 2.65, title_f, blist, title_size=13, bullet_size=11.5) if col == ORANGE else \
(lambda: (add_rect(slide, x, y, 4.0, 0.42, col),
add_textbox(slide, x+0.1, y+0.05, 3.8, 0.35, title_f, size=13, bold=True, color=WHITE),
[exec("""
tb = slide.shapes.add_textbox(Inches(x), Inches(y+0.42), Inches(4.0), Inches(2.23))
tf = tb.text_frame; tf.word_wrap = True
tf.margin_left = Inches(0.1); tf.margin_top = Inches(0.05)
""") for _ in [1]],
[(tf.paragraphs[0] if i == 0 else tf.add_paragraph()).add_run().__setattr__('text', '• ' + b) or
setattr((tf.paragraphs[0] if i == 0 else tf.paragraphs[-1]).runs[-1].font, 'size', Pt(11.5))
for i, b in enumerate(blist)]))()
# Simpler approach for navy boxes
for (x, y), (title_f, blist, col) in zip(positions, factors):
if col == NAVY:
add_rect(slide, x, y, 4.0, 0.42, NAVY)
add_textbox(slide, x+0.1, y+0.05, 3.8, 0.35, title_f, size=13, bold=True, color=WHITE)
tb = slide.shapes.add_textbox(Inches(x), Inches(y+0.42), Inches(4.0), Inches(2.23))
tf = tb.text_frame; tf.word_wrap = True
tf.margin_left = Inches(0.1); tf.margin_top = Inches(0.05)
for i, b in enumerate(blist):
p = tf.paragraphs[0] if i == 0 else tf.add_paragraph()
run = p.add_run(); run.text = "• " + b
run.font.name = "Calibri"; run.font.size = Pt(11.5); run.font.color.rgb = DARK_TEXT
# ── SLIDE 9: Bilateral Small Kidneys & RPC ────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Bilateral Small Kidneys & Renal Parenchymal Changes (RPC)",
"Radiological-pathological correlation in CKD")
add_rect(slide, 0.3, 1.25, 5.8, 5.75, WHITE)
add_textbox(slide, 0.5, 1.35, 5.4, 0.38, "RPC Grading on Ultrasound",
size=14, bold=True, color=NAVY)
grades = [
("Grade 0\n(Normal)", "Echogenicity ≤ liver/spleen\nCorticomedullary differentiation preserved\nSize: 10–14 cm (M), 9–13 cm (F)", RGBColor(0x27,0xAE,0x60)),
("Grade 1\n(Mild)", "Mildly ↑ echogenicity\nSlightly reduced CMD\nSize: mildly reduced or normal", TEAL),
("Grade 2\n(Moderate)", "Echogenicity = liver (isoechoic)\nReduced/indistinct CMD\nSize: reduced (small kidneys)", ORANGE),
("Grade 3\n(Severe)", "Echogenicity > liver (hyperechoic)\nCMD lost\nSize: markedly small/shrunken", RED_WARN),
]
for j, (grade, desc, col) in enumerate(grades):
y_pos = 1.85 + j * 1.22
add_rect(slide, 0.4, y_pos, 1.5, 0.95, col)
add_textbox(slide, 0.42, y_pos+0.15, 1.46, 0.72, grade,
size=11, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
add_textbox(slide, 2.0, y_pos+0.05, 4.0, 0.9, desc, size=11, color=DARK_TEXT)
add_rect(slide, 6.4, 1.25, 6.6, 5.75, LIGHT_TEAL)
add_textbox(slide, 6.6, 1.35, 6.2, 0.38, "Pathological Correlates",
size=14, bold=True, color=NAVY)
correlates = [
("↑ Echogenicity", "Fibrosis replacing normal parenchyma;\nloss of normal medullary pyramids", TEAL),
("↓ Corticomedullary\nDifferentiation", "Cortical fibrosis raises cortex echogenicity\nto match medulla", ORANGE),
("Small Kidney Size", "Glomerulosclerosis + tubular atrophy +\ninterstitial fibrosis → parenchymal contraction", NAVY),
("Smooth Contour", "Diffuse atrophy (DM/HTN/GN) –\nnot focal scarring (reflux/infarct)", RGBColor(0x27,0xAE,0x60)),
("Sinus Fat Prominence", "Compensatory lipomatosis:\nparenchymal volume loss → fat fills space", TEAL),
]
for k, (sign, patho, col) in enumerate(correlates):
y_pos = 1.85 + k * 0.98
add_rect(slide, 6.6, y_pos, 2.2, 0.78, col)
add_textbox(slide, 6.65, y_pos+0.12, 2.1, 0.62, sign,
size=11, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
add_textbox(slide, 8.9, y_pos+0.05, 3.9, 0.7, patho, size=11.5, color=DARK_TEXT)
add_rect(slide, 0.3, 6.75, 12.7, 0.45, NAVY)
add_textbox(slide, 0.5, 6.8, 12.3, 0.35,
"Grade 2 RPC + bilateral small kidneys → CKD G3+ | Significant irreversible damage | Biopsy often contraindicated",
size=12, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
# ── SLIDE 10: Renoprotective Strategies Overview ──────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Renoprotective Strategies – Overview",
"Targeting the common pathway at multiple points for maximum benefit")
add_rect(slide, 0.3, 1.25, 12.7, 0.55, TEAL)
add_textbox(slide, 0.5, 1.3, 12.3, 0.45,
"Core Principle: Block the common pathway at multiple points — single-agent therapy is insufficient",
size=13.5, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
therapies = [
("RAAS Inhibitors\n(ACEi / ARB)", [
"↑ Efferent arteriole dilation → ↓ Pgc",
"Reduce proteinuria (30–50%)",
"Direct anti-fibrotic (↓ TGF-β1 via ↓ AngII)",
"Target: SBP <130 mmHg; ACR <30 mg/g",
"1st-line in all proteinuric CKD",
], NAVY),
("SGLT2 Inhibitors\n(Dapagliflozin, Empagliflozin)", [
"Restore tubuloglomerular feedback via macula densa",
"↑ Afferent arteriolar tone → ↓ Pgc",
"Direct anti-inflammatory + anti-fibrotic renal effects",
"DAPA-CKD: 39% ↓ ESKD risk (independent of DM)",
"EMPA-KIDNEY: consistent benefit at low eGFR",
], TEAL),
("Non-Steroidal MRA\n(Finerenone)", [
"Blocks aldosterone + cortisol receptor in kidney",
"↓ Podocyte toxicity, ↓ tubular inflammation",
"FIDELIO-DKD / FIGARO-DKD: ↓ CKD progression + CV events",
"Add to RAAS inhibitor in DKD with residual proteinuria",
"Less hyperkalaemia vs. spironolactone",
], ORANGE),
("BP Control", [
"Target <130/80 mmHg in all CKD (KDIGO 2024)",
"Every 10 mmHg ↓ SBP = ~15% ↓ ESKD risk",
"Avoid hypotension (↓ renal perfusion → AKI)",
"Use RAAS inhibitor as backbone agent",
"CCB: add-on; diuretics for volume control",
], RGBColor(0x1A,0x60,0x90)),
("Dual Endothelin/\nAngII Antagonist (Sparsentan)", [
"Blocks ET-A and AT1 receptors simultaneously",
"DUPLEX trial: superior proteinuria reduction vs. irbesartan",
"FDA approved for IgA nephropathy (2023)",
"Ongoing trials in FSGS and other glomerulopathies",
"Emerging as an add-on renoprotective strategy",
], RGBColor(0x6A,0x1B,0x9A)),
("GLP-1 Receptor Agonists\n(Semaglutide)", [
"FLOW trial (2024): semaglutide ↓ kidney failure by 24%",
"Anti-inflammatory, ↓ proteinuria, weight reduction",
"Benefit partially independent of glycaemic control",
"Particularly useful in obese/diabetic CKD",
"Emerging as 4th pillar alongside RAAS/SGLT2i/MRA",
], RGBColor(0x00,0x7A,0x5E)),
]
positions2 = [
(0.3, 2.0), (4.55, 2.0), (8.8, 2.0),
(0.3, 4.65), (4.55, 4.65), (8.8, 4.65),
]
for (x, y), (title_t, blist, col) in zip(positions2, therapies):
add_rect(slide, x, y, 4.0, 0.48, col)
add_textbox(slide, x+0.1, y+0.06, 3.8, 0.4, title_t, size=12, bold=True, color=WHITE)
tb = slide.shapes.add_textbox(Inches(x), Inches(y+0.48), Inches(4.0), Inches(2.0))
tf = tb.text_frame; tf.word_wrap = True
tf.margin_left = Inches(0.08); tf.margin_top = Inches(0.05)
for i, b in enumerate(blist):
p = tf.paragraphs[0] if i == 0 else tf.add_paragraph()
run = p.add_run(); run.text = "• " + b
run.font.name = "Calibri"; run.font.size = Pt(11)
run.font.color.rgb = DARK_TEXT
# ── SLIDE 11: RAAS + SGLT2i Deep Dive ────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Deep Dive: RAAS Inhibitors & SGLT2 Inhibitors",
"The two cornerstone agents for renoprotection with complementary mechanisms")
# RAAS side
add_rect(slide, 0.3, 1.25, 6.2, 5.95, WHITE)
add_rect(slide, 0.3, 1.25, 6.2, 0.42, NAVY)
add_textbox(slide, 0.5, 1.3, 5.8, 0.38, "RAAS Inhibitors (ACEi / ARB)",
size=14, bold=True, color=WHITE)
tb = slide.shapes.add_textbox(Inches(0.5), Inches(1.72), Inches(5.8), Inches(5.0))
tf = tb.text_frame; tf.word_wrap = True
raas_content = [
("MECHANISM OF ACTION", True, NAVY),
("• ACEi: blocks AngI→AngII conversion; ↑ bradykinin", False, DARK_TEXT),
("• ARB: blocks AT1 receptor; no bradykinin effect", False, DARK_TEXT),
("• Both: ↑ efferent arteriole dilation → ↓ intraglomerular pressure (Pgc)", False, DARK_TEXT),
("• Independent anti-fibrotic via ↓ AngII-TGF-β1 axis", False, DARK_TEXT),
("• ↓ Proteinuria by 30–50%", False, DARK_TEXT),
("", False, DARK_TEXT),
("KEY TRIAL EVIDENCE", True, NAVY),
("• RENAAL (losartan in DKD): 16% ↓ ESKD risk", False, DARK_TEXT),
("• IDNT (irbesartan in DKD): 23% ↓ ESKD risk", False, DARK_TEXT),
("• REIN (ramipril in non-DM proteinuric CKD): ↓ GFR slope", False, DARK_TEXT),
("", False, DARK_TEXT),
("PRACTICAL POINTS", True, NAVY),
("• Monitor K⁺ and creatinine after initiation (esp. bilateral RAS)", False, DARK_TEXT),
("• Acceptable: Cr rise ≤30% in first 2 months → continue", False, DARK_TEXT),
("• Avoid dual blockade (ACEi + ARB) — ↑ AKI + hyperkalaemia", False, DARK_TEXT),
("• Do NOT stop in CKD — reduction in Pgc is the desired effect", False, DARK_TEXT),
("• Adjust dose if GFR <30; hold during AKI/procedures", False, DARK_TEXT),
]
for i, (text, bold, col) in enumerate(raas_content):
p = tf.paragraphs[0] if i == 0 else tf.add_paragraph()
run = p.add_run(); run.text = text
run.font.name = "Calibri"; run.font.size = Pt(12.5)
run.font.bold = bold; run.font.color.rgb = col
# SGLT2i side
add_rect(slide, 6.8, 1.25, 6.2, 5.95, LIGHT_TEAL)
add_rect(slide, 6.8, 1.25, 6.2, 0.42, TEAL)
add_textbox(slide, 7.0, 1.3, 5.8, 0.38, "SGLT2 Inhibitors",
size=14, bold=True, color=WHITE)
tb2 = slide.shapes.add_textbox(Inches(7.0), Inches(1.72), Inches(5.8), Inches(5.0))
tf2 = tb2.text_frame; tf2.word_wrap = True
sglt2_content = [
("MECHANISM OF ACTION", True, NAVY),
("• Inhibit SGLT2 co-transporter in proximal tubule S1 segment", False, DARK_TEXT),
("• ↑ Tubular NaCl delivery to macula densa → TGF activation", False, DARK_TEXT),
("• TGF → afferent arteriolar vasoconstriction → ↓ Pgc", False, DARK_TEXT),
("• Direct anti-inflammatory: ↓ NF-κB, ↓ NLRP3 inflammasome", False, DARK_TEXT),
("• Anti-fibrotic: ↓ TGF-β1, ↓ EMT in tubular cells", False, DARK_TEXT),
("• Mild osmotic diuresis → ↓ preload, ↓ tubular O₂ demand", False, DARK_TEXT),
("• Modest haematocrit ↑ → ↑ renal O₂ delivery", False, DARK_TEXT),
("", False, DARK_TEXT),
("KEY TRIAL EVIDENCE", True, NAVY),
("• CREDENCE (canagliflozin, DKD): 30% ↓ ESKD", False, DARK_TEXT),
("• DAPA-CKD (dapagliflozin): 39% ↓ ESKD — even non-DM", False, DARK_TEXT),
("• EMPA-KIDNEY (empagliflozin): benefit to eGFR ≥20", False, DARK_TEXT),
("", False, DARK_TEXT),
("PRACTICAL POINTS", True, NAVY),
("• No dose adjustment needed at low eGFR (non-glycaemic benefit)", False, DARK_TEXT),
("• Risk of DKA (rare), genital mycotic infections", False, DARK_TEXT),
("• Hold perioperatively and during AKI ('sick day rules')", False, DARK_TEXT),
("• Add to ACEi/ARB for complementary Pgc reduction", False, DARK_TEXT),
]
for i, (text, bold, col) in enumerate(sglt2_content):
p = tf2.paragraphs[0] if i == 0 else tf2.add_paragraph()
run = p.add_run(); run.text = text
run.font.name = "Calibri"; run.font.size = Pt(12.5)
run.font.bold = bold; run.font.color.rgb = col
# ── SLIDE 12: Additional Strategies ──────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, LIGHT_BG)
slide_header(slide, "Additional Renoprotective & Supportive Strategies",
"Addressing complications and modifiable risk factors in CKD")
add_rect(slide, 0.3, 1.25, 4.0, 2.9, WHITE)
add_rect(slide, 0.3, 1.25, 4.0, 0.38, NAVY)
add_textbox(slide, 0.4, 1.28, 3.8, 0.32, "Glycaemic Control", size=13, bold=True, color=WHITE)
for b in ["HbA1c target 7–8% in DKD (avoid hypoglycaemia)","Metformin: safe to eGFR ≥30, suspend if <30","SGLT2i: primary choice (dual glycaemic + renal)","GLP-1 RA: secondary benefit (FLOW trial 2024)","Avoid sulphonylureas at low eGFR (hypo risk)"]:
tb = slide.shapes.add_textbox(Inches(0.4), Inches(1.65 + ["HbA1c target 7–8% in DKD (avoid hypoglycaemia)","Metformin: safe to eGFR ≥30, suspend if <30","SGLT2i: primary choice (dual glycaemic + renal)","GLP-1 RA: secondary benefit (FLOW trial 2024)","Avoid sulphonylureas at low eGFR (hypo risk)"].index(b)*0.38), Inches(3.8), Inches(0.36))
p = tb.text_frame.paragraphs[0]; run = p.add_run(); run.text = "• " + b
run.font.name = "Calibri"; run.font.size = Pt(11.5); run.font.color.rgb = DARK_TEXT
add_rect(slide, 4.55, 1.25, 4.0, 2.9, WHITE)
add_rect(slide, 4.55, 1.25, 4.0, 0.38, TEAL)
add_textbox(slide, 4.65, 1.28, 3.8, 0.32, "Dietary & Lifestyle Measures", size=13, bold=True, color=WHITE)
for i, b in enumerate(["Protein: 0.8 g/kg/day in non-dialysis CKD","Low salt: <5 g/day (↓ BP, ↓ proteinuria)","Phosphate restriction in CKD G3b+","Potassium restriction when hyperkalaemia","Avoid NSAIDs, contrast nephropathy, nephrotoxins","Regular aerobic exercise improves BP and outcomes"]):
tb = slide.shapes.add_textbox(Inches(4.65), Inches(1.65 + i*0.37), Inches(3.8), Inches(0.35))
p = tb.text_frame.paragraphs[0]; run = p.add_run(); run.text = "• " + b
run.font.name = "Calibri"; run.font.size = Pt(11.5); run.font.color.rgb = DARK_TEXT
add_rect(slide, 8.8, 1.25, 4.2, 2.9, WHITE)
add_rect(slide, 8.8, 1.25, 4.2, 0.38, ORANGE)
add_textbox(slide, 8.9, 1.28, 4.0, 0.32, "Managing CKD Complications", size=13, bold=True, color=WHITE)
for i, b in enumerate(["Anaemia: ESA when Hb <10 g/dL (target 10–11.5)","IV iron if ferritin <200 or TSAT <20%","Acidosis: NaHCO₃ if bicarbonate <22 mEq/L","Hyperphosphataemia: phosphate binders","Secondary HPT: active vitamin D (calcitriol)","Volume overload: loop diuretics, dietary salt/fluid Rx"]):
tb = slide.shapes.add_textbox(Inches(8.9), Inches(1.65 + i*0.37), Inches(4.0), Inches(0.35))
p = tb.text_frame.paragraphs[0]; run = p.add_run(); run.text = "• " + b
run.font.name = "Calibri"; run.font.size = Pt(11.5); run.font.color.rgb = DARK_TEXT
add_rect(slide, 0.3, 4.3, 12.7, 2.9, WHITE)
add_rect(slide, 0.3, 4.3, 12.7, 0.38, NAVY)
add_textbox(slide, 0.5, 4.33, 12.3, 0.32, "KDIGO 2024: The Comprehensive Risk-Based Approach to CKD Management", size=13.5, bold=True, color=WHITE)
table_data = [
("GFR Category", "G1–G2 (≥60)", "G3a (45–59)", "G3b (30–44)", "G4 (15–29)", "G5 (<15 / dialysis)"),
("Monitoring (per yr)", "1–2x", "2–3x", "3–4x", "4–5x", "Monthly or per Rx"),
("RAAS Inhibitor", "Yes (if proteinuria)", "Yes (continue)", "Yes (continue)", "Yes (continue)", "Per specialist"),
("SGLT2 Inhibitor", "Yes (all)", "Yes", "Yes", "Benefit shown ≥20", "Not studied"),
("Dietitian referral", "If needed", "Recommended", "Required", "Required", "Required"),
]
col_widths = [2.0, 1.9, 1.9, 1.9, 1.9, 2.8]
col_x = [0.35]
for w in col_widths[:-1]:
col_x.append(col_x[-1] + w + 0.08)
for row_i, row in enumerate(table_data):
for col_i, cell in enumerate(row):
x = col_x[col_i]; y = 4.72 + row_i * 0.42
bg = LIGHT_TEAL if row_i == 0 else (LIGHT_BG if row_i % 2 == 0 else WHITE)
add_rect(slide, x, y, col_widths[col_i], 0.4, bg)
add_textbox(slide, x+0.05, y+0.06, col_widths[col_i]-0.1, 0.3, cell,
size=10.5, bold=(row_i == 0), color=NAVY if row_i == 0 else DARK_TEXT)
# ── SLIDE 13: Summary ─────────────────────────────────────
slide = blank_slide(prs)
add_rect(slide, 0, 0, 13.333, 7.5, NAVY)
add_rect(slide, 0, 0, 13.333, 1.1, TEAL)
add_textbox(slide, 0.5, 0.12, 12.3, 0.85, "Summary & Key Take-Home Points",
size=26, bold=True, color=WHITE)
takeaways = [
("1", "Common Pathway", "Regardless of cause, CKD progresses through glomerular capillary hypertension → proteinuria → TIF → glomerulosclerosis. This cycle is self-perpetuating."),
("2", "Small Kidneys = Chronicity", "Bilateral small kidneys with Grade 2 RPC on USS indicate significant irreversible damage (CKD G3+). Smooth contour = diffuse disease (DM/HTN/GN)."),
("3", "RAAS First", "ACEi/ARB remain the cornerstone — they reduce intraglomerular pressure AND proteinuria AND fibrosis. Never stop unless truly contraindicated."),
("4", "Add SGLT2i", "Dapagliflozin/Empagliflozin provide complementary Pgc reduction via TGF, with direct anti-inflammatory and anti-fibrotic renal effects — benefit extends to non-diabetic CKD."),
("5", "Then Add Finerenone", "In diabetic CKD with residual proteinuria on RAAS blockade, finerenone (non-steroidal MRA) provides additive renal and cardiovascular benefit with acceptable K⁺ profile."),
("6", "Emerging 4th Pillar", "GLP-1 RA (semaglutide – FLOW 2024) show 24% kidney failure reduction. Sparsentan is FDA-approved for IgA nephropathy. The renoprotection toolkit is expanding."),
("7", "Treat the Whole Patient", "Address acidosis (NaHCO₃), anaemia (ESA/iron), hyperphosphataemia, BP control, and prevent AKI episodes — each is an independent contributor to CKD progression."),
]
for k, (num, title_s, body_s) in enumerate(takeaways):
col = k % 2
row = k // 2
x = 0.3 if col == 0 else 6.85
y = 1.25 + row * 1.38
if k == 6: # last item spans center
x = 3.5; y = 1.25 + 3 * 1.38
add_rect(slide, x, y, 0.6, 0.8, TEAL)
add_textbox(slide, x+0.05, y+0.15, 0.5, 0.55, num, size=18, bold=True, color=WHITE, align=PP_ALIGN.CENTER)
add_rect(slide, x+0.6, y, 5.7 if k < 6 else 6.3, 0.8, RGBColor(0x15,0x3A,0x6E))
add_textbox(slide, x+0.7, y+0.04, 5.5 if k < 6 else 6.1, 0.28, title_s, size=12, bold=True, color=TEAL)
add_textbox(slide, x+0.7, y+0.3, 5.5 if k < 6 else 6.1, 0.46, body_s, size=10.5, color=RGBColor(0xCC,0xDD,0xEE))
add_rect(slide, 0.3, 6.65, 12.7, 0.55, RGBColor(0x0A,0x1E,0x40))
add_textbox(slide, 0.5, 6.7, 12.3, 0.42,
"Brenner & Rector's The Kidney | Harrison's Principles of Internal Medicine 22E | Goldman-Cecil Medicine | KDIGO Guidelines",
size=10.5, color=RGBColor(0x80,0xA0,0xC0), align=PP_ALIGN.CENTER)
# ── SAVE ─────────────────────────────────────────────────
out = "/tmp/workspace/ckd-presentation/CKD_Pathophysiology_Renoprotection.pptx"
buf = BytesIO()
prs.save(buf)
with open(out, "wb") as f:
f.write(buf.getvalue())
print(f"Saved: {out}")
print(f"Slides: {len(prs.slides)}")
cd /tmp/workspace/ckd-presentation && python create_ckd_pptx.py 2>&1
ls -lh /tmp/workspace/ckd-presentation/CKD_Pathophysiology_Renoprotection.pptx
CKD Pathophysiology Renoprotection
Presentation · PPTX
| Slide | Content |
|---|---|
| 1 | Title slide |
| 2 | Presentation overview / agenda |
| 3 | CKD definition, KDIGO G-categories, epidemiology stats |
| 4 | Intact Nephron Hypothesis (Bricker) - with step-down flow diagram |
| 5 | Glomerular Hemodynamic Adaptations (Brenner Hypothesis) - Pgc table |
| 6 | Proteinuria as a mediator of tubular injury - 5-column pathway layout |
| 7 | Tubulointerstitial fibrosis, glomerulosclerosis & the vicious cycle |
| 8 | 6 non-hemodynamic amplifying factors (oxidative stress, acidosis, RAAS, FGF-23, anemia, AKI) |
| 9 | Bilateral small kidneys - RPC grading table + pathological correlates |
| 10 | Renoprotective strategies overview (all 6 drug classes) |
| 11 | Deep dive: RAAS inhibitors vs. SGLT2 inhibitors - mechanisms + trial evidence |
| 12 | Additional strategies + KDIGO 2024 monitoring table by GFR category |
| 13 | Summary - 7 take-home points |