I am mbbs student and tomorrow is my 1st day of third year and tomorrow is my posting on dental ward and I don't know about dental history taking and all the other things so please guide me and provide me well formed PDF
dental ward history taking MBBS clinical posting guide oral examination
https://pocketdentistry.com/1-clinical-examination-and-histo…
dental ward common conditions MBBS student guide gingivitis periodontitis caries abscess
mkdir -p /home/daytona/workspace/dental-ward-guide && python3 << 'EOF' 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, HRFlowable, PageBreak, ListFlowable, ListItem from reportlab.lib.enums import TA_CENTER, TA_LEFT, TA_JUSTIFY from reportlab.pdfgen import canvas output_path = "/home/daytona/workspace/dental-ward-guide/Dental_Ward_Guide_MBBS.pdf" # ---- Custom canvas for header/footer ---- class NumberedCanvas(canvas.Canvas): def __init__(self, *args, **kwargs): canvas.Canvas.__init__(self, *args, **kwargs) self._saved_page_states = [] def showPage(self): self._saved_page_states.append(dict(self.__dict__)) self._startPage() def save(self): num_pages = len(self._saved_page_states) for state in self._saved_page_states: self.__dict__.update(state) self.draw_page_number(num_pages) canvas.Canvas.showPage(self) canvas.Canvas.save(self) def draw_page_number(self, page_count): self.setFont("Helvetica", 8) self.setFillColor(colors.HexColor("#666666")) self.drawRightString(A4[0] - 2*cm, 1.2*cm, f"Page {self._pageNumber} of {page_count}") self.drawString(2*cm, 1.2*cm, "Dental Ward Guide | MBBS 3rd Year") self.setStrokeColor(colors.HexColor("#CCCCCC")) self.line(2*cm, 1.5*cm, A4[0]-2*cm, 1.5*cm) doc = SimpleDocTemplate( output_path, pagesize=A4, rightMargin=2*cm, leftMargin=2*cm, topMargin=2.5*cm, bottomMargin=2.5*cm, title="Dental Ward Guide for MBBS 3rd Year Students", author="Orris Medical AI" ) styles = getSampleStyleSheet() # Custom styles title_style = ParagraphStyle( 'CustomTitle', parent=styles['Title'], fontSize=26, textColor=colors.HexColor("#1a3a5c"), spaceAfter=6, fontName='Helvetica-Bold', alignment=TA_CENTER ) subtitle_style = ParagraphStyle( 'SubTitle', parent=styles['Normal'], fontSize=13, textColor=colors.HexColor("#2c6fad"), spaceAfter=4, fontName='Helvetica', alignment=TA_CENTER ) h1_style = ParagraphStyle( 'H1Custom', parent=styles['Heading1'], fontSize=16, textColor=colors.white, fontName='Helvetica-Bold', spaceBefore=14, spaceAfter=6, backColor=colors.HexColor("#1a3a5c"), leftIndent=-10, rightIndent=-10, leading=20, borderPad=6 ) h2_style = ParagraphStyle( 'H2Custom', parent=styles['Heading2'], fontSize=13, textColor=colors.HexColor("#1a3a5c"), fontName='Helvetica-Bold', spaceBefore=10, spaceAfter=4, borderPad=4, borderColor=colors.HexColor("#2c6fad"), leftIndent=0, leading=16 ) h3_style = ParagraphStyle( 'H3Custom', parent=styles['Heading3'], fontSize=11, textColor=colors.HexColor("#2c6fad"), fontName='Helvetica-Bold', spaceBefore=8, spaceAfter=3, leading=14 ) body_style = ParagraphStyle( 'BodyCustom', parent=styles['Normal'], fontSize=10, fontName='Helvetica', leading=14, spaceAfter=4, alignment=TA_JUSTIFY, textColor=colors.HexColor("#222222") ) bullet_style = ParagraphStyle( 'BulletCustom', parent=styles['Normal'], fontSize=10, fontName='Helvetica', leading=14, spaceAfter=3, leftIndent=16, bulletIndent=4, textColor=colors.HexColor("#222222") ) note_style = ParagraphStyle( 'NoteStyle', parent=styles['Normal'], fontSize=9.5, fontName='Helvetica-Oblique', leading=13, spaceAfter=4, textColor=colors.HexColor("#555555"), backColor=colors.HexColor("#f0f6ff"), leftIndent=8, rightIndent=8, borderPad=5 ) def section_header(text): """Returns a section header paragraph with colored background.""" return Paragraph(f" {text}", h1_style) def subsection_header(text): return Paragraph(text, h2_style) def sub_subsection(text): return Paragraph(text, h3_style) def body(text): return Paragraph(text, body_style) def bullet(text): return Paragraph(f"• {text}", bullet_style) def note(text): return Paragraph(f"<i>Note: {text}</i>", note_style) def spacer(h=0.3): return Spacer(1, h*cm) def hr(): return HRFlowable(width="100%", thickness=0.5, color=colors.HexColor("#CCCCCC"), spaceAfter=4, spaceBefore=4) # ---- TABLE HELPER ---- def make_table(data, col_widths=None, header_bg=colors.HexColor("#1a3a5c")): if col_widths is None: col_widths = [4*cm] * len(data[0]) t = Table(data, colWidths=col_widths, repeatRows=1) style = [ ('BACKGROUND', (0,0), (-1,0), header_bg), ('TEXTCOLOR', (0,0), (-1,0), colors.white), ('FONTNAME', (0,0), (-1,0), 'Helvetica-Bold'), ('FONTSIZE', (0,0), (-1,0), 9), ('FONTSIZE', (0,1), (-1,-1), 9), ('FONTNAME', (0,1), (-1,-1), 'Helvetica'), ('ROWBACKGROUNDS', (0,1), (-1,-1), [colors.white, colors.HexColor("#eef4fb")]), ('GRID', (0,0), (-1,-1), 0.4, colors.HexColor("#AAAAAA")), ('ALIGN', (0,0), (-1,-1), 'LEFT'), ('VALIGN', (0,0), (-1,-1), 'TOP'), ('TOPPADDING', (0,0), (-1,-1), 4), ('BOTTOMPADDING', (0,0), (-1,-1), 4), ('LEFTPADDING', (0,0), (-1,-1), 5), ('RIGHTPADDING', (0,0), (-1,-1), 5), ] t.setStyle(TableStyle(style)) return t # ============================ # BUILD CONTENT # ============================ story = [] # ---- COVER ---- story.append(spacer(3)) story.append(Paragraph("DENTAL WARD GUIDE", title_style)) story.append(Paragraph("For MBBS 3rd Year Students", subtitle_style)) story.append(spacer(0.3)) story.append(Paragraph("Complete Reference for Clinical Posting", ParagraphStyle('sub2', parent=subtitle_style, fontSize=11, textColor=colors.HexColor("#555555")))) story.append(spacer(0.5)) # Cover box cover_data = [["Prepared for:", "MBBS 3rd Year - 1st Day Dental Ward Posting"], ["Date:", "July 2026"], ["Compiled by:", "Orris Medical AI | Based on Goldman-Cecil Medicine, Harrison's (2025)"]] cover_table = Table(cover_data, colWidths=[4*cm, 13.5*cm]) cover_table.setStyle(TableStyle([ ('BACKGROUND', (0,0), (0,-1), colors.HexColor("#eef4fb")), ('FONTNAME', (0,0), (0,-1), 'Helvetica-Bold'), ('FONTNAME', (1,0), (1,-1), 'Helvetica'), ('FONTSIZE', (0,0), (-1,-1), 10), ('GRID', (0,0), (-1,-1), 0.5, colors.HexColor("#AAAAAA")), ('TOPPADDING', (0,0), (-1,-1), 6), ('BOTTOMPADDING', (0,0), (-1,-1), 6), ('LEFTPADDING', (0,0), (-1,-1), 8), ])) story.append(cover_table) story.append(spacer(0.5)) # Table of contents preview toc_data = [ ["#", "Section", "Page"], ["1", "Introduction & Ward Etiquette", "2"], ["2", "Dental History Taking", "2"], ["3", "Systematic Examination of the Oral Cavity", "4"], ["4", "Dental Charting & Notation", "5"], ["5", "Common Dental Conditions", "6"], ["6", "Investigations in Dentistry", "9"], ["7", "Systemic Diseases & Oral Manifestations", "10"], ["8", "Basic Dental Procedures (Observer's Guide)", "11"], ["9", "Emergency Situations in Dental Ward", "12"], ["10", "Quick Reference Checklists", "13"], ] story.append(Paragraph("Table of Contents", ParagraphStyle('toc_h', parent=h2_style, alignment=TA_CENTER))) story.append(make_table(toc_data, col_widths=[1.5*cm, 12.5*cm, 3.5*cm])) story.append(PageBreak()) # ============================ # SECTION 1 - INTRODUCTION # ============================ story.append(section_header("1. Introduction & Ward Etiquette")) story.append(spacer(0.2)) story.append(body("Welcome to your first clinical posting in the Dental Ward. This guide is designed to help you navigate the ward confidently, understand how to take a proper dental history, perform a systematic oral examination, and recognize common dental conditions. You are here primarily as an observer and learner - always seek permission before touching any patient and always work under supervision.")) story.append(spacer(0.2)) story.append(subsection_header("1.1 Ward Etiquette")) for b in [ "Always introduce yourself as a medical student and obtain patient consent before any interaction.", "Maintain professional attire - white coat, clean hands, and a name badge at all times.", "Wash hands before and after every patient contact (WHO 5 moments of hand hygiene).", "Do not use your mobile phone while at the bedside or during consultations.", "Address patients respectfully by their name and maintain patient confidentiality.", "When in doubt, always ask your supervisor before doing anything.", "Observe dental procedures from a safe distance unless invited closer by the dentist.", "Record all findings accurately and legibly in the case sheet." ]: story.append(bullet(b)) story.append(spacer(0.3)) story.append(note("Dental procedures carry infection risk. Always wear gloves, mask, and eye protection if you are assisting in a procedure.")) # ============================ # SECTION 2 - HISTORY TAKING # ============================ story.append(PageBreak()) story.append(section_header("2. Dental History Taking")) story.append(spacer(0.2)) story.append(body("A thorough history is the cornerstone of dental diagnosis. The dental history format follows the standard medical history framework but includes specific dental components. The primary goal is to understand the patient's complaint, place it in clinical context, and identify any systemic factors that could influence dental treatment.")) story.append(spacer(0.2)) story.append(subsection_header("2.1 Standard Format for Dental History")) # History table hist_data = [ ["Component", "What to Ask / Record"], ["Patient Details", "Name, age, sex, occupation, address, date of consultation"], ["Chief Complaint (CC)", "In patient's own words - 'What brings you here today?' - Record verbatim. Include site, duration."], ["History of Present Illness (HPI)", "Onset (sudden/gradual), duration, severity, character (throbbing, dull, sharp, constant/intermittent), aggravating factors (hot, cold, sweet), relieving factors, any previous similar episodes, any treatment taken"], ["Past Dental History (PDH)", "Frequency of dental visits (regular/irregular/never), previous extractions, fillings, root canals, orthodontic treatment, dentures. Any adverse reactions: haemorrhage post-extraction, difficulty with local anaesthesia, fainting."], ["Past Medical History (PMH)", "Diabetes, hypertension, cardiac disease, bleeding disorders, epilepsy, immunosuppression, liver/kidney disease. Hospitalizations, surgeries, blood transfusions."], ["Drug History", "Current medications (especially anticoagulants like warfarin, antiplatelets, bisphosphonates, steroids, antihypertensives, antiepileptics). OTC drugs, herbal supplements. Drug allergies (especially to local anaesthetics, penicillin, NSAIDs, latex)."], ["Allergy History", "Drug allergies, latex allergy, food allergies. Always ask specifically even if patient says 'no allergies'."], ["Family History (FH)", "Dental caries pattern in family, periodontal disease, malocclusion, genetic conditions (e.g., amelogenesis imperfecta, dentinogenesis imperfecta), oral cancer."], ["Social History (SH)", "Smoking (cigarettes, bidis, hookah - how much, how long), tobacco chewing/gutkha/paan, alcohol consumption (type, quantity, frequency), occupation (exposure to acids/trauma), stress levels, diet (frequency of sugar intake, fizzy drinks)."], ["Systemic Review", "Any swelling, lumps, weight loss, fever, fatigue, altered taste, dry mouth, difficulty chewing or swallowing, jaw clicking or locking."], ] story.append(make_table(hist_data, col_widths=[4.5*cm, 13*cm])) story.append(spacer(0.3)) story.append(subsection_header("2.2 Special Questions for Common Dental Complaints")) story.append(sub_subsection("For Pain (Toothache):")) pain_q = [ "SOCRATES: Site - which tooth/area? Onset - when did it start? Character - throbbing, dull, sharp, electric?", "Radiation - does pain radiate to ear, jaw, temple, neck?", "Associated features - swelling, fever, bad taste/smell, loose tooth?", "Timing - constant or intermittent? Worse at night?", "Exacerbating factors - hot food/drink, cold water, sweet foods, biting down, lying flat?", "Relieving factors - cold water (pulpitis sometimes relieved by cold), painkillers, holding cold water in mouth?", "Previous episodes of similar pain?", "Severity - score 0-10", ] for q in pain_q: story.append(bullet(q)) story.append(sub_subsection("For Swelling:")) for q in [ "Site and extent of swelling - intraoral or extraoral or both?", "Duration - how long has it been present?", "Onset - sudden or gradual? Any triggering event (trauma, previous toothache)?", "Character - hard or soft? Fluctuant (suggests abscess with pus)?", "Associated symptoms - pain, fever, trismus (difficulty opening mouth), difficulty swallowing?", "Any previous similar swelling? Any treatment?", ]: story.append(bullet(q)) story.append(sub_subsection("For Bleeding Gums:")) for q in [ "Spontaneous or on provocation (brushing, eating)?", "Duration and frequency", "Associated symptoms - pain, bad breath (halitosis), loose teeth?", "Oral hygiene practices - brushing frequency, technique, flossing?", "Any systemic bleeding elsewhere (nose bleeds, easy bruising)? - important to rule out haematological causes", "Medications - anticoagulants, phenytoin (causes gingival overgrowth), calcium channel blockers?", ]: story.append(bullet(q)) story.append(sub_subsection("For Mouth Ulcers:")) for q in [ "Single or multiple? Site (keratinized vs non-keratinized mucosa)?", "Duration - >3 weeks is a red flag and requires biopsy/further investigation", "Pain - aphthous ulcers are painful; malignant ulcers may be painless", "Recurrence pattern (suggests aphthous stomatitis)", "Associated systemic symptoms - bowel problems (Crohn's), genital ulcers (Behcet's), skin rash?", "Tobacco/alcohol use (risk for malignancy)", "Prior similar episodes and any treatment given", ]: story.append(bullet(q)) story.append(spacer(0.2)) story.append(note("RED FLAGS in dental history: Ulcer lasting >3 weeks | Unexplained loose teeth in a young patient | Jaw numbness/paraesthesia | Unexplained weight loss | Difficulty swallowing | Non-healing extraction socket | Trismus")) # ============================ # SECTION 3 - EXAMINATION # ============================ story.append(PageBreak()) story.append(section_header("3. Systematic Examination of the Oral Cavity")) story.append(spacer(0.2)) story.append(body("The oral examination follows a systematic 'outside-in' approach. You must examine from the outside (face and neck) progressively inward (lips, mucosa, gingiva, teeth, tongue, palate, oropharynx). Always use good lighting, dental mirror, and probe under supervision.")) story.append(subsection_header("3.1 General Examination")) for b in [ "General appearance: Well/ill-looking, pallor, jaundice, nutritional status", "Vitals if relevant: Pulse, BP (especially before dental procedures), temperature (if infection suspected)", "Build and nutrition: Obesity (diabetes risk), wasting (malignancy risk)", "Demeanour: Anxious (dental phobia - very common), distressed (acute pain)", ]: story.append(bullet(b)) story.append(subsection_header("3.2 Extraoral Examination (EO)")) story.append(sub_subsection("Face:")) for b in [ "Symmetry: Look for facial asymmetry (swelling, muscle wasting, Bell's palsy)", "Swelling: Location - submandibular, parotid, submental, buccal space?", "Skin changes over swelling: Erythema, pointing/fluctuance (abscess), sinus openings", "Draining sinuses: Cutaneous sinus tracts may indicate chronic dental abscess", "Lips: Colour, symmetry, angular cheilitis (B2/B12/iron deficiency or candida), herpes labialis", ]: story.append(bullet(b)) story.append(sub_subsection("Temporomandibular Joint (TMJ):")) for b in [ "Palpate TMJ bilaterally as patient opens/closes mouth", "Clicking or crepitus on movement", "Tenderness over joint", "Maximum mouth opening (normal: 35-45 mm, about 3 finger breadths)", "Deviation of jaw on opening (deviates toward affected side in TMJ disorder)", ]: story.append(bullet(b)) story.append(sub_subsection("Lymph Nodes:")) for b in [ "Submental, submandibular, anterior cervical chain, posterior cervical chain", "Preauricular, postauricular, occipital, supraclavicular", "Note: size, consistency (soft/firm/hard/rubbery), mobility (mobile/fixed), tenderness", "Hard, fixed, non-tender lymph nodes are a red flag for malignancy", ]: story.append(bullet(b)) story.append(subsection_header("3.3 Intraoral Examination (IO)")) story.append(body("Use a dental mirror and adequate light. Examine in a systematic order - do not go straight to the tooth the patient is pointing to.")) exam_order = [ ["Step", "Structure", "What to Look For"], ["1", "Lips (inner surface)", "Ulcers, pigmentation, fibroma, mucoceles"], ["2", "Buccal mucosa (cheeks)", "Linea alba (normal), ulcers, leukoplakia, erythroplakia, Fordyce spots, candidiasis, buccal mucosa carcinoma - examine using mirror/tongue depressor"], ["3", "Vestibule & Sulcus", "Swelling, sinus/fistula openings (parulis), obliteration of sulcus (suggests swelling)"], ["4", "Gingiva", "Colour (normal: coral pink), contour (scalloped), consistency, bleeding on probing, recession, hyperplasia, ulceration"], ["5", "Teeth", "Count teeth present, note missing, decayed, filled teeth (use dental charting). Colour changes, fractures, mobility (grade 1/2/3), sensitivity, shape/size anomalies"], ["6", "Hard palate", "Torus palatinus (normal bony prominence - do not confuse with pathology), ulcers, candidiasis"], ["7", "Soft palate & uvula", "Movement on saying 'Aah', ulcers, petechiae (thrombocytopenia), Kaposi's sarcoma"], ["8", "Tongue", "Dorsum: fissured, geographic, hairy tongue, coated tongue. Lateral borders (carcinoma site!) and ventral surface. Mobility and function."], ["9", "Floor of mouth", "Submandibular duct openings (Wharton's duct), ranula (mucous cyst), swelling, ulceration"], ["10", "Oropharynx", "Tonsils, posterior pharyngeal wall, any masses"], ] story.append(make_table(exam_order, col_widths=[1.5*cm, 4.5*cm, 11.5*cm])) story.append(spacer(0.2)) story.append(note("Any oral ulcer persisting for more than 3 weeks must be considered potentially malignant and referred for biopsy. Lateral border of tongue and floor of mouth are the most common sites for oral squamous cell carcinoma.")) # ============================ # SECTION 4 - DENTAL CHARTING # ============================ story.append(PageBreak()) story.append(section_header("4. Dental Charting & Notation")) story.append(spacer(0.2)) story.append(body("Dental charting is a standardized way of recording the condition of each tooth. Two main notation systems are used worldwide.")) story.append(subsection_header("4.1 FDI (Federation Dentaire Internationale) / ISO System")) story.append(body("This is the most widely used system internationally (also used in India). Each tooth has a 2-digit number: first digit = quadrant (1-4), second digit = tooth number within quadrant (1-8 from central incisor to 3rd molar).")) quadrant_data = [ ["Quadrant", "Permanent Teeth", "Primary Teeth"], ["Upper Right (Q1)", "11-18", "51-55"], ["Upper Left (Q2)", "21-28", "61-65"], ["Lower Left (Q3)", "31-38", "71-75"], ["Lower Right (Q4)", "41-48", "81-85"], ] story.append(make_table(quadrant_data, col_widths=[5*cm, 6.5*cm, 6*cm])) story.append(spacer(0.2)) story.append(body("Example: Tooth 36 = lower left first molar (Q3, tooth 6). Tooth 11 = upper right central incisor.")) story.append(subsection_header("4.2 Universal Numbering System (USA)")) story.append(body("Numbers 1-32 for permanent teeth (1 = upper right 3rd molar, going round to 32 = lower right 3rd molar). Letters A-T for primary teeth. Less commonly used outside USA.")) story.append(subsection_header("4.3 Dental Charting Symbols (Common)")) charting_data = [ ["Symbol/Abbreviation", "Meaning"], ["/ (slash through box)", "Extracted tooth"], ["X or shaded box", "Decayed (carious) tooth"], ["F or shaded tooth surface", "Filled tooth"], ["UE", "Unerupted"], ["PE", "Partially erupted"], ["RCT or RC", "Root canal treated"], ["Cr or Crown symbol", "Crown/cap placed"], ["Mobility Grade 1", "Slightly more than normal movement"], ["Mobility Grade 2", "Moderate movement (1-2 mm buccolingual)"], ["Mobility Grade 3", "Severe movement (>2 mm) in all directions or depressible"], ["BPE 0-4", "Basic Periodontal Examination scores"], ] story.append(make_table(charting_data, col_widths=[6*cm, 11.5*cm])) story.append(spacer(0.2)) story.append(subsection_header("4.4 DMFT Index")) story.append(body("The DMFT Index is the most commonly used index to measure dental caries experience in a population or individual. D = Decayed, M = Missing (due to caries), F = Filled, T = Teeth. Maximum score = 28 (or 32 if wisdom teeth counted). Higher DMFT = poorer dental health.")) # ============================ # SECTION 5 - COMMON CONDITIONS # ============================ story.append(PageBreak()) story.append(section_header("5. Common Dental Conditions")) story.append(spacer(0.2)) story.append(subsection_header("5.1 Dental Caries (Tooth Decay)")) story.append(body("<b>Definition:</b> Infectious, multi-factorial disease resulting in demineralization and destruction of the hard tissues of the tooth by acids produced by bacteria (primarily <i>Streptococcus mutans</i>).")) caries_data = [ ["Feature", "Details"], ["Cause", "Bacteria (S. mutans, Lactobacillus) + fermentable carbohydrates + susceptible tooth + time (Keyes triad)"], ["Symptoms", "Initially asymptomatic. Later: sensitivity to sweet, cold, hot. Pain when cavity reaches pulp."], ["Signs", "White spot (early demineralization), brown/black cavity, visible hole in tooth"], ["Classification", "Black's classification: Class I (pit & fissure), Class II (proximal of posteriors), Class III (proximal of anteriors), Class IV (proximal + incisal edge), Class V (gingival 1/3 of buccal/lingual), Class VI (cusp tips)"], ["Treatment", "Early: remineralization with fluoride. Cavity: excavation + restoration (filling). Pulp involved: root canal treatment (RCT). Irreparable: extraction."], ["Prevention", "Fluoride toothpaste, fissure sealants, dietary advice, oral hygiene instruction, regular check-ups"], ] story.append(make_table(caries_data, col_widths=[4*cm, 13.5*cm])) story.append(spacer(0.3)) story.append(subsection_header("5.2 Pulpitis")) story.append(body("<b>Definition:</b> Inflammation of the dental pulp (nerve and blood vessels inside the tooth), usually a sequel to caries.")) pulp_data = [ ["Type", "Reversible Pulpitis", "Irreversible Pulpitis"], ["Pain character", "Sharp, short-lived on stimulus (cold, sweet)", "Severe, spontaneous, throbbing, prolonged after stimulus"], ["Pain at night", "Usually absent", "Often worse at night (throbbing)"], ["Relief with cold", "Pain resolves within seconds", "Pain may linger for minutes or hours after cold"], ["Treatment", "Remove cause (fill cavity), pulp may recover", "Root canal treatment (RCT) or extraction"], ] t = Table(pulp_data, colWidths=[5.5*cm, 6.5*cm, 5.5*cm]) t.setStyle(TableStyle([ ('BACKGROUND', (0,0), (-1,0), colors.HexColor("#1a3a5c")), ('TEXTCOLOR', (0,0), (-1,0), colors.white), ('FONTNAME', (0,0), (-1,0), 'Helvetica-Bold'), ('FONTNAME', (0,1), (-1,-1), 'Helvetica'), ('FONTSIZE', (0,0), (-1,-1), 9), ('BACKGROUND', (0,1), (0,-1), colors.HexColor("#eef4fb")), ('FONTNAME', (0,1), (0,-1), 'Helvetica-Bold'), ('ROWBACKGROUNDS', (1,1), (-1,-1), [colors.white, colors.HexColor("#f5f5f5")]), ('GRID', (0,0), (-1,-1), 0.4, colors.HexColor("#AAAAAA")), ('ALIGN', (0,0), (-1,-1), 'LEFT'), ('VALIGN', (0,0), (-1,-1), 'TOP'), ('TOPPADDING', (0,0), (-1,-1), 5), ('BOTTOMPADDING', (0,0), (-1,-1), 5), ('LEFTPADDING', (0,0), (-1,-1), 5), ])) story.append(t) story.append(spacer(0.3)) story.append(subsection_header("5.3 Periapical Abscess")) story.append(body("<b>Definition:</b> Localized collection of pus at the apex (tip) of the tooth root, usually following pulp necrosis (dead pulp). This is one of the most common reasons for emergency dental attendance.")) for b in [ "<b>Symptoms:</b> Severe, constant, throbbing pain. Tender on biting/touching the tooth. The tooth is 'raised' in its socket (patient feels the tooth is high when biting).", "<b>Signs:</b> Tooth tender to percussion (TTP - tap tooth with mirror handle). Swelling (may spread to face - cellulitis). Sinus/fistula in gum (parulis - discharge of pus). Systemic: fever, malaise, cervical lymphadenopathy.", "<b>Investigations:</b> Periapical X-ray shows periapical radiolucency (dark area at root tip). Vitality test - non-vital tooth.", "<b>Treatment:</b> Drainage - either through root canal (open access cavity) or via incision of swelling if fluctuant (I&D). Antibiotics if systemic features (amoxicillin 500mg TDS or metronidazole 400mg TDS). Definitive: RCT or extraction.", "<b>Danger:</b> Untreated dental abscess can spread to deep neck spaces (Ludwig's angina - life-threatening airway emergency), cavernous sinus, or cause septicaemia.", ] for b in [ "Symptoms: Severe, constant, throbbing pain. Tender on biting. Tooth feels 'raised' (extruded in socket due to pressure).", "Signs: Tender to percussion (TTP). Facial swelling/cellulitis. Parulis (gum boil - sinus opening). Fever and lymphadenopathy if spreading.", "Investigations: Periapical X-ray - periapical radiolucency. Vitality test - non-vital.", "Treatment: Drainage (through root canal or I&D if fluctuant), antibiotics if systemic features, then RCT or extraction.", "WARNING: Can spread to cause Ludwig's angina (floor of mouth cellulitis - airway emergency) or cavernous sinus thrombosis.", ]: story.append(bullet(b)) story.append(spacer(0.3)) story.append(subsection_header("5.4 Periodontal Disease")) story.append(body("<b>Gingivitis:</b> Inflammation confined to the gingiva (gums) without bone loss. Reversible. Caused by plaque accumulation. Signs: redness, swelling, bleeding on probing/brushing, halitosis. Treatment: professional scaling + oral hygiene instruction.")) story.append(spacer(0.15)) story.append(body("<b>Periodontitis:</b> Extension of inflammation to periodontal ligament and supporting alveolar bone with irreversible bone loss. Signs: pocket formation (>3mm), gingival recession, bone loss on X-ray, tooth mobility, furcation involvement. Treatment: scaling and root planing (SRP), surgical periodontal therapy for advanced cases.")) story.append(spacer(0.15)) story.append(body("<b>Pericoronitis:</b> Inflammation around a partially erupted tooth (most commonly lower 3rd molar/wisdom tooth). Food and bacteria trapped under operculum (flap of gum). Signs: pain, swelling, trismus, bad taste. Treatment: irrigation under operculum, antibiotics, operculectomy or extraction when acute episode settles.")) story.append(spacer(0.3)) story.append(subsection_header("5.5 Oral Mucosal Diseases")) story.append(sub_subsection("Aphthous Stomatitis (Canker Sores):")) story.append(body("Most common cause of oral ulcers. Affects up to 20% of population. Recurrent, painful ulcers on non-keratinized mucosa (buccal mucosa, ventral tongue, lips, alveolar mucosa).")) aphth_data = [ ["Type", "Size", "Duration", "No."], ["Minor (most common)", "<0.5 cm, flat", "5-10 days", "1-5"], ["Major", ">0.5 cm, raised borders, deeper", "Weeks to months", "Usually 1"], ["Herpetiform", "Very small, cluster", "7-10 days", "Multiple (10-100)"], ] story.append(make_table(aphth_data, col_widths=[5*cm, 5.5*cm, 3.5*cm, 3.5*cm])) story.append(body("Treatment: Topical steroids (triamcinolone gel), topical anaesthetic (lignocaine gel), tetracycline mouthwash. No cure for recurrence.")) story.append(note("Aphthous ulcers occur on non-keratinized (movable) mucosa. Herpes ulcers occur on keratinized (attached, fixed) mucosa - hard palate and attached gingiva - this is a key distinguishing feature.")) story.append(sub_subsection("Oral Candidiasis (Thrush):")) story.append(body("Fungal infection by <i>Candida albicans</i>. Most common oral fungal infection. Forms:")) for b in [ "Pseudomembranous (most common): White, creamy plaques that can be WIPED OFF leaving raw/bleeding surface. Common in neonates, elderly, immunosuppressed (HIV, steroid users, diabetics).", "Erythematous: Red patches on palate or dorsum of tongue.", "Angular cheilitis: Redness/cracking at corners of mouth.", "Treatment: Topical antifungals (nystatin suspension 4x/day) or systemic (fluconazole 150mg single dose for severe cases). Treat underlying cause.", ]: story.append(bullet(b)) story.append(sub_subsection("Leukoplakia:")) story.append(body("White patch that cannot be rubbed off and cannot be diagnosed as any other condition. Potentially malignant. Risk factors: tobacco (smoking or chewing), alcohol, chronic irritation. Must biopsy any leukoplakia to assess for dysplasia or malignancy. Erythroplakia (red patch) carries higher malignant transformation risk than leukoplakia.")) story.append(sub_subsection("Oral Submucous Fibrosis (OSMF):")) story.append(body("Chronic progressive scarring condition of oral mucosa. Strongly associated with areca nut (betel nut/gutkha) chewing. Very common in South Asia. Progressive trismus (restricted mouth opening), blanching and stiffening of mucosa, burning sensation. Potentially malignant - 7-13% malignant transformation. Treatment: cessation of habit, intralesional steroids, physiotherapy for trismus.")) # ============================ # SECTION 6 - INVESTIGATIONS # ============================ story.append(PageBreak()) story.append(section_header("6. Investigations in Dentistry")) story.append(spacer(0.2)) story.append(subsection_header("6.1 Radiographs (X-rays)")) xray_data = [ ["Type of X-ray", "What it Shows", "Common Uses"], ["Periapical (PA) X-ray", "Individual tooth and surrounding bone (root, PDL space, lamina dura, periapex)", "Caries, periapical abscess, root fracture, impacted teeth"], ["Bitewing X-ray", "Crowns of upper and lower posterior teeth on same film", "Proximal (interproximal) caries - best view for early caries; assessing bone levels"], ["Orthopantomogram (OPG / Panoramic)", "Entire dentition, jaws, TMJ, sinuses in one film", "Overview of all teeth, impacted wisdom teeth, fractures, cysts, tumours, bone assessment"], ["Occlusal X-ray", "Cross-sectional view of arch (upper or lower)", "Stones in salivary ducts, palatal/mandibular cysts, supernumerary teeth"], ["CBCT (Cone Beam CT)", "3D imaging of jaws and teeth", "Implant planning, complex impactions, jaw tumours, bone defects - not routine, used for specific indications"], ["Lateral Cephalogram", "Side profile of skull and jaws", "Orthodontic assessment, skeletal relationships"], ] story.append(make_table(xray_data, col_widths=[4.5*cm, 5.5*cm, 7.5*cm])) story.append(spacer(0.2)) story.append(note("On a PA X-ray: Dense (white) = bone/enamel/metal/root. Lucent (dark) = caries/abscess/cyst/pulp. Periapical radiolucency (dark halo around root tip) = periapical infection/granuloma/cyst.")) story.append(subsection_header("6.2 Vitality Tests")) vital_data = [ ["Test", "Method", "Normal Response", "Clinical Use"], ["Cold Test (most common)", "Ethyl chloride spray or ice on cotton pellet applied to tooth", "Brief, sharp sensation that resolves immediately", "Non-vital tooth = NO response. Irreversible pulpitis = prolonged pain after removal of stimulus."], ["Heat Test", "Warm gutta percha or warm water applied to tooth", "Brief sensation", "Useful if patient reports heat aggravates pain"], ["Electric Pulp Test (EPT)", "Electric current applied via probe on tooth surface", "Patient reports tingling/sensation", "Confirms pulp vitality but does not assess health of pulp"], ["Test Cavity", "Drill into tooth without anaesthesia", "Pain response", "Only if other tests equivocal; rarely used"], ] story.append(make_table(vital_data, col_widths=[3.5*cm, 4*cm, 4*cm, 6*cm])) story.append(subsection_header("6.3 Periodontal Investigations")) for b in [ "Probing pocket depth (PPD): Measured with calibrated periodontal probe. Normal sulcus <3mm. Periodontitis: >3mm.", "Bleeding on Probing (BOP): Indicates active gingival inflammation.", "Furcation involvement: Probing between roots of multi-rooted teeth. Grades I/II/III.", "BPE (Basic Periodontal Examination): Screening tool using WHO probe. Scores 0-4 per sextant. Score 4 = pocket >5.5mm.", "Tooth mobility grading: Grade 1 (<1mm horizontal), Grade 2 (1-2mm horizontal), Grade 3 (>2mm or vertical movement).", ]: story.append(bullet(b)) story.append(subsection_header("6.4 Laboratory Investigations")) for b in [ "CBC (Complete Blood Count): For suspected anaemia, leukaemia, bleeding disorders, infection.", "Blood glucose (fasting/random): Diabetes screening (associated with periodontal disease, poor healing, candidiasis).", "Coagulation profile (PT/INR, aPTT): Before surgical procedures, especially in patients on anticoagulants.", "Biopsy: For any suspicious oral lesion (ulcer >3 weeks, leukoplakia, erythroplakia, suspected malignancy).", "Culture and sensitivity: For oral infections, especially if not responding to empirical antibiotics.", "FNAC (Fine Needle Aspiration Cytology): For neck lumps/lymphadenopathy.", ]: story.append(bullet(b)) # ============================ # SECTION 7 - SYSTEMIC DISEASES # ============================ story.append(PageBreak()) story.append(section_header("7. Systemic Diseases & Oral Manifestations")) story.append(spacer(0.2)) story.append(body("The oral cavity is often a mirror of systemic health. Many systemic diseases have characteristic oral manifestations that an MBBS student should recognize. This is also relevant for clinical considerations before dental treatment.")) sys_data = [ ["Systemic Disease", "Oral Manifestation / Dental Relevance"], ["Diabetes Mellitus", "Increased caries, severe periodontitis, poor healing, recurrent candidiasis, xerostomia (dry mouth), burning mouth syndrome. Uncontrolled DM = contraindication for elective surgery."], ["Haematological disorders\n(anaemia, leukaemia,\nthrombocytopenia)", "Anaemia: Pale oral mucosa, atrophic glossitis, angular cheilitis. Leukaemia: Gingival bleeding, gingival hyperplasia, oral ulcers (especially AML). Thrombocytopenia: Petechiae on soft palate, gingival bleeding."], ["HIV/AIDS", "Oral candidiasis (often first sign), hairy leukoplakia (lateral tongue, caused by EBV), Kaposi's sarcoma (red/purple lesions on palate), major aphthous ulcers, linear gingival erythema, necrotising periodontitis."], ["Hypertension", "Calcium channel blockers (amlodipine, nifedipine) cause gingival hyperplasia. Risk of hypertensive crisis with vasoconstrictors in LA. Check BP before dental treatment."], ["Cardiac disease\n(valvular disease)", "Antibiotic prophylaxis needed before invasive dental procedures in patients with high-risk cardiac conditions (prosthetic valves, previous infective endocarditis, cyanotic congenital heart disease)."], ["Anticoagulant therapy\n(warfarin, aspirin)", "Increased bleeding risk. Check INR <3.5 for minor procedures. Do NOT stop warfarin for simple extractions - apply local haemostatic measures instead."], ["Bisphosphonate therapy", "MRONJ (Medication-Related Osteonecrosis of the Jaw): Exposed bone that fails to heal, particularly after extraction. More common with IV bisphosphonates. Avoid extractions if possible."], ["Vitamin deficiencies", "Vitamin C deficiency (scurvy): Gingival bleeding, haemorrhagic gingivitis. B12/folate deficiency: Atrophic glossitis, aphthous ulcers. Vitamin D deficiency: Delayed tooth eruption, dental caries."], ["Renal failure", "Uraemic stomatitis (white/grey pseudomembrane), altered taste (metallic), dry mouth. Avoid nephrotoxic drugs. Adjust drug doses."], ["Pregnancy", "Pregnancy gingivitis (hormonal - always explain this to pregnant patients). Pregnancy epulis (pyogenic granuloma on gums). Avoid X-rays in 1st trimester, avoid certain drugs."], ["Paget's disease of bone", "Enlargement of maxilla causing dental spacing, difficulty fitting dentures, leonine facies in advanced cases."], ["Crohn's disease / IBD", "Aphthous-like ulcers, cobblestone appearance of buccal mucosa, lip swelling, mucogingivitis."], ["Sjogren's syndrome", "Severe xerostomia (dry mouth), parotid enlargement, dramatically increased caries (especially cervical caries), dysphagia. Dry eyes (sicca syndrome)."], ] story.append(make_table(sys_data, col_widths=[5*cm, 12.5*cm])) # ============================ # SECTION 8 - PROCEDURES # ============================ story.append(PageBreak()) story.append(section_header("8. Basic Dental Procedures (Observer's Guide)")) story.append(spacer(0.2)) story.append(body("As an MBBS student on posting, you will mainly observe these procedures. Understanding what is happening will help you learn and ask good questions.")) proc_data = [ ["Procedure", "What Happens", "Key Points to Note"], ["Scaling & Root Planing", "Removal of calculus (tartar) and plaque from tooth surfaces and roots using ultrasonic scaler + hand instruments", "Painful if LA not given. Bleeding expected. Post-op sensitivity for days. Foundation of periodontal treatment."], ["Dental Extraction", "Tooth removal under local anaesthesia (LA) using forceps/elevators", "LA injection technique, socket bleeding, sutures if needed. Post-op instructions: bite on gauze, no hot food, no rinsing for 24h, no smoking."], ["Root Canal Treatment (RCT/Endodontics)", "Removal of pulp tissue, shaping and filling of root canals. Done to save a non-vital tooth.", "Multiple visits usually. Rubber dam used. Pain after first visit is common. Final restoration needed after RCT."], ["Dental Filling (Restoration)", "Caries removed, cavity prepared, filled with composite resin (tooth-coloured) or amalgam", "Bonding agents, acid etching for composite. Occlusion checked after filling."], ["Incision & Drainage (I&D)", "Surgical drainage of dental abscess by incision into fluctuant swelling under LA", "Corrugated rubber drain may be placed. Antibiotics used as adjunct, not substitute for drainage."], ["Local Anaesthesia (LA)", "Most common: Inferior alveolar nerve block (mandibular teeth), infiltration anaesthesia (maxillary teeth). Lignocaine 2% with adrenaline 1:80,000 is standard.", "Aspirate before injection (avoid IV injection). Adrenaline contraindicated in uncontrolled cardiac disease. Complications: failed block, haematoma, temporary facial nerve palsy."], ["Suturing", "Absorbable (Vicryl 3-0) or non-absorbable sutures after surgical extractions or I&D. Non-absorbable removed in 5-7 days.", "Interrupted sutures most common. Figure-of-8 for extraction socket haemostasis."], ["Dental X-ray", "Patient bites on periapical film/sensor, X-ray tube positioned outside. Bitewing: both arches same film.", "Radiation protection: lead apron for patient. Paralleling technique for accurate images."], ] story.append(make_table(proc_data, col_widths=[4*cm, 6.5*cm, 7*cm])) # ============================ # SECTION 9 - EMERGENCIES # ============================ story.append(PageBreak()) story.append(section_header("9. Emergency Situations in the Dental Ward")) story.append(spacer(0.2)) story.append(body("Emergencies can occur during or after dental procedures. Know what to look for and call for help immediately.")) story.append(subsection_header("9.1 Post-extraction Haemorrhage")) for b in [ "Primary: Bleeding during/immediately after extraction. Usually controlled by pressure (bite on gauze for 30 min).", "Reactionary: Bleeding within first few hours - clot dislodged, vasoconstriction wearing off.", "Secondary: Bleeding 5-10 days post-extraction - usually due to infection.", "Management: Apply pressure, check clotting, irrigate socket, pack with haemostatic material, suture if needed. Rule out bleeding disorder.", ]: story.append(bullet(b)) story.append(subsection_header("9.2 Syncope (Vasovagal Attack)")) story.append(body("Most common medical emergency in dental practice. Caused by anxiety, pain, or sight of blood/needle.")) for b in [ "Features: Prodrome of pallor, sweating, nausea, dizziness, then brief loss of consciousness.", "Management: Lay patient flat (Trendelenburg position), loosen clothing, ensure airway. Usually self-limiting. Monitor vital signs.", ]: story.append(bullet(b)) story.append(subsection_header("9.3 Anaphylaxis")) for b in [ "Causes: LA, latex, antibiotics (penicillin), iodine.", "Features: Urticaria, angioedema, bronchospasm, hypotension, tachycardia.", "Management: STOP procedure. Adrenaline (epinephrine) 0.5mg IM (0.5mL of 1:1000) immediately. Call for help. ABC management. Antihistamine + steroid as adjuncts.", ]: story.append(bullet(b)) story.append(subsection_header("9.4 Ludwig's Angina")) story.append(body("Life-threatening bilateral cellulitis of submandibular, sublingual, and submental spaces. Usually from mandibular 2nd/3rd molar infection. AIRWAY EMERGENCY.")) for b in [ "Features: Brawny (board-like, non-fluctuant) swelling of floor of mouth and neck, 'hot potato' voice, dysphagia, drooling, stridor, raised tongue.", "Management: AIRWAY FIRST - may need emergency tracheostomy. IV antibiotics (high-dose penicillin + metronidazole), surgical drainage.", ]: story.append(bullet(b)) story.append(subsection_header("9.5 Dry Socket (Alveolar Osteitis)")) for b in [ "Painful condition 2-4 days after extraction due to loss/disintegration of blood clot.", "Features: Severe throbbing pain radiating to ear/temple. Empty socket with visible bone. Halitosis.", "Risk factors: Smoking, poor oral hygiene, mandibular molars, oral contraceptive use, traumatic extraction.", "Management: Gentle irrigation, placement of alvogyl (eugenol-based dressing) in socket. Analgesics. Dressing changed every 2-3 days.", ]: story.append(bullet(b)) # ============================ # SECTION 10 - CHECKLISTS # ============================ story.append(PageBreak()) story.append(section_header("10. Quick Reference Checklists")) story.append(spacer(0.2)) story.append(subsection_header("Checklist 1: Complete Dental History (for Case Sheet)")) checklist1 = [ "[ ] Patient ID: Name, Age, Sex, Occupation, Address", "[ ] Chief Complaint: In patient's own words, site, duration", "[ ] History of Presenting Illness: SOCRATES (Site, Onset, Character, Radiation, Associated factors, Timing, Exacerbating/Relieving factors, Severity)", "[ ] Past Dental History: Regularity of dental visits, previous treatments, adverse reactions to LA/extractions", "[ ] Past Medical History: Diabetes, hypertension, cardiac disease, bleeding disorder, epilepsy, liver/renal disease", "[ ] Drug History: Current medications, especially anticoagulants, bisphosphonates, antihypertensives, steroids", "[ ] Allergy History: Drug allergies, latex allergy (ask even if patient says 'no allergies')", "[ ] Social History: Tobacco use (smoking/chewing type, quantity, duration), alcohol, diet habits", "[ ] Family History: Relevant genetic/dental conditions", "[ ] Systemic Review: Swelling, fever, dysphagia, weight loss, altered sensation", ] for item in checklist1: story.append(Paragraph(item, ParagraphStyle('check', parent=bullet_style, fontName='Courier', fontSize=9.5))) story.append(spacer(0.3)) story.append(subsection_header("Checklist 2: Systematic Oral Examination")) checklist2 = [ "[ ] General examination: Appearance, build, pallor", "[ ] Extraoral - Face: Symmetry, swelling, skin changes, scars, sinuses", "[ ] Extraoral - Lips: Colour, angular cheilitis, herpes labialis", "[ ] Extraoral - TMJ: Click, crepitus, tenderness, mouth opening measurement", "[ ] Extraoral - Lymph nodes: Submental, submandibular, cervical chain", "[ ] Intraoral - Lips (inner), buccal mucosa (both sides), sulcus", "[ ] Intraoral - Gingiva: Colour, contour, bleeding, recession, hyperplasia", "[ ] Intraoral - Teeth: Missing, decayed, filled, mobility, sensitivity, charting", "[ ] Intraoral - Hard palate, soft palate, uvula", "[ ] Intraoral - Tongue: Dorsum, lateral borders, ventral surface, floor of mouth", "[ ] Intraoral - Oropharynx, tonsils", "[ ] Record all findings systematically in case sheet", ] for item in checklist2: story.append(Paragraph(item, ParagraphStyle('check2', parent=bullet_style, fontName='Courier', fontSize=9.5))) story.append(spacer(0.3)) story.append(subsection_header("Checklist 3: Red Flags - Always Report to Supervisor")) redflag_data = [ ["Red Flag", "Possible Significance"], ["Oral ulcer persisting >3 weeks", "Oral squamous cell carcinoma or other malignancy"], ["White/red patch that cannot be rubbed off", "Leukoplakia/erythroplakia - potentially malignant"], ["Unexplained loose teeth in young patient", "Periodontitis, leukaemia, LCH (Langerhans cell histiocytosis), aggressive tumour"], ["Jaw numbness or lip paraesthesia", "Inferior alveolar nerve involvement by tumour (Vincent's sign)"], ["Unexplained swelling not responding to antibiotics", "Deep neck space infection, malignancy, TB lymphadenopathy"], ["Restricted mouth opening (trismus) without clear cause", "OSMF, fibrosis, masticator space infection, malignancy"], ["Rapidly expanding jaw swelling in child", "Ameloblastoma, dentigerous cyst, Burkitt's lymphoma (in endemic malaria areas)"], ["Unexplained weight loss + oral lesion", "Underlying malignancy, HIV"], ["Gingival bleeding not responding to scaling", "Leukaemia, thrombocytopenia, haemophilia"], ] story.append(make_table(redflag_data, col_widths=[6*cm, 11.5*cm], header_bg=colors.HexColor("#8B0000"))) story.append(spacer(0.3)) story.append(Paragraph("Good Luck on Your First Day!", ParagraphStyle('goodluck', parent=title_style, fontSize=18, textColor=colors.HexColor("#1a3a5c")))) story.append(body("Remember: observe carefully, ask questions respectfully, and never perform any procedure without direct supervision. The dental team is there to teach you. Be enthusiastic, be punctual, and maintain professionalism at all times.")) story.append(spacer(0.2)) story.append(Paragraph("Sources: Goldman-Cecil Medicine (2024) | Harrison's Principles of Internal Medicine 22E (2025) | Pocket Dentistry (Greenwood) | Oxford Handbook of Clinical Dentistry (Mitchell)", ParagraphStyle('refs', parent=styles['Normal'], fontSize=8, textColor=colors.HexColor("#777777"), alignment=TA_CENTER))) # BUILD doc.build(story, canvasmaker=NumberedCanvas) print("PDF created successfully:", output_path) EOF
Retry please
mkdir -p /home/daytona/workspace/dental-ward-guide
~/dental-ward-guide/generate_pdf.py
from reportlab.lib.pagesizes import A4
from reportlab.lib import colors
from reportlab.lib.styles import getSampleStyleSheet, ParagraphStyle
from reportlab.lib.units import cm
from reportlab.platypus import SimpleDocTemplate, Paragraph, Spacer, Table, TableStyle, HRFlowable, PageBreak
from reportlab.lib.enums import TA_CENTER, TA_LEFT, TA_JUSTIFY
from reportlab.pdfgen import canvas
output_path = "/home/daytona/workspace/dental-ward-guide/Dental_Ward_Guide_MBBS.pdf"
class NumberedCanvas(canvas.Canvas):
def __init__(self, *args, **kwargs):
canvas.Canvas.__init__(self, *args, **kwargs)
self._saved_page_states = []
def showPage(self):
self._saved_page_states.append(dict(self.__dict__))
self._startPage()
def save(self):
num_pages = len(self._saved_page_states)
for state in self._saved_page_states:
self.__dict__.update(state)
self.draw_page_number(num_pages)
canvas.Canvas.showPage(self)
canvas.Canvas.save(self)
def draw_page_number(self, page_count):
self.setFont("Helvetica", 8)
self.setFillColor(colors.HexColor("#666666"))
self.drawRightString(A4[0] - 2*cm, 1.2*cm, "Page %d of %d" % (self._pageNumber, page_count))
self.drawString(2*cm, 1.2*cm, "Dental Ward Guide | MBBS 3rd Year")
self.setStrokeColor(colors.HexColor("#CCCCCC"))
self.line(2*cm, 1.5*cm, A4[0]-2*cm, 1.5*cm)
doc = SimpleDocTemplate(
output_path,
pagesize=A4,
rightMargin=2*cm,
leftMargin=2*cm,
topMargin=2.5*cm,
bottomMargin=2.5*cm,
title="Dental Ward Guide for MBBS 3rd Year Students",
author="Orris Medical AI"
)
styles = getSampleStyleSheet()
title_style = ParagraphStyle('CustomTitle', parent=styles['Title'],
fontSize=26, textColor=colors.HexColor("#1a3a5c"),
spaceAfter=6, fontName='Helvetica-Bold', alignment=TA_CENTER)
subtitle_style = ParagraphStyle('SubTitle', parent=styles['Normal'],
fontSize=13, textColor=colors.HexColor("#2c6fad"),
spaceAfter=4, fontName='Helvetica', alignment=TA_CENTER)
h1_style = ParagraphStyle('H1Custom', parent=styles['Heading1'],
fontSize=15, textColor=colors.white, fontName='Helvetica-Bold',
spaceBefore=14, spaceAfter=6,
backColor=colors.HexColor("#1a3a5c"),
leading=20, borderPad=6)
h2_style = ParagraphStyle('H2Custom', parent=styles['Heading2'],
fontSize=13, textColor=colors.HexColor("#1a3a5c"),
fontName='Helvetica-Bold', spaceBefore=10, spaceAfter=4, leading=16)
h3_style = ParagraphStyle('H3Custom', parent=styles['Heading3'],
fontSize=11, textColor=colors.HexColor("#2c6fad"),
fontName='Helvetica-Bold', spaceBefore=8, spaceAfter=3, leading=14)
body_style = ParagraphStyle('BodyCustom', parent=styles['Normal'],
fontSize=10, fontName='Helvetica', leading=14, spaceAfter=4,
alignment=TA_JUSTIFY, textColor=colors.HexColor("#222222"))
bullet_style = ParagraphStyle('BulletCustom', parent=styles['Normal'],
fontSize=10, fontName='Helvetica', leading=14, spaceAfter=3,
leftIndent=16, textColor=colors.HexColor("#222222"))
note_style = ParagraphStyle('NoteStyle', parent=styles['Normal'],
fontSize=9.5, fontName='Helvetica-Oblique', leading=13, spaceAfter=4,
textColor=colors.HexColor("#444444"), backColor=colors.HexColor("#fff8e1"),
leftIndent=8, rightIndent=8, borderPad=5)
check_style = ParagraphStyle('CheckStyle', parent=styles['Normal'],
fontSize=9.5, fontName='Courier', leading=14, spaceAfter=3,
leftIndent=8, textColor=colors.HexColor("#222222"))
ref_style = ParagraphStyle('RefStyle', parent=styles['Normal'],
fontSize=8, textColor=colors.HexColor("#777777"), alignment=TA_CENTER)
def sec(text):
return Paragraph(" " + text, h1_style)
def sub(text):
return Paragraph(text, h2_style)
def subsub(text):
return Paragraph(text, h3_style)
def body(text):
return Paragraph(text, body_style)
def bul(text):
return Paragraph(u"\u2022 " + text, bullet_style)
def note(text):
return Paragraph("<i>Note: " + text + "</i>", note_style)
def sp(h=0.3):
return Spacer(1, h*cm)
def hr():
return HRFlowable(width="100%", thickness=0.5,
color=colors.HexColor("#CCCCCC"), spaceAfter=4, spaceBefore=4)
def make_table(data, col_widths=None, hdr_bg=None):
if hdr_bg is None:
hdr_bg = colors.HexColor("#1a3a5c")
if col_widths is None:
col_widths = [4*cm] * len(data[0])
t = Table(data, colWidths=col_widths, repeatRows=1)
ts = TableStyle([
('BACKGROUND', (0, 0), (-1, 0), hdr_bg),
('TEXTCOLOR', (0, 0), (-1, 0), colors.white),
('FONTNAME', (0, 0), (-1, 0), 'Helvetica-Bold'),
('FONTSIZE', (0, 0), (-1, 0), 9),
('FONTSIZE', (0, 1), (-1, -1), 9),
('FONTNAME', (0, 1), (-1, -1), 'Helvetica'),
('ROWBACKGROUNDS', (0, 1), (-1, -1), [colors.white, colors.HexColor("#eef4fb")]),
('GRID', (0, 0), (-1, -1), 0.4, colors.HexColor("#AAAAAA")),
('ALIGN', (0, 0), (-1, -1), 'LEFT'),
('VALIGN', (0, 0), (-1, -1), 'TOP'),
('TOPPADDING', (0, 0), (-1, -1), 4),
('BOTTOMPADDING', (0, 0), (-1, -1), 4),
('LEFTPADDING', (0, 0), (-1, -1), 5),
('RIGHTPADDING', (0, 0), (-1, -1), 5),
])
t.setStyle(ts)
return t
story = []
# ── COVER ──────────────────────────────────────────────────────────────────
story.append(sp(3))
story.append(Paragraph("DENTAL WARD GUIDE", title_style))
story.append(Paragraph("For MBBS 3rd Year Students", subtitle_style))
story.append(sp(0.3))
story.append(Paragraph("Complete Reference for Your First Clinical Posting",
ParagraphStyle('sub2', parent=subtitle_style, fontSize=11,
textColor=colors.HexColor("#555555"))))
story.append(sp(0.6))
cover_data = [
["Prepared for:", "MBBS 3rd Year - 1st Day Dental Ward Posting"],
["Date:", "July 2026"],
["Compiled by:", "Orris Medical AI | Based on Goldman-Cecil Medicine & Harrison's 22E (2025)"],
]
ct = Table(cover_data, colWidths=[4*cm, 13.5*cm])
ct.setStyle(TableStyle([
('BACKGROUND', (0, 0), (0, -1), colors.HexColor("#eef4fb")),
('FONTNAME', (0, 0), (0, -1), 'Helvetica-Bold'),
('FONTNAME', (1, 0), (1, -1), 'Helvetica'),
('FONTSIZE', (0, 0), (-1, -1), 10),
('GRID', (0, 0), (-1, -1), 0.5, colors.HexColor("#AAAAAA")),
('TOPPADDING', (0, 0), (-1, -1), 6),
('BOTTOMPADDING', (0, 0), (-1, -1), 6),
('LEFTPADDING', (0, 0), (-1, -1), 8),
]))
story.append(ct)
story.append(sp(0.6))
toc_data = [
["#", "Section"],
["1", "Introduction & Ward Etiquette"],
["2", "Dental History Taking"],
["3", "Systematic Oral Examination"],
["4", "Dental Charting & Notation"],
["5", "Common Dental Conditions"],
["6", "Investigations in Dentistry"],
["7", "Systemic Diseases & Oral Manifestations"],
["8", "Basic Dental Procedures - Observer's Guide"],
["9", "Dental Emergencies"],
["10", "Quick Reference Checklists"],
]
story.append(Paragraph("Table of Contents",
ParagraphStyle('toc_h', parent=h2_style, alignment=TA_CENTER)))
story.append(make_table(toc_data, col_widths=[1.5*cm, 16*cm]))
story.append(PageBreak())
# ── SECTION 1 ──────────────────────────────────────────────────────────────
story.append(sec("1. Introduction & Ward Etiquette"))
story.append(sp(0.2))
story.append(body(
"Welcome to your first clinical posting in the Dental Ward. This guide will help you "
"navigate the ward confidently, take a proper dental history, perform a systematic oral "
"examination, and recognise common dental conditions. You are primarily an observer and "
"learner - always seek permission before touching any patient and work under supervision."))
story.append(sp(0.2))
story.append(sub("1.1 Ward Etiquette"))
for t in [
"Always introduce yourself as a medical student and obtain patient consent before any interaction.",
"Maintain professional attire: white coat, clean hands, and a name badge at all times.",
"Wash hands before and after every patient contact (WHO 5 Moments of Hand Hygiene).",
"Do not use your mobile phone at the bedside or during consultations.",
"Address patients respectfully by name and maintain strict patient confidentiality.",
"When in doubt, always ask your supervisor before doing anything.",
"Observe dental procedures from a safe distance unless invited closer by the dentist.",
"Record all findings accurately and legibly in the case sheet.",
]:
story.append(bul(t))
story.append(sp(0.2))
story.append(note(
"Dental procedures carry infection risk. Always wear gloves, mask, and eye protection "
"if you are assisting in any procedure."))
# ── SECTION 2 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("2. Dental History Taking"))
story.append(sp(0.2))
story.append(body(
"A thorough history is the cornerstone of dental diagnosis. The dental history follows "
"the standard medical history framework but includes specific dental components. The goal "
"is to understand the patient's complaint, place it in context, and identify systemic "
"factors that could influence dental treatment."))
story.append(sp(0.2))
story.append(sub("2.1 Standard Format for Dental History"))
hist_data = [
["Component", "What to Ask / Record"],
["Patient Details",
"Name, age, sex, occupation, address, date of consultation"],
["Chief Complaint (CC)",
"In patient's own words. 'What brings you here today?' Record verbatim with site and duration."],
["History of Present Illness (HPI)",
"Onset (sudden/gradual), duration, severity, character (throbbing/dull/sharp/constant/"
"intermittent), aggravating factors (hot, cold, sweet foods), relieving factors, "
"previous episodes, any treatment taken."],
["Past Dental History (PDH)",
"Frequency of dental visits (regular/irregular/never), previous extractions, fillings, "
"root canals, orthodontic treatment, dentures. Adverse reactions: haemorrhage "
"post-extraction, problems with local anaesthesia, fainting."],
["Past Medical History (PMH)",
"Diabetes, hypertension, cardiac disease, bleeding disorders, epilepsy, "
"immunosuppression, liver/kidney disease. Hospitalisations, surgeries, blood transfusions."],
["Drug History",
"Current medications - especially anticoagulants (warfarin, aspirin), bisphosphonates, "
"steroids, antihypertensives, antiepileptics, calcium channel blockers. OTC drugs, "
"herbal supplements. Any drug allergies."],
["Allergy History",
"Drug allergies (especially local anaesthetics, penicillin, NSAIDs), latex allergy, "
"food allergies. Always ask specifically even if patient volunteers 'no allergies'."],
["Family History (FH)",
"Caries pattern in family, periodontal disease, malocclusion, genetic dental conditions "
"(amelogenesis/dentinogenesis imperfecta), oral cancer."],
["Social History (SH)",
"Tobacco smoking (cigarettes/bidis/hookah - type, quantity, duration). Tobacco chewing "
"(gutkha/paan/areca nut). Alcohol (type, quantity, frequency). Occupation (acid/trauma "
"exposure). Diet (frequency of sugar intake, fizzy drinks)."],
["Systemic Review",
"Swelling, lumps, fever, weight loss, fatigue, altered taste, dry mouth (xerostomia), "
"difficulty chewing (masticatory dysfunction) or swallowing (dysphagia), jaw clicking "
"or locking."],
]
story.append(make_table(hist_data, col_widths=[4.5*cm, 13*cm]))
story.append(sp(0.3))
story.append(sub("2.2 Special Questions for Common Dental Complaints"))
story.append(subsub("For Pain (Toothache):"))
for t in [
"SOCRATES: Site - which tooth/area? Onset? Character - throbbing, dull, sharp, electric?",
"Radiation - does pain radiate to ear, jaw, temple, or neck?",
"Associated features - swelling, fever, bad taste/smell, loose tooth?",
"Timing - constant or intermittent? Worse at night (suggests irreversible pulpitis)?",
"Aggravating factors: hot food/drink, cold water, sweet foods, biting down, lying flat?",
"Relieving factors: cold water (may relieve reversible pulpitis temporarily), painkillers?",
"Severity: 0-10 pain scale.",
]:
story.append(bul(t))
story.append(subsub("For Swelling:"))
for t in [
"Site and extent - intraoral or extraoral or both?",
"Duration - how long present? Onset: sudden or gradual? Triggering event (trauma, toothache)?",
"Character - hard or soft? Fluctuant (suggests abscess with pus)?",
"Associated symptoms: pain, fever, trismus (difficulty opening mouth), difficulty swallowing?",
]:
story.append(bul(t))
story.append(subsub("For Bleeding Gums:"))
for t in [
"Spontaneous or provoked (brushing, eating)?",
"Duration and frequency.",
"Associated symptoms: pain, halitosis (bad breath), loose teeth?",
"Oral hygiene: brushing frequency and technique, flossing?",
"Any systemic bleeding elsewhere (nose bleeds, easy bruising)? - rule out haematological cause.",
"Medications: anticoagulants, phenytoin (causes gingival overgrowth), CCBs (amlodipine)?",
]:
story.append(bul(t))
story.append(subsub("For Mouth Ulcers:"))
for t in [
"Single or multiple? Site (keratinized vs non-keratinized mucosa)?",
"Duration - >3 weeks is a RED FLAG requiring biopsy or urgent referral.",
"Pain: aphthous ulcers are painful; malignant ulcers may be painless.",
"Recurrence pattern (suggests aphthous stomatitis).",
"Systemic associations: bowel problems (Crohn's), genital ulcers (Behcet's), skin rash?",
"Tobacco/alcohol use (risk factors for oral malignancy).",
]:
story.append(bul(t))
story.append(sp(0.2))
story.append(note(
"RED FLAGS in dental history: Ulcer >3 weeks | Unexplained loose teeth in young patient | "
"Jaw/lip numbness or paraesthesia | Unexplained weight loss | Difficulty swallowing | "
"Non-healing extraction socket | Trismus without clear cause"))
# ── SECTION 3 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("3. Systematic Examination of the Oral Cavity"))
story.append(sp(0.2))
story.append(body(
"The oral examination follows a systematic 'outside-in' approach. Examine from the "
"outside (face and neck) progressively inward (lips, mucosa, gingiva, teeth, tongue, "
"palate, oropharynx). Always use good lighting and dental mirror under supervision."))
story.append(sub("3.1 General Examination"))
for t in [
"General appearance: Well/ill-looking, pallor, jaundice, nutritional status.",
"Vital signs if relevant: Pulse, blood pressure (before procedures), temperature if infection suspected.",
"Demeanour: Anxious (dental phobia is very common), distressed (acute pain).",
]:
story.append(bul(t))
story.append(sub("3.2 Extraoral (EO) Examination"))
story.append(subsub("Face:"))
for t in [
"Symmetry: facial asymmetry (swelling, muscle wasting, Bell's palsy)?",
"Swelling: location - submandibular, parotid, submental, buccal space?",
"Skin over swelling: erythema, fluctuance (abscess), sinus/fistula openings.",
"Lips: colour, angular cheilitis (B-vitamin/iron deficiency or candida), herpes labialis.",
]:
story.append(bul(t))
story.append(subsub("Temporomandibular Joint (TMJ):"))
for t in [
"Palpate bilaterally as patient opens and closes mouth.",
"Clicking or crepitus on movement.",
"Maximum mouth opening: normal 35-45 mm (approximately 3 finger-breadths).",
"Deviation of mandible on opening (deviates toward affected side in TMJ dysfunction).",
]:
story.append(bul(t))
story.append(subsub("Lymph Nodes:"))
for t in [
"Palpate: submental, submandibular, anterior/posterior cervical chain, preauricular, supraclavicular.",
"Record: size, consistency (soft/firm/hard/rubbery), mobility, tenderness.",
"Hard, fixed, non-tender lymph nodes = RED FLAG for malignancy.",
]:
story.append(bul(t))
story.append(sub("3.3 Intraoral (IO) Examination"))
story.append(body(
"Examine systematically in a fixed order. Do NOT go straight to the tooth the patient "
"is pointing to - you may miss other important pathology."))
exam_data = [
["Step", "Structure", "What to Look For"],
["1", "Lips (inner surface)", "Ulcers, mucoceles, fibroma, pigmentation"],
["2", "Buccal mucosa (both cheeks)",
"Linea alba (normal), ulcers, leukoplakia, erythroplakia, Fordyce spots, "
"candidiasis. Use mirror/tongue depressor."],
["3", "Vestibule & Sulcus",
"Swelling, sinus/fistula openings (parulis = gum boil), obliteration of sulcus"],
["4", "Gingiva",
"Colour (normal: coral pink), contour (scalloped), consistency, bleeding on probing, "
"recession, hyperplasia, ulceration"],
["5", "Teeth",
"Count teeth present; note missing, decayed, filled teeth. Colour changes, fractures, "
"mobility (grade 1/2/3), sensitivity, shape/size anomalies. Dental charting."],
["6", "Hard palate",
"Torus palatinus (normal bony prominence - do not confuse with pathology), "
"ulcers, candidiasis"],
["7", "Soft palate & uvula",
"Movement on saying 'Aah', petechiae (thrombocytopenia), Kaposi's sarcoma, ulcers"],
["8", "Tongue",
"Dorsum: fissured, geographic, hairy, coated. "
"Lateral borders (most common site for oral carcinoma!) and ventral surface. Mobility."],
["9", "Floor of mouth",
"Wharton's duct openings, ranula (mucous cyst), swelling, ulceration, calculi"],
["10", "Oropharynx",
"Tonsils, posterior pharyngeal wall, any masses"],
]
story.append(make_table(exam_data, col_widths=[1.5*cm, 4.5*cm, 11.5*cm]))
story.append(sp(0.2))
story.append(note(
"Any oral ulcer persisting >3 weeks must be considered potentially malignant and "
"referred for biopsy. The lateral border of the tongue and the floor of the mouth are "
"the most common sites for oral squamous cell carcinoma."))
# ── SECTION 4 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("4. Dental Charting & Notation"))
story.append(sp(0.2))
story.append(sub("4.1 FDI (ISO) System - Most Widely Used"))
story.append(body(
"Each tooth has a 2-digit number. First digit = quadrant (1-4 for permanent, 5-8 for "
"primary). Second digit = tooth position within quadrant (1-8 from central incisor to "
"3rd molar)."))
quad_data = [
["Quadrant", "Permanent Teeth (Adult)", "Primary Teeth (Child)"],
["Upper Right (Q1)", "11 - 18", "51 - 55"],
["Upper Left (Q2)", "21 - 28", "61 - 65"],
["Lower Left (Q3)", "31 - 38", "71 - 75"],
["Lower Right (Q4)", "41 - 48", "81 - 85"],
]
story.append(make_table(quad_data, col_widths=[5*cm, 6*cm, 6.5*cm]))
story.append(sp(0.15))
story.append(body(
"<b>Examples:</b> Tooth 36 = lower left first molar. "
"Tooth 11 = upper right central incisor. Tooth 21 = upper left central incisor."))
story.append(sp(0.2))
story.append(sub("4.2 Common Charting Symbols"))
sym_data = [
["Symbol / Abbreviation", "Meaning"],
["/ (diagonal line through box)", "Extracted tooth"],
["Shaded/coloured box or X", "Decayed (carious) tooth - shade the affected surfaces"],
["F or shaded tooth surface outline", "Filled/restored tooth"],
["UE", "Unerupted"],
["PE", "Partially erupted"],
["RCT or RC", "Root canal treated"],
["Cr", "Crown placed"],
["Mobility Grade 1", "Slight horizontal movement (just perceptible)"],
["Mobility Grade 2", "1-2 mm horizontal buccolingual movement"],
["Mobility Grade 3", ">2 mm movement in all directions including vertical (depressible)"],
["TTP", "Tender to percussion - tap tooth with mirror handle"],
]
story.append(make_table(sym_data, col_widths=[6.5*cm, 11*cm]))
story.append(sp(0.2))
story.append(sub("4.3 DMFT Index"))
story.append(body(
"The DMFT Index measures caries experience. "
"<b>D</b> = Decayed teeth, <b>M</b> = Missing due to caries, <b>F</b> = Filled teeth, "
"<b>T</b> = Teeth examined. Maximum score = 28 (or 32 including wisdom teeth). "
"Higher DMFT = greater caries burden."))
# ── SECTION 5 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("5. Common Dental Conditions"))
story.append(sp(0.2))
story.append(sub("5.1 Dental Caries (Tooth Decay)"))
story.append(body(
"<b>Definition:</b> Infectious, multifactorial disease causing demineralisation and "
"destruction of tooth hard tissues by acids produced by bacteria "
"(<i>Streptococcus mutans</i>, <i>Lactobacillus</i>)."))
caries_data = [
["Feature", "Details"],
["Aetiology (Keyes Triad)", "Bacteria + Fermentable carbohydrates + Susceptible tooth + Time"],
["Symptoms",
"Initially asymptomatic. Later: sensitivity to sweet, cold, hot. "
"Severe pain when cavity reaches pulp."],
["Signs", "White spot (early demineralisation), brown/black cavity, visible hole"],
["Black's Classification",
"Class I: Pit & fissure | Class II: Proximal of posteriors | "
"Class III: Proximal of anteriors | Class IV: Proximal + incisal edge | "
"Class V: Gingival 1/3 of buccal/lingual | Class VI: Cusp tips"],
["Treatment",
"Early (white spot): remineralisation with fluoride. "
"Cavity: excavation + restoration (filling). "
"Pulp involved: root canal treatment (RCT). Irreparable: extraction."],
["Prevention", "Fluoride toothpaste, fissure sealants, dietary advice, regular check-ups"],
]
story.append(make_table(caries_data, col_widths=[4.5*cm, 13*cm]))
story.append(sp(0.3))
story.append(sub("5.2 Pulpitis"))
story.append(body("<b>Definition:</b> Inflammation of the dental pulp, usually a sequel to untreated caries."))
pulp_data = [
["Feature", "Reversible Pulpitis", "Irreversible Pulpitis"],
["Pain character", "Sharp, brief on stimulus (cold, sweet)", "Severe, spontaneous, throbbing, prolonged"],
["Pain at night", "Usually absent", "Often worse at night"],
["Response to cold", "Brief pain resolving in seconds", "Pain lingers for minutes after stimulus removed"],
["Treatment", "Remove cause (fill cavity) - pulp recovers", "Root canal treatment (RCT) or extraction"],
]
pt = Table(pulp_data, colWidths=[4.5*cm, 6.5*cm, 6.5*cm])
pt.setStyle(TableStyle([
('BACKGROUND', (0, 0), (-1, 0), colors.HexColor("#1a3a5c")),
('TEXTCOLOR', (0, 0), (-1, 0), colors.white),
('FONTNAME', (0, 0), (-1, 0), 'Helvetica-Bold'),
('BACKGROUND', (0, 1), (0, -1), colors.HexColor("#eef4fb")),
('FONTNAME', (0, 1), (0, -1), 'Helvetica-Bold'),
('FONTNAME', (1, 0), (-1, -1), 'Helvetica'),
('FONTSIZE', (0, 0), (-1, -1), 9),
('ROWBACKGROUNDS', (1, 1), (-1, -1), [colors.white, colors.HexColor("#f5f5f5")]),
('GRID', (0, 0), (-1, -1), 0.4, colors.HexColor("#AAAAAA")),
('ALIGN', (0, 0), (-1, -1), 'LEFT'),
('VALIGN', (0, 0), (-1, -1), 'TOP'),
('TOPPADDING', (0, 0), (-1, -1), 5),
('BOTTOMPADDING', (0, 0), (-1, -1), 5),
('LEFTPADDING', (0, 0), (-1, -1), 5),
]))
story.append(pt)
story.append(sp(0.3))
story.append(sub("5.3 Periapical Abscess"))
story.append(body(
"<b>Definition:</b> Localised collection of pus at the root apex, following pulp necrosis. "
"One of the most common dental emergencies."))
for t in [
"<b>Symptoms:</b> Severe, constant, throbbing pain. Tender on biting. Tooth feels 'raised' "
"(extruded in socket due to pressure of pus).",
"<b>Signs:</b> Tender to percussion (TTP). Facial swelling/cellulitis if spreading. "
"Parulis (gum boil - sinus with pus discharge). Fever and cervical lymphadenopathy.",
"<b>Investigations:</b> Periapical X-ray shows periapical radiolucency (dark halo at root tip). "
"Vitality test: non-vital (no response).",
"<b>Treatment:</b> Drainage via root canal access or incision & drainage (I&D) if fluctuant. "
"Antibiotics if systemic features: amoxicillin 500 mg TDS or metronidazole 400 mg TDS. "
"Definitive: RCT or extraction.",
"<b>WARNING:</b> Untreated abscess can spread to cause Ludwig's angina (floor of mouth "
"cellulitis - life-threatening airway emergency), cavernous sinus thrombosis, or septicaemia.",
]:
story.append(bul(t))
story.append(sp(0.3))
story.append(sub("5.4 Periodontal Diseases"))
story.append(body(
"<b>Gingivitis:</b> Inflammation confined to the gingiva without bone loss. Reversible. "
"Caused by plaque. Signs: redness, swelling, bleeding on brushing/probing, halitosis. "
"Treatment: professional scaling + oral hygiene instruction."))
story.append(sp(0.1))
story.append(body(
"<b>Periodontitis:</b> Extension of inflammation to periodontal ligament and alveolar bone "
"with irreversible bone loss. Signs: periodontal pocket formation (>3 mm), gingival "
"recession, bone loss on X-ray, tooth mobility, furcation involvement. "
"Treatment: scaling and root planing (SRP); surgical therapy for advanced cases."))
story.append(sp(0.1))
story.append(body(
"<b>Pericoronitis:</b> Inflammation around a partially erupted tooth (most commonly lower "
"wisdom tooth - 38 or 48). Food and bacteria trapped under the operculum (gum flap). "
"Signs: pain, swelling, trismus, bad taste, halitosis. Treatment: irrigation under operculum, "
"antibiotics, operculectomy or extraction when acute episode resolves."))
story.append(sp(0.3))
story.append(sub("5.5 Oral Mucosal Diseases"))
story.append(subsub("Aphthous Stomatitis (Canker Sores):"))
story.append(body(
"Most common cause of oral ulcers - affects up to 20% of the population. "
"Recurrent, painful ulcers on <b>non-keratinized</b> mucosa (buccal mucosa, "
"ventral tongue, lips, alveolar mucosa). Three types:"))
aph_data = [
["Type", "Size", "Duration", "Number"],
["Minor (most common, 80%)", "<0.5 cm, flat", "5-10 days", "1-5"],
["Major", ">0.5 cm, raised borders, deep", "Weeks to months", "Usually solitary"],
["Herpetiform", "Tiny (<3 mm), clusters", "7-10 days", "10-100"],
]
story.append(make_table(aph_data, col_widths=[5*cm, 4.5*cm, 3.5*cm, 4.5*cm]))
story.append(body(
"Treatment: topical steroids (triamcinolone acetonide gel), topical lignocaine, "
"tetracycline mouthwash. No curative treatment for recurrence."))
story.append(note(
"Key distinction: Aphthous ulcers occur on NON-keratinized (movable) mucosa. "
"Herpes simplex ulcers occur on KERATINIZED (fixed, attached) mucosa - hard palate "
"and attached gingiva."))
story.append(subsub("Oral Candidiasis (Thrush):"))
story.append(body(
"Fungal infection by <i>Candida albicans</i>. Most common oral fungal infection. "
"Predisposing factors: immunosuppression, diabetes, prolonged antibiotics, steroid "
"inhalers, xerostomia, dentures."))
for t in [
"Pseudomembranous (most common): White creamy plaques that CAN BE WIPED OFF, "
"leaving a raw/bleeding surface. Common in neonates, elderly, HIV patients.",
"Erythematous: Red patches on palate or dorsum of tongue.",
"Angular cheilitis: Redness and cracking at corners of mouth.",
"Treatment: nystatin suspension 100,000 units/mL, 4x/day (swish & swallow). "
"Systemic: fluconazole 150 mg stat for severe/resistant cases. Always treat underlying cause.",
]:
story.append(bul(t))
story.append(subsub("Leukoplakia & Erythroplakia:"))
story.append(body(
"<b>Leukoplakia:</b> White patch that cannot be rubbed off and cannot be attributed to any "
"other definable condition. Potentially malignant. Risk factors: tobacco (any form), alcohol, "
"chronic irritation. ALL leukoplakias require biopsy to assess for dysplasia or malignancy."))
story.append(body(
"<b>Erythroplakia:</b> Red velvety patch - carries a HIGHER malignant transformation risk "
"than leukoplakia. Treat with high index of suspicion."))
story.append(subsub("Oral Submucous Fibrosis (OSMF):"))
story.append(body(
"Chronic progressive scarring of oral mucosa. Strongly associated with areca nut (betel "
"nut/gutkha/paan) chewing - very common in South Asia. Features: progressive trismus "
"(restricted mouth opening), blanching and stiffening of mucosa, burning sensation on "
"eating spicy food. Potentially malignant - 7-13% malignant transformation rate. "
"Treatment: habit cessation, intralesional steroids, physiotherapy for trismus."))
# ── SECTION 6 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("6. Investigations in Dentistry"))
story.append(sp(0.2))
story.append(sub("6.1 Dental Radiographs"))
xray_data = [
["Type", "What It Shows", "Common Uses"],
["Periapical (PA) X-ray",
"Individual tooth + surrounding bone (root, PDL space, lamina dura, periapex)",
"Caries, periapical abscess/cyst, root fracture, impacted teeth"],
["Bitewing X-ray",
"Crowns of upper & lower posteriors on same film",
"Proximal (interproximal) caries - best for early caries; bone level assessment"],
["OPG / Panoramic",
"Entire dentition, both jaws, TMJ, sinuses in one film",
"Overview of all teeth, impacted wisdom teeth, fractures, cysts, tumours"],
["Occlusal X-ray",
"Cross-sectional view of entire arch",
"Salivary duct stones, cysts, supernumerary teeth"],
["CBCT",
"3D imaging of jaws/teeth",
"Implant planning, complex impactions, jaw tumours - not routine"],
["Lateral Cephalogram",
"Side profile of skull and jaws",
"Orthodontic assessment, skeletal relationships"],
]
story.append(make_table(xray_data, col_widths=[3.5*cm, 6*cm, 8*cm]))
story.append(note(
"On a PA X-ray: Dense (WHITE) = enamel, bone, metal restorations. "
"Radiolucent (DARK) = caries, abscess, cyst, pulp chamber. "
"A periapical radiolucency (dark halo at root tip) = periapical infection/granuloma/cyst."))
story.append(sub("6.2 Vitality (Sensibility) Tests"))
vital_data = [
["Test", "Method", "Normal / Abnormal Response"],
["Cold Test (most common)",
"Ethyl chloride spray or ice on cotton pellet applied to tooth",
"Normal: brief sharp sensation resolving in <10 sec. "
"Non-vital: NO response. Irreversible pulpitis: prolonged lingering pain."],
["Heat Test",
"Warm gutta-percha or warm water on tooth",
"Normal: brief sensation. Positive if reproduces patient's pain."],
["Electric Pulp Test (EPT)",
"Low electric current via probe on enamel surface",
"Tingling sensation = vital pulp. No response = non-vital."],
]
story.append(make_table(vital_data, col_widths=[3.5*cm, 5.5*cm, 8.5*cm]))
story.append(sub("6.3 Periodontal Assessment"))
for t in [
"Probing Pocket Depth (PPD): Measured with calibrated periodontal probe. Normal sulcus <3 mm. "
"Pathological pocket in periodontitis: >3 mm.",
"Bleeding on Probing (BOP): Indicates active gingival/periodontal inflammation.",
"Furcation Involvement (multi-rooted teeth): Grade I/II/III depending on probe penetration.",
"BPE (Basic Periodontal Examination): Screening using WHO probe. Scores 0-4 per sextant. "
"Score 4 = complex periodontal treatment needed.",
"Tooth Mobility: Grade 1 (<1 mm horizontal), Grade 2 (1-2 mm horizontal), "
"Grade 3 (>2 mm or vertical).",
]:
story.append(bul(t))
story.append(sub("6.4 Laboratory Investigations"))
for t in [
"CBC (Complete Blood Count): Suspected anaemia, leukaemia, bleeding disorder, or infection.",
"Blood glucose (fasting/random): Diabetes screening (associated with severe periodontitis).",
"Coagulation profile (PT/INR, aPTT): Before surgical procedures; patients on anticoagulants.",
"Biopsy (incisional): Any suspicious lesion - ulcer >3 weeks, leukoplakia, erythroplakia, "
"suspected malignancy. Gold standard for diagnosis.",
"FNAC (Fine Needle Aspiration Cytology): Neck lumps/lymphadenopathy workup.",
"Culture & Sensitivity: Oral infections not responding to empirical antibiotics.",
]:
story.append(bul(t))
# ── SECTION 7 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("7. Systemic Diseases & Oral Manifestations"))
story.append(sp(0.2))
story.append(body(
"The oral cavity is often a mirror of systemic health. Many systemic diseases have "
"characteristic oral manifestations. This knowledge is essential both for diagnosis "
"and for safe dental treatment planning."))
sys_data = [
["Systemic Disease", "Oral Manifestation / Clinical Relevance"],
["Diabetes Mellitus",
"Severe periodontitis, increased caries, poor wound healing, recurrent candidiasis, "
"xerostomia, burning mouth. Uncontrolled DM = relative contraindication for elective surgery."],
["Anaemia",
"Pale oral mucosa, atrophic/smooth glossitis (iron, B12, folate deficiency), "
"angular cheilitis. Koilonychia (spoon nails) in iron deficiency."],
["Leukaemia (especially AML)",
"Gingival bleeding, gingival hyperplasia/enlargement, oral ulcers, petechiae. "
"May be first presentation of leukaemia."],
["Thrombocytopenia",
"Petechiae on soft palate (vibrating line), spontaneous gingival bleeding, "
"prolonged bleeding after minor trauma."],
["HIV / AIDS",
"Oral candidiasis (often first sign of HIV), hairy leukoplakia (lateral tongue - EBV), "
"Kaposi's sarcoma (red/purple lesions on palate), major aphthous ulcers, "
"linear gingival erythema, necrotising periodontitis."],
["Hypertension (on CCBs)",
"Calcium channel blockers (amlodipine, nifedipine) cause gingival hyperplasia. "
"Check BP before dental treatment; caution with adrenaline in LA."],
["Cardiac Disease\n(valvular)",
"Antibiotic prophylaxis required before invasive dental procedures in HIGH-RISK patients: "
"prosthetic cardiac valves, previous infective endocarditis, unrepaired cyanotic CHD."],
["Anticoagulant Therapy\n(warfarin/aspirin)",
"Increased bleeding risk. Check INR <3.5 for minor procedures. Do NOT routinely stop "
"warfarin - apply local haemostatic measures (sutures, haemostatic packing)."],
["Bisphosphonate Therapy",
"MRONJ (Medication-Related Osteonecrosis of the Jaw): exposed bone failing to heal, "
"especially post-extraction. More common with IV bisphosphonates. "
"Avoid extractions if at all possible."],
["Sjogren's Syndrome",
"Severe xerostomia (dry mouth), parotid enlargement, dramatically increased cervical "
"caries, dysphagia. Dry eyes (keratoconjunctivitis sicca). Sicca symptoms."],
["Vitamin Deficiencies",
"Vit C deficiency (scurvy): haemorrhagic gingivitis, loose teeth. "
"B12/folate: atrophic glossitis, aphthous ulcers. "
"Vit D: delayed tooth eruption, increased caries susceptibility."],
["Crohn's Disease / IBD",
"Aphthous-like ulcers, cobblestone appearance of buccal mucosa, lip swelling "
"(orofacial granulomatosis), mucogingivitis."],
["Pregnancy",
"Pregnancy gingivitis (hormonal - very common). Pregnancy epulis (pyogenic granuloma "
"on gums). Avoid X-rays in 1st trimester; avoid certain drugs (tetracyclines, metronidazole "
"in 1st trimester)."],
["Renal Failure",
"Uraemic stomatitis (whitish-grey pseudomembrane), metallic taste, xerostomia, "
"hypoplastic enamel. Adjust drug doses for renal function."],
]
story.append(make_table(sys_data, col_widths=[4.5*cm, 13*cm]))
# ── SECTION 8 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("8. Basic Dental Procedures - Observer's Guide"))
story.append(sp(0.2))
story.append(body(
"As an MBBS student on posting, you will mainly observe. Understanding what is "
"happening will help you learn and ask good questions."))
proc_data = [
["Procedure", "What Happens", "Key Points to Observe"],
["Local Anaesthesia (LA)",
"Most common: Inferior alveolar nerve block (mandibular teeth) or "
"infiltration anaesthesia (maxillary teeth). Lignocaine 2% with "
"adrenaline 1:80,000 is standard.",
"Always aspirate before injecting. Adrenaline contraindicated in uncontrolled "
"cardiac disease. Complications: failed block, haematoma, transient facial nerve palsy."],
["Scaling & Root Planing",
"Removal of calculus (tartar/plaque) from tooth surfaces and roots using "
"ultrasonic scaler + hand instruments.",
"Foundation of periodontal treatment. Bleeding expected. "
"Post-op sensitivity for a few days is normal."],
["Dental Filling (Restoration)",
"Caries removed, cavity prepared, filled with composite resin (tooth-coloured) "
"or glass ionomer cement.",
"Acid etching and bonding agents for composite. "
"Occlusion checked with articulating paper after filling."],
["Root Canal Treatment (RCT)",
"Pulp tissue removed, root canals shaped, cleaned, and filled with "
"gutta-percha. Done to save a non-vital tooth.",
"Multiple visits usually required. Rubber dam used for isolation. "
"Pain for a few days after 1st visit is common. Final crown needed after RCT."],
["Dental Extraction",
"Tooth removed under LA using forceps and elevators. Socket curretted, "
"haemostasis achieved.",
"Post-op instructions: bite on gauze 30 min, no hot food/drinks, "
"no rinsing for 24h, no smoking. Watch for post-extraction haemorrhage."],
["Incision & Drainage (I&D)",
"Surgical drainage of fluctuant dental abscess. Incision made, pus drained, "
"corrugated drain placed.",
"Antibiotics are adjunct, NOT a substitute for drainage. "
"Drain reviewed and removed in 24-48h."],
["Dental X-ray",
"Patient bites on periapical film/digital sensor. X-ray tube positioned "
"outside mouth. Paralleling technique for accuracy.",
"Lead apron for patient. "
"Bitewing: both arches on same film for proximal caries."],
]
story.append(make_table(proc_data, col_widths=[4*cm, 6*cm, 7.5*cm]))
# ── SECTION 9 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("9. Dental Emergencies"))
story.append(sp(0.2))
story.append(body(
"Emergencies can occur during or after dental procedures. Know what to look for "
"and call for help immediately."))
story.append(sub("9.1 Post-extraction Haemorrhage"))
for t in [
"Primary: Bleeding during/immediately after extraction. Control with local pressure "
"(bite on gauze for 30 minutes).",
"Reactionary: Bleeding within first few hours - clot dislodged or vasoconstriction wearing off.",
"Secondary: Bleeding 5-10 days post-extraction - usually due to infection.",
"Management: Local pressure, irrigate socket, pack with haemostatic material (Surgicel/Gelfoam), "
"suture if needed. Check coagulation profile if persistent. Rule out bleeding disorder.",
]:
story.append(bul(t))
story.append(sub("9.2 Syncope (Vasovagal Attack)"))
story.append(body("Most common medical emergency in dental practice. Caused by anxiety, pain, or sight of needle/blood."))
for t in [
"Features: Prodrome of pallor, sweating, nausea, dizziness, then brief loss of consciousness.",
"Management: Lay patient flat (Trendelenburg position), loosen clothing, ensure airway. "
"Usually self-limiting within 1-2 minutes. Monitor vital signs.",
]:
story.append(bul(t))
story.append(sub("9.3 Anaphylaxis"))
for t in [
"Causes: Local anaesthetic, latex, antibiotics (penicillin), NSAIDs.",
"Features: Urticaria, angioedema, bronchospasm, hypotension, tachycardia.",
"Management: STOP procedure immediately. "
"Adrenaline (epinephrine) 0.5 mg IM (0.5 mL of 1:1000 solution) into anterolateral thigh. "
"Call for emergency help. ABC management. IV fluids, antihistamine, hydrocortisone as adjuncts.",
]:
story.append(bul(t))
story.append(sub("9.4 Ludwig's Angina"))
story.append(body(
"Life-threatening bilateral cellulitis involving submandibular, sublingual, and "
"submental spaces. Usually originates from mandibular 2nd or 3rd molar infection. "
"<b>AIRWAY EMERGENCY.</b>"))
for t in [
"Features: Brawny (firm, board-like, NON-fluctuant) swelling of floor of mouth and neck. "
"'Hot potato' voice, dysphagia, drooling, elevated and displaced tongue, stridor.",
"Management: AIRWAY FIRST - early intubation or surgical airway (tracheostomy/cricothyrotomy). "
"High-dose IV antibiotics (penicillin + metronidazole). Surgical drainage of spaces.",
]:
story.append(bul(t))
story.append(sub("9.5 Dry Socket (Alveolar Osteitis)"))
for t in [
"Painful condition 2-4 days post-extraction due to loss or disintegration of blood clot.",
"Features: Severe throbbing pain radiating to ear or temple. Empty socket with exposed bone. Halitosis.",
"Risk factors: Smoking, poor oral hygiene, mandibular molar extractions, "
"oral contraceptive use, traumatic extraction.",
"Management: Gentle saline irrigation of socket. Placement of alvogyl dressing "
"(eugenol-impregnated). Analgesics (NSAIDs). Dressing changed every 2-3 days until healed.",
]:
story.append(bul(t))
story.append(sub("9.6 Dental Trauma"))
for t in [
"Ellis Classification: Class I (enamel only), Class II (enamel + dentine), "
"Class III (enamel + dentine + pulp exposed - dental emergency).",
"Avulsed (knocked-out) tooth: Replant within 30 min if possible. "
"Store in milk, saline, or patient's saliva if transport needed. "
"Do NOT scrub root surface.",
"Refer all dental trauma cases immediately.",
]:
story.append(bul(t))
# ── SECTION 10 ──────────────────────────────────────────────────────────────
story.append(PageBreak())
story.append(sec("10. Quick Reference Checklists"))
story.append(sp(0.2))
story.append(sub("Checklist 1: Complete Dental History"))
checklist1 = [
"[ ] Patient ID: Name, age, sex, occupation, address, date",
"[ ] Chief Complaint: patient's own words, site, duration",
"[ ] HPI: SOCRATES (Site, Onset, Character, Radiation, Associated features, Timing, "
"Exacerbating/Relieving factors, Severity)",
"[ ] Past Dental History: visit regularity, previous treatments, adverse reactions to LA",
"[ ] Past Medical History: DM, HTN, cardiac disease, bleeding disorder, epilepsy, "
"renal/liver disease",
"[ ] Drug History: anticoagulants, bisphosphonates, CCBs, steroids, antiepileptics",
"[ ] Allergy History: LA, penicillin, NSAIDs, latex - ask even if patient says 'none'",
"[ ] Social History: tobacco (type, amount, duration), alcohol, diet",
"[ ] Family History: relevant genetic or dental conditions",
"[ ] Systemic Review: swelling, fever, dysphagia, weight loss, altered sensation",
]
for item in checklist1:
story.append(Paragraph(item, check_style))
story.append(sp(0.3))
story.append(sub("Checklist 2: Systematic Oral Examination"))
checklist2 = [
"[ ] General: appearance, pallor, jaundice, nutrition",
"[ ] EO - Face: symmetry, swelling, skin changes, draining sinuses",
"[ ] EO - Lips: colour, angular cheilitis, herpes labialis",
"[ ] EO - TMJ: click, crepitus, tenderness, maximum mouth opening",
"[ ] EO - Lymph nodes: submental, submandibular, cervical chains",
"[ ] IO - Lips (inner surface) and labial mucosa",
"[ ] IO - Buccal mucosa bilaterally and sulcus",
"[ ] IO - Gingiva: colour, contour, BOP, recession, hyperplasia",
"[ ] IO - Teeth: chart, mobility, TTP, caries, restorations",
"[ ] IO - Hard palate and soft palate/uvula",
"[ ] IO - Tongue: dorsum, lateral borders (critical!), ventral surface",
"[ ] IO - Floor of mouth",
"[ ] IO - Oropharynx and tonsils",
"[ ] Record all findings systematically in case sheet",
]
for item in checklist2:
story.append(Paragraph(item, check_style))
story.append(sp(0.3))
story.append(sub("Checklist 3: Red Flags - Always Report to Supervisor Immediately"))
rf_data = [
["Red Flag", "Possible Significance"],
["Oral ulcer persisting >3 weeks", "Oral squamous cell carcinoma or other malignancy"],
["White or red patch that cannot be rubbed off",
"Leukoplakia / erythroplakia - potentially malignant, biopsy needed"],
["Unexplained loose teeth in young patient",
"Aggressive periodontitis, leukaemia, Langerhans cell histiocytosis, tumour"],
["Jaw or lip numbness / paraesthesia",
"IAN involvement by tumour (Vincent's sign) - urgent investigation"],
["Swelling not responding to antibiotics",
"Deep neck space infection, malignancy, TB lymphadenopathy"],
["Trismus without clear cause",
"OSMF, masticator space infection, malignancy, fibrosis"],
["Rapidly expanding jaw swelling in child",
"Ameloblastoma, dentigerous cyst, Burkitt's lymphoma"],
["Weight loss + oral lesion",
"Underlying malignancy, HIV, systemic disease"],
["Gingival bleeding not responding to scaling",
"Leukaemia, thrombocytopenia, haemophilia - requires haematological workup"],
]
story.append(make_table(rf_data, col_widths=[6*cm, 11.5*cm],
hdr_bg=colors.HexColor("#8B0000")))
story.append(sp(0.5))
story.append(Paragraph("Good Luck on Your First Day!",
ParagraphStyle('gl', parent=title_style, fontSize=20,
textColor=colors.HexColor("#1a3a5c"))))
story.append(sp(0.2))
story.append(body(
"Remember: observe carefully, ask questions respectfully, and never perform any procedure "
"without direct supervision. The dental team is there to teach you. "
"Be enthusiastic, be punctual, and maintain professionalism at all times. "
"Every patient encounter is a learning opportunity."))
story.append(sp(0.3))
story.append(hr())
story.append(Paragraph(
"Sources: Goldman-Cecil Medicine 2024 | Harrison's Principles of Internal Medicine 22E (2025) "
"| Pocket Dentistry - Greenwood | Oxford Handbook of Clinical Dentistry - Mitchell | "
"ADA Medical/Dental Health History Guidelines",
ref_style))
doc.build(story, canvasmaker=NumberedCanvas)
print("SUCCESS:", output_path)
cd /home/daytona/workspace/dental-ward-guide && python3 generate_pdf.py
ls -lh /home/daytona/workspace/dental-ward-guide/Dental_Ward_Guide_MBBS.pdf
Dental Ward Guide MBBS
PDF Document · PDF
| # | Section | Highlights |
|---|---|---|
| 1 | Introduction & Ward Etiquette | How to behave, infection control, consent |
| 2 | Dental History Taking | Full format table + special questions for pain, swelling, bleeding gums, ulcers |
| 3 | Systematic Oral Examination | Outside-in approach: EO face/TMJ/lymph nodes → IO step-by-step (10 structures) |
| 4 | Dental Charting & Notation | FDI/ISO system, quadrant numbering, charting symbols, DMFT index |
| 5 | Common Dental Conditions | Caries (Keyes triad, Black's classification), Pulpitis (reversible vs irreversible), Periapical abscess, Periodontitis, Aphthous stomatitis, Candidiasis, Leukoplakia, OSMF |
| 6 | Investigations | Periapical/Bitewing/OPG X-rays explained, vitality tests, periodontal probing, lab tests |
| 7 | Systemic Diseases & Oral Manifestations | 14 conditions: DM, HIV, leukaemia, Sjogren's, bisphosphonates, warfarin, pregnancy, and more |
| 8 | Procedures - Observer's Guide | LA, scaling, fillings, RCT, extraction, I&D, X-ray - what happens and what to watch for |
| 9 | Dental Emergencies | Post-extraction haemorrhage, syncope, anaphylaxis, Ludwig's angina, dry socket, dental trauma |
| 10 | Quick Reference Checklists | History checklist, examination checklist, red flags table |
This File is not downloading
ls -lh /home/daytona/workspace/dental-ward-guide/ && python3 -c " from pypdf import PdfReader r = PdfReader('/home/daytona/workspace/dental-ward-guide/Dental_Ward_Guide_MBBS.pdf') print('Pages:', len(r.pages)) print('First page text snippet:', r.pages[0].extract_text()[:200]) "
base64 /home/daytona/workspace/dental-ward-guide/Dental_Ward_Guide_MBBS.pdf | wc -c
base64 /home/daytona/workspace/dental-ward-guide/Dental_Ward_Guide_MBBS.pdf
JVBERi0xLjQ... and ends with ...VBERU9GCg==).download.html and open it in your browser - it will auto-download the PDF:python3 -c " import base64, os with open('/home/daytona/workspace/dental-ward-guide/Dental_Ward_Guide_MBBS.pdf','rb') as f: b64 = base64.b64encode(f.read()).decode() html = '''<!DOCTYPE html> <html> <head><title>Dental Ward Guide Download</title></head> <body> <h2>Dental Ward Guide - MBBS 3rd Year</h2> <p>Click the button below to download your PDF guide.</p> <a href=\"data:application/pdf;base64,''' + b64 + '''\" download=\"Dental_Ward_Guide_MBBS.pdf\"> <button style=\"padding:15px 30px;font-size:18px;background:#1a3a5c;color:white;border:none;border-radius:8px;cursor:pointer;\"> Download PDF (17 pages) </button> </a> </body> </html>''' with open('/home/daytona/workspace/dental-ward-guide/download.html','w') as f: f.write(html) print('HTML created, size:', os.path.getsize('/home/daytona/workspace/dental-ward-guide/download.html'), 'bytes') "
download
HTML File · HTML
Dental Ward Guide MBBS
PDF Document · PDF
None
~/dental-ward-guide/generate_docx.js
const {
Document, Packer, Paragraph, TextRun, Table, TableRow, TableCell,
HeadingLevel, AlignmentType, WidthType, BorderStyle, ShadingType,
PageBreak, Header, Footer, PageNumber, NumberFormat, VerticalAlign
} = require('docx');
const fs = require('fs');
// ── COLOUR PALETTE ──────────────────────────────────────────────────────────
const NAVY = "1a3a5c";
const BLUE = "2c6fad";
const WHITE = "FFFFFF";
const YELLOW = "FFF8E1";
const RED = "8B0000";
const LGRAY = "EEF4FB";
const GRAY = "555555";
// ── HELPER: thin border set ──────────────────────────────────────────────────
function thinBorder() {
const b = { style: BorderStyle.SINGLE, size: 4, color: "AAAAAA" };
return { top: b, bottom: b, left: b, right: b, insideHorizontal: b, insideVertical: b };
}
// ── HELPER: heading paragraph ────────────────────────────────────────────────
function h1(text) {
return new Paragraph({
heading: HeadingLevel.HEADING_1,
children: [new TextRun({ text, bold: true, color: WHITE, size: 32 })],
shading: { type: ShadingType.SOLID, color: NAVY, fill: NAVY },
spacing: { before: 280, after: 120 },
});
}
function h2(text) {
return new Paragraph({
heading: HeadingLevel.HEADING_2,
children: [new TextRun({ text, bold: true, color: NAVY, size: 28 })],
spacing: { before: 200, after: 80 },
border: { bottom: { style: BorderStyle.SINGLE, size: 4, color: BLUE } },
});
}
function h3(text) {
return new Paragraph({
heading: HeadingLevel.HEADING_3,
children: [new TextRun({ text, bold: true, color: BLUE, size: 24 })],
spacing: { before: 160, after: 60 },
});
}
function body(text) {
return new Paragraph({
children: [new TextRun({ text, size: 20 })],
spacing: { after: 80 },
});
}
function bodyRich(runs) {
return new Paragraph({ children: runs, spacing: { after: 80 } });
}
function bullet(text) {
return new Paragraph({
children: [new TextRun({ text: "\u2022 " + text, size: 20 })],
indent: { left: 360 },
spacing: { after: 60 },
});
}
function bulletBold(label, rest) {
return new Paragraph({
children: [
new TextRun({ text: "\u2022 " + label, bold: true, size: 20 }),
new TextRun({ text: rest, size: 20 }),
],
indent: { left: 360 },
spacing: { after: 60 },
});
}
function noteBox(text) {
return new Paragraph({
children: [new TextRun({ text: "Note: " + text, italics: true, size: 18, color: "444444" })],
shading: { type: ShadingType.SOLID, color: "FFF8E1", fill: "FFF8E1" },
border: { left: { style: BorderStyle.SINGLE, size: 8, color: BLUE } },
indent: { left: 180 },
spacing: { after: 100 },
});
}
function pageBreak() {
return new Paragraph({ children: [new PageBreak()] });
}
function sp() {
return new Paragraph({ children: [new TextRun({ text: "" })], spacing: { after: 60 } });
}
// ── HELPER: table ─────────────────────────────────────────────────────────────
function makeTable(rows, widths, hdrBg) {
if (!hdrBg) hdrBg = NAVY;
return new Table({
width: { size: 100, type: WidthType.PERCENTAGE },
borders: thinBorder(),
rows: rows.map((row, ri) => new TableRow({
children: row.map((cell, ci) => new TableCell({
width: widths ? { size: widths[ci], type: WidthType.PERCENTAGE } : undefined,
shading: ri === 0
? { type: ShadingType.SOLID, color: hdrBg, fill: hdrBg }
: (ri % 2 === 0
? { type: ShadingType.SOLID, color: LGRAY, fill: LGRAY }
: { type: ShadingType.SOLID, color: WHITE, fill: WHITE }),
verticalAlign: VerticalAlign.TOP,
children: [new Paragraph({
children: [new TextRun({
text: String(cell),
bold: ri === 0,
color: ri === 0 ? WHITE : "222222",
size: ri === 0 ? 19 : 18,
})],
spacing: { before: 60, after: 60 },
indent: { left: 80, right: 80 },
})],
})),
})),
});
}
// ════════════════════════════════════════════════════════════════════════════
// BUILD DOCUMENT
// ════════════════════════════════════════════════════════════════════════════
const children = [];
// ── COVER ───────────────────────────────────────────────────────────────────
children.push(new Paragraph({
children: [new TextRun({ text: "DENTAL WARD GUIDE", bold: true, size: 56, color: NAVY })],
alignment: AlignmentType.CENTER, spacing: { before: 800, after: 200 },
}));
children.push(new Paragraph({
children: [new TextRun({ text: "For MBBS 3rd Year Students", size: 32, color: BLUE })],
alignment: AlignmentType.CENTER, spacing: { after: 100 },
}));
children.push(new Paragraph({
children: [new TextRun({ text: "Complete Reference for Your First Clinical Posting", size: 24, color: GRAY, italics: true })],
alignment: AlignmentType.CENTER, spacing: { after: 400 },
}));
children.push(makeTable([
["Prepared for:", "MBBS 3rd Year - 1st Day Dental Ward Posting"],
["Date:", "July 2026"],
["Compiled by:", "Orris Medical AI | Goldman-Cecil Medicine & Harrison's 22E (2025)"],
], [25, 75]));
children.push(sp()); children.push(sp());
children.push(new Paragraph({
children: [new TextRun({ text: "Table of Contents", bold: true, size: 28, color: NAVY })],
spacing: { before: 200, after: 120 },
}));
children.push(makeTable([
["#", "Section"],
["1", "Introduction & Ward Etiquette"],
["2", "Dental History Taking"],
["3", "Systematic Oral Examination"],
["4", "Dental Charting & Notation"],
["5", "Common Dental Conditions"],
["6", "Investigations in Dentistry"],
["7", "Systemic Diseases & Oral Manifestations"],
["8", "Basic Dental Procedures - Observer's Guide"],
["9", "Dental Emergencies"],
["10", "Quick Reference Checklists"],
], [10, 90]));
children.push(pageBreak());
// ── SECTION 1 ────────────────────────────────────────────────────────────────
children.push(h1("1. Introduction & Ward Etiquette"));
children.push(body("Welcome to your first clinical posting in the Dental Ward. This guide will help you navigate the ward confidently, take a proper dental history, perform a systematic oral examination, and recognise common dental conditions. You are primarily an observer and learner - always seek permission before touching any patient and work under supervision."));
children.push(h2("1.1 Ward Etiquette"));
for (const t of [
"Always introduce yourself as a medical student and obtain patient consent before any interaction.",
"Maintain professional attire: white coat, clean hands, and a name badge at all times.",
"Wash hands before and after every patient contact (WHO 5 Moments of Hand Hygiene).",
"Do not use your mobile phone at the bedside or during consultations.",
"Address patients respectfully by name and maintain strict patient confidentiality.",
"When in doubt, always ask your supervisor before doing anything.",
"Observe dental procedures from a safe distance unless invited closer by the dentist.",
"Record all findings accurately and legibly in the case sheet.",
]) children.push(bullet(t));
children.push(noteBox("Dental procedures carry infection risk. Always wear gloves, mask, and eye protection if you are assisting in any procedure."));
// ── SECTION 2 ────────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("2. Dental History Taking"));
children.push(body("A thorough history is the cornerstone of dental diagnosis. The dental history follows the standard medical history framework but includes specific dental components. The goal is to understand the patient's complaint, place it in context, and identify systemic factors that could influence dental treatment."));
children.push(h2("2.1 Standard Format for Dental History"));
children.push(makeTable([
["Component", "What to Ask / Record"],
["Patient Details", "Name, age, sex, occupation, address, date of consultation"],
["Chief Complaint (CC)", "In patient's own words. 'What brings you here today?' Record verbatim with site and duration."],
["History of Present Illness (HPI)", "Onset (sudden/gradual), duration, severity, character (throbbing/dull/sharp/constant/intermittent), aggravating factors (hot, cold, sweet foods), relieving factors, previous episodes, any treatment taken."],
["Past Dental History (PDH)", "Frequency of dental visits (regular/irregular/never), previous extractions, fillings, root canals, orthodontic treatment, dentures. Adverse reactions: haemorrhage post-extraction, problems with local anaesthesia, fainting."],
["Past Medical History (PMH)", "Diabetes, hypertension, cardiac disease, bleeding disorders, epilepsy, immunosuppression, liver/kidney disease. Hospitalisations, surgeries, blood transfusions."],
["Drug History", "Current medications - especially anticoagulants (warfarin, aspirin), bisphosphonates, steroids, antihypertensives, antiepileptics, calcium channel blockers. OTC drugs, herbal supplements. Any drug allergies."],
["Allergy History", "Drug allergies (especially local anaesthetics, penicillin, NSAIDs), latex allergy, food allergies. Always ask specifically even if patient says 'no allergies'."],
["Family History", "Caries pattern in family, periodontal disease, malocclusion, genetic dental conditions, oral cancer."],
["Social History", "Tobacco smoking (cigarettes/bidis/hookah - type, quantity, duration). Tobacco chewing (gutkha/paan/areca nut). Alcohol (type, quantity). Diet (frequency of sugar intake, fizzy drinks)."],
["Systemic Review", "Swelling, lumps, fever, weight loss, dry mouth (xerostomia), difficulty chewing or swallowing, jaw clicking or locking."],
], [25, 75]));
children.push(h2("2.2 Special Questions for Common Dental Complaints"));
children.push(h3("For Pain (Toothache):"));
for (const t of [
"SOCRATES: Site - which tooth/area? Onset? Character - throbbing, dull, sharp, electric?",
"Radiation - does pain radiate to ear, jaw, temple, or neck?",
"Associated features - swelling, fever, bad taste/smell, loose tooth?",
"Timing - constant or intermittent? Worse at night (suggests irreversible pulpitis)?",
"Aggravating factors: hot food/drink, cold water, sweet foods, biting down, lying flat?",
"Relieving factors: cold water, painkillers? Severity 0-10.",
]) children.push(bullet(t));
children.push(h3("For Swelling:"));
for (const t of [
"Site and extent - intraoral, extraoral, or both?",
"Duration, onset - sudden or gradual? Triggering event (trauma, toothache)?",
"Character - hard or soft? Fluctuant (suggests pus/abscess)?",
"Associated symptoms: pain, fever, trismus (restricted mouth opening), difficulty swallowing?",
]) children.push(bullet(t));
children.push(h3("For Bleeding Gums:"));
for (const t of [
"Spontaneous or provoked (brushing, eating)?",
"Duration and frequency.",
"Associated symptoms: pain, halitosis (bad breath), loose teeth?",
"Oral hygiene: brushing frequency and technique, flossing?",
"Any systemic bleeding elsewhere (nose bleeds, easy bruising)? - rule out haematological cause.",
"Medications: anticoagulants, phenytoin (gingival overgrowth), calcium channel blockers?",
]) children.push(bullet(t));
children.push(h3("For Mouth Ulcers:"));
for (const t of [
"Single or multiple? Site (keratinized vs non-keratinized mucosa)?",
"Duration - >3 weeks is a RED FLAG requiring biopsy or urgent referral.",
"Pain: aphthous ulcers are painful; malignant ulcers may be painless.",
"Recurrence pattern (suggests aphthous stomatitis).",
"Systemic associations: bowel problems (Crohn's), genital ulcers (Behcet's), skin rash?",
"Tobacco/alcohol use (risk factors for oral malignancy).",
]) children.push(bullet(t));
children.push(noteBox("RED FLAGS in dental history: Ulcer >3 weeks | Unexplained loose teeth in young patient | Jaw/lip numbness or paraesthesia | Unexplained weight loss | Difficulty swallowing | Non-healing extraction socket | Trismus without clear cause"));
// ── SECTION 3 ────────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("3. Systematic Examination of the Oral Cavity"));
children.push(body("The oral examination follows a systematic 'outside-in' approach. Examine from the outside (face and neck) progressively inward (lips, mucosa, gingiva, teeth, tongue, palate, oropharynx). Always use good lighting and dental mirror under supervision."));
children.push(h2("3.1 General Examination"));
for (const t of [
"General appearance: well/ill-looking, pallor, jaundice, nutritional status.",
"Vital signs if relevant: pulse, blood pressure (before procedures), temperature if infection suspected.",
"Demeanour: anxious (dental phobia is very common), distressed (acute pain).",
]) children.push(bullet(t));
children.push(h2("3.2 Extraoral (EO) Examination"));
children.push(h3("Face:"));
for (const t of [
"Symmetry: facial asymmetry (swelling, muscle wasting, Bell's palsy)?",
"Swelling: location - submandibular, parotid, submental, buccal space?",
"Skin over swelling: erythema, fluctuance (abscess), sinus/fistula openings.",
"Lips: colour, angular cheilitis (B-vitamin/iron deficiency or candida), herpes labialis.",
]) children.push(bullet(t));
children.push(h3("TMJ (Temporomandibular Joint):"));
for (const t of [
"Palpate bilaterally as patient opens and closes mouth.",
"Clicking or crepitus on movement.",
"Maximum mouth opening: normal 35-45 mm (approximately 3 finger-breadths).",
"Deviation of mandible on opening (deviates toward affected side in TMJ dysfunction).",
]) children.push(bullet(t));
children.push(h3("Lymph Nodes:"));
for (const t of [
"Palpate: submental, submandibular, anterior/posterior cervical chain, preauricular, supraclavicular.",
"Record: size, consistency (soft/firm/hard/rubbery), mobility, tenderness.",
"Hard, fixed, non-tender lymph nodes = RED FLAG for malignancy.",
]) children.push(bullet(t));
children.push(h2("3.3 Intraoral (IO) Examination - Systematic Order"));
children.push(body("Examine in a fixed order. Do NOT go straight to the tooth the patient is pointing to - you may miss other important pathology."));
children.push(makeTable([
["Step", "Structure", "What to Look For"],
["1", "Lips (inner surface)", "Ulcers, mucoceles, fibroma, pigmentation"],
["2", "Buccal mucosa (both cheeks)", "Linea alba (normal), ulcers, leukoplakia, erythroplakia, Fordyce spots, candidiasis. Use mirror/tongue depressor."],
["3", "Vestibule & Sulcus", "Swelling, sinus/fistula openings (parulis = gum boil), obliteration of sulcus"],
["4", "Gingiva", "Colour (normal: coral pink), contour (scalloped), consistency, bleeding on probing, recession, hyperplasia, ulceration"],
["5", "Teeth", "Count teeth present; note missing, decayed, filled. Colour changes, fractures, mobility (grade 1/2/3), sensitivity. Dental charting."],
["6", "Hard palate", "Torus palatinus (normal bony prominence - do not confuse with pathology), ulcers, candidiasis"],
["7", "Soft palate & uvula", "Movement on 'Aah', petechiae (thrombocytopenia), Kaposi's sarcoma, ulcers"],
["8", "Tongue", "Dorsum: fissured, geographic, hairy, coated. Lateral borders (most common site for oral carcinoma!) and ventral surface. Mobility."],
["9", "Floor of mouth", "Wharton's duct openings, ranula (mucous cyst), swelling, ulceration, calculi"],
["10", "Oropharynx", "Tonsils, posterior pharyngeal wall, any masses"],
], [8, 25, 67]));
children.push(noteBox("Any oral ulcer persisting >3 weeks must be considered potentially malignant. The lateral border of the tongue and the floor of the mouth are the most common sites for oral squamous cell carcinoma."));
// ── SECTION 4 ────────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("4. Dental Charting & Notation"));
children.push(h2("4.1 FDI (ISO) System - Most Widely Used"));
children.push(body("Each tooth has a 2-digit number. First digit = quadrant (1-4 for permanent, 5-8 for primary). Second digit = tooth position within quadrant (1-8 from central incisor to 3rd molar)."));
children.push(makeTable([
["Quadrant", "Permanent Teeth", "Primary Teeth"],
["Upper Right (Q1)", "11 - 18", "51 - 55"],
["Upper Left (Q2)", "21 - 28", "61 - 65"],
["Lower Left (Q3)", "31 - 38", "71 - 75"],
["Lower Right (Q4)", "41 - 48", "81 - 85"],
], [34, 33, 33]));
children.push(body("Examples: Tooth 36 = lower left first molar. Tooth 11 = upper right central incisor. Tooth 21 = upper left central incisor."));
children.push(h2("4.2 Common Charting Symbols"));
children.push(makeTable([
["Symbol / Abbreviation", "Meaning"],
["/ (diagonal line through box)", "Extracted tooth"],
["Shaded box or X", "Decayed (carious) tooth - shade affected surfaces"],
["F or shaded outline", "Filled/restored tooth"],
["UE / PE", "Unerupted / Partially erupted"],
["RCT or RC", "Root canal treated"],
["Cr", "Crown placed"],
["Mobility Grade 1", "Slight horizontal movement (just perceptible)"],
["Mobility Grade 2", "1-2 mm horizontal buccolingual movement"],
["Mobility Grade 3", ">2 mm movement in all directions including vertical (depressible)"],
["TTP", "Tender to percussion - tap tooth gently with mirror handle"],
], [35, 65]));
children.push(h2("4.3 DMFT Index"));
children.push(body("D = Decayed teeth, M = Missing due to caries, F = Filled teeth, T = Teeth examined. Maximum score = 28 (or 32). Higher DMFT = greater caries burden. Widely used in epidemiological surveys and clinical assessments."));
// ── SECTION 5 ────────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("5. Common Dental Conditions"));
children.push(h2("5.1 Dental Caries (Tooth Decay)"));
children.push(body("Infectious, multifactorial disease causing demineralisation and destruction of tooth hard tissues by acids produced by bacteria (Streptococcus mutans, Lactobacillus)."));
children.push(makeTable([
["Feature", "Details"],
["Aetiology (Keyes Triad)", "Bacteria + Fermentable carbohydrates + Susceptible tooth + Time"],
["Symptoms", "Initially asymptomatic. Later: sensitivity to sweet, cold, hot. Severe pain when cavity reaches pulp."],
["Signs", "White spot (early demineralisation), brown/black cavity, visible hole"],
["Black's Classification", "Class I: Pit & fissure | Class II: Proximal of posteriors | Class III: Proximal of anteriors | Class IV: Proximal + incisal edge | Class V: Gingival 1/3 of buccal/lingual"],
["Treatment", "Early: remineralisation with fluoride. Cavity: excavation + restoration (filling). Pulp involved: RCT. Irreparable: extraction."],
["Prevention", "Fluoride toothpaste, fissure sealants, dietary advice, regular check-ups"],
], [25, 75]));
children.push(h2("5.2 Pulpitis"));
children.push(makeTable([
["Feature", "Reversible Pulpitis", "Irreversible Pulpitis"],
["Pain character", "Sharp, brief on stimulus (cold, sweet)", "Severe, spontaneous, throbbing, prolonged"],
["Pain at night", "Usually absent", "Often worse at night"],
["Response to cold", "Brief pain resolving in seconds", "Pain lingers for minutes after stimulus removed"],
["Treatment", "Remove cause (fill cavity) - pulp recovers", "Root canal treatment (RCT) or extraction"],
], [30, 35, 35]));
children.push(h2("5.3 Periapical Abscess"));
children.push(body("Localised collection of pus at the root apex, following pulp necrosis. One of the most common dental emergencies."));
for (const [label, rest] of [
["Symptoms: ", "Severe, constant, throbbing pain. Tender on biting. Tooth feels 'raised' (extruded in socket due to pus pressure)."],
["Signs: ", "Tender to percussion (TTP). Facial swelling/cellulitis. Parulis (gum boil - sinus with pus). Fever and cervical lymphadenopathy."],
["Investigations: ", "Periapical X-ray: periapical radiolucency (dark halo at root tip). Vitality test: non-vital (no response to cold)."],
["Treatment: ", "Drainage via root canal access or I&D if fluctuant. Antibiotics if systemic features. Definitive: RCT or extraction."],
["WARNING: ", "Untreated abscess can spread to cause Ludwig's angina (floor of mouth cellulitis - life-threatening airway emergency) or cavernous sinus thrombosis."],
]) children.push(bulletBold(label, rest));
children.push(h2("5.4 Periodontal Diseases"));
children.push(bodyRich([
new TextRun({ text: "Gingivitis: ", bold: true, size: 20 }),
new TextRun({ text: "Inflammation confined to the gingiva without bone loss. Reversible. Caused by plaque. Signs: redness, swelling, bleeding on brushing/probing, halitosis. Treatment: professional scaling + oral hygiene instruction.", size: 20 }),
]));
children.push(bodyRich([
new TextRun({ text: "Periodontitis: ", bold: true, size: 20 }),
new TextRun({ text: "Extension of inflammation to periodontal ligament and alveolar bone with irreversible bone loss. Signs: periodontal pocket formation (>3 mm), gingival recession, bone loss on X-ray, tooth mobility, furcation involvement. Treatment: scaling and root planing (SRP); surgical therapy for advanced cases.", size: 20 }),
]));
children.push(bodyRich([
new TextRun({ text: "Pericoronitis: ", bold: true, size: 20 }),
new TextRun({ text: "Inflammation around a partially erupted wisdom tooth. Food and bacteria trapped under the operculum (gum flap). Signs: pain, swelling, trismus, bad taste. Treatment: irrigation under operculum, antibiotics, operculectomy or extraction when acute episode resolves.", size: 20 }),
]));
children.push(h2("5.5 Oral Mucosal Diseases"));
children.push(h3("Aphthous Stomatitis (Canker Sores):"));
children.push(body("Most common cause of oral ulcers - affects up to 20% of the population. Recurrent, painful ulcers on non-keratinized mucosa (buccal mucosa, ventral tongue, lips, alveolar mucosa)."));
children.push(makeTable([
["Type", "Size", "Duration", "Number"],
["Minor (most common, 80%)", "<0.5 cm, flat", "5-10 days", "1-5"],
["Major", ">0.5 cm, raised borders, deep", "Weeks to months", "Usually solitary"],
["Herpetiform", "Tiny (<3 mm), clusters", "7-10 days", "10-100"],
], [30, 25, 25, 20]));
children.push(body("Treatment: topical steroids (triamcinolone gel), topical lignocaine, tetracycline mouthwash. No curative treatment for recurrence."));
children.push(noteBox("Key distinction: Aphthous ulcers occur on NON-keratinized (movable) mucosa. Herpes simplex ulcers occur on KERATINIZED (fixed, attached) mucosa - hard palate and attached gingiva."));
children.push(h3("Oral Candidiasis (Thrush):"));
for (const t of [
"Pseudomembranous (most common): White creamy plaques that CAN BE WIPED OFF, leaving raw/bleeding surface. Common in neonates, elderly, HIV patients, steroid inhaler users, diabetics.",
"Erythematous: Red patches on palate or dorsum of tongue.",
"Angular cheilitis: Redness and cracking at corners of mouth.",
"Treatment: nystatin suspension 4x/day (swish & swallow). Systemic: fluconazole 150 mg stat for severe cases. Treat underlying cause.",
]) children.push(bullet(t));
children.push(h3("Leukoplakia & Erythroplakia:"));
children.push(bodyRich([
new TextRun({ text: "Leukoplakia: ", bold: true, size: 20 }),
new TextRun({ text: "White patch that cannot be rubbed off and cannot be attributed to any other definable condition. Potentially malignant. Risk factors: tobacco (any form), alcohol, chronic irritation. ALL leukoplakias require biopsy to assess for dysplasia or malignancy.", size: 20 }),
]));
children.push(bodyRich([
new TextRun({ text: "Erythroplakia: ", bold: true, size: 20 }),
new TextRun({ text: "Red velvety patch - carries HIGHER malignant transformation risk than leukoplakia. Treat with high index of suspicion.", size: 20 }),
]));
children.push(h3("Oral Submucous Fibrosis (OSMF):"));
children.push(body("Chronic progressive scarring of oral mucosa. Strongly associated with areca nut/gutkha/paan chewing - very common in South Asia. Features: progressive trismus (restricted mouth opening), blanching and stiffening of mucosa, burning sensation. Potentially malignant - 7-13% malignant transformation rate. Treatment: habit cessation, intralesional steroids, physiotherapy for trismus."));
// ── SECTION 6 ────────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("6. Investigations in Dentistry"));
children.push(h2("6.1 Dental Radiographs"));
children.push(makeTable([
["Type", "What It Shows", "Common Uses"],
["Periapical (PA) X-ray", "Individual tooth + surrounding bone (root, PDL space, lamina dura, periapex)", "Caries, periapical abscess/cyst, root fracture, impacted teeth"],
["Bitewing X-ray", "Crowns of upper & lower posteriors on same film", "Proximal (interproximal) caries - best for early caries; bone level assessment"],
["OPG / Panoramic", "Entire dentition, both jaws, TMJ, sinuses in one film", "Overview of all teeth, impacted wisdom teeth, fractures, cysts, tumours"],
["Occlusal X-ray", "Cross-sectional view of entire arch", "Salivary duct stones, cysts, supernumerary teeth"],
["CBCT", "3D imaging of jaws/teeth", "Implant planning, complex impactions, jaw tumours - not routine"],
["Lateral Cephalogram", "Side profile of skull and jaws", "Orthodontic assessment, skeletal relationships"],
], [22, 38, 40]));
children.push(noteBox("On a PA X-ray: Dense (WHITE) = enamel, bone, metal restorations. Radiolucent (DARK) = caries, abscess, cyst, pulp chamber. A periapical radiolucency (dark halo at root tip) = periapical infection/granuloma/cyst."));
children.push(h2("6.2 Vitality (Sensibility) Tests"));
children.push(makeTable([
["Test", "Method", "Normal / Abnormal Response"],
["Cold Test (most common)", "Ethyl chloride spray or ice on cotton pellet applied to tooth", "Normal: brief sharp sensation resolving in <10 sec. Non-vital: NO response. Irreversible pulpitis: prolonged lingering pain."],
["Heat Test", "Warm gutta-percha or warm water on tooth", "Normal: brief sensation. Positive if reproduces patient's pain."],
["Electric Pulp Test (EPT)", "Low electric current via probe on enamel surface", "Tingling sensation = vital pulp. No response = non-vital."],
], [22, 38, 40]));
children.push(h2("6.3 Periodontal Assessment"));
for (const t of [
"Probing Pocket Depth (PPD): Calibrated periodontal probe. Normal sulcus <3 mm. Pathological pocket in periodontitis: >3 mm.",
"Bleeding on Probing (BOP): Indicates active gingival/periodontal inflammation.",
"Furcation Involvement: Grade I/II/III depending on probe penetration between roots.",
"BPE (Basic Periodontal Examination): Screening using WHO probe. Scores 0-4 per sextant. Score 4 = complex periodontal treatment needed.",
"Tooth Mobility: Grade 1 (<1 mm horizontal), Grade 2 (1-2 mm horizontal), Grade 3 (>2 mm or vertical).",
]) children.push(bullet(t));
children.push(h2("6.4 Laboratory Investigations"));
for (const t of [
"CBC: Suspected anaemia, leukaemia, bleeding disorder, or infection.",
"Blood glucose (fasting/random): Diabetes screening (associated with severe periodontitis).",
"Coagulation profile (PT/INR, aPTT): Before surgical procedures; patients on anticoagulants.",
"Biopsy (incisional): Any suspicious lesion - ulcer >3 weeks, leukoplakia, erythroplakia, suspected malignancy. Gold standard.",
"FNAC (Fine Needle Aspiration Cytology): Neck lumps/lymphadenopathy workup.",
]) children.push(bullet(t));
// ── SECTION 7 ────────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("7. Systemic Diseases & Oral Manifestations"));
children.push(body("The oral cavity is often a mirror of systemic health. Many systemic diseases have characteristic oral manifestations. This knowledge is essential for diagnosis and safe dental treatment planning."));
children.push(makeTable([
["Systemic Disease", "Oral Manifestation / Clinical Relevance"],
["Diabetes Mellitus", "Severe periodontitis, increased caries, poor wound healing, recurrent candidiasis, xerostomia, burning mouth. Uncontrolled DM = relative contraindication for elective surgery."],
["Anaemia", "Pale oral mucosa, atrophic/smooth glossitis (iron, B12, folate deficiency), angular cheilitis."],
["Leukaemia (especially AML)", "Gingival bleeding, gingival hyperplasia/enlargement, oral ulcers, petechiae. May be first presentation of leukaemia."],
["Thrombocytopenia", "Petechiae on soft palate, spontaneous gingival bleeding, prolonged bleeding after minor trauma."],
["HIV / AIDS", "Oral candidiasis (often first sign of HIV), hairy leukoplakia (lateral tongue - EBV), Kaposi's sarcoma (red/purple lesions on palate), major aphthous ulcers, linear gingival erythema."],
["Hypertension (on CCBs)", "Calcium channel blockers (amlodipine, nifedipine) cause gingival hyperplasia. Check BP before dental treatment; caution with adrenaline in LA."],
["Cardiac Disease (valvular)", "Antibiotic prophylaxis required before invasive dental procedures in HIGH-RISK patients: prosthetic cardiac valves, previous infective endocarditis, unrepaired cyanotic CHD."],
["Anticoagulant Therapy", "Increased bleeding risk. Check INR <3.5 for minor procedures. Do NOT routinely stop warfarin - apply local haemostatic measures."],
["Bisphosphonate Therapy", "MRONJ (Medication-Related Osteonecrosis of the Jaw): exposed bone failing to heal, especially post-extraction. More common with IV bisphosphonates."],
["Sjogren's Syndrome", "Severe xerostomia (dry mouth), parotid enlargement, dramatically increased cervical caries, dysphagia. Dry eyes (sicca symptoms)."],
["Vitamin Deficiencies", "Vit C (scurvy): haemorrhagic gingivitis, loose teeth. B12/folate: atrophic glossitis, aphthous ulcers. Vit D: delayed tooth eruption, increased caries."],
["Crohn's Disease / IBD", "Aphthous-like ulcers, cobblestone appearance of buccal mucosa, lip swelling (orofacial granulomatosis)."],
["Pregnancy", "Pregnancy gingivitis (hormonal - very common). Pregnancy epulis (pyogenic granuloma on gums). Avoid X-rays in 1st trimester."],
["Renal Failure", "Uraemic stomatitis, metallic taste, xerostomia, hypoplastic enamel. Adjust drug doses for renal function."],
], [28, 72]));
// ── SECTION 8 ────────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("8. Basic Dental Procedures - Observer's Guide"));
children.push(makeTable([
["Procedure", "What Happens", "Key Points to Observe"],
["Local Anaesthesia (LA)", "Inferior alveolar nerve block (mandibular teeth) or infiltration anaesthesia (maxillary teeth). Lignocaine 2% with adrenaline 1:80,000 is standard.", "Always aspirate before injecting. Adrenaline contraindicated in uncontrolled cardiac disease. Complications: failed block, haematoma, transient facial nerve palsy."],
["Scaling & Root Planing", "Removal of calculus (tartar) from tooth surfaces and roots using ultrasonic scaler + hand instruments.", "Foundation of periodontal treatment. Bleeding expected. Post-op sensitivity for a few days is normal."],
["Dental Filling (Restoration)", "Caries removed, cavity prepared, filled with composite resin (tooth-coloured) or glass ionomer cement.", "Acid etching and bonding agents for composite. Occlusion checked with articulating paper after filling."],
["Root Canal Treatment (RCT)", "Pulp tissue removed, root canals shaped, cleaned, and filled with gutta-percha. Done to save a non-vital tooth.", "Multiple visits usually required. Rubber dam used for isolation. Pain for a few days after 1st visit is common. Crown needed after RCT."],
["Dental Extraction", "Tooth removed under LA using forceps and elevators. Socket curetted, haemostasis achieved.", "Post-op: bite on gauze 30 min, no hot food, no rinsing for 24h, no smoking. Watch for post-extraction haemorrhage."],
["Incision & Drainage (I&D)", "Surgical drainage of fluctuant dental abscess. Incision made, pus drained, corrugated drain placed.", "Antibiotics are adjunct, NOT substitute for drainage. Drain reviewed and removed in 24-48h."],
["Dental X-ray", "Patient bites on periapical film/digital sensor. X-ray tube positioned outside mouth.", "Lead apron for patient. Bitewing: both arches on same film for proximal caries detection."],
], [22, 38, 40]));
// ── SECTION 9 ────────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("9. Dental Emergencies"));
children.push(h2("9.1 Post-extraction Haemorrhage"));
for (const t of [
"Primary: Bleeding during/immediately after extraction. Control with local pressure (bite on gauze for 30 minutes).",
"Reactionary: Bleeding within first few hours - clot dislodged or vasoconstriction wearing off.",
"Secondary: Bleeding 5-10 days post-extraction - usually due to infection.",
"Management: Local pressure, irrigate socket, pack with haemostatic material (Surgicel/Gelfoam), suture if needed. Check coagulation if persistent.",
]) children.push(bullet(t));
children.push(h2("9.2 Syncope (Vasovagal Attack)"));
children.push(body("Most common medical emergency in dental practice. Caused by anxiety, pain, or sight of needle/blood."));
for (const t of [
"Features: Prodrome of pallor, sweating, nausea, dizziness, then brief loss of consciousness.",
"Management: Lay patient flat (Trendelenburg position), loosen clothing, ensure airway. Usually self-limiting within 1-2 minutes. Monitor vital signs.",
]) children.push(bullet(t));
children.push(h2("9.3 Anaphylaxis"));
for (const t of [
"Causes: Local anaesthetic, latex, antibiotics (penicillin), NSAIDs.",
"Features: Urticaria, angioedema, bronchospasm, hypotension, tachycardia.",
"Management: STOP procedure immediately. Adrenaline (epinephrine) 0.5 mg IM (0.5 mL of 1:1000) into anterolateral thigh. Call for emergency help. ABC management. IV fluids, antihistamine, hydrocortisone as adjuncts.",
]) children.push(bullet(t));
children.push(h2("9.4 Ludwig's Angina - AIRWAY EMERGENCY"));
children.push(body("Life-threatening bilateral cellulitis involving submandibular, sublingual, and submental spaces. Usually from mandibular 2nd/3rd molar infection."));
for (const t of [
"Features: Brawny (firm, board-like, NON-fluctuant) swelling of floor of mouth and neck. 'Hot potato' voice, dysphagia, drooling, elevated/displaced tongue, stridor.",
"Management: AIRWAY FIRST - early intubation or surgical airway (tracheostomy/cricothyrotomy). High-dose IV antibiotics (penicillin + metronidazole). Surgical drainage of spaces.",
]) children.push(bullet(t));
children.push(h2("9.5 Dry Socket (Alveolar Osteitis)"));
for (const t of [
"Painful condition 2-4 days post-extraction due to loss or disintegration of blood clot.",
"Features: Severe throbbing pain radiating to ear or temple. Empty socket with exposed bone. Halitosis.",
"Risk factors: Smoking, poor oral hygiene, mandibular molar extractions, oral contraceptive use, traumatic extraction.",
"Management: Gentle saline irrigation of socket. Placement of alvogyl dressing (eugenol-impregnated). Analgesics (NSAIDs). Dressing changed every 2-3 days until healed.",
]) children.push(bullet(t));
// ── SECTION 10 ───────────────────────────────────────────────────────────────
children.push(pageBreak());
children.push(h1("10. Quick Reference Checklists"));
children.push(h2("Checklist 1: Complete Dental History"));
for (const t of [
"[ ] Patient ID: Name, age, sex, occupation, address, date",
"[ ] Chief Complaint: patient's own words, site, duration",
"[ ] HPI: SOCRATES (Site, Onset, Character, Radiation, Associated features, Timing, Exacerbating/Relieving factors, Severity)",
"[ ] Past Dental History: visit regularity, previous treatments, adverse reactions to LA",
"[ ] Past Medical History: DM, HTN, cardiac disease, bleeding disorder, epilepsy, renal/liver disease",
"[ ] Drug History: anticoagulants, bisphosphonates, CCBs, steroids, antiepileptics",
"[ ] Allergy History: LA, penicillin, NSAIDs, latex - ask even if patient says 'none'",
"[ ] Social History: tobacco (type, amount, duration), alcohol, diet",
"[ ] Family History: relevant genetic or dental conditions",
"[ ] Systemic Review: swelling, fever, dysphagia, weight loss, altered sensation",
]) children.push(new Paragraph({ children: [new TextRun({ text: t, size: 19, font: "Courier New" })], spacing: { after: 60 }, indent: { left: 180 } }));
children.push(h2("Checklist 2: Systematic Oral Examination"));
for (const t of [
"[ ] General: appearance, pallor, jaundice, nutrition",
"[ ] EO - Face: symmetry, swelling, skin changes, draining sinuses",
"[ ] EO - Lips: colour, angular cheilitis, herpes labialis",
"[ ] EO - TMJ: click, crepitus, tenderness, maximum mouth opening",
"[ ] EO - Lymph nodes: submental, submandibular, cervical chains",
"[ ] IO - Lips (inner surface) and labial mucosa",
"[ ] IO - Buccal mucosa bilaterally and sulcus",
"[ ] IO - Gingiva: colour, contour, BOP, recession, hyperplasia",
"[ ] IO - Teeth: chart, mobility, TTP, caries, restorations",
"[ ] IO - Hard palate and soft palate/uvula",
"[ ] IO - Tongue: dorsum, lateral borders (critical!), ventral surface",
"[ ] IO - Floor of mouth",
"[ ] IO - Oropharynx and tonsils",
"[ ] Record all findings systematically in case sheet",
]) children.push(new Paragraph({ children: [new TextRun({ text: t, size: 19, font: "Courier New" })], spacing: { after: 60 }, indent: { left: 180 } }));
children.push(h2("Checklist 3: Red Flags - Always Report to Supervisor Immediately"));
children.push(makeTable([
["Red Flag", "Possible Significance"],
["Oral ulcer persisting >3 weeks", "Oral squamous cell carcinoma or other malignancy"],
["White or red patch that cannot be rubbed off", "Leukoplakia / erythroplakia - potentially malignant, biopsy needed"],
["Unexplained loose teeth in young patient", "Aggressive periodontitis, leukaemia, Langerhans cell histiocytosis, tumour"],
["Jaw or lip numbness / paraesthesia", "IAN involvement by tumour (Vincent's sign) - urgent investigation"],
["Swelling not responding to antibiotics", "Deep neck space infection, malignancy, TB lymphadenopathy"],
["Trismus without clear cause", "OSMF, masticator space infection, malignancy, fibrosis"],
["Rapidly expanding jaw swelling in child", "Ameloblastoma, dentigerous cyst, Burkitt's lymphoma"],
["Weight loss + oral lesion", "Underlying malignancy, HIV, systemic disease"],
["Gingival bleeding not responding to scaling", "Leukaemia, thrombocytopenia, haemophilia - haematological workup needed"],
], [40, 60], RED));
children.push(sp()); children.push(sp());
children.push(new Paragraph({
children: [new TextRun({ text: "Good Luck on Your First Day!", bold: true, size: 36, color: NAVY })],
alignment: AlignmentType.CENTER, spacing: { before: 200, after: 200 },
}));
children.push(body("Remember: observe carefully, ask questions respectfully, and never perform any procedure without direct supervision. The dental team is there to teach you. Be enthusiastic, be punctual, and maintain professionalism at all times."));
children.push(new Paragraph({
children: [new TextRun({ text: "Sources: Goldman-Cecil Medicine 2024 | Harrison's Principles of Internal Medicine 22E (2025) | Pocket Dentistry (Greenwood) | Oxford Handbook of Clinical Dentistry (Mitchell) | ADA Health History Guidelines", size: 16, color: GRAY, italics: true })],
alignment: AlignmentType.CENTER, spacing: { before: 160 },
}));
// ── BUILD ─────────────────────────────────────────────────────────────────────
const doc = new Document({
creator: "Orris Medical AI",
title: "Dental Ward Guide for MBBS 3rd Year Students",
description: "Complete reference for dental ward clinical posting",
sections: [{
properties: {},
headers: {
default: new Header({
children: [new Paragraph({
children: [new TextRun({ text: "Dental Ward Guide | MBBS 3rd Year | Orris Medical AI", size: 16, color: GRAY })],
alignment: AlignmentType.RIGHT,
})],
}),
},
footers: {
default: new Footer({
children: [new Paragraph({
children: [
new TextRun({ text: "Page ", size: 16, color: GRAY }),
new PageNumber({ start: 1 }),
],
alignment: AlignmentType.CENTER,
})],
}),
},
children,
}],
});
Packer.toBuffer(doc).then(buffer => {
fs.writeFileSync('/home/daytona/workspace/dental-ward-guide/Dental_Ward_Guide_MBBS.docx', buffer);
console.log('SUCCESS: DOCX created');
}).catch(err => { console.error('ERROR:', err.message); process.exit(1); });
cd /home/daytona/workspace/dental-ward-guide && node generate_docx.js 2>&1
~/dental-ward-guide/generate_docx.js
Successfully replaced 1 instance(s) of the string in '/home/daytona/workspace/dental-ward-guide/generate_docx.js'
cd /home/daytona/workspace/dental-ward-guide && node generate_docx.js 2>&1 && ls -lh Dental_Ward_Guide_MBBS.docx
Dental Ward Guide MBBS
Word Document · DOCX