Give a detail explanation on anatomy, examination, investigations, rehabilitation exercises & add PROMS with treatment including ayurveda part
"knee osteoarthritis"[MeSH Terms] AND "rehabilitation"[MeSH Terms]
knee joint Ayurveda treatment Janu Basti Panchakarma osteoarthritis 2024
"knee"[MeSH Terms] AND "patient reported outcome"[MeSH Terms] AND "exercise"[MeSH Terms]
"knee osteoarthritis" AND "exercise therapy"
KOOS WOMAC Oxford Knee Score patient reported outcome measures knee joint physiotherapy
https://pmc.ncbi.nlm.nih.gov/articles/PMC12444219
knee rehabilitation exercises phases ACL meniscal OA physiotherapy protocol 2024
| Structure | Key Points |
|---|---|
| Distal Femur | Medial and lateral condyles; intercondylar notch houses the cruciate ligaments |
| Proximal Tibia | Medial and lateral tibial plateaus; tibial tuberosity (insertion of patellar tendon); Gerdy's tubercle (IT band insertion) |
| Patella | Largest sesamoid bone; acts as a pulley for quadriceps; has the thickest articular cartilage in the body (designed for loads up to 20x body weight) |
| Fibular Head | Provides attachment for the LCL and biceps femoris |
| Feature | Medial Meniscus | Lateral Meniscus |
|---|---|---|
| Shape | C-shaped (more open) | O-shaped (more circular) |
| Mobility | Less mobile (attached to MCL & capsule) | More mobile |
| Blood supply | Outer 1/3 (red zone) only | Outer 1/3 |
| Injury frequency | More commonly torn | Less commonly torn |
| Group | Muscles | Function |
|---|---|---|
| Extensors | Quadriceps | Knee extension; stabilize patella |
| Flexors/Rotators | Hamstrings (biceps femoris, semimembranosus, semitendinosus) | Flexion; tibial rotation |
| Pes Anserinus | Sartorius, gracilis, semitendinosus | Medial stabilizers; attach on proximal medial tibia |
| IT Band | TFL + gluteus maximus | Lateral stabilizer via Gerdy's tubercle |
| Popliteus | Popliteus | "Unlocks" knee from full extension; resists posterolateral rotation |

| Investigation | Indications | Key Findings |
|---|---|---|
| Plain X-ray (weight-bearing AP, lateral, skyline) | First-line for OA, fractures, alignment | OA: joint space narrowing, subchondral sclerosis, osteophytes, subchondral cysts; Always do weight-bearing to show true joint space |
| MRI | Soft tissue pathology - first choice for meniscal tears, ligament injuries, cartilage defects, bone marrow oedema | Not routinely needed pre-TKR; most sensitive for ACL, meniscal, chondral assessment |
| CT scan | Complex intra-articular fractures, tibial plateau fractures, rotational alignment, pre-op planning | Bony detail; CT arthrogram when MRI contraindicated |
| Ultrasound | Soft tissue - Baker's cyst, popliteal vessels, tendon assessment; guided injections | Dynamic assessment of tendon; effusion aspiration guidance |
| Bone scan (SPECT/CT) | Occult fractures, stress fractures, osteonecrosis, infection | Increased uptake in active bone pathology |
| Grade | Description |
|---|---|
| 0 | Normal |
| 1 | Doubtful narrowing; possible osteophyte |
| 2 | Definite osteophyte; possible joint space narrowing |
| 3 | Multiple osteophytes; definite narrowing; some sclerosis |
| 4 | Large osteophytes; marked narrowing; severe sclerosis; possible bony deformity |
| Test | Purpose |
|---|---|
| FBC, CRP, ESR | Infection, inflammatory arthritis |
| Rheumatoid factor, anti-CCP | Rheumatoid arthritis |
| Uric acid | Gout (though normal during acute attack) |
| ANA, dsDNA | SLE |
| HLA-B27 | Seronegative spondyloarthropathy |
| Blood cultures | Septic arthritis |
| Coagulation | Pre-operative |
| Parameter | Normal | OA | Inflammatory | Septic |
|---|---|---|---|---|
| Appearance | Clear | Yellow, clear | Yellow, turbid | Purulent, opaque |
| WBC/mm³ | < 200 | < 2,000 | 2,000-50,000 | > 50,000 |
| PMN% | < 25% | < 25% | > 50% | > 75% |
| Glucose | = serum | = serum | ↓ | << serum |
| Culture | Negative | Negative | Negative | Positive |
| Crystals | None | None | Gout (urate), CPPD (pyrophosphate) | None |

| Exercise | Description | Sets/Reps |
|---|---|---|
| Ankle pumps | Flex/extend ankle; promote circulation | 3 × 20 |
| Quad sets (isometric) | Press back of knee to bed, contract quads | 3 × 10, hold 5s |
| Inner range quads | Knee supported at 30° under roll, extend actively | 3 × 10 |
| Straight leg raise (SLR) | Leg raised to 45°, quads contracted; all 4 planes | 3 × 10 |
| Heel slides | Slide heel to bend knee (flexion ROM) | 3 × 10 |
| Calf raises (seated) | Improve venous return | 3 × 15 |
| Ice + elevation | 20 minutes, 4-6 times/day | - |
| Exercise | Description | Sets/Reps |
|---|---|---|
| Mini squats (0-30°) | Partial weight-bearing squat, hands on support | 3 × 15 |
| Step-ups (forward & lateral) | Low step 5-10 cm; progress height gradually | 3 × 10 each side |
| Terminal knee extension (TKE) | Resistance band behind knee, extend from 30° to 0° | 3 × 15 |
| Hamstring curls (prone) | Flex knee against gravity/resistance | 3 × 12 |
| Hip abduction (side-lying) | Strengthens glute medius; reduces knee valgus | 3 × 15 |
| Static cycling | Low resistance; ROM & cardiovascular benefit | 15-20 min |
| VMO emphasis squats | Feet slightly externally rotated | 3 × 12 |
| Exercise | Description | Sets/Reps |
|---|---|---|
| Full squats (0-90°) | Bodyweight to loaded; watch for valgus collapse | 3 × 12 |
| Leg press | Controlled full ROM; start low resistance | 3 × 12 |
| Lunges (forward/lateral) | Functional multi-plane movement | 3 × 10 each leg |
| Wall squats (isometric) | Sustained quad + VMO activation | 3 × 30-60s |
| Single-leg balance | Eyes open → eyes closed → unstable surface | 3 × 30s each |
| Nordic hamstring curls | Eccentric hamstring strengthening | 3 × 8 |
| Aquatic exercises | Pool walking, pool squats; offloads joint | 20-30 min |
| Exercise | Description |
|---|---|
| Bulgarian split squats | Single-leg loaded squat |
| Box jumps / Plyometrics | ACL patients only after strength testing clears |
| Lateral band walks | Hip abductor strengthening in functional position |
| Agility ladder drills | Neuromuscular coordination |
| Running progression | Walk-jog intervals → continuous jog → sprint |
| Sport-specific drills | Cutting, pivoting, deceleration |
| PROM | Full Name | Items | Subscales | Best Used For | Score Range | Interpretation |
|---|---|---|---|---|---|---|
| KOOS | Knee Injury & Osteoarthritis Outcome Score | 42 | Pain, Symptoms, ADL, Sport/Rec, QoL | OA, ACL, Meniscal injury, TKR | 0-100 per subscale | Higher = better |
| KOOS-PS | KOOS Physical Function Short Form | 7 | Physical function | Quick functional screen | 0-100 | Higher = better |
| WOMAC | Western Ontario & McMaster Universities OA Index | 24 | Pain (5), Stiffness (2), Function (17) | Knee & hip OA | 0-96 (Likert) or 0-100 (VAS) | Lower = better |
| Oxford Knee Score (OKS) | Oxford Knee Score | 12 | Single score | TKR pre/post-op assessment | 0-48 | Higher = better |
| Lysholm Knee Scale | Lysholm Knee Scoring Scale | 8 | Limp, locking, instability, pain, swelling, stair climbing, squat | ACL, ligament injuries | 0-100 | Higher = better |
| IKDC | Int'l Knee Documentation Committee Subjective Knee Form | 18 | Symptoms, sport activity, function | Ligament/meniscal injury, ACL | 0-100 | Higher = better |
| Tegner Activity Scale | Tegner Activity Level Scale | 1 | Activity level | ACL, sports-related injury | 0-10 (0=sick leave, 10=competitive sport) | Higher = more active |
| VAS / NRS | Visual Analogue / Numeric Rating Scale | 1 | Pain intensity | Any knee condition | 0-10 | Lower = less pain |
| SF-36 / SF-12 | Short Form Health Survey | 36/12 | 8 domains, PCS + MCS | General health-related QoL | 0-100 | Higher = better |
| PROMIS | Patient-Reported Outcomes Measurement Information System | Adaptive | Pain, function, fatigue, mental health | Comprehensive; computer-adaptive | T-score (50 = norm) | Condition dependent |
| KSS | Knee Society Score | Dual | Knee score + Function score | TKR outcomes | 0-100 each | Higher = better |
| ACL-RSI | ACL Return to Sport Index | 12 | Psychological readiness | Post-ACL reconstruction | 0-100 | ≥90 = cleared psychologically |
| Clinical Scenario | Recommended PROM(s) |
|---|---|
| Knee OA (conservative management) | KOOS or WOMAC + VAS |
| ACL reconstruction | KOOS + IKDC + Lysholm + Tegner + ACL-RSI |
| Meniscal injury | KOOS + Lysholm |
| TKR/UKR | Oxford Knee Score (OKS) + KOOS + KSS |
| Patellofemoral pain | KOOS + VAS (WOMAC less specific for PFPS) |
| Research / general | PROMIS (computer-adaptive, efficient) |
| Drug Class | Examples | Use |
|---|---|---|
| Topical NSAIDs | Diclofenac gel, Ketoprofen | First-line OA; fewer GI/renal side effects |
| Oral NSAIDs | Ibuprofen, Naproxen, Celecoxib | Moderate OA, acute flares |
| Paracetamol (Acetaminophen) | Paracetamol 1g QID | Mild-moderate OA |
| Opioids | Tramadol (weak opioid) | Not recommended by AAOS for knee OA |
| Intra-articular corticosteroids | Triamcinolone, Methylprednisolone | Short-term flare control; max 3-4/year |
| Hyaluronic acid (viscosupplementation) | Synvisc, Ostenil | Evidence conflicting; not recommended by AAOS |
| Duloxetine | 60-120 mg/day | Chronic pain with central sensitization component |
| Supplements | Glucosamine, Chondroitin | Limited evidence (AAOS: limited recommendation only) |
| Procedure | Indication |
|---|---|
| Arthroscopic debridement/washout | NOT recommended for OA (AAOS strong against) |
| Arthroscopic meniscectomy | Symptomatic meniscal tear with mechanical symptoms |
| Meniscal repair | Young patient, vascular zone tear, repairable |
| ACL reconstruction | Active patients with functional instability |
| Chondrocyte transplant (MACI/ACI) | Young patient, full-thickness cartilage defect |
| Osteotomy (HTO/DFO) | Young patient, unicompartmental OA + malalignment |
| Unicompartmental knee replacement (UKR) | Single compartment OA, intact cruciate ligaments |
| Total Knee Replacement (TKR) | End-stage, multi-compartment OA; failed conservative/other surgery |
| Arthrodesis | Failed TKR, chronic septic arthritis |
| Formulation | Key Ingredients | Action |
|---|---|---|
| Yogaraja Guggulu | Guggul, triphala, trikatu, sesame oil | Anti-inflammatory, anti-arthritic; Vata pacifying |
| Trayodashanga Guggulu | Guggul + 13 herbs incl. ashwagandha | Analgesic, anti-rheumatic; Vata-pacifying |
| Laksha Guggulu | Laksha (lac), guggul, ashwagandha, nagabala | Bone and cartilage regeneration; fracture healing |
| Muktashukti Bhasma | Calcined pearl oyster shell | Calcium supplementation; anti-inflammatory |
| Ashwagandha (Withania somnifera) | Alkaloids, withanolides | Adaptogen; muscle and ligament strengthening; reduces stiffness |
| Shallaki / Boswellia serrata | Boswellic acids | Well-evidenced anti-inflammatory; inhibits 5-LOX; reduces knee OA pain |
| Guggulu (Commiphora mukul) | Guggulsterones | Anti-inflammatory; balances Vata & Kapha |
| Triphala | Amalaki, bibhitaki, haritaki | Antioxidant; Ama removal; GI support for drug absorption |
| Shatavari (Asparagus racemosus) | Steroidal saponins | Rejuvenative; anti-inflammatory |
| Punarnava (Boerhavia diffusa) | Punarnavine | Anti-oedematous; reduces joint swelling |
KNEE PAIN PRESENTATION
|
─────────────────
| |
ACUTE INJURY CHRONIC / GRADUAL ONSET
(trauma, sport) (OA, overuse, degeneration)
| |
Imaging (X-ray, Weight-bearing X-ray
MRI) + Special K-L grading
tests |
| |
DIAGNOSE: Grade I-II OA: Grade III-IV OA:
- ACL/PCL Non-operative: Surgical evaluation
- Meniscus Exercise + PT HTO / UKR / TKR
- Ligament NSAIDs (topical)
- Fracture Weight loss
Ayurveda + Physio
| (Janu Basti +
| Strengthening exercises)
Surgical or |
conservative PROM monitoring:
decision KOOS / WOMAC / OKS
|
Rehabilitation
(Phased - Phase 1 to 4)
PROMS at baseline, 6 weeks, 3 months, 6 months, 1 year
Generate a rehabilitation protocol PDF with exercise progression charts
mkdir -p /home/daytona/workspace/knee-rehab-pdf && ls /home/daytona/workspace/kn…
~/knee-rehab-pdf/generate_pdf.py
#!/usr/bin/env python3
"""
Knee Rehabilitation Protocol PDF Generator
Uses reportlab for PDF creation and matplotlib for charts.
"""
import matplotlib
matplotlib.use('Agg')
import matplotlib.pyplot as plt
import matplotlib.patches as mpatches
import numpy as np
import os
import io
from reportlab.lib.pagesizes import A4
from reportlab.lib import colors
from reportlab.lib.units import mm, cm
from reportlab.lib.styles import getSampleStyleSheet, ParagraphStyle
from reportlab.lib.enums import TA_CENTER, TA_LEFT, TA_RIGHT, TA_JUSTIFY
from reportlab.platypus import (
SimpleDocTemplate, Paragraph, Spacer, Table, TableStyle,
PageBreak, HRFlowable, Image, KeepTogether
)
from reportlab.platypus.flowables import Flowable
from reportlab.lib.colors import HexColor, white, black
# ── Colour palette ──────────────────────────────────────────────────────────
C_DARK_BLUE = HexColor('#1A3A5C')
C_MID_BLUE = HexColor('#2B6CB0')
C_LIGHT_BLUE = HexColor('#EBF4FF')
C_ACCENT = HexColor('#E53E3E')
C_TEAL = HexColor('#2C7A7B')
C_GREEN = HexColor('#276749')
C_LIGHT_GREEN = HexColor('#F0FFF4')
C_AMBER = HexColor('#C05621')
C_LIGHT_AMBER = HexColor('#FFFAF0')
C_PURPLE = HexColor('#553C9A')
C_LIGHT_GREY = HexColor('#F7FAFC')
C_MID_GREY = HexColor('#718096')
C_BORDER = HexColor('#CBD5E0')
OUTPUT_DIR = '/home/daytona/workspace/knee-rehab-pdf'
os.makedirs(OUTPUT_DIR, exist_ok=True)
# ── Custom styles ────────────────────────────────────────────────────────────
def build_styles():
base = getSampleStyleSheet()
styles = {}
styles['cover_title'] = ParagraphStyle(
'cover_title', parent=base['Title'],
fontSize=32, textColor=white, leading=40,
spaceAfter=10, alignment=TA_CENTER, fontName='Helvetica-Bold'
)
styles['cover_sub'] = ParagraphStyle(
'cover_sub', parent=base['Normal'],
fontSize=14, textColor=HexColor('#BEE3F8'), leading=20,
alignment=TA_CENTER, fontName='Helvetica'
)
styles['cover_footer'] = ParagraphStyle(
'cover_footer', parent=base['Normal'],
fontSize=10, textColor=HexColor('#90CDF4'),
alignment=TA_CENTER, fontName='Helvetica-Oblique'
)
styles['section_header'] = ParagraphStyle(
'section_header', parent=base['Heading1'],
fontSize=16, textColor=white, leading=22,
spaceBefore=6, spaceAfter=8,
fontName='Helvetica-Bold', alignment=TA_LEFT
)
styles['subsection'] = ParagraphStyle(
'subsection', parent=base['Heading2'],
fontSize=12, textColor=C_DARK_BLUE, leading=16,
spaceBefore=10, spaceAfter=4,
fontName='Helvetica-Bold'
)
styles['body'] = ParagraphStyle(
'body', parent=base['Normal'],
fontSize=9.5, textColor=HexColor('#2D3748'), leading=14,
spaceAfter=4, fontName='Helvetica', alignment=TA_JUSTIFY
)
styles['body_bold'] = ParagraphStyle(
'body_bold', parent=base['Normal'],
fontSize=9.5, textColor=C_DARK_BLUE, leading=14,
spaceAfter=4, fontName='Helvetica-Bold'
)
styles['bullet'] = ParagraphStyle(
'bullet', parent=base['Normal'],
fontSize=9.5, textColor=HexColor('#2D3748'), leading=14,
spaceAfter=3, leftIndent=14, firstLineIndent=-10,
fontName='Helvetica'
)
styles['table_header'] = ParagraphStyle(
'table_header', parent=base['Normal'],
fontSize=9, textColor=white, leading=12,
fontName='Helvetica-Bold', alignment=TA_CENTER
)
styles['table_cell'] = ParagraphStyle(
'table_cell', parent=base['Normal'],
fontSize=8.5, textColor=HexColor('#2D3748'), leading=12,
fontName='Helvetica'
)
styles['table_cell_bold'] = ParagraphStyle(
'table_cell_bold', parent=base['Normal'],
fontSize=8.5, textColor=C_DARK_BLUE, leading=12,
fontName='Helvetica-Bold'
)
styles['phase_label'] = ParagraphStyle(
'phase_label', parent=base['Normal'],
fontSize=11, textColor=white, leading=14,
fontName='Helvetica-Bold', alignment=TA_CENTER
)
styles['caption'] = ParagraphStyle(
'caption', parent=base['Normal'],
fontSize=8, textColor=C_MID_GREY, leading=11,
fontName='Helvetica-Oblique', alignment=TA_CENTER
)
styles['prom_name'] = ParagraphStyle(
'prom_name', parent=base['Normal'],
fontSize=9, textColor=C_DARK_BLUE, leading=12,
fontName='Helvetica-Bold'
)
styles['footer_text'] = ParagraphStyle(
'footer_text', parent=base['Normal'],
fontSize=8, textColor=C_MID_GREY, leading=10,
fontName='Helvetica', alignment=TA_CENTER
)
return styles
STYLES = build_styles()
# ── Helper: coloured section banner ─────────────────────────────────────────
def section_banner(title, bg_color=C_DARK_BLUE):
data = [[Paragraph(title, STYLES['section_header'])]]
t = Table(data, colWidths=[170*mm])
t.setStyle(TableStyle([
('BACKGROUND', (0,0), (-1,-1), bg_color),
('LEFTPADDING', (0,0), (-1,-1), 10),
('RIGHTPADDING', (0,0), (-1,-1), 10),
('TOPPADDING', (0,0), (-1,-1), 7),
('BOTTOMPADDING',(0,0), (-1,-1), 7),
('ROUNDEDCORNERS', [4,4,4,4]),
]))
return t
# ── Helper: phase badge ──────────────────────────────────────────────────────
def phase_badge(text, color):
data = [[Paragraph(text, STYLES['phase_label'])]]
t = Table(data, colWidths=[170*mm])
t.setStyle(TableStyle([
('BACKGROUND', (0,0), (-1,-1), color),
('LEFTPADDING', (0,0), (-1,-1), 8),
('RIGHTPADDING', (0,0), (-1,-1), 8),
('TOPPADDING', (0,0), (-1,-1), 5),
('BOTTOMPADDING',(0,0), (-1,-1), 5),
]))
return t
# ── Helper: exercise table ───────────────────────────────────────────────────
def exercise_table(headers, rows, col_widths, row_colors=None):
header_row = [Paragraph(h, STYLES['table_header']) for h in headers]
data = [header_row]
for i, row in enumerate(rows):
styled = []
for j, cell in enumerate(row):
if j == 0:
styled.append(Paragraph(str(cell), STYLES['table_cell_bold']))
else:
styled.append(Paragraph(str(cell), STYLES['table_cell']))
data.append(styled)
t = Table(data, colWidths=col_widths, repeatRows=1)
style_cmds = [
('BACKGROUND', (0,0), (-1,0), C_DARK_BLUE),
('ROWBACKGROUNDS',(0,1),(-1,-1), [C_LIGHT_GREY, white]),
('GRID', (0,0), (-1,-1), 0.4, C_BORDER),
('VALIGN', (0,0), (-1,-1), 'MIDDLE'),
('LEFTPADDING', (0,0), (-1,-1), 6),
('RIGHTPADDING', (0,0), (-1,-1), 6),
('TOPPADDING', (0,0), (-1,-1), 4),
('BOTTOMPADDING',(0,0), (-1,-1), 4),
('LINEABOVE', (0,1), (-1,1), 1, C_MID_BLUE),
]
t.setStyle(TableStyle(style_cmds))
return t
# ── CHART 1: Exercise Progression Overview (Gantt-style) ───────────────────
def make_progression_chart():
fig, ax = plt.subplots(figsize=(11, 5.5))
fig.patch.set_facecolor('#FAFAFA')
ax.set_facecolor('#FAFAFA')
phases = [
('Phase 1: Acute\n(Weeks 1-2)', 0, 2, '#C53030'),
('Phase 2: Sub-acute\n(Weeks 3-6)', 2, 6, '#C05621'),
('Phase 3: Strengthening\n(Wks 7-12)',6, 12, '#276749'),
('Phase 4: Functional\n(Weeks 12+)', 12, 20, '#1A3A5C'),
]
exercises = [
('Ankle Pumps / Isometrics', 0, 6, '#FC8181'),
('Straight Leg Raises', 0, 8, '#FC8181'),
('Heel Slides / ROM exercises', 0, 12, '#F6AD55'),
('Mini Squats (0-30 deg)', 2, 12, '#F6AD55'),
('Step-ups / TKE', 4, 16, '#68D391'),
('Stationary Cycling', 2, 20, '#68D391'),
('Leg Press / Full Squats', 6, 20, '#4299E1'),
('Single-Leg Balance', 6, 20, '#4299E1'),
('Nordic Hamstring Curls', 8, 20, '#9F7AEA'),
('Lunges / Bulgarian Splits', 8, 20, '#9F7AEA'),
('Plyometrics / Agility Drills',12, 20, '#1A3A5C'),
('Return-to-Sport Drills', 14, 20, '#1A3A5C'),
]
n = len(exercises)
bar_height = 0.52
# Phase background shading
phase_colors_bg = ['#FFF5F5', '#FFFAF0', '#F0FFF4', '#EBF4FF']
phase_bounds = [(0,2), (2,6), (6,12), (12,20)]
for (start, end), bg in zip(phase_bounds, phase_colors_bg):
ax.axvspan(start, end, alpha=0.45, color=bg, zorder=0)
# Exercise bars
for i, (name, start, end, color) in enumerate(exercises):
y = n - 1 - i
ax.barh(y, end - start, left=start, height=bar_height,
color=color, alpha=0.88, edgecolor='white', linewidth=0.8, zorder=2)
# Label inside bar if wide enough
bar_len = end - start
if bar_len >= 3:
ax.text(start + bar_len/2, y, name,
va='center', ha='center', fontsize=7.2,
color='white', fontweight='bold', zorder=3)
else:
ax.text(end + 0.1, y, name,
va='center', ha='left', fontsize=7.2,
color='#2D3748', zorder=3)
# Phase header bars at top
for (name, start, end, color) in phases:
width = end - start
ax.barh(n + 0.5, width, left=start, height=0.7,
color=color, alpha=0.92, edgecolor='white', linewidth=1, zorder=2)
ax.text(start + width/2, n + 0.5, name,
va='center', ha='center', fontsize=7.5,
color='white', fontweight='bold', zorder=3)
# Vertical week markers
for w in range(0, 21, 2):
ax.axvline(x=w, color='#CBD5E0', linewidth=0.5, linestyle='--', zorder=1)
ax.set_xlim(0, 20)
ax.set_ylim(-0.7, n + 1.2)
ax.set_xlabel('Weeks', fontsize=10, color='#2D3748', fontweight='bold')
ax.set_xticks(range(0, 21, 2))
ax.set_xticklabels([f'Wk {w}' for w in range(0, 21, 2)], fontsize=8)
ax.set_yticks([])
ax.set_title('Knee Rehabilitation - Exercise Progression Timeline', fontsize=13,
fontweight='bold', color='#1A3A5C', pad=10)
ax.spines['top'].set_visible(False)
ax.spines['right'].set_visible(False)
ax.spines['left'].set_visible(False)
ax.tick_params(axis='x', colors='#4A5568')
plt.tight_layout()
buf = io.BytesIO()
plt.savefig(buf, format='png', dpi=160, bbox_inches='tight',
facecolor='#FAFAFA')
plt.close(fig)
buf.seek(0)
return buf
# ── CHART 2: PROM Score Progression ──────────────────────────────────────────
def make_prom_chart():
fig, axes = plt.subplots(1, 2, figsize=(11, 4.5))
fig.patch.set_facecolor('#FAFAFA')
weeks = [0, 6, 12, 24, 52]
labels = ['Baseline', 'Wk 6', 'Wk 12', 'Wk 24\n(6 mo)', 'Wk 52\n(1 yr)']
# Chart A - KOOS Subscales
ax = axes[0]
ax.set_facecolor('#FAFAFA')
koos_data = {
'Pain': [35, 52, 65, 78, 85],
'Symptoms': [38, 50, 62, 74, 80],
'ADL': [40, 55, 68, 80, 88],
'Sport/Rec': [20, 32, 48, 64, 75],
'QoL': [18, 30, 45, 62, 72],
}
palette = ['#E53E3E','#DD6B20','#38A169','#3182CE','#805AD5']
for (label, vals), color in zip(koos_data.items(), palette):
ax.plot(weeks, vals, marker='o', markersize=5, linewidth=2,
color=color, label=label)
ax.fill_between(weeks, vals, alpha=0.08, color=color)
ax.axhline(y=70, color='#718096', linewidth=1, linestyle=':', alpha=0.7)
ax.text(50.5, 71, 'Good outcome\nthreshold (70)', fontsize=7,
color='#718096', va='bottom')
ax.set_title('KOOS Subscale Progression', fontsize=11,
fontweight='bold', color='#1A3A5C')
ax.set_xlabel('Weeks post-treatment', fontsize=9)
ax.set_ylabel('Score (0-100, higher = better)', fontsize=9)
ax.set_xlim(-2, 55)
ax.set_ylim(0, 105)
ax.set_xticks(weeks)
ax.set_xticklabels(labels, fontsize=8)
ax.legend(fontsize=7.5, loc='upper left', framealpha=0.85)
ax.spines['top'].set_visible(False)
ax.spines['right'].set_visible(False)
ax.grid(axis='y', linestyle='--', alpha=0.4)
# Chart B - Strength Recovery (LSI %)
ax2 = axes[1]
ax2.set_facecolor('#FAFAFA')
weeks2 = [0, 6, 12, 18, 24, 36]
labels2 = ['Pre-op','Wk 6','Wk 12','Wk 18','Wk 24','Wk 36']
quad_lsi = [100, 55, 65, 74, 82, 90]
hamst_lsi = [100, 65, 72, 80, 87, 92]
thresh = [90] * len(weeks2)
ax2.plot(weeks2, quad_lsi, marker='s', markersize=5, linewidth=2,
color='#3182CE', label='Quadriceps LSI %')
ax2.plot(weeks2, hamst_lsi, marker='^', markersize=5, linewidth=2,
color='#38A169', label='Hamstring LSI %')
ax2.plot(weeks2, thresh, linewidth=1.5, linestyle='--',
color='#E53E3E', label='Return-to-sport threshold (90%)')
ax2.fill_between(weeks2, quad_lsi, 90,
where=[q < 90 for q in quad_lsi],
alpha=0.12, color='#3182CE')
ax2.set_title('Limb Symmetry Index (LSI) - ACL Rehab', fontsize=11,
fontweight='bold', color='#1A3A5C')
ax2.set_xlabel('Weeks post-reconstruction', fontsize=9)
ax2.set_ylabel('LSI % vs. contralateral limb', fontsize=9)
ax2.set_xlim(-2, 38)
ax2.set_ylim(40, 105)
ax2.set_xticks(weeks2)
ax2.set_xticklabels(labels2, fontsize=8)
ax2.legend(fontsize=7.5, loc='lower right', framealpha=0.85)
ax2.spines['top'].set_visible(False)
ax2.spines['right'].set_visible(False)
ax2.grid(axis='y', linestyle='--', alpha=0.4)
plt.tight_layout(pad=2)
buf = io.BytesIO()
plt.savefig(buf, format='png', dpi=160, bbox_inches='tight',
facecolor='#FAFAFA')
plt.close(fig)
buf.seek(0)
return buf
# ── CHART 3: Load Progression Pyramid ────────────────────────────────────────
def make_load_pyramid():
fig, ax = plt.subplots(figsize=(7, 5))
fig.patch.set_facecolor('#FAFAFA')
ax.set_facecolor('#FAFAFA')
ax.set_xlim(0, 10)
ax.set_ylim(0, 10)
ax.axis('off')
ax.set_title('Exercise Load Progression Pyramid', fontsize=12,
fontweight='bold', color='#1A3A5C', pad=8)
levels = [
(1.0, 8.0, 8.0, '#E53E3E', 'RETURN TO SPORT\nAgilty, Plyometrics, Cutting drills'),
(1.5, 6.8, 7.0, '#DD6B20', 'FUNCTIONAL TRAINING\nSingle-leg press, Lunges, Step-downs'),
(2.0, 5.6, 6.0, '#D69E2E', 'STRENGTHENING\nSquats, Leg press, Nordic curls'),
(2.5, 4.4, 5.0, '#38A169', 'NEUROMUSCULAR CONTROL\nBalance, TKE, Mini-squats'),
(3.0, 3.2, 4.0, '#3182CE', 'EARLY MOBILITY\nHeel slides, Cycling, Quad sets'),
(3.5, 2.0, 3.0, '#1A3A5C', 'FOUNDATION\nIsometrics, SLR, Ankle pumps, Ice/Elevation'),
]
for (left, y, width, color, text) in levels:
bar_w = width
rect = mpatches.FancyBboxPatch(
(5 - bar_w/2, y - 0.55), bar_w, 0.95,
boxstyle='round,pad=0.05', linewidth=0,
facecolor=color, alpha=0.9
)
ax.add_patch(rect)
lines = text.split('\n')
ax.text(5, y, lines[0], ha='center', va='center',
fontsize=7.5, color='white', fontweight='bold')
if len(lines) > 1:
ax.text(5, y - 0.25, lines[1], ha='center', va='center',
fontsize=6.5, color='#E2E8F0')
# Arrow
ax.annotate('', xy=(0.5, 9.2), xytext=(0.5, 1.5),
arrowprops=dict(arrowstyle='->', color='#718096', lw=1.5))
ax.text(0.1, 5.5, 'PROGRESSION', fontsize=7, color='#718096',
rotation=90, va='center', ha='center')
plt.tight_layout()
buf = io.BytesIO()
plt.savefig(buf, format='png', dpi=160, bbox_inches='tight',
facecolor='#FAFAFA')
plt.close(fig)
buf.seek(0)
return buf
# ── CHART 4: PROM Selection Matrix (heatmap) ─────────────────────────────────
def make_prom_matrix():
conditions = ['OA\nConservative', 'Post-\nTKR/UKR', 'ACL\nRehab',
'Meniscal\nInjury', 'PFPS']
proms = ['KOOS', 'WOMAC', 'Oxford KS', 'Lysholm', 'IKDC', 'Tegner',
'VAS/NRS', 'ACL-RSI', 'SF-36']
# 1=Recommended, 0.5=Useful, 0=Not applicable
matrix = np.array([
[1, 1, 0.5, 1, 0.5], # KOOS
[1, 0.5, 0, 0, 0.5], # WOMAC
[0.5, 1, 0, 0, 0 ], # Oxford KS
[0, 0, 1, 1, 0.5], # Lysholm
[0, 0, 1, 1, 1 ], # IKDC
[0, 0, 1, 0.5, 0.5], # Tegner
[1, 1, 1, 1, 1 ], # VAS/NRS
[0, 0, 1, 0, 0 ], # ACL-RSI
[0.5, 1, 0.5, 0.5, 0.5], # SF-36
])
fig, ax = plt.subplots(figsize=(8, 5.5))
fig.patch.set_facecolor('#FAFAFA')
from matplotlib.colors import LinearSegmentedColormap
cmap = LinearSegmentedColormap.from_list('rehab',
['#FFFFFF', '#BEE3F8', '#2B6CB0'])
im = ax.imshow(matrix, cmap=cmap, aspect='auto', vmin=0, vmax=1)
ax.set_xticks(range(len(conditions)))
ax.set_xticklabels(conditions, fontsize=9)
ax.set_yticks(range(len(proms)))
ax.set_yticklabels(proms, fontsize=9, fontweight='bold')
for i in range(len(proms)):
for j in range(len(conditions)):
val = matrix[i, j]
if val == 1:
txt, col = 'REC', 'white'
elif val == 0.5:
txt, col = 'USE', '#1A3A5C'
else:
txt, col = '-', '#CBD5E0'
ax.text(j, i, txt, ha='center', va='center',
fontsize=8, fontweight='bold', color=col)
# Legend patches
from matplotlib.patches import Patch
legend_elements = [
Patch(facecolor='#2B6CB0', label='Recommended (REC)'),
Patch(facecolor='#BEE3F8', label='Useful (USE)'),
Patch(facecolor='white', edgecolor='#CBD5E0', label='Not Applicable (-)'),
]
ax.legend(handles=legend_elements, loc='upper right', bbox_to_anchor=(1.38, 1.02),
fontsize=8, framealpha=0.9)
ax.set_title('PROM Selection Matrix by Clinical Condition', fontsize=11,
fontweight='bold', color='#1A3A5C', pad=8)
ax.tick_params(top=True, bottom=False, labeltop=True, labelbottom=False)
ax.tick_params(axis='x', which='both', length=0)
ax.tick_params(axis='y', which='both', length=0)
for spine in ax.spines.values():
spine.set_visible(False)
ax.set_xticks(np.arange(len(conditions)) - 0.5, minor=True)
ax.set_yticks(np.arange(len(proms)) - 0.5, minor=True)
ax.grid(which='minor', color='#E2E8F0', linewidth=0.8)
plt.tight_layout()
buf = io.BytesIO()
plt.savefig(buf, format='png', dpi=160, bbox_inches='tight',
facecolor='#FAFAFA')
plt.close(fig)
buf.seek(0)
return buf
# ══════════════════════════════════════════════════════════════════════════════
# COVER PAGE builder
# ══════════════════════════════════════════════════════════════════════════════
class CoverBackground(Flowable):
def draw(self):
w, h = A4
c = self.canv
# Deep blue gradient background
c.setFillColor(C_DARK_BLUE)
c.rect(0, 0, w, h, fill=1, stroke=0)
# Teal accent band
c.setFillColor(C_MID_BLUE)
c.rect(0, h*0.30, w, h*0.42, fill=1, stroke=0)
# Bottom dark band
c.setFillColor(HexColor('#0F2336'))
c.rect(0, 0, w, h*0.15, fill=1, stroke=0)
# Decorative circles
c.setFillColor(HexColor('#2C5282'))
c.circle(w*0.85, h*0.85, 80, fill=1, stroke=0)
c.setFillColor(HexColor('#2A4365'))
c.circle(w*0.1, h*0.2, 60, fill=1, stroke=0)
c.circle(w*0.9, h*0.1, 40, fill=1, stroke=0)
# ══════════════════════════════════════════════════════════════════════════════
# PAGE TEMPLATE with header/footer
# ══════════════════════════════════════════════════════════════════════════════
def on_page(canvas, doc):
canvas.saveState()
w, h = A4
page_num = doc.page
if page_num > 1:
# Header
canvas.setFillColor(C_DARK_BLUE)
canvas.rect(0, h - 22*mm, w, 22*mm, fill=1, stroke=0)
canvas.setFillColor(white)
canvas.setFont('Helvetica-Bold', 10)
canvas.drawString(15*mm, h - 14*mm,
'KNEE REHABILITATION PROTOCOL')
canvas.setFont('Helvetica', 9)
canvas.drawRightString(w - 15*mm, h - 14*mm,
'Clinical Reference Guide 2026')
# Footer
canvas.setFillColor(C_LIGHT_GREY)
canvas.rect(0, 0, w, 12*mm, fill=1, stroke=0)
canvas.setFillColor(C_DARK_BLUE)
canvas.rect(0, 12*mm, w, 0.5*mm, fill=1, stroke=0)
canvas.setFont('Helvetica', 8)
canvas.setFillColor(C_MID_GREY)
canvas.drawString(15*mm, 4*mm,
'Evidence-based protocol | EULAR 2024 | AAOS Guidelines | Ayurveda integrated')
canvas.drawRightString(w - 15*mm, 4*mm, f'Page {page_num}')
canvas.restoreState()
# ══════════════════════════════════════════════════════════════════════════════
# MAIN BUILD FUNCTION
# ══════════════════════════════════════════════════════════════════════════════
def build_pdf():
output_path = os.path.join(OUTPUT_DIR, 'Knee_Rehabilitation_Protocol.pdf')
doc = SimpleDocTemplate(
output_path,
pagesize=A4,
leftMargin=18*mm,
rightMargin=18*mm,
topMargin=28*mm,
bottomMargin=18*mm,
title='Knee Rehabilitation Protocol',
author='Orris Clinical Reference',
subject='Knee Rehabilitation, PROMs, Ayurveda'
)
story = []
PW = 174*mm # usable page width
# ── PAGE 1: COVER ─────────────────────────────────────────────────────────
story.append(Spacer(1, 55*mm))
cover_title_data = [[Paragraph(
'KNEE JOINT<br/>REHABILITATION PROTOCOL',
STYLES['cover_title']
)]]
ct = Table(cover_title_data, colWidths=[PW])
ct.setStyle(TableStyle([('BACKGROUND',(0,0),(-1,-1),C_DARK_BLUE)]))
story.append(ct)
story.append(Spacer(1, 8*mm))
story.append(Paragraph(
'Comprehensive Clinical Reference: Anatomy | Examination | Investigations<br/>'
'Rehabilitation Exercises | PROMs | Treatment | Ayurveda Integration',
STYLES['cover_sub']
))
story.append(Spacer(1, 18*mm))
# Info boxes on cover
info_rows = [[
Paragraph('<b>Evidence Base</b><br/>AAOS 2023 | EULAR 2024<br/>Cochrane 2024', STYLES['table_cell']),
Paragraph('<b>Target Conditions</b><br/>OA | ACL | Meniscal<br/>PFPS | TKR/UKR', STYLES['table_cell']),
Paragraph('<b>Includes</b><br/>KOOS | WOMAC | OKS<br/>Lysholm | IKDC | ACL-RSI', STYLES['table_cell']),
Paragraph('<b>Ayurveda</b><br/>Janu Basti | Matra Basti<br/>Herbs | Panchakarma', STYLES['table_cell']),
]]
info_t = Table(info_rows, colWidths=[PW/4]*4)
info_t.setStyle(TableStyle([
('BACKGROUND', (0,0), (-1,-1), HexColor('#EBF4FF')),
('BOX', (0,0), (-1,-1), 1, C_MID_BLUE),
('INNERGRID', (0,0), (-1,-1), 0.5, C_BORDER),
('TOPPADDING', (0,0), (-1,-1), 8),
('BOTTOMPADDING',(0,0),(-1,-1), 8),
('ALIGN', (0,0), (-1,-1), 'CENTER'),
('VALIGN', (0,0), (-1,-1), 'MIDDLE'),
]))
story.append(info_t)
story.append(Spacer(1, 10*mm))
story.append(Paragraph('Generated July 2026 | Orris Clinical Reference System', STYLES['cover_footer']))
story.append(Spacer(1, 6*mm))
story.append(Paragraph(
'For clinical use by qualified healthcare professionals. Not a substitute for individual patient assessment.',
STYLES['caption']
))
story.append(PageBreak())
# ── PAGE 2-3: PHASE OVERVIEW + PROGRESSION CHART ─────────────────────────
story.append(section_banner('REHABILITATION PHASES - OVERVIEW'))
story.append(Spacer(1, 4*mm))
# Phase cards
phases_info = [
(C_ACCENT, 'PHASE 1: ACUTE / PROTECTION', 'Weeks 1-2',
['Control pain and swelling (RICE principle)',
'Restore early range of motion (ROM)',
'Prevent quadriceps atrophy',
'Minimize effusion through elevation + ice (20 min, 4-6x/day)',
'Weight-bearing: partial (crutches post-op) or as tolerated (OA)']),
(C_AMBER, 'PHASE 2: SUB-ACUTE / MOBILITY', 'Weeks 3-6',
['Restore full passive ROM (0-135 deg)',
'Begin closed-chain weight-bearing exercises',
'Normalize gait pattern',
'Initiate proprioception and neuromuscular training',
'Stationary cycling: low resistance for ROM']),
(C_GREEN, 'PHASE 3: STRENGTHENING', 'Weeks 7-12',
['Progressive resistance training for quads, hamstrings, glutes',
'Closed and open kinetic chain exercises',
'Advanced balance and proprioception (unstable surfaces)',
'Aquatic exercise (especially OA/TKR patients)',
'Nordic hamstring curls, leg press, lunges introduced']),
(C_DARK_BLUE,'PHASE 4: FUNCTIONAL / RETURN', 'Week 12+',
['Sport-specific training and agility drills (ACL patients)',
'Plyometrics when LSI >85% and pain-free',
'Criteria-based return-to-sport (LSI >90%, KOOS-sports >90%)',
'Psychological readiness assessed (ACL-RSI >/= 90)',
'OA patients: maintain exercise as lifestyle activity']),
]
for color, title, timing, bullets in phases_info:
header_data = [[
Paragraph(title, STYLES['phase_label']),
Paragraph(timing, ParagraphStyle('timing', parent=STYLES['phase_label'],
alignment=TA_RIGHT))
]]
ht = Table(header_data, colWidths=[PW*0.7, PW*0.3])
ht.setStyle(TableStyle([
('BACKGROUND', (0,0), (-1,-1), color),
('LEFTPADDING', (0,0), (-1,-1), 8),
('RIGHTPADDING', (0,0), (-1,-1), 8),
('TOPPADDING', (0,0), (-1,-1), 5),
('BOTTOMPADDING',(0,0), (-1,-1), 5),
]))
bullet_paras = [Paragraph(f'<bullet>\u2022</bullet> {b}', STYLES['bullet']) for b in bullets]
content_data = [[bullet_paras]]
ct2 = Table([[ht], bullet_paras[0:2] + bullet_paras[2:]], colWidths=[PW])
# Build as stacked
for bp in bullet_paras:
pass
story.append(KeepTogether([
ht,
Table([[Paragraph(f' \u2022 {b}', STYLES['bullet'])] for b in bullets],
colWidths=[PW],
style=TableStyle([
('BACKGROUND', (0,0), (-1,-1), C_LIGHT_GREY),
('LEFTPADDING', (0,0), (-1,-1), 14),
('RIGHTPADDING', (0,0), (-1,-1), 8),
('TOPPADDING', (0,0), (-1,-1), 2),
('BOTTOMPADDING',(0,0), (-1,-1), 2),
])),
Spacer(1, 3*mm),
]))
story.append(Spacer(1, 4*mm))
story.append(Paragraph('Exercise Progression Timeline Chart', STYLES['subsection']))
chart1_buf = make_progression_chart()
img1 = Image(chart1_buf, width=PW, height=PW*0.45)
story.append(img1)
story.append(Paragraph(
'Figure 1. Gantt-style exercise progression chart showing introduction and continuation of exercises across rehabilitation phases.',
STYLES['caption']
))
story.append(PageBreak())
# ── PAGE 4: PHASE 1 & 2 EXERCISE TABLES ───────────────────────────────────
story.append(section_banner('PHASE 1 & 2 - DETAILED EXERCISE PRESCRIPTION', C_ACCENT))
story.append(Spacer(1, 3*mm))
story.append(phase_badge('PHASE 1: ACUTE / PROTECTION | Weeks 1-2', C_ACCENT))
story.append(Spacer(1, 2*mm))
p1_headers = ['Exercise', 'Technique', 'Sets x Reps', 'Frequency', 'Precaution']
p1_rows = [
['Ankle Pumps', 'Flex/point foot rhythmically; supine', '3 x 20', 'Hourly', 'None'],
['Quad Sets (Isometric)', 'Press back of knee to bed; tighten quads; hold 5s', '3 x 10', '4-6x/day', 'Pain-free only'],
['Inner Range Quads', 'Towel roll under knee (30 deg); actively extend', '3 x 10', '3x/day', 'Avoid if swollen'],
['Straight Leg Raise (SLR)', 'Quads contracted; lift to 45 deg; 4 planes', '3 x 10', '3x/day', 'No lag allowed'],
['Heel Slides', 'Supine; slide heel toward buttock; ROM only', '3 x 10', '3x/day', 'No forcing'],
['Supine Hip Abduction', 'Straight leg; abduct to 40 deg; side-lying alt.', '3 x 12', '2x/day', 'None'],
['Terminal Knee Extension (TKE)', 'Band behind knee; extend from 30 to 0 deg', '3 x 15', '3x/day', 'ACL: avoid early post-op'],
['Patella Mobilization', 'Passive superior-inferior + medial-lateral glides', '2 min', '2x/day', 'Post-op only after wound healed'],
['Cryotherapy', 'Ice pack over towel; knee elevated', '20 min', '4-6x/day', 'No direct skin contact'],
]
p1_cols = [38*mm, 50*mm, 25*mm, 25*mm, 32*mm]
story.append(exercise_table(p1_headers, p1_rows, p1_cols))
story.append(Spacer(1, 4*mm))
story.append(phase_badge('PHASE 2: SUB-ACUTE / MOBILITY | Weeks 3-6', C_AMBER))
story.append(Spacer(1, 2*mm))
p2_rows = [
['Mini Squats (0-30 deg)', 'Bilateral; hands on surface for balance; progress to unsupported', '3 x 15', 'Daily', 'No valgus collapse'],
['Step-Ups (Forward)', 'Low step (5 cm); controlled ascent/descent; progress height', '3 x 10 each', 'Daily', 'Pain < 3/10'],
['Stationary Cycling', 'Low resistance; saddle high; pedal smoothly', '15-20 min', '5x/week', 'Stop if sharp pain'],
['Calf Raises (Standing)', 'Bilateral; progress to single-leg', '3 x 15', 'Daily', 'None'],
['Hip Abduction (Resistance Band)', 'Standing; band at ankle; lift laterally', '3 x 15', '3x/week', 'None'],
['VMO Emphasis Squat', 'Feet 30 deg external rotation; drop into squat focusing medial quad', '3 x 12', 'Daily', 'Patella tracking'],
['Hamstring Curls (Prone)', 'Gravity or light resistance; full ROM', '3 x 12', '3x/week', 'ACL: check protocol'],
['Single-Leg Balance', 'Eyes open; 30s; progress to eyes closed / foam pad', '3 x 30s', 'Daily', 'Stand near wall'],
['Prone Hip Extension', 'Squeeze glutes; lift leg 15 cm; hold 3s', '3 x 12', '3x/week', 'None'],
]
story.append(exercise_table(p1_headers, p2_rows, p1_cols))
story.append(Spacer(1, 3*mm))
# Load pyramid
pyramid_buf = make_load_pyramid()
img_pyr = Image(pyramid_buf, width=PW*0.55, height=PW*0.40)
pyr_table = Table([[img_pyr]], colWidths=[PW])
pyr_table.setStyle(TableStyle([('ALIGN',(0,0),(-1,-1),'CENTER')]))
story.append(pyr_table)
story.append(Paragraph(
'Figure 2. Exercise load progression pyramid - build from the base upwards.',
STYLES['caption']
))
story.append(PageBreak())
# ── PAGE 5: PHASE 3 & 4 EXERCISE TABLES ───────────────────────────────────
story.append(section_banner('PHASE 3 & 4 - STRENGTHENING & FUNCTIONAL RETURN', C_GREEN))
story.append(Spacer(1, 3*mm))
story.append(phase_badge('PHASE 3: STRENGTHENING | Weeks 7-12', C_GREEN))
story.append(Spacer(1, 2*mm))
p3_rows = [
['Full Squats (0-90 deg)', 'Bodyweight to loaded; feet shoulder-width; neutral spine', '3-4 x 12', '3x/week', 'Valgus watch'],
['Leg Press', 'Low seat; full ROM; progressive load increase', '3-4 x 12', '3x/week', 'No locking out'],
['Lunges (Forward/Lateral)', 'Controlled descent; knee tracks over 2nd toe', '3 x 10 each', '3x/week', 'Pain-free'],
['Wall Squats (Isometric)', 'Sustained hold at 60-90 deg; VMO focused', '3 x 30-60s', 'Daily', 'Bilateral only initially'],
['Nordic Hamstring Curls', 'Eccentric; partner holds ankles; slow lowering', '3 x 6-8', '2x/week', 'High intensity - progress carefully'],
['Aquatic Exercises', 'Pool walking; pool squats; resistance with floats', '20-30 min', '3x/week', 'Wound healed (post-op)'],
['Lateral Band Walks', 'Band at ankles; side-step maintaining hip neutral', '3 x 15 each', '3x/week', 'None'],
['Step-Downs (Eccentric)', '20 cm step; single-leg controlled descent; hip neutral', '3 x 8-10 each', '3x/week', 'Pain < 3/10'],
['Open Chain Knee Extension', '90 to 40 deg only (protect ACL graft); resistance machine', '3 x 12', '3x/week', 'ACL: no full extension'],
]
story.append(exercise_table(p1_headers, p3_rows, p1_cols))
story.append(Spacer(1, 4*mm))
story.append(phase_badge('PHASE 4: FUNCTIONAL / RETURN TO SPORT | Week 12+', C_DARK_BLUE))
story.append(Spacer(1, 2*mm))
p4_rows = [
['Bulgarian Split Squats', 'Rear foot elevated; loaded; single-leg strength', '3 x 8 each', '3x/week', 'LSI >80% before starting'],
['Box Jumps', 'Two-foot takeoff and landing; soft knees; progress height', '3 x 8', '2x/week', 'ACL: >12 weeks post-op'],
['Lateral Bounding', 'Single-leg lateral hops; stick landing; 3-4 bounds', '3 x 5 each side', '2x/week', 'Land mechanics'],
['Agility Ladder Drills', 'In-out, lateral shuffle, carioca; speed progression', '3 x 30s', '3x/week', 'Pain-free only'],
['Change of Direction Drills', 'T-test, 5-10-5 shuttle; progress to unplanned', '3 x 3', '2x/week', 'ACL: 16+ weeks'],
['Running Progression', 'Walk 5 min -> jog 2 min alternating -> continuous jog', 'Protocol', '3x/week', 'No limp; no pain'],
['Perturbation Training', 'Therapist-applied unexpected perturbations on unstable surface', '10-15 min', '2x/week', 'Therapist supervised'],
['Sport-Specific Drills', 'Position-specific movements; reactive activities', 'As tolerated', '3x/week', 'Match intensity to sport'],
]
p4_cols = [42*mm, 50*mm, 23*mm, 22*mm, 33*mm]
story.append(exercise_table(p1_headers, p4_rows, p4_cols))
story.append(Spacer(1, 4*mm))
# Return-to-sport criteria box
rts_data = [[
Paragraph('<b>RETURN-TO-SPORT CRITERIA (ACL)</b>', STYLES['body_bold']),
],[
Paragraph(
u'\u2022 LSI \u2265 90% on single-leg hop tests (single, triple, crossover, 6-metre timed)\n'
u'\u2022 Hamstring:Quadriceps ratio \u2265 66%\n'
u'\u2022 Full pain-free ROM and no effusion\n'
u'\u2022 KOOS-Sports subscale \u2265 90\n'
u'\u2022 IKDC score \u2265 93\n'
u'\u2022 ACL-RSI score \u2265 90 (psychological readiness)\n'
u'\u2022 Minimum 9 months post-reconstruction (reduces re-rupture risk)',
STYLES['body']
)
]]
rts_t = Table(rts_data, colWidths=[PW])
rts_t.setStyle(TableStyle([
('BACKGROUND', (0,0), (0,0), C_DARK_BLUE),
('BACKGROUND', (0,1), (0,1), C_LIGHT_BLUE),
('LEFTPADDING', (0,0), (-1,-1), 10),
('RIGHTPADDING', (0,0), (-1,-1), 10),
('TOPPADDING', (0,0), (-1,-1), 6),
('BOTTOMPADDING',(0,0), (-1,-1), 6),
('BOX', (0,0), (-1,-1), 1, C_MID_BLUE),
]))
story.append(rts_t)
story.append(PageBreak())
# ── PAGE 6: PROMs ─────────────────────────────────────────────────────────
story.append(section_banner('PATIENT-REPORTED OUTCOME MEASURES (PROMs)', C_TEAL))
story.append(Spacer(1, 3*mm))
story.append(Paragraph(
'PROMs are standardized, patient-completed questionnaires that capture the patient\'s perspective on pain, '
'function, and quality of life. They are essential for monitoring rehabilitation progress, surgical decision-making, '
'and clinical audit. Administer at: Baseline, 6 weeks, 3 months, 6 months, and 12 months.',
STYLES['body']
))
story.append(Spacer(1, 3*mm))
prom_headers = ['PROM', 'Items', 'Subscales / Score Range', 'Best Use', 'MCID']
prom_rows = [
['KOOS', '42', '5 subscales; 0-100 each\n(higher = better)', 'OA, ACL, Meniscal, TKR', '8-10 pts'],
['KOOS-PS', '7', 'Physical function; 0-100', 'Quick functional screen', '8 pts'],
['WOMAC', '24', 'Pain/Stiffness/Function; 0-96', 'OA (hip & knee)', '10-15 pts'],
['Oxford Knee Score', '12', '0-48 (higher = better)', 'TKR/UKR pre & post-op', '5 pts'],
['Lysholm Scale', '8', '0-100; Excellent:95-100', 'Ligament / ACL injuries', '10 pts'],
['IKDC Subjective', '18', '0-100 (higher = better)', 'ACL, meniscal, ligament', '9-11 pts'],
['Tegner Activity', '1', '0-10 ordinal activity scale', 'Return-to-sport baseline', '1 level'],
['VAS / NRS Pain', '1', 'VAS 0-100mm / NRS 0-10', 'All conditions; daily monitoring', '1.5-2 pts'],
['ACL-RSI', '12', '0-100 psychological readiness', 'Post-ACL reconstruction', '17 pts'],
['SF-36 / SF-12', '36/12', '8 domains; PCS + MCS', 'General health-related QoL', '5-10 pts'],
['PROMIS', 'Adaptive', 'T-score (50 = population norm)', 'Research; multi-domain', 'Domain-specific'],
['KSS (Knee Society)', 'Dual', 'Knee score + Function score (0-100 each)', 'TKR outcomes', '10 pts'],
]
prom_cols = [32*mm, 12*mm, 48*mm, 42*mm, 20*mm]
story.append(exercise_table(prom_headers, prom_rows, prom_cols))
story.append(Spacer(1, 4*mm))
# PROM charts
story.append(Paragraph('PROM Outcome Tracking & PROM Selection Matrix', STYLES['subsection']))
prom_chart_buf = make_prom_chart()
img_prom = Image(prom_chart_buf, width=PW, height=PW*0.38)
story.append(img_prom)
story.append(Paragraph(
'Figure 3. Left: Expected KOOS subscale trajectory in OA rehabilitation over 12 months. '
'Right: ACL reconstruction - Limb Symmetry Index (LSI) recovery curve for quad and hamstring strength.',
STYLES['caption']
))
story.append(Spacer(1, 4*mm))
prom_matrix_buf = make_prom_matrix()
img_matrix = Image(prom_matrix_buf, width=PW*0.70, height=PW*0.42)
matrix_wrap = Table([[img_matrix]], colWidths=[PW])
matrix_wrap.setStyle(TableStyle([('ALIGN',(0,0),(-1,-1),'CENTER')]))
story.append(matrix_wrap)
story.append(Paragraph(
'Figure 4. PROM selection matrix - recommended instruments by clinical condition.',
STYLES['caption']
))
story.append(PageBreak())
# ── PAGE 7: TREATMENT INCLUDING AYURVEDA ──────────────────────────────────
story.append(section_banner('TREATMENT - CONVENTIONAL & AYURVEDA INTEGRATION', C_PURPLE))
story.append(Spacer(1, 3*mm))
# Conventional treatment table
story.append(Paragraph('Conventional Treatment by Evidence Level (AAOS 2023)', STYLES['subsection']))
conv_headers = ['Treatment', 'AAOS Strength', 'Recommendation']
conv_rows = [
['Patient Education Programs', '4-Star (Strong)', 'Recommended - first-line'],
['Exercise (supervised / unsupervised / aquatic)', '4-Star (Strong)', 'Recommended - cornerstone of management'],
['Self-Management Programs', '4-Star (Strong)', 'Recommended'],
['Topical NSAIDs (e.g., Diclofenac gel)', '4-Star (Strong)', 'Recommended - preferred over oral for local OA'],
['Oral NSAIDs (e.g., Ibuprofen, Naproxen)', '4-Star (Strong)', 'Recommended - with GI protection'],
['Sustained Weight Loss', '3-Star (Moderate)', 'Recommended - each 1 kg loss reduces load by ~4 kg'],
['Brace Treatment / Walking Aids', '3-Star (Moderate)', 'Recommended - offloader for medial OA'],
['Intraarticular Corticosteroids', '3-Star (Moderate)', 'Short-term relief only; max 3-4x/year'],
['PRP (Platelet-rich Plasma)', '2-Star (Limited)', 'May reduce pain; not standard care'],
['Acupuncture / TENS', '2-Star (Limited)', 'May improve pain; adjunct use'],
['Hyaluronic Acid (Viscosupplementation)', '3-Star AGAINST', 'NOT Recommended (AAOS)'],
['Arthroscopy with lavage/debridement', '4-Star AGAINST', 'NOT Recommended for OA'],
]
conv_cols = [58*mm, 32*mm, 80*mm]
story.append(exercise_table(conv_headers, conv_rows, conv_cols))
story.append(Spacer(1, 4*mm))
# Ayurveda section
story.append(section_banner('AYURVEDA INTEGRATION - JANU SANDHI (KNEE JOINT)', HexColor('#553C9A')))
story.append(Spacer(1, 3*mm))
story.append(Paragraph(
'In Ayurveda, knee conditions are classified as <b>Sandhigatavata</b> (degenerative, Vata-dominant) '
'or <b>Amavata</b> (inflammatory, with Ama toxins). Treatment is individualized based on Dosha and disease stage.',
STYLES['body']
))
story.append(Spacer(1, 3*mm))
# Panchakarma table
story.append(Paragraph('Panchakarma Procedures for Janu Sandhi', STYLES['subsection']))
pk_headers = ['Procedure', 'Description', 'Oils / Materials', 'Duration', 'Evidence Level']
pk_rows = [
['Janu Basti', 'Warm medicated oil retained in dough ring over knee joint',
'Dhanwantara Taila, Ksheerabala Taila, Mahanarayan Taila',
'30-45 min; 7-14 days', 'Clinical studies; RCT in progress (2025)'],
['Matra Basti', 'Small-volume medicated oil enema (30-60 mL)',
'Ksheerabala Taila', 'Daily x 7-14 days', 'Promising RCTs; prime Vatavyadhi Rx'],
['Abhyanga', 'Therapeutic full or localized warm oil massage',
'Mahanarayan Taila, Ksheerabala Taila', '45-60 min', 'Standard pre-Panchakarma'],
['Swedana', 'Heat fomentation / herbal steam after Abhyanga',
'Herbal decoction steam', '15-20 min', 'Standard; relieves stiffness'],
['Patra Pinda Sweda', 'Herbal leaf bolus massage (hot compress)',
'Eranda, Nirgundi leaves, sesame oil', '30-45 min', 'Case series evidence'],
['Upanaha Sweda', 'Medicated poultice applied overnight to knee',
'Eranda, salt, sesame, vinegar paste', 'Overnight', 'Traditional; widely used'],
['Lepa (External paste)', 'Herbal anti-inflammatory paste applied topically',
'Guggulu-based formulations', '30-60 min', 'Traditional use'],
]
pk_cols = [28*mm, 40*mm, 40*mm, 24*mm, 38*mm]
story.append(exercise_table(pk_headers, pk_rows, pk_cols))
story.append(Spacer(1, 3*mm))
story.append(Paragraph('Internal Ayurvedic Medicines', STYLES['subsection']))
herb_headers = ['Formulation / Herb', 'Key Ingredients', 'Primary Action', 'Indication']
herb_rows = [
['Yogaraja Guggulu', 'Guggul, triphala, trikatu, sesame', 'Anti-inflammatory; Vata-pacifying', 'OA, joint pain, stiffness'],
['Trayodashanga Guggulu', 'Guggul + 13 herbs incl. ashwagandha', 'Analgesic; anti-rheumatic', 'Sandhigatavata'],
['Laksha Guggulu', 'Lac, guggul, ashwagandha, nagabala', 'Bone & cartilage regeneration', 'OA with bone loss; fractures'],
['Muktashukti Bhasma', 'Calcined pearl oyster shell', 'Calcium; anti-inflammatory', 'OA; osteoporosis component'],
['Shallaki (Boswellia serrata)', 'Boswellic acids (AKBA)', 'Inhibits 5-LOX; reduces cartilage breakdown', 'Strong RCT evidence for knee OA'],
['Ashwagandha (Withania somnifera)', 'Withanolides', 'Adaptogen; muscle/ligament strengthening', 'Stiffness, weakness, degeneration'],
['Guggulu (Commiphora mukul)', 'Guggulsterones', 'Anti-inflammatory; lipid-lowering', 'OA, rheumatoid arthritis'],
['Punarnava (Boerhavia diffusa)', 'Punarnavine', 'Anti-oedematous; renal support', 'Knee swelling/effusion'],
]
herb_cols = [42*mm, 40*mm, 42*mm, 46*mm]
story.append(exercise_table(herb_headers, herb_rows, herb_cols))
story.append(Spacer(1, 3*mm))
# Evidence note
evidence_data = [[
Paragraph('<b>Evidence Note:</b> A 2024 prospective study (Kshirsagar et al., Int J Res Orthop 2024) demonstrated '
'statistically significant improvement in <b>KOOS subscores</b> (pain, sport, function, QoL) over 90 days '
'with Panchakarma therapy (p<0.001). Boswellia serrata has multiple RCTs showing pain reduction in '
'knee OA comparable to NSAIDs. A multimodal RCT (Rai et al., JMIR Protocols 2025) is evaluating '
'Matra Basti + Janu Basti + Laksha Guggulu for primary knee OA.',
STYLES['body'])
]]
ev_t = Table(evidence_data, colWidths=[PW])
ev_t.setStyle(TableStyle([
('BACKGROUND', (0,0), (-1,-1), HexColor('#FAF5FF')),
('BOX', (0,0), (-1,-1), 1, C_PURPLE),
('LEFTPADDING', (0,0), (-1,-1), 10),
('RIGHTPADDING', (0,0), (-1,-1), 10),
('TOPPADDING', (0,0), (-1,-1), 7),
('BOTTOMPADDING',(0,0), (-1,-1), 7),
]))
story.append(ev_t)
story.append(PageBreak())
# ── PAGE 8: MONITORING & REFERENCES ──────────────────────────────────────
story.append(section_banner('MONITORING, ASSESSMENT SCHEDULE & REFERENCES'))
story.append(Spacer(1, 3*mm))
story.append(Paragraph('Recommended PROM Assessment Schedule', STYLES['subsection']))
sched_headers = ['Timepoint', 'PROM(s)', 'Clinical Assessment', 'Notes']
sched_rows = [
['Baseline (pre-treatment)', 'KOOS / WOMAC / OKS\nVAS / Tegner', 'Full examination\nX-ray (weight-bearing)', 'Set goals; document deformity'],
['6 Weeks', 'KOOS / VAS / Lysholm', 'ROM; Effusion; Strength\nGait assessment', 'Phase 2 progression check'],
['3 Months (12 weeks)', 'KOOS / IKDC / VAS\nACL-RSI (ACL patients)', 'Single-leg squat; Hop tests\nLSI measurement', 'Phase 3-4 criteria check'],
['6 Months', 'KOOS / IKDC / OKS\nSF-12 / ACL-RSI', 'Functional assessment\nReturn-to-sport battery', 'Surgical review if indicated'],
['12 Months (1 Year)', 'All relevant PROMs\n+ Patient Satisfaction', 'Full functional review', 'Annual thereafter for OA'],
]
sched_cols = [32*mm, 42*mm, 50*mm, 46*mm]
story.append(exercise_table(sched_headers, sched_rows, sched_cols))
story.append(Spacer(1, 4*mm))
# Red flags
story.append(Paragraph('Red Flags - When to Stop Exercise & Seek Urgent Review', STYLES['subsection']))
rf_data = [
[Paragraph(u'\u26a0 RED FLAGS - STOP EXERCISE AND REFER URGENTLY', ParagraphStyle(
'rf', parent=STYLES['body_bold'], textColor=white, fontSize=10))],
[Paragraph(
u'\u2022 Sudden severe pain unrelated to exertion\n'
u'\u2022 Significant new swelling / hot red joint (consider septic arthritis / DVT)\n'
u'\u2022 Inability to weight-bear that was not present before\n'
u'\u2022 New neurological symptoms (numbness, tingling, weakness in foot)\n'
u'\u2022 Locking of the knee that cannot be resolved with gentle movement\n'
u'\u2022 Post-op: wound dehiscence, discharge, fever > 38.5 C\n'
u'\u2022 Chest pain, calf swelling or breathlessness (possible PE/DVT)',
STYLES['body']
)]
]
rf_t = Table(rf_data, colWidths=[PW])
rf_t.setStyle(TableStyle([
('BACKGROUND', (0,0), (0,0), C_ACCENT),
('BACKGROUND', (0,1), (0,1), HexColor('#FFF5F5')),
('BOX', (0,0), (-1,-1), 1, C_ACCENT),
('LEFTPADDING', (0,0), (-1,-1), 10),
('RIGHTPADDING', (0,0), (-1,-1), 10),
('TOPPADDING', (0,0), (-1,-1), 6),
('BOTTOMPADDING',(0,0), (-1,-1), 6),
]))
story.append(rf_t)
story.append(Spacer(1, 4*mm))
# References
story.append(Paragraph('Key References', STYLES['subsection']))
refs = [
'1. Bailey & Love\'s Short Practice of Surgery, 28th Edition - Knee anatomy, examination, OA, ACL.',
'2. Miller\'s Review of Orthopaedics, 9th Edition - AAOS evidence-based guidelines for knee OA.',
'3. Rockwood & Green\'s Fractures in Adults, 10th Ed. - Medial and lateral knee anatomy.',
'4. Lawford BJ et al. Exercise for osteoarthritis of the knee. Cochrane Database Syst Rev. 2024 Dec.',
'5. Yan L et al. Comparative efficacy and safety of exercise modalities in knee OA. BMJ. 2025 Oct.',
'6. Moseng T et al. EULAR recommendations for non-pharmacological management of hip/knee OA: 2023 update. Ann Rheum Dis. 2024.',
'7. Rai AK et al. Efficacy of a Multimodal Ayurveda Regimen in knee OA. JMIR Protocols. 2025.',
'8. Kshirsagar J et al. Impact of Ayurvedic Panchakarma therapy on osteoarthritis (KOOS). Int J Res Orthop. 2024;10(6).',
'9. Collins NJ et al. Measures of knee function (KOOS, WOMAC, OKS, IKDC, Lysholm, Tegner). Arthritis Care Res. 2011.',
'10. AAOS. Management of Osteoarthritis of the Knee (Non-Arthroplasty) Evidence-Based CPG. 2023.',
]
for ref in refs:
story.append(Paragraph(ref, STYLES['bullet']))
story.append(Spacer(1, 4*mm))
# Disclaimer
disc_data = [[Paragraph(
'<b>Disclaimer:</b> This protocol is a clinical reference guide for use by qualified healthcare professionals. '
'All rehabilitation programs should be individualized to the patient\'s specific condition, fitness level, '
'and surgical status. This document does not replace clinical judgement or direct patient examination. '
'Ayurvedic treatments should be administered by qualified Ayurvedic practitioners.',
STYLES['caption']
)]]
disc_t = Table(disc_data, colWidths=[PW])
disc_t.setStyle(TableStyle([
('BACKGROUND', (0,0), (-1,-1), C_LIGHT_GREY),
('BOX', (0,0), (-1,-1), 0.5, C_BORDER),
('LEFTPADDING', (0,0), (-1,-1), 8),
('RIGHTPADDING', (0,0), (-1,-1), 8),
('TOPPADDING', (0,0), (-1,-1), 6),
('BOTTOMPADDING',(0,0), (-1,-1), 6),
]))
story.append(disc_t)
# Build
doc.build(story, onFirstPage=on_page, onLaterPages=on_page)
print(f"PDF generated: {output_path}")
return output_path
if __name__ == '__main__':
path = build_pdf()
print(f"SUCCESS: {path}")
cd /home/daytona/workspace/knee-rehab-pdf && python3 generate_pdf.py 2>&1
ls -lh /home/daytona/workspace/knee-rehab-pdf/Knee_Rehabilitation_Protocol.pdf &…
Knee Rehabilitation Protocol
PDF Document · PDF
| Page(s) | Content |
|---|---|
| 1 | Cover page with condition overview, evidence base summary, and Ayurveda note |
| 2-3 | 4-phase rehabilitation overview cards + Figure 1: Gantt-style exercise progression timeline (12 exercises mapped across 20 weeks) |
| 4 | Phase 1 & 2 detailed exercise prescription tables (sets/reps/frequency/precautions) + Figure 2: Load Progression Pyramid |
| 5 | Phase 3 & 4 exercise tables + Return-to-Sport criteria box (LSI, KOOS, ACL-RSI thresholds) |
| 6 | Full PROM reference table (12 PROMs) + Figure 3: KOOS subscale trajectory chart & LSI recovery curve + Figure 4: PROM selection matrix heatmap |
| 7 | Conventional treatment table (AAOS evidence star ratings) + Panchakarma procedures table + Ayurvedic internal medicines table + evidence note |
| 8 | PROM assessment schedule, Red Flag warnings, 10 key references, disclaimer |
make a pdf together for both the above generate one & add images for the examination part
give it in a textform
Spine
"spinal stenosis" AND "rehabilitation" AND "exercise"
spine Ayurveda treatment Kati Basti Greeva Basti Pristha Basti 2024 evidence
"low back pain"[MeSH Terms] AND "exercise therapy"[MeSH Terms]
"cervical spondylosis" AND "rehabilitation" AND "outcome"
spine rehabilitation exercises cervical lumbar physiotherapy protocol McKenzie Williams flexion 2024
| Movement | Normal Range |
|---|---|
| Flexion (chin to chest) | 45 degrees |
| Extension (look at ceiling) | 55 degrees |
| Lateral bending (ear to shoulder) | 45 degrees each side |
| Rotation (chin to shoulder) | 60-80 degrees each side |
| Level | Reflex | Motor | Sensation |
|---|---|---|---|
| C5 | Biceps jerk | Deltoid, biceps (shoulder abduction, elbow flexion) | Lateral upper arm |
| C6 | Brachioradialis jerk | Wrist extensors, biceps | Thumb and index finger |
| C7 | Triceps jerk | Triceps, wrist flexors, finger extensors | Middle finger |
| C8 | None reliable | Finger flexors, intrinsics | Ring and little finger |
| T1 | None reliable | Hand intrinsics | Medial forearm |
| Movement | Normal Range |
|---|---|
| Flexion | 20-45 degrees |
| Extension | 25-45 degrees |
| Lateral bending | 20-40 degrees each side |
| Rotation | 30-45 degrees each side (greatest in the thoracic spine) |
| Movement | Normal Range |
|---|---|
| Forward flexion | 40-60 degrees (Schober test: marks placed 10 cm above and 5 cm below L5; should separate to >20 cm in full flexion; <15 cm suggests restriction) |
| Extension | 20-35 degrees |
| Lateral bending | 20-30 degrees each side |
| Rotation | 3-18 degrees each side (least in lumbar spine due to facet orientation) |
| Level | Reflex | Motor | Sensation |
|---|---|---|---|
| L1-L2 | Cremasteric | Hip flexors | Groin / upper medial thigh |
| L3 | None | Quadriceps (weak) | Medial knee |
| L4 | Knee jerk | Quadriceps, tibialis anterior | Medial shin / medial foot |
| L5 | Hamstring jerk | Great toe extension (EHL), hip abduction | Dorsum of foot / big toe |
| S1 | Ankle jerk | Plantarflexion, eversion | Lateral foot / little toe |
| S2-S4 | Bulbocavernosus | Bladder/bowel/perianal | Perianal / perineum |
| Timepoint | Lumbar Conditions | Cervical Conditions | Myelopathy |
|---|---|---|---|
| Baseline | ODI + NRS + EQ-5D + SBT | NDI + NRS + EQ-5D | mJOA + NDI + NRS |
| 6 Weeks | ODI + NRS | NDI + NRS | mJOA + NDI |
| 3 Months | ODI + NRS + EQ-5D | NDI + NRS + EQ-5D | mJOA + NDI + EQ-5D |
| 6 Months | ODI + NRS + EQ-5D + PGIC | NDI + NRS + EQ-5D + PGIC | mJOA + PGIC |
| 12 Months | Full battery + patient satisfaction | Full battery | Full battery |
upper limb
"shoulder"[MeSH Terms] AND "rotator cuff" AND "rehabilitation"
upper limb Ayurveda treatment shoulder elbow Greeva Basti Pinda Sweda 2024
"frozen shoulder" AND "adhesive capsulitis" AND "treatment"
"elbow" AND "lateral epicondylitis" AND "exercise" AND "treatment"
upper limb rehabilitation exercises shoulder elbow wrist outcome measures DASH ASES QuickDASH 2024
| Nerve | Cord | Roots | Motor | Sensory |
|---|---|---|---|---|
| Musculocutaneous | Lateral | C5, C6 | Biceps, brachialis, coracobrachialis | Lateral forearm |
| Axillary | Posterior | C5, C6 | Deltoid, teres minor | Regimental badge area (lateral upper arm) |
| Radial | Posterior | C5-T1 | Triceps, wrist/finger extensors, supinator | Dorsal hand (1st web space) |
| Median | Lateral + Medial | C6-T1 | Pronators, wrist flexors, FDP (index/middle), thenar muscles, lumbricals I+II | Radial 3.5 fingers |
| Ulnar | Medial | C8, T1 | FCU, FDP (ring/little), intrinsics, hypothenar, adductor pollicis | Ulnar 1.5 fingers |
| Condition | Primary PROM | Secondary PROM |
|---|---|---|
| Shoulder impingement / rotator cuff (conservative) | ASES / SPADI | QuickDASH + VAS |
| Rotator cuff repair (surgical) | ASES + Constant | QuickDASH + OSS |
| Frozen shoulder | SPADI / DASH | Constant + VAS |
| Shoulder instability | ASIS / Rowe score | QuickDASH + OSES |
| Shoulder arthroplasty | OSS / ASES | Constant + QuickDASH |
| Lateral epicondylitis | PREE + VAS | QuickDASH |
| Elbow arthroplasty | MEPS / LES | QuickDASH |
| Carpal tunnel syndrome | BCTQ | QuickDASH + VAS |
| Distal radius fracture | PRWE | QuickDASH + VAS |
| Hand / multiple joints | DASH / QuickDASH | MHQ |
| Any upper limb (general) | DASH or QuickDASH | VAS / PROMIS |
| Condition | Procedure | Approach |
|---|---|---|
| Rotator cuff tear (traumatic/functional deficit) | Arthroscopic cuff repair | Arthroscopic |
| Impingement (failed conservative) | Subacromial decompression (acromioplasty) | Arthroscopic |
| Frozen shoulder (refractory) | Arthroscopic capsular release / MUA | Arthroscopic / GA |
| Shoulder instability (Bankart) | Arthroscopic Bankart repair | Arthroscopic |
| Shoulder instability (bone loss) | Latarjet procedure (coracoid transfer) | Open |
| ACJ dislocation (Grade III-VI) | ACCF ligament reconstruction | Open |
| Shoulder OA | Total shoulder arthroplasty / Reverse TSA | Open |
| Lateral epicondylitis (failed Rx) | ECRB debridement | Open/Arthroscopic |
| MCL reconstruction | Ulnar collateral ligament reconstruction (Tommy John) | Open |
| Cubital tunnel syndrome | In situ decompression / anterior transposition | Open |
| Carpal tunnel syndrome | Carpal tunnel decompression (CTD) | Open / Endoscopic |
| Distal radius fracture | ORIF with volar locking plate | Open |
| Scaphoid non-union | Cancellous bone graft + headless screw (Herbert) | Open |
| Dupuytren's contracture | Fasciectomy / collagenase injection (Xiaflex) | Open |