Make me detailed pdf on topic thyroid gland with its anatomy , physiology, clinical examination, diseases , various surgical procedures with their details with pictures from scott and brown otorhinolaryngology and Cummings book

Reading File
Finding Sources
Reading File
Finding Sources
Finding Sources
Finding Sources
Reading File
Reading File
Reading File
Reading File
Reading File
Reading File
Finding Sources
Finding Sources
Reading File
Reading File
Reading File
Reading File
Running Command

mkdir -p /tmp/workspace/thyroid-pdf && ls /tmp/workspace/thyroid-pdf/

Writing File

~/thyroid-pdf/generate_thyroid_pdf.py

#!/usr/bin/env python3
"""
Comprehensive PDF on the Thyroid Gland
Sources: Scott-Brown's Otorhinolaryngology Head & Neck Surgery
         Cummings Otolaryngology Head and Neck Surgery
"""

import io
import os
import urllib.request
from reportlab.lib.pagesizes import A4
from reportlab.lib import colors
from reportlab.lib.styles import getSampleStyleSheet, ParagraphStyle
from reportlab.lib.units import cm, mm
from reportlab.platypus import (
    SimpleDocTemplate, Paragraph, Spacer, Table, TableStyle,
    PageBreak, HRFlowable, Image, KeepTogether
)
from reportlab.platypus.tableofcontents import TableOfContents
from reportlab.lib.enums import TA_CENTER, TA_LEFT, TA_JUSTIFY
from reportlab.pdfgen import canvas
from reportlab.lib.colors import HexColor

# ─── COLOR PALETTE ─────────────────────────────────────────────────────────
NAVY     = HexColor("#1a3a5c")
TEAL     = HexColor("#1e7d8a")
LIGHT_BG = HexColor("#eaf4f5")
HEADER_BG= HexColor("#1a3a5c")
SUBH_BG  = HexColor("#2a6d8c")
TABLE_H  = HexColor("#d0e8ed")
TABLE_ALT= HexColor("#f5fbfc")
ACCENT   = HexColor("#e84e1b")
ORANGE   = HexColor("#e07b39")

W, H = A4

# ─── IMAGE HELPER ────────────────────────────────────────────────────────────
def fetch_image_from_url(url, max_width=14*cm, max_height=8*cm):
    """Download image and return ReportLab Image flowable, or None on failure."""
    try:
        req = urllib.request.Request(url, headers={"User-Agent": "Mozilla/5.0"})
        data = urllib.request.urlopen(req, timeout=10).read()
        img_io = io.BytesIO(data)
        img = Image(img_io)
        # Scale maintaining aspect ratio
        iw, ih = img.drawWidth, img.drawHeight
        scale = min(max_width / iw, max_height / ih, 1.0)
        img.drawWidth  = iw * scale
        img.drawHeight = ih * scale
        return img
    except Exception as e:
        return None

# ─── DOCUMENT SETUP ──────────────────────────────────────────────────────────
OUTPUT = "/tmp/workspace/thyroid-pdf/Thyroid_Gland_Comprehensive.pdf"

styles = getSampleStyleSheet()

title_style = ParagraphStyle(
    "TitleStyle",
    fontName="Helvetica-Bold",
    fontSize=26,
    textColor=colors.white,
    spaceAfter=6,
    alignment=TA_CENTER,
    leading=32,
)
subtitle_style = ParagraphStyle(
    "SubTitle",
    fontName="Helvetica",
    fontSize=13,
    textColor=HexColor("#b0d8e0"),
    spaceAfter=4,
    alignment=TA_CENTER,
)
source_style = ParagraphStyle(
    "SourceStyle",
    fontName="Helvetica-Oblique",
    fontSize=10,
    textColor=HexColor("#90c8d0"),
    alignment=TA_CENTER,
)
h1_style = ParagraphStyle(
    "H1",
    fontName="Helvetica-Bold",
    fontSize=16,
    textColor=colors.white,
    spaceBefore=14,
    spaceAfter=6,
    leading=20,
    backColor=HEADER_BG,
    leftIndent=-12,
    rightIndent=-12,
    borderPad=8,
)
h2_style = ParagraphStyle(
    "H2",
    fontName="Helvetica-Bold",
    fontSize=13,
    textColor=colors.white,
    spaceBefore=10,
    spaceAfter=4,
    leading=16,
    backColor=SUBH_BG,
    leftIndent=-8,
    rightIndent=-8,
    borderPad=5,
)
h3_style = ParagraphStyle(
    "H3",
    fontName="Helvetica-Bold",
    fontSize=11,
    textColor=NAVY,
    spaceBefore=8,
    spaceAfter=3,
    leading=14,
    borderPad=3,
    leftIndent=0,
)
body_style = ParagraphStyle(
    "Body",
    fontName="Helvetica",
    fontSize=9.5,
    textColor=HexColor("#1a1a2e"),
    spaceAfter=5,
    leading=14,
    alignment=TA_JUSTIFY,
)
bullet_style = ParagraphStyle(
    "Bullet",
    fontName="Helvetica",
    fontSize=9.5,
    textColor=HexColor("#1a1a2e"),
    spaceAfter=3,
    leading=13,
    leftIndent=14,
    bulletIndent=4,
    alignment=TA_LEFT,
)
caption_style = ParagraphStyle(
    "Caption",
    fontName="Helvetica-Oblique",
    fontSize=8.5,
    textColor=HexColor("#555566"),
    spaceAfter=6,
    alignment=TA_CENTER,
    leading=12,
)
highlight_style = ParagraphStyle(
    "Highlight",
    fontName="Helvetica",
    fontSize=9.5,
    textColor=NAVY,
    spaceAfter=5,
    leading=14,
    leftIndent=10,
    rightIndent=10,
    backColor=LIGHT_BG,
    borderPad=6,
    borderColor=TEAL,
    borderWidth=1,
    alignment=TA_JUSTIFY,
)
ref_style = ParagraphStyle(
    "Ref",
    fontName="Helvetica-Oblique",
    fontSize=8,
    textColor=HexColor("#557788"),
    spaceAfter=2,
    leading=11,
)

def H1(text): return Paragraph(f"  {text}", h1_style)
def H2(text): return Paragraph(f"  {text}", h2_style)
def H3(text): return Paragraph(text, h3_style)
def P(text):  return Paragraph(text, body_style)
def B(text):  return Paragraph(f"\u2022  {text}", bullet_style)
def HL(text): return Paragraph(text, highlight_style)
def Cap(text): return Paragraph(text, caption_style)
def Ref(text): return Paragraph(text, ref_style)
def SP(n=6):  return Spacer(1, n)
def HR():     return HRFlowable(width="100%", thickness=0.5, color=TEAL, spaceAfter=4)

# ─── BUILD STORY ─────────────────────────────────────────────────────────────
story = []

# ── COVER PAGE ──────────────────────────────────────────────────────────────
def cover_page(canvas_obj, doc):
    canvas_obj.saveState()
    # Background gradient-like fill
    canvas_obj.setFillColor(NAVY)
    canvas_obj.rect(0, 0, W, H, fill=True, stroke=False)
    # Decorative bands
    canvas_obj.setFillColor(TEAL)
    canvas_obj.rect(0, H*0.68, W, H*0.02, fill=True, stroke=False)
    canvas_obj.rect(0, H*0.10, W, H*0.02, fill=True, stroke=False)
    # accent line
    canvas_obj.setFillColor(ORANGE)
    canvas_obj.rect(0, H*0.66, W, H*0.008, fill=True, stroke=False)
    # Title text
    canvas_obj.setFont("Helvetica-Bold", 34)
    canvas_obj.setFillColor(colors.white)
    canvas_obj.drawCentredString(W/2, H*0.72, "THYROID GLAND")
    canvas_obj.setFont("Helvetica-Bold", 18)
    canvas_obj.setFillColor(HexColor("#b0d8e0"))
    canvas_obj.drawCentredString(W/2, H*0.65, "Comprehensive Clinical Reference")
    # Subtitle lines
    canvas_obj.setFont("Helvetica", 11)
    canvas_obj.setFillColor(HexColor("#90c8d0"))
    canvas_obj.drawCentredString(W/2, H*0.59, "Anatomy  •  Physiology  •  Clinical Examination")
    canvas_obj.drawCentredString(W/2, H*0.56, "Diseases  •  Surgical Procedures")
    # Source books
    canvas_obj.setFillColor(TEAL)
    canvas_obj.rect(W*0.12, H*0.28, W*0.76, 0.6*cm, fill=True, stroke=False)
    canvas_obj.setFont("Helvetica-Bold", 9.5)
    canvas_obj.setFillColor(colors.white)
    canvas_obj.drawCentredString(W/2, H*0.285, "SOURCE TEXTBOOKS")
    canvas_obj.setFont("Helvetica", 9)
    canvas_obj.setFillColor(HexColor("#cce8ee"))
    canvas_obj.drawCentredString(W/2, H*0.25, "Scott-Brown's Otorhinolaryngology Head & Neck Surgery")
    canvas_obj.drawCentredString(W/2, H*0.23, "Cummings Otolaryngology Head and Neck Surgery")
    # Date
    canvas_obj.setFont("Helvetica", 8)
    canvas_obj.setFillColor(HexColor("#607080"))
    canvas_obj.drawCentredString(W/2, H*0.07, "August 2026  |  Educational Reference Document")
    canvas_obj.restoreState()

class MyDocTemplate(SimpleDocTemplate):
    def __init__(self, filename, **kwargs):
        super().__init__(filename, **kwargs)
        self._cover = True

    def handle_pageBegin(self):
        super().handle_pageBegin()

    def afterPage(self):
        pass

doc = SimpleDocTemplate(
    OUTPUT,
    pagesize=A4,
    leftMargin=2.2*cm, rightMargin=2.2*cm,
    topMargin=2.5*cm, bottomMargin=2.2*cm,
    title="Thyroid Gland - Comprehensive Clinical Reference",
    author="Compiled from Scott-Brown & Cummings",
)

# Cover
story.append(Spacer(1, 6*cm))  # push content down on cover

# We'll use a different approach - add a large colored table as cover
cover_data = [
    [Paragraph("<b>THYROID GLAND</b>", ParagraphStyle("ct", fontName="Helvetica-Bold", fontSize=30, textColor=colors.white, alignment=TA_CENTER, leading=36))],
    [Paragraph("Comprehensive Clinical Reference", ParagraphStyle("cs", fontName="Helvetica", fontSize=16, textColor=HexColor("#b0d8e0"), alignment=TA_CENTER))],
    [Spacer(1, 0.5*cm)],
    [Paragraph("Anatomy • Physiology • Clinical Examination<br/>Diseases • Surgical Procedures", ParagraphStyle("csu", fontName="Helvetica", fontSize=11, textColor=HexColor("#90c8d0"), alignment=TA_CENTER, leading=18))],
    [Spacer(1, 1.5*cm)],
    [Paragraph("<b>SOURCE TEXTBOOKS</b>", ParagraphStyle("src_hdr", fontName="Helvetica-Bold", fontSize=10, textColor=TEAL, alignment=TA_CENTER))],
    [Paragraph("Scott-Brown's Otorhinolaryngology Head &amp; Neck Surgery<br/>Cummings Otolaryngology Head and Neck Surgery", ParagraphStyle("src", fontName="Helvetica-Oblique", fontSize=10, textColor=HexColor("#557799"), alignment=TA_CENTER, leading=16))],
    [Spacer(1, 0.5*cm)],
    [Paragraph("August 2026 | Educational Reference Document", ParagraphStyle("dt", fontName="Helvetica", fontSize=9, textColor=HexColor("#778899"), alignment=TA_CENTER))],
]
cover_table = Table(cover_data, colWidths=[16*cm])
cover_table.setStyle(TableStyle([
    ("BACKGROUND", (0,0), (-1,-1), NAVY),
    ("TOPPADDING", (0,0), (-1,-1), 8),
    ("BOTTOMPADDING", (0,0), (-1,-1), 8),
    ("LINEABOVE", (0,1), (-1,1), 2, TEAL),
    ("LINEBELOW", (0,3), (-1,3), 2, ORANGE),
    ("BOX", (0,0), (-1,-1), 2, TEAL),
]))
story.append(cover_table)
story.append(PageBreak())

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 1: ANATOMY
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("1. ANATOMY OF THE THYROID GLAND"))
story.append(SP())

story.append(H2("1.1 Macroscopic Anatomy"))
story.append(P("The thyroid gland is situated in the lower anterior neck straddling the upper trachea. It is the largest endocrine organ in the body, weighing <b>15–25 g</b> in adulthood. It is a highly vascular, reddish-brown, bi-lobed structure with each lobe joined by a narrow isthmus."))
story.append(P("Each lobe is pear-shaped, measuring approximately <b>4–5 cm in length, 1.5–3 cm in width and 1.5–2 cm in depth</b>. The apex of each lobe extends beneath the sternothyroid muscle up to its insertion on the oblique line of the thyroid cartilage. The more rounded lower pole extends down to the level of the <b>fourth–sixth tracheal ring</b>. It lies lateral to the trachea and oesophagus and medial to the carotid sheath. The isthmus overlies the <b>second to fourth tracheal rings</b>."))

story.append(HL("Key anatomical fact: Approximately 40% of patients have a pyramidal lobe that arises from either lobe or the midline isthmus and extends superiorly – a vestige of the thyroglossal duct."))

story.append(H3("Capsule and Ligaments"))
story.append(P("The thyroid gland is enclosed between layers of the deep cervical fascia. Two capsular layers are described:"))
story.append(B("<b>True (visceral) capsule:</b> Tightly adherent to the thyroid parenchyma; extends inwards to form fibrous septa dividing the gland into lobules."))
story.append(B("<b>False (surgical) capsule:</b> A loose outer layer derived from the pretracheal fascia; the plane of dissection during thyroidectomy."))
story.append(B("<b>Berry ligament (posterior suspensory ligament):</b> A condensation of the middle layer of deep cervical fascia connecting the thyroid lobes to the cricoid cartilage and first two tracheal rings. The recurrent laryngeal nerve passes through or immediately adjacent to this ligament – a critical surgical landmark."))
story.append(SP())

# IMAGE: Thyroid embryology diagram
img_embryo = fetch_image_from_url(
    "https://cdn.orris.care/cdss_images/b1dda232e3b680c8cdca167d306625b5b0a5fb8bb3cf67e05bcc080baaa104c9.png",
    max_width=11*cm, max_height=7*cm
)
if img_embryo:
    story.append(img_embryo)
    story.append(Cap("Fig. 1 – Schematic representation of the early development of the median and lateral anlagen of the thyroid and parathyroid glands. (Scott-Brown's, Ch.53)"))
    story.append(SP())

story.append(H2("1.2 Vascular Supply"))
story.append(H3("Arterial Supply"))
story.append(B("<b>Superior thyroid artery:</b> First branch of the external carotid artery; enters the superior pole of each lobe. The external branch of the superior laryngeal nerve (EBSLN) runs parallel – surgical injury causes changes in voice pitch."))
story.append(B("<b>Inferior thyroid artery:</b> Branch of the thyrocervical trunk (subclavian artery); enters the posterior surface of the middle-lower lobe. The recurrent laryngeal nerve crosses in close relation to this vessel."))
story.append(B("<b>Thyroidea ima artery:</b> Present in ~3% of individuals; arises directly from the aorta or brachiocephalic trunk, entering the isthmus inferiorly."))

story.append(H3("Venous Drainage"))
story.append(B("<b>Superior thyroid vein:</b> Drains into the internal jugular vein."))
story.append(B("<b>Middle thyroid vein:</b> Drains directly into the internal jugular vein (no corresponding artery)."))
story.append(B("<b>Inferior thyroid veins:</b> Drain into the brachiocephalic veins; important in retrosternal goitre."))

story.append(H3("Lymphatic Drainage"))
story.append(P("Lymphatics drain to the prelaryngeal (Delphian) node, pretracheal and paratracheal nodes, and then to the deep cervical chain (levels III, IV, VI). The Delphian node, when enlarged and hard, is a sign of thyroid malignancy. The lateral compartment (levels II–V) is involved via skip metastases in papillary thyroid carcinoma."))

story.append(H2("1.3 Nerve Supply and Critical Relationships"))
story.append(HL("The most important nerves at risk during thyroidectomy are: (1) the Recurrent Laryngeal Nerve (RLN) and (2) the External Branch of the Superior Laryngeal Nerve (EBSLN)."))
story.append(B("<b>Recurrent laryngeal nerve (RLN):</b> Branch of the vagus; enters the larynx posterior to the cricothyroid joint. On the right it loops under the subclavian artery; on the left under the arch of the aorta. It ascends in the tracheo-oesophageal groove and passes through or adjacent to the Berry ligament. A non-recurrent RLN occurs on the right in ~0.5–2%."))
story.append(B("<b>External branch of SLN (EBSLN):</b> Innervates the cricothyroid muscle (fine pitch control). Lies on the inferior constrictor; may travel close to the superior thyroid vessels in up to 20% of patients (Cernea classification)."))

story.append(H2("1.4 Parathyroid Glands"))
story.append(P("Four parathyroid glands are normally present, each weighing 40–60 mg. The superior parathyroids are more constant in position (85% within a 2 cm radius, 1 cm above the crossing of inferior thyroid artery and RLN). The inferior parathyroids are more variable. Identification and preservation of all four glands is a critical goal of thyroidectomy."))
story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 2: EMBRYOLOGY
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("2. EMBRYOLOGY"))
story.append(SP())

story.append(P("The thyroid gland develops from two anlages:"))
story.append(B("<b>Median (central) anlage:</b> Derives from the endoderm at the foramen cecum (junction of anterior two-thirds and posterior one-third of the tongue, first and second pharyngeal pouches). The diverticulum descends through a midline path during weeks 4–7, tethered by the thyroglossal duct, which subsequently degenerates."))
story.append(B("<b>Lateral anlage:</b> Arises from the fourth and fifth pharyngeal pouches; contributes parafollicular C cells (from neural crest cells of the fourth pouch). C cells are restricted to the middle to upper thirds of the lateral lobes."))
story.append(SP())

# Timeline table
timeline_data = [
    ["Gestational Age", "Developmental Event"],
    ["Day 10", "Endodermal thickening seen"],
    ["Day 16–17", "Median and lateral anlagen discernible"],
    ["Day 24", "Median anlage forms a flask-like diverticulum from the floor of buccal cavity"],
    ["Day 30", "Formation of bi-lobulated structure"],
    ["Day 40", "Median and lateral anlagen fuse; thyroglossal duct degenerates"],
    ["Day 50", "Descent complete; thyroid reaches final pretracheal location; precolloid phase starts"],
    ["Week 10", "Colloid phase; thyroid hormone receptors detectable in brain"],
    ["Week 11", "Histogenesis virtually complete; thyroid capable of trapping/oxidizing iodide"],
    ["Week 16", "TSH secretion becomes principal regulator of thyroid growth"],
]
tbl = Table(timeline_data, colWidths=[4.5*cm, 11*cm])
tbl.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), TABLE_H),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 8.5),
    ("FONTNAME",     (0,1), (0,-1), "Helvetica-Bold"),
    ("BACKGROUND",   (0,2), (-1,2), TABLE_ALT),
    ("BACKGROUND",   (0,4), (-1,4), TABLE_ALT),
    ("BACKGROUND",   (0,6), (-1,6), TABLE_ALT),
    ("BACKGROUND",   (0,8), (-1,8), TABLE_ALT),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 6),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(tbl)
story.append(Cap("Table 1. Timeline of thyroid development in humans. (Scott-Brown's, Table 53.1)"))
story.append(SP())

story.append(H3("Developmental Anomalies"))
story.append(B("<b>Thyroglossal duct cyst:</b> Persistence of the thyroglossal duct tract. Presents as a midline neck mass that moves upward with tongue protrusion. Treatment: Sistrunk operation."))
story.append(B("<b>Lingual thyroid:</b> Failure of descent; thyroid tissue remains at foramen cecum. May be the only functioning thyroid tissue in 70% of cases – check with isotope scan before removal."))
story.append(B("<b>Ectopic thyroid:</b> Can be found anywhere along the descent path (sublingual, intralingual, tracheal, oesophageal, mediastinal)."))
story.append(B("<b>Agenesis/hemiagenesis:</b> Rare cause of congenital hypothyroidism."))
story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 3: PHYSIOLOGY
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("3. PHYSIOLOGY OF THE THYROID GLAND"))
story.append(SP())

story.append(H2("3.1 Thyroid Hormone Synthesis"))
story.append(P("The thyroid produces two major hormones: <b>T4 (thyroxine, tetraiodothyronine)</b> and <b>T3 (triiodothyronine)</b> – both iodinated derivatives of tyrosine. The gland is unique in having a large extracellular storage space (follicular lumen) where hormones and precursors are stored as thyroglobulin colloid."))

# Hormone synthesis steps table
synth_data = [
    ["Step", "Process", "Key Enzyme/Protein"],
    ["1. Iodide uptake", "Na⁺/I⁻ symporter (NIS) at basal membrane concentrates iodide 20–40× against electrochemical gradient", "NIS (sodium/iodide symporter)"],
    ["2. Iodide transport to lumen", "Pendrin (apical membrane protein) releases iodide into follicular lumen", "Pendrin"],
    ["3. Thyroglobulin synthesis", "660 kDa glycoprotein synthesized on ER, processed in Golgi, secreted into follicular lumen", "Thyroglobulin (Tg)"],
    ["4. Oxidation & organification", "I⁻ oxidized to I⁰ and incorporated into tyrosine residues of Tg forming MIT and DIT", "Thyroid peroxidase (TPO) + H₂O₂"],
    ["5. Coupling", "Two DIT → T4; MIT + DIT → T3. Reaction on Tg within follicular lumen", "Thyroid peroxidase"],
    ["6. Endocytosis", "Tg retrieved by micropinocytosis or macropinocytosis from follicular lumen", "TSH-stimulated process"],
    ["7. Proteolysis & release", "Lysosomes hydrolyze Tg; T4 and T3 released into bloodstream", "Cathepsins"],
    ["8. Deiodination", "MIT and DIT de-iodinated; iodide recycled within the gland", "Iodotyrosine deiodinase"],
]
st = Table(synth_data, colWidths=[3.5*cm, 7*cm, 5*cm])
st.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), TABLE_H),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("FONTNAME",     (0,1), (0,-1), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 8.0),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 5),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(st)
story.append(Cap("Table 2. Steps in thyroid hormone synthesis. (Cummings, Ch.121)"))
story.append(SP())

# IMAGE: Thyroid hormone synthesis diagram
img_synth = fetch_image_from_url(
    "https://cdn.orris.care/cdss_images/c44a2e87c058ad291b5e5422dbc14bbdefba612a78f9407db41c46b44eecc575.png",
    max_width=12*cm, max_height=7*cm
)
if img_synth:
    story.append(img_synth)
    story.append(Cap("Fig. 2 – Synthesis and release of thyroid hormone (Cummings, Fig. 121.1). Steps 1–8 are depicted showing iodide transport, Tg synthesis, organification, endocytosis, and hormone release."))
    story.append(SP())

story.append(H2("3.2 Hypothalamic-Pituitary-Thyroid Axis"))
story.append(P("Thyroid function is regulated by a classic negative feedback axis:"))
story.append(B("<b>TRH (Thyrotropin-releasing hormone):</b> Released from paraventricular nucleus of hypothalamus; stimulates TSH release from anterior pituitary."))
story.append(B("<b>TSH (Thyroid-stimulating hormone):</b> Acts on TSH receptors (TSHr) on thyrocytes via Gs-cAMP pathway. Stimulates all steps of hormone synthesis and thyroid cell growth."))
story.append(B("<b>Negative feedback:</b> T3 and T4 suppress both TRH and TSH at hypothalamus and pituitary. T3 is more potent (the active form); T4 is peripherally converted to T3 by deiodinase enzymes."))
story.append(HL("Normal reference ranges: TSH 0.4–4.0 mIU/L; Free T4 9–25 pmol/L; Free T3 3.5–7.8 pmol/L. Peripheral T3 is predominantly (>80%) derived from deiodination of T4, not direct thyroid secretion."))

story.append(H2("3.3 Actions of Thyroid Hormones"))
story.append(P("Thyroid hormones act via nuclear receptors (TRα, TRβ) to regulate gene transcription. Key physiological effects:"))

actions_data = [
    ["System", "Effect of Thyroid Hormone"],
    ["Metabolism", "Increase basal metabolic rate; stimulate mitochondrial oxidative phosphorylation; increase O₂ consumption in most tissues (except brain, testis, spleen)"],
    ["Cardiovascular", "Increase heart rate and cardiac output; decrease peripheral resistance; increase expression of β-adrenoreceptors"],
    ["Development/CNS", "Essential for normal CNS maturation; deficiency in fetal/neonatal period causes cretinism (irreversible cognitive impairment)"],
    ["Bone", "Stimulate bone turnover; essential for normal growth plate function and linear growth"],
    ["GI tract", "Increase gut motility; increase appetite; stimulate hepatic glucose production"],
    ["Respiratory", "Maintain normal hypoxic/hypercapnic ventilatory drive"],
    ["Haemopoietic", "Stimulate erythropoietin; increase red cell 2,3-DPG to facilitate O₂ delivery"],
    ["Reproductive", "Essential for normal gonadal function; excess disrupts menstrual cycle"],
]
at = Table(actions_data, colWidths=[4*cm, 12*cm])
at.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), TABLE_H),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("FONTNAME",     (0,1), (0,-1), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 8.5),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 5),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(at)
story.append(Cap("Table 3. Physiological actions of thyroid hormones by organ system."))
story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 4: CLINICAL EXAMINATION
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("4. CLINICAL EXAMINATION OF THE THYROID"))
story.append(SP())

story.append(H2("4.1 History"))
story.append(P("A systematic history in thyroid disease should cover:"))
story.append(B("<b>Symptoms of hyperthyroidism:</b> Weight loss despite normal/increased appetite, heat intolerance, palpitations, tremor, anxiety, diarrhoea, menstrual irregularity, exophthalmos (Graves')."))
story.append(B("<b>Symptoms of hypothyroidism:</b> Weight gain, cold intolerance, fatigue, constipation, dry skin and hair, menorrhagia, depression, hoarseness, bradycardia, delayed tendon reflexes."))
story.append(B("<b>Local symptoms (goitre/nodule):</b> Neck swelling, dysphagia, dyspnoea, hoarseness (suggests RLN involvement = malignancy until proven otherwise), stridor."))
story.append(B("<b>Risk factors for malignancy:</b> Age <20 or >60 years, male sex, previous neck irradiation, family history of medullary carcinoma or MEN syndrome (2A or 2B), rapid growth."))
story.append(B("<b>Drug history:</b> Amiodarone (iodine-rich, causes both hypo- and hyperthyroidism), lithium (causes hypothyroidism/goitre), PTU, carbimazole."))

story.append(H2("4.2 Inspection"))
story.append(B("Inspect the neck from the front and side with adequate lighting."))
story.append(B("Note any visible swelling in the anterior neck, especially in the thyroid region."))
story.append(B("Ask the patient to swallow a sip of water: thyroid swellings and thyroglossal cysts rise on swallowing (attached to pretracheal fascia), while most other neck masses do not."))
story.append(B("Ask the patient to protrude the tongue: thyroglossal cysts rise on tongue protrusion (attached to thyroglossal duct remnant), distinguishing them from thyroid masses."))
story.append(B("Inspect for signs of thyroid status: tremor, eye signs (Graves'), pretibial myxoedema, thyroid acropachy."))

story.append(H2("4.3 Palpation"))
story.append(P("Stand behind the patient seated in a chair. Ask the patient to slightly flex the neck (relaxes strap muscles). Palpate with both hands, using fingertips on either side of the trachea."))
story.append(B("<b>Size:</b> Estimate each lobe separately; the isthmus is palpable in the midline."))
story.append(B("<b>Consistency:</b> Soft (colloid goitre, cyst), firm/rubbery (Hashimoto's thyroiditis, lymphoma), hard/stony (carcinoma, calcification, Riedel's thyroiditis)."))
story.append(B("<b>Surface:</b> Smooth (Graves', Hashimoto's early) vs. nodular (multinodular goitre) vs. dominant nodule."))
story.append(B("<b>Tenderness:</b> Acute/subacute thyroiditis, haemorrhage into cyst."))
story.append(B("<b>Mobility:</b> Thyroid moves with swallowing; fixation to surrounding structures suggests malignant invasion."))
story.append(B("<b>Lower border:</b> If impalpable, suggests retrosternal extension."))
story.append(B("<b>Palpable lymph nodes:</b> Central (level VI) and lateral neck (levels II–V) nodes must be assessed for metastases."))

story.append(H2("4.4 Percussion and Auscultation"))
story.append(B("<b>Percussion:</b> Percuss over the manubrium sterni for retrosternal dullness (retrosternal goitre)."))
story.append(B("<b>Auscultation:</b> A bruit over the thyroid is characteristic of Graves' disease (indicates marked hypervascularity). Distinguish from a venous hum or carotid bruit."))

story.append(H2("4.5 Systemic Signs of Thyroid Status"))
story.append(P("After examining the thyroid, assess thyroid status:"))

exam_data = [
    ["System", "Hyperthyroidism Signs", "Hypothyroidism Signs"],
    ["Hands", "Fine tremor, warm/moist skin, palmar erythema, onycholysis (Plummer's nails), thyroid acropachy", "Dry skin, cool peripheries, carpal tunnel syndrome"],
    ["Pulse", "Tachycardia, AF, bounding pulse", "Bradycardia, low-volume pulse"],
    ["Eyes", "Lid lag, lid retraction (any cause); proptosis/exophthalmos, chemosis, ophthalmopathy (Graves' only)", "Periorbital puffiness, loss of outer 1/3 eyebrow"],
    ["Neck", "Goitre ± bruit (Graves')", "Goitre (Hashimoto's early), tracheal deviation"],
    ["Reflexes", "Hyperreflexia", "Slow relaxation phase (hung-up reflex)"],
    ["Other", "Weight loss, heat intolerance, diarrhoea, menstrual irregularity, anxiety", "Weight gain, cold intolerance, constipation, depression, hoarseness"],
]
et = Table(exam_data, colWidths=[3*cm, 6.5*cm, 6.5*cm])
et.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), TABLE_H),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("FONTNAME",     (0,1), (0,-1), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 8.0),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 5),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(et)
story.append(Cap("Table 4. Comparison of clinical signs in hyperthyroidism and hypothyroidism."))

story.append(H2("4.6 Investigations"))
story.append(B("<b>Thyroid function tests:</b> TSH (first-line), Free T4, Free T3."))
story.append(B("<b>Thyroid antibodies:</b> Anti-TPO (Hashimoto's, Graves'), anti-Tg, anti-TSH receptor (Graves' disease – positive in >95%)."))
story.append(B("<b>Serum calcitonin:</b> Elevated in medullary thyroid carcinoma; role as routine screening is debated."))
story.append(B("<b>Ultrasound:</b> First-line imaging; assesses nodule characteristics, vascularity (TIRADS scoring), cervical lymph nodes."))
story.append(B("<b>Fine-needle aspiration cytology (FNAC):</b> Gold standard for cytological diagnosis of thyroid nodules. Bethesda classification (I–VI) guides management."))
story.append(B("<b>Radionuclide scanning (⁹⁹ᵐTc or ¹³¹I):</b> Assesses function (hot/warm/cold nodules). Cold nodules have higher risk of malignancy. Most useful for ectopic thyroid, post-thyroidectomy remnant assessment."))
story.append(B("<b>CT/MRI neck:</b> Assesses extent of large goitres, retrosternal extension, tracheal deviation/compression, malignant invasion of adjacent structures."))
story.append(B("<b>Laryngoscopy:</b> Mandatory pre-operatively to assess vocal cord mobility."))
story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 5: DISEASES
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("5. DISEASES OF THE THYROID GLAND"))
story.append(SP())

story.append(H2("5.1 Hyperthyroidism (Thyrotoxicosis)"))
story.append(P("<b>Causes (in order of frequency):</b> Graves' disease (80%), toxic multinodular goitre, toxic adenoma (Plummer's disease), subacute thyroiditis, excess iodine (Jod-Basedow), amiodarone, TSH-secreting pituitary adenoma, factitious thyrotoxicosis."))

story.append(H3("Graves' Disease"))
story.append(P("An autoimmune condition caused by stimulating TSH-receptor antibodies (TRAb/LATS). More common in women (F:M = 7:1), peak incidence 30–50 years."))
story.append(B("<b>Triad:</b> Diffuse goitre + thyrotoxicosis + ophthalmopathy (Graves' orbitopathy)."))
story.append(B("<b>Graves' orbitopathy:</b> Caused by autoimmune inflammation of orbital fibroblasts and extraocular muscles. Presents with proptosis, chemosis, lid retraction, lid lag, diplopia, corneal exposure. Classified by NOSPECS or CAS (Clinical Activity Score)."))
story.append(B("<b>Other features:</b> Pretibial myxoedema (scleromyxoedema of skin over shins), thyroid acropachy."))
story.append(B("<b>Management:</b> (1) Antithyroid drugs (carbimazole, PTU) – first-line; (2) Radioactive iodine (¹³¹I) – definitive; (3) Thyroidectomy – for large goitres, suspicious nodules, compliance issues, or failure of medical therapy."))

story.append(H3("Thyroid Storm"))
story.append(HL("Thyroid storm is a life-threatening exacerbation of thyrotoxicosis. Precipitants: surgery, infection, trauma, radioiodine. Features: hyperthermia (>38.5°C), tachycardia/arrhythmias, CNS dysfunction (agitation, delirium, seizures, coma), GI symptoms. Treatment: supportive care, beta-blockers (IV propranolol), PTU (blocks synthesis + peripheral conversion), Lugol's iodine (given 1 hr after PTU), hydrocortisone, cooling measures."))

story.append(H2("5.2 Hypothyroidism"))
story.append(P("<b>Causes:</b> Autoimmune (Hashimoto's thyroiditis – most common cause of hypothyroidism in iodine-sufficient areas), post-thyroidectomy, post-radioiodine, iodine deficiency (worldwide most common cause), congenital (TSH receptor mutation, thyroid dysgenesis, Pendred syndrome)."))
story.append(B("<b>Primary hypothyroidism:</b> Elevated TSH, low Free T4."))
story.append(B("<b>Secondary/central hypothyroidism:</b> Low TSH, low Free T4 (pituitary/hypothalamic disease)."))
story.append(B("<b>Subclinical hypothyroidism:</b> Elevated TSH, normal Free T4. Treat if TSH >10 mIU/L, symptoms, or pregnancy."))
story.append(B("<b>Myxoedema coma:</b> Rare, life-threatening decompensation. Features: hypothermia, bradycardia, hypoventilation, hyponatraemia, decreased GCS. Treatment: IV T3 or T4, hydrocortisone, supportive care."))
story.append(B("<b>Treatment:</b> Levothyroxine (T4) oral replacement. Starting dose 1.6 µg/kg/day; lower doses in elderly and cardiac patients. Target: normalise TSH."))

story.append(H2("5.3 Goitre"))
story.append(P("Any enlargement of the thyroid gland. Classification:"))
story.append(B("<b>Diffuse:</b> Graves' disease, Hashimoto's thyroiditis (early), simple/colloid goitre, iodine deficiency."))
story.append(B("<b>Nodular:</b> Simple nodular goitre, multinodular goitre, adenoma, carcinoma."))
story.append(B("<b>Substernal/retrosternal goitre:</b> Inferior extension below the thoracic inlet. Presents with superior vena cava syndrome, dysphagia, stridor. Pemberton's sign: elevation of arms causes facial congestion and stridor."))
story.append(B("<b>WHO goitre grading:</b> Grade 0 (no goitre); Grade 1 (palpable but not visible); Grade 2 (visible with neck in normal position)."))

story.append(H2("5.4 Hashimoto's Thyroiditis (Autoimmune Thyroiditis)"))
story.append(P("The most common cause of hypothyroidism in the developed world. Characterized by anti-TPO and anti-thyroglobulin antibodies, lymphocytic infiltration, Hürthle cell change, and follicular atrophy. Stages: initial hyperthyroid (Hashitoxicosis) → euthyroid → hypothyroid. Increased risk of primary thyroid lymphoma (B-cell, MALT type)."))

story.append(H2("5.5 De Quervain's (Subacute Granulomatous) Thyroiditis"))
story.append(P("Painful, usually post-viral thyroiditis (paramyxovirus). Phases: (1) thyrotoxicosis (follicle destruction releasing hormone); (2) hypothyroidism; (3) recovery. Elevated ESR, low radioiodine uptake, tender thyroid. Treatment: NSAIDs; steroids for severe pain."))

story.append(H2("5.6 Thyroid Nodules"))
story.append(HL("Clinical rule: 5% of thyroid nodules are malignant. The risk of malignancy is the same in a solitary nodule and in the dominant nodule of a multinodular gland."))
story.append(P("Features suggesting malignancy: age <20 or >70, male sex, hard/fixed consistency, rapid growth, lymphadenopathy, hoarseness, history of neck irradiation, family history of medullary cancer or MEN."))
story.append(P("Work-up: TSH (if low → radionuclide scan first), USS (TIRADS), FNAC (Bethesda classification)."))

bethesda_data = [
    ["Bethesda Category", "Cytology", "Malignancy Risk", "Action"],
    ["I", "Non-diagnostic", "1–4%", "Repeat FNAC with USS guidance"],
    ["II", "Benign", "0–3%", "Clinical follow-up"],
    ["III", "Atypia of undetermined significance (AUS)", "~10–30%", "Repeat FNAC or molecular testing"],
    ["IV", "Follicular neoplasm / Hürthle cell neoplasm", "25–40%", "Lobectomy / molecular testing"],
    ["V", "Suspicious for malignancy", "50–75%", "Total thyroidectomy"],
    ["VI", "Malignant", "97–99%", "Total thyroidectomy"],
]
bt = Table(bethesda_data, colWidths=[2.5*cm, 4*cm, 3*cm, 6.5*cm])
bt.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), TABLE_H),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 8.0),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 5),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(bt)
story.append(Cap("Table 5. Bethesda Classification of Thyroid FNA Cytology. (Cummings, Ch.122)"))

story.append(H2("5.7 Thyroid Cancer"))
story.append(P("Thyroid cancer accounts for approximately 37,000 new cases per year in the USA. The 10-year disease-specific mortality rate is <7% for PTC and <15% for FTC. Most patients with well-differentiated carcinomas have an excellent prognosis."))

cancer_data = [
    ["Type", "Frequency", "Origin", "Characteristics", "Prognosis"],
    ["Papillary Thyroid Carcinoma (PTC)", "~85%", "Follicular cells", "Psammoma bodies; 'Orphan Annie eye' nuclei; ground-glass nuclei; nuclear grooves; RET/PTC, BRAF mutations; lymph node spread common", "Excellent; >95% 10-yr survival"],
    ["Follicular Thyroid Carcinoma (FTC)", "~10%", "Follicular cells", "Requires capsular/vascular invasion for diagnosis (FNA cannot distinguish from adenoma); haematogenous spread (bone, lung); RAS, PTEN mutations", "Good; 85–90% 10-yr survival"],
    ["Hürthle Cell Carcinoma", "~3%", "Oncocytic follicular cells", "Variant of FTC; often multifocal, bilateral; radioiodine-resistant", "Intermediate"],
    ["Medullary Thyroid Carcinoma (MTC)", "~3–5%", "Parafollicular C cells", "Secretes calcitonin and CEA; 25% familial (RET mutations; MEN2A, MEN2B, FMTC); desmoplastic stroma with amyloid", "Intermediate; 80% 10-yr if localized"],
    ["Anaplastic Thyroid Carcinoma (ATC)", "~1–2%", "Follicular cells (dedifferentiated)", "Rapidly fatal; presents with rapidly growing hard mass; airway compromise; average survival <6 months", "Poor; almost universally fatal"],
    ["Primary Thyroid Lymphoma", "<1%", "B lymphocytes", "Background Hashimoto's; MALT type; presents with rapidly enlarging goitre; chemosensitive/radiosensitive", "Good with treatment"],
]
ct = Table(cancer_data, colWidths=[3.2*cm, 1.8*cm, 2*cm, 5.5*cm, 3.5*cm])
ct.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), SUBH_BG),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("TEXTCOLOR",    (0,0), (-1,0), colors.white),
    ("FONTNAME",     (0,1), (0,-1), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 7.5),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 4),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(ct)
story.append(Cap("Table 6. Classification, features and prognosis of thyroid carcinomas. (Cummings, Ch.122)"))
story.append(SP())

story.append(H3("Staging of Differentiated Thyroid Cancer (ATA/AJCC)"))
story.append(P("Risk stratification (ATA guidelines) guides extent of surgery and adjuvant therapy:"))
story.append(B("<b>Low risk:</b> Intrathyroidal PTC, no vascular invasion, ≤5 microscopic lymph nodes, no distant metastases."))
story.append(B("<b>Intermediate risk:</b> Aggressive histology, minor extrathyroidal extension, vascular invasion, >5 lymph nodes."))
story.append(B("<b>High risk:</b> Gross extrathyroidal extension, incomplete resection, distant metastases, extrathyroidal PTC with any T4, all ATC."))
story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 6: SURGICAL PROCEDURES
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("6. SURGICAL PROCEDURES"))
story.append(SP())

story.append(H2("6.1 Types of Thyroid Surgery"))
story.append(P("The following nomenclature (from Scott-Brown's) should be used consistently:"))
surg_types = [
    ["Procedure", "Definition", "Indication"],
    ["Total Lobectomy (TL)", "Removal of one entire lobe, usually with isthmusectomy", "Diagnostic (indeterminate FNAC), unilateral benign nodule, thyroid cysts"],
    ["Thyroid Isthmusectomy", "Excision of the isthmus ± pyramidal lobe", "Nodule confined to isthmus ≤4 cm"],
    ["Subtotal Thyroidectomy (ST)", "Bilateral excision of >50% gland on each side + isthmus", "HISTORICALLY used for Graves'; NOT recommended now"],
    ["Near-Total / Dunhill's Thyroidectomy", "90% excision; small remnant left at Berry ligament on one side", "Alternative to total for Graves' or MNG"],
    ["Total Thyroidectomy (TT)", "Removal of entire thyroid gland", "Thyroid cancer, bilateral MNG, Graves' disease, large goitres"],
    ["Completion Thyroidectomy", "Removal of residual thyroid after prior lobectomy", "Malignancy found on final histology after lobectomy"],
]
stt = Table(surg_types, colWidths=[3.5*cm, 6*cm, 6.5*cm])
stt.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), TABLE_H),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("FONTNAME",     (0,1), (0,-1), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 8.0),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 5),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(stt)
story.append(Cap("Table 7. Types of thyroid surgery and indications. (Scott-Brown's, Ch.67)"))
story.append(SP())

story.append(H2("6.2 Pre-operative Considerations"))
story.append(B("1. Full clinical, cytological/histopathological evidence and adequate imaging should be available."))
story.append(B("2. Pre-operative laryngoscopy (fibreoptic) to assess vocal cord mobility – mandatory in all patients."))
story.append(B("3. Patient must be euthyroid; thyrotoxic patients need pre-operative preparation to prevent thyroid storm (carbimazole + Lugol's iodine for 10 days before surgery)."))
story.append(B("4. Informed consent covering: RLN injury (0.5–2%), hypoparathyroidism (1–3% permanent), bleeding/haematoma, wound complications, hypothyroidism."))
story.append(B("5. General anaesthesia with north-facing (Ring-Adair-Elwyn) endotracheal tube to keep the tube away from the operative field."))
story.append(B("6. Intraoperative nerve monitoring (IONM) of RLN recommended."))
story.append(B("7. Neuromonitoring probes, surgical loops/microscope, fine bipolar forceps, energy devices (Harmonic scalpel, LigaSure) should be available."))
story.append(SP())

story.append(H2("6.3 Standard (Open) Thyroidectomy – Surgical Technique"))
story.append(H3("Positioning"))
story.append(P("Supine position, soft shoulder support under the neck and soft head ring to allow maximum neck extension. Arms tucked at sides. A pillow under the knees for comfort. Adequate padding of pressure points."))

# Patient positioning image
img_pos = fetch_image_from_url(
    "https://cdn.orris.care/cdss_images/322caed0936e4deb6642598702cc06b30183b4903666ab057713546f28bf7174.png",
    max_width=10*cm, max_height=6*cm
)
if img_pos:
    story.append(img_pos)
    story.append(Cap("Fig. 3 – Patient position for thyroidectomy: supine with neck extension. (Scott-Brown's, Fig. 67.1)"))
    story.append(SP())

story.append(H3("Kocher Collar Incision"))
story.append(P("The classical Kocher collar incision: a transverse cervical skin crease incision placed <b>halfway between the cricoid cartilage and the sternal notch</b>. Planning considerations:"))
story.append(B("<b>Length:</b> Minimum 3–4 cm; may be extended for large goitres. Must provide access to the superior, inferior and lateral aspects."))
story.append(B("<b>Symmetry:</b> Must be symmetrical across the midline to avoid cosmetic asymmetry."))
story.append(B("<b>Crease placement:</b> Placing the incision in a natural skin crease gives the best cosmetic result."))

story.append(H3("Step-by-Step Operative Technique"))
story.append(P("1. <b>Incision:</b> Kocher collar incision through skin, platysma, and subcutaneous tissue. Subplatysmal flaps raised superiorly to the level of the thyroid notch and inferiorly to the sternal notch."))
story.append(P("2. <b>Midline division:</b> Strap muscles (sternohyoid and sternothyroid) divided in the midline raphe. Strap muscles are retracted laterally. Division of strap muscles is only needed for large goitres or malignancy; prefer to retract intact when possible."))
story.append(P("3. <b>Identification of superior pole:</b> Superior pole vessels identified and ligated individually, as close to the gland as possible, to preserve the EBSLN."))
story.append(P("4. <b>Identification and preservation of RLN:</b> The RLN is identified in the tracheo-oesophageal groove or at the level of the Berry ligament. IONM probe confirms identity. The nerve is traced throughout its course and protected."))
story.append(P("5. <b>Identification of parathyroid glands:</b> All four glands identified and carefully preserved with their blood supply. Any inadvertently devascularized or removed gland is auto-transplanted to the sternocleidomastoid or forearm."))
story.append(P("6. <b>Division of Berry ligament:</b> The Berry ligament is carefully divided close to the trachea. The RLN passes through or immediately adjacent to it."))
story.append(P("7. <b>Lobe removal:</b> The lobe is rolled medially and inferiorly. The inferior thyroid artery branches are ligated close to the gland. The lobe is separated from the trachea."))
story.append(P("8. <b>Contralateral lobe:</b> For total thyroidectomy, the procedure is repeated on the contralateral side."))
story.append(P("9. <b>Haemostasis and closure:</b> Meticulous haemostasis. Closed suction drain placed if significant raw surfaces. Strap muscles approximated, platysma closed, skin closed with subcuticular suture."))
story.append(SP())

story.append(H2("6.4 Minimally Invasive and Endoscopic Thyroidectomy"))
story.append(P("Minimally invasive approaches have evolved to reduce scar visibility:"))
story.append(B("<b>Minimally invasive video-assisted thyroidectomy (MIVAT):</b> Described by Miccoli; incision as small as 1.5 cm; uses endoscopic instruments through the incision. Best for small glands, benign lesions, PTC <2 cm."))
story.append(B("<b>Robot-assisted transaxillary thyroidectomy (RATS):</b> Gasless approach via single axillary incision using da Vinci robotic system; developed by Kang et al. (2009). Large Korean series with low complication rates. Complications in Western centres include brachial plexopathies, vascular injury, RLN injury."))
story.append(B("<b>Robotic facelift thyroidectomy:</b> Uses postauricular (facelift-type) incision; dissection along sternocleidomastoid. Completely avoids a cervical scar."))
story.append(B("<b>Transoral endoscopic thyroidectomy via vestibular approach (TOETVA):</b> Entirely through the oral vestibule; no external incision. Growing evidence base."))

# Robotic thyroidectomy image
img_robot = fetch_image_from_url(
    "https://cdn.orris.care/cdss_images/7995f23efc6c9854b464eeeff81199424d4b1632cb0ea9be6ea625ba24653ca0.png",
    max_width=11*cm, max_height=7*cm
)
if img_robot:
    story.append(img_robot)
    story.append(Cap("Fig. 4 – Robotic axillary thyroidectomy: rigid retractor maintains the operative pocket. (Cummings, Fig. 124.9)"))
    story.append(SP())

story.append(H2("6.5 Central Neck Dissection (Level VI)"))
story.append(P("Removal of pretracheal, prelaryngeal (Delphian), and bilateral paratracheal lymph nodes. Indicated in:"))
story.append(B("<b>Therapeutic CND:</b> Clinically or radiologically positive central nodes (cN1b)."))
story.append(B("<b>Prophylactic CND:</b> Controversial; may be considered in T3/T4 tumours, high-risk PTC, or MTC."))
story.append(P("Complications: hypoparathyroidism (rates higher than total thyroidectomy alone), RLN injury."))

story.append(H2("6.6 Lateral Neck Dissection"))
story.append(P("Modified radical neck dissection (MRND) or selective neck dissection (levels II–V) for lateral compartment nodal metastases (cN1b). Preserves the sternocleidomastoid muscle, internal jugular vein, and spinal accessory nerve."))

story.append(H2("6.7 Sistrunk Operation (for Thyroglossal Duct Cyst)"))
story.append(P("Standard operation for thyroglossal duct cyst. Key steps:"))
story.append(B("1. Horizontal elliptical incision over the cyst."))
story.append(B("2. En-bloc removal of the cyst, thyroglossal tract, and the <b>central portion of the hyoid bone</b> (essential to reduce recurrence rate from ~50% to <5%)."))
story.append(B("3. Dissection traced to the base of tongue, where the tract is ligated and divided."))
story.append(B("4. Recurrence rate without hyoid resection: ~50%; with Sistrunk operation: <5%."))

story.append(H2("6.8 Radioiodine Therapy (¹³¹I)"))
story.append(P("Post-surgical adjuvant for differentiated thyroid cancer. Indications based on ATA risk stratification:"))
story.append(B("<b>Remnant ablation:</b> Destroys residual thyroid tissue; facilitates follow-up with Tg monitoring and whole-body scanning."))
story.append(B("<b>Adjuvant therapy:</b> Treatment of presumed microscopic residual disease."))
story.append(B("<b>Therapeutic:</b> Treatment of known residual or metastatic disease."))
story.append(P("Requires TSH stimulation (thyroid hormone withdrawal or recombinant TSH [Thyrogen]). Given as outpatient capsule. Radiation precautions observed for 3–5 days."))

story.append(H2("6.9 Complications of Thyroidectomy"))
comp_data = [
    ["Complication", "Incidence", "Mechanism", "Management"],
    ["RLN injury – temporary", "~5%", "Traction, thermal, devascularisation; resolves by 6 months", "Voice therapy, monitor; >95% recover"],
    ["RLN injury – permanent", "0.5–2%", "Transection or devascularisation", "Voice therapy; medialization laryngoplasty if unilateral; tracheostomy if bilateral"],
    ["Hypoparathyroidism – temporary", "~20%", "Devascularisation of parathyroid glands", "Oral calcium ± calcitriol; monitor PTH/Ca²⁺; resolves in weeks–months"],
    ["Hypoparathyroidism – permanent", "1–3%", "Inadvertent removal or devascularisation of all glands", "Long-term calcium + calcitriol; consider rh-PTH (teriparatide)"],
    ["Post-op haematoma", "~0.5–1%", "Inadequate haemostasis; may cause airway compromise", "Surgical emergency: open wound at bedside; return to theatre"],
    ["Hypothyroidism", "100% after TT", "Loss of thyroid tissue", "Lifelong levothyroxine replacement"],
    ["Wound infection/seroma", "1–2%", "Superficial or deep; seroma more common", "Antibiotics; aspiration"],
    ["Tracheomalacia", "Rare, after large goitres", "Softening of tracheal rings after prolonged compression", "Usually managed with ETT; rarely tracheostomy"],
]
compt = Table(comp_data, colWidths=[3.5*cm, 2*cm, 5*cm, 5.5*cm])
compt.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), SUBH_BG),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("TEXTCOLOR",    (0,0), (-1,0), colors.white),
    ("FONTNAME",     (0,1), (0,-1), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 7.5),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 4),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(compt)
story.append(Cap("Table 8. Complications of thyroidectomy with incidence, mechanism and management. (Scott-Brown's Ch.67, Cummings Ch.122)"))
story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 7: THYROID ULTRASOUND AND TIRADS
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("7. THYROID ULTRASOUND AND TIRADS"))
story.append(SP())

story.append(P("Ultrasound is the primary imaging modality for thyroid nodule assessment. The ACR-TIRADS (Thyroid Imaging Reporting and Data System) provides a standardised scoring system:"))

tirads_data = [
    ["Category", "Features", "Malignancy Risk", "FNA Threshold"],
    ["TR1 – Benign", "Purely cystic or almost entirely cystic", "<1%", "No FNA needed"],
    ["TR2 – Not Suspicious", "Spongiform nodule or nearly cystic", "<2%", "No FNA needed"],
    ["TR3 – Mildly Suspicious", "No suspicious features; iso- or hyperechoic, oval shape", "~5%", "FNA if ≥2.5 cm"],
    ["TR4 – Moderately Suspicious", "One suspicious feature: hypoechoic, non-oval, lobulated/irregular margin, punctate echogenic foci", "~15%", "FNA if ≥1.5 cm"],
    ["TR5 – Highly Suspicious", "≥2 suspicious features: markedly hypoechoic, non-oval, lobulated margin, punctate calcifications, extra-thyroidal extension", ">35%", "FNA if ≥1 cm"],
]
tt = Table(tirads_data, colWidths=[3*cm, 5.5*cm, 2.5*cm, 5*cm])
tt.setStyle(TableStyle([
    ("BACKGROUND",   (0,0), (-1,0), TABLE_H),
    ("FONTNAME",     (0,0), (-1,0), "Helvetica-Bold"),
    ("FONTNAME",     (0,1), (0,-1), "Helvetica-Bold"),
    ("FONTSIZE",     (0,0), (-1,-1), 8.0),
    ("ROWBACKGROUNDS",(0,1),(-1,-1), [colors.white, TABLE_ALT]),
    ("BOX",          (0,0), (-1,-1), 0.5, TEAL),
    ("INNERGRID",    (0,0), (-1,-1), 0.3, HexColor("#ccddee")),
    ("TOPPADDING",   (0,0), (-1,-1), 4),
    ("BOTTOMPADDING",(0,0), (-1,-1), 4),
    ("LEFTPADDING",  (0,0), (-1,-1), 5),
    ("VALIGN",       (0,0), (-1,-1), "TOP"),
]))
story.append(tt)
story.append(Cap("Table 9. ACR-TIRADS classification for thyroid nodule risk stratification. (Cummings, Ch.122)"))
story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 8: SPECIAL SITUATIONS
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("8. SPECIAL SITUATIONS"))
story.append(SP())

story.append(H2("8.1 Thyroid Disease in Pregnancy"))
story.append(B("Physiological changes: increased TBG (oestrogen effect), increased total T4 and T3, hCG stimulates TSH receptors in first trimester causing gestational hyperthyroidism."))
story.append(B("<b>Hypothyroidism:</b> Most common; treat with levothyroxine. Dose requirements increase ~45% in pregnancy. Target TSH <2.5 mIU/L in first trimester."))
story.append(B("<b>Graves' disease in pregnancy:</b> PTU preferred in first trimester (risk of carbimazole embryopathy); switch to carbimazole in second and third trimesters (PTU hepatotoxicity risk). Avoid radioiodine. Surgery if required – best in second trimester."))
story.append(B("<b>Thyroid cancer in pregnancy:</b> If PTC found, can observe with serial USS until delivery; surgery if rapid growth or lymph nodes positive."))

story.append(H2("8.2 Thyroid Incidentaloma"))
story.append(P("Thyroid nodules found incidentally on CT, MRI or PET-CT. PET-avid nodules carry a ~30% malignancy risk; all require USS and FNAC. CT-detected nodules >1 cm require USS follow-up."))

story.append(H2("8.3 Graves' Orbitopathy"))
story.append(P("Managed jointly by endocrinology and ophthalmology. Severity graded by NOSPECS or CAS. Active moderate-to-severe disease: IV methylprednisolone pulse therapy (EUGOGO protocol). Rehabilitative surgery for inactive disease: orbital decompression, squint surgery, lid surgery."))

story.append(H2("8.4 Thyroid Storm – Diagnostic Criteria (Burch-Wartofsky Score)"))
story.append(P("The Burch-Wartofsky Point Scale (BWPS) is used to estimate likelihood of thyroid storm. Factors assessed: temperature, CNS disturbance, cardiovascular effects (heart rate, AF, heart failure), GI/hepatic dysfunction, precipitating cause. Score ≥45 = thyroid storm; 25–44 = impending storm; <25 = unlikely."))
story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# SECTION 9: KEY POINTS SUMMARY
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("9. KEY CLINICAL PEARLS"))
story.append(SP())

pearls = [
    "A thyroid swelling moves upward on swallowing but NOT on tongue protrusion (unlike a thyroglossal cyst).",
    "A thyroid bruit is virtually pathognomonic of Graves' disease (hypervascularity due to TRAb stimulation).",
    "Hard, fixed thyroid mass with hoarseness = carcinoma until proven otherwise.",
    "The RLN passes through or immediately adjacent to the Berry ligament – the most dangerous point in thyroidectomy.",
    "The Delphian (prelaryngeal) node, when hard and enlarged, strongly suggests thyroid malignancy.",
    "FNA cannot distinguish follicular adenoma from follicular carcinoma; diagnosis requires demonstration of capsular/vascular invasion on histology.",
    "Papillary thyroid cancer spreads via lymphatics (lateral aberrant thyroid = nodal PTC metastasis); follicular cancer spreads haematogenously.",
    "C cells (origin of medullary thyroid carcinoma) are concentrated in the middle-upper third of lateral lobes – the area at highest risk of malignancy in MTC.",
    "Before removing a lingual thyroid, always confirm it is not the ONLY thyroid tissue (⁹⁹ᵐTc scan).",
    "Post-thyroidectomy hypocalcaemia: most common cause of readmission after thyroidectomy. Check 6-hr post-op PTH; if low, begin oral calcium + calcitriol preemptively.",
    "Non-recurrent RLN: occurs on the right side only (0.5–2%); associated with aberrant right subclavian artery (arteria lusoria). The surgeon must anticipate this variant.",
    "Pemberton's sign (facial flushing and stridor on arm elevation) = retrosternal goitre compressing superior thoracic inlet.",
]
for i, pearl in enumerate(pearls, 1):
    story.append(HL(f"<b>{i}.</b>  {pearl}"))
    story.append(SP(3))

story.append(SP(10))

# ─────────────────────────────────────────────────────────────────────────────
# REFERENCES
# ─────────────────────────────────────────────────────────────────────────────
story.append(H1("10. REFERENCES"))
story.append(SP())
refs = [
    "1. Watkinson JC, Clarke RW. Scott-Brown's Otorhinolaryngology Head & Neck Surgery, 8th Edition. CRC Press, 2018. Chapters 53 (Developmental Anatomy), 55 (Physiology), 67 (Thyroid Surgery), 68 (Scott-Brown Vol 1).",
    "2. Flint PW, Haughey BH, Lund VJ, et al. Cummings Otolaryngology Head and Neck Surgery, 7th Edition. Elsevier, 2021. Chapters 121 (Thyroid Physiology), 122 (Thyroid Cancer & Surgery), 124 (Minimally Invasive Approaches).",
    "3. Haugen BR, Alexander EK, Bible KC, et al. 2015 American Thyroid Association Management Guidelines for Adult Patients with Thyroid Nodules and Differentiated Thyroid Cancer. Thyroid 2016;26(1):1–133.",
    "4. Tessler FN, Middleton WD, Grant EG, et al. ACR Thyroid Imaging, Reporting and Data System (TI-RADS). J Am Coll Radiol 2017;14(5):587–595.",
    "5. Cibas ES, Ali SZ. The 2017 Bethesda System for Reporting Thyroid Cytopathology. Thyroid 2017;27(11):1341–1346.",
    "6. Burch HB, Wartofsky L. Life-threatening thyrotoxicosis. Thyroid storm. Endocrinol Metab Clin North Am 1993;22(2):263–277.",
    "7. Bartalena L, Baldeschi L, Boboridis K, et al. The 2016 European Thyroid Association/European Group on Graves' Orbitopathy Guidelines for the Management of Graves' Orbitopathy. Eur Thyroid J 2016;5(1):9–26.",
    "8. Kang SW, Jeong JJ, Nam KH, et al. Robot-assisted endoscopic thyroidectomy for thyroid malignancies using a gasless transaxillary approach. J Am Coll Surg 2009;209(2):e1–7.",
]
for ref in refs:
    story.append(Ref(ref))
    story.append(SP(3))

story.append(SP(10))
story.append(HR())
story.append(P("<i>This document was compiled from Scott-Brown's Otorhinolaryngology Head &amp; Neck Surgery (8th Ed.) and Cummings Otolaryngology Head and Neck Surgery (7th Ed.) for educational purposes only. Clinical decision-making must be guided by current institutional guidelines and the latest evidence-based literature.</i>"))

# ─────────────────────────────────────────────────────────────────────────────
# PAGE NUMBERS AND HEADERS
# ─────────────────────────────────────────────────────────────────────────────
def add_page_number(canvas_obj, doc):
    canvas_obj.saveState()
    page_num = canvas_obj.getPageNumber()
    if page_num == 1:
        canvas_obj.restoreState()
        return
    # Header
    canvas_obj.setFont("Helvetica-Bold", 8)
    canvas_obj.setFillColor(NAVY)
    canvas_obj.drawString(2.2*cm, H - 1.5*cm, "THYROID GLAND – Comprehensive Clinical Reference")
    canvas_obj.setFont("Helvetica", 8)
    canvas_obj.setFillColor(TEAL)
    canvas_obj.drawRightString(W - 2.2*cm, H - 1.5*cm, "Scott-Brown's  |  Cummings")
    canvas_obj.setStrokeColor(TEAL)
    canvas_obj.setLineWidth(0.5)
    canvas_obj.line(2.2*cm, H - 1.7*cm, W - 2.2*cm, H - 1.7*cm)
    # Footer
    canvas_obj.setStrokeColor(HexColor("#ccddee"))
    canvas_obj.line(2.2*cm, 1.6*cm, W - 2.2*cm, 1.6*cm)
    canvas_obj.setFont("Helvetica", 8)
    canvas_obj.setFillColor(HexColor("#778899"))
    canvas_obj.drawCentredString(W/2, 1.1*cm, f"Page {page_num}")
    canvas_obj.restoreState()

# Build PDF
doc.build(story, onFirstPage=add_page_number, onLaterPages=add_page_number)
print(f"PDF created: {OUTPUT}")
print(f"File size: {os.path.getsize(OUTPUT):,} bytes")
Running Command

cd /tmp/workspace/thyroid-pdf && python generate_thyroid_pdf.py 2>&1

Your credits are exhausted. You can purchase a top-up or subscribe to a plan to continue using Orris. If you're already subscribed, your daily credits will reset tomorrow.
This is a shared conversation. Sign in to Orris to start your own chat.