CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/npm-mathjax

JavaScript display engine for LaTeX, MathML, and AsciiMath mathematical notation in browsers and Node.js

Pending
Quality

Pending

Does it follow best practices?

Impact

Pending

No eval scenarios have been run

SecuritybySnyk

Pending

The risk profile of this skill

Overview
Eval results
Files

accessibility.mddocs/

Accessibility Features

MathJax provides comprehensive accessibility support including speech generation, semantic enrichment, interactive exploration, and assistive technology integration to make mathematical content accessible to users with disabilities.

Capabilities

Speech Generation

Generate spoken descriptions of mathematical expressions for screen readers and voice output.

interface AccessibilityOptions {
  /** Background color for highlighting */
  backgroundColor?: string;
  /** Background opacity (0-1) */
  backgroundOpacity?: number;
  /** Foreground color for highlighting */
  foregroundColor?: string;
  /** Foreground opacity (0-1) */
  foregroundOpacity?: number;
  /** Highlight color scheme */
  highlight?: 'None' | 'Hover' | 'Flame' | 'Blue' | 'Green' | 'Magenta' | 'Red';
  /** Enable subtitles display */
  subtitles?: boolean;
  /** Enable speech output */
  speech?: boolean;
}

Usage Examples:

// Enable accessibility features
MathJax.config.options = {
  enableAssistiveMml: true,
  enableExplorer: true,
  a11y: {
    backgroundColor: 'Blue',
    backgroundOpacity: 0.2,
    foregroundColor: 'Yellow', 
    foregroundOpacity: 1,
    highlight: 'Flame',
    subtitles: true,
    speech: true
  }
};

// Load accessibility components
MathJax.config.loader.load.push(
  'a11y/semantic-enrich',
  'a11y/speech',
  'a11y/explorer',
  'a11y/assistive-mml'
);

Semantic Enrichment

Enhance mathematical expressions with semantic information for better accessibility.

// Semantic enrichment is automatically applied when accessibility is enabled
// No direct API calls needed - works transparently with input processors

Configuration Examples:

// Configure semantic enrichment
MathJax.config.options = {
  enableAssistiveMml: true,  // Enable assistive MathML generation
  sre: {
    domain: 'mathspeak',     // Speech domain
    style: 'default',        // Speech style
    locale: 'en',           // Language locale
    modality: 'speech'       // Output modality
  }
};

// Advanced semantic options
MathJax.config.sre = {
  json: '/path/to/mathmaps',  // Path to semantic rules
  xpath: '/path/to/xpath',    // XPath evaluator
  domain: 'clearspeak',       // Alternative speech domain
  style: 'brief'              // Brief speech style
};

Interactive Explorer

Provide interactive navigation and exploration of mathematical expressions.

// Explorer is activated automatically when enabled
// Users can navigate using keyboard shortcuts:
// - Arrow keys: Navigate expression tree
// - Enter: Speak current sub-expression  
// - Escape: Exit exploration mode

Configuration Examples:

// Enable interactive explorer
MathJax.config.options = {
  enableExplorer: true,
  a11y: {
    keyMagnifier: true,     // Magnify focused elements
    speechTags: true,       // Include speech tags
    braille: false          // Braille output (experimental)
  }
};

// Explorer keyboard shortcuts
const explorerKeys = {
  'ArrowRight': 'next sibling',
  'ArrowLeft': 'previous sibling', 
  'ArrowDown': 'first child',
  'ArrowUp': 'parent',
  'Enter': 'speak current',
  'Escape': 'exit explorer'
};

Assistive MathML

Generate enhanced MathML with accessibility attributes for assistive technologies.

// Assistive MathML is generated automatically when enabled
// Adds aria-label, role, and other accessibility attributes

Examples:

// Enable assistive MathML
MathJax.config.options = {
  enableAssistiveMml: true
};

// Result includes accessibility attributes:
// <math aria-label="x squared plus y squared equals z squared" role="img">
//   <mrow>
//     <msup aria-label="x squared">
//       <mi>x</mi>
//       <mn>2</mn>
//     </msup>
//     <mo>+</mo>
//     <msup aria-label="y squared">
//       <mi>y</mi>
//       <mn>2</mn>
//     </msup>
//     <mo>=</mo>
//     <msup aria-label="z squared">
//       <mi>z</mi>
//       <mn>2</mn>
//     </msup>
//   </mrow>
// </math>

Accessibility Components

Speech Recognition Engine (SRE)

The Speech Rule Engine provides the core functionality for semantic analysis and speech generation.

// SRE is loaded automatically with accessibility features
MathJax.config.loader.load.push('a11y/sre');

// SRE provides multiple speech domains:
// - mathspeak: MathSpeak standard
// - clearspeak: ClearSpeak standard  
// - chromevox: ChromeVox style
// - emacspeak: Emacspeak style

Complexity Analysis

Analyze mathematical complexity to optimize speech output.

// Load complexity analyzer
MathJax.config.loader.load.push('a11y/complexity');

// Complexity affects speech verbosity
MathJax.config.sre = {
  domain: 'clearspeak',
  style: 'auto'  // Automatically adjust based on complexity
};

Visual Highlighting

Provide visual feedback during navigation and exploration.

// Configure visual highlighting
MathJax.config.options = {
  a11y: {
    backgroundColor: 'Blue',
    backgroundOpacity: 0.3,
    foregroundColor: 'White',
    foregroundOpacity: 1,
    highlight: 'Hover'  // Highlight on mouse hover
  }
};

// Available highlight modes:
// - 'None': No highlighting
// - 'Hover': Highlight on hover
// - 'Flame': Red highlighting
// - 'Blue': Blue highlighting  
// - 'Green': Green highlighting
// - 'Magenta': Magenta highlighting
// - 'Red': Red highlighting

Configuration Options

Global Accessibility Configuration

interface GlobalAccessibilityOptions {
  /** Enable assistive MathML generation */
  enableAssistiveMml?: boolean;
  /** Enable interactive explorer */
  enableExplorer?: boolean;
  /** Accessibility-specific options */
  a11y?: AccessibilityDisplayOptions;
  /** Speech Rule Engine options */
  sre?: SREOptions;
}

Display Options

interface AccessibilityDisplayOptions {
  /** Background highlight color */
  backgroundColor?: string;
  /** Background opacity (0-1) */
  backgroundOpacity?: number;
  /** Foreground highlight color */
  foregroundColor?: string;
  /** Foreground opacity (0-1) */
  foregroundOpacity?: number;
  /** Highlight color scheme */
  highlight?: 'None' | 'Hover' | 'Flame' | 'Blue' | 'Green' | 'Magenta' | 'Red';
  /** Show subtitles */
  subtitles?: boolean;
  /** Enable speech output */
  speech?: boolean;
  /** Magnify focused elements */
  keyMagnifier?: boolean;
  /** Include speech tags in output */
  speechTags?: boolean;
  /** Enable braille output (experimental) */
  braille?: boolean;
}

Speech Rule Engine Options

interface SREOptions {
  /** Speech domain */
  domain?: 'mathspeak' | 'clearspeak' | 'chromevox' | 'emacspeak';
  /** Speech style */
  style?: 'default' | 'brief' | 'sbrief' | 'auto';
  /** Language locale */
  locale?: string;
  /** Output modality */
  modality?: 'speech' | 'braille' | 'prefix' | 'summary';
  /** Path to semantic rules */
  json?: string;
  /** XPath evaluator path */
  xpath?: string;
}

Complete Configuration Example

// Comprehensive accessibility setup
window.MathJax = {
  // Load accessibility components
  loader: {
    load: [
      'input/tex', 'output/chtml',
      'a11y/semantic-enrich',
      'a11y/speech', 
      'a11y/explorer',
      'a11y/complexity',
      'a11y/assistive-mml'
    ]
  },
  
  // Enable accessibility features
  options: {
    enableAssistiveMml: true,
    enableExplorer: true,
    
    // Visual highlighting
    a11y: {
      backgroundColor: 'Blue',
      backgroundOpacity: 0.2,
      foregroundColor: 'Yellow',
      foregroundOpacity: 1,
      highlight: 'Hover',
      subtitles: true,
      speech: true,
      keyMagnifier: true,
      speechTags: true
    },
    
    // Speech configuration
    sre: {
      domain: 'clearspeak',
      style: 'default',
      locale: 'en',
      modality: 'speech'
    }
  },
  
  // TeX input with accessibility-friendly packages
  tex: {
    packages: ['base', 'ams', 'color'],
    macros: {
      // Define accessible macros
      accessible: ['\\text{#1}', 1]
    }
  },
  
  // CommonHTML output with accessibility
  chtml: {
    fontURL: 'https://cdn.jsdelivr.net/npm/mathjax@4/fonts/woff-v2',
    adaptiveCSS: true
  }
};

Speech Domains and Styles

MathSpeak Domain

Standard mathematical speech rules from Design Science.

MathJax.config.sre = {
  domain: 'mathspeak',
  style: 'default'  // or 'brief', 'sbrief'
};

// Examples:
// "x^2" → "x squared"
// "\\frac{a}{b}" → "fraction a over b"
// "\\sum_{i=1}^n" → "sum from i equals 1 to n"

ClearSpeak Domain

Mathematical speech rules optimized for clarity.

MathJax.config.sre = {
  domain: 'clearspeak',
  style: 'default'  // or 'brief'
};

// Examples:
// "x^2" → "x squared"  
// "\\frac{a}{b}" → "the fraction with numerator a and denominator b"
// "\\sqrt{x}" → "the square root of x"

ChromeVox Domain

Speech rules optimized for the ChromeVox screen reader.

MathJax.config.sre = {
  domain: 'chromevox',
  style: 'default'
};

Interactive Navigation

Keyboard Shortcuts

Users can navigate mathematical expressions using keyboard shortcuts:

KeyAction
Move to next sibling
Move to previous sibling
Move to first child
Move to parent
EnterSpeak current element
EscapeExit exploration mode
SpaceToggle subtitles

Navigation Example

// Enable explorer and handle events
MathJax.config.options = {
  enableExplorer: true,
  a11y: {
    subtitles: true,
    speech: true
  }
};

// Listen for navigation events (if needed for custom handling)
document.addEventListener('click', (event) => {
  const mathElement = event.target.closest('.mjx-chtml, .mjx-svg');
  if (mathElement) {
    // Math element clicked - explorer will activate automatically
    console.log('Math explorer activated');
  }
});

Screen Reader Integration

NVDA Integration

// Optimize for NVDA screen reader
MathJax.config.options = {
  enableAssistiveMml: true,
  sre: {
    domain: 'mathspeak',
    style: 'default',
    locale: 'en'
  }
};

JAWS Integration

// Optimize for JAWS screen reader
MathJax.config.options = {
  enableAssistiveMml: true,
  sre: {
    domain: 'clearspeak',
    style: 'brief',
    locale: 'en'
  }
};

VoiceOver Integration

// Optimize for VoiceOver (macOS/iOS)
MathJax.config.options = {
  enableAssistiveMml: true,
  sre: {
    domain: 'mathspeak',
    style: 'sbrief',  // Super brief for VoiceOver
    locale: 'en'
  }
};

Advanced Accessibility Features

Custom Speech Rules

// Add custom speech rules (requires SRE knowledge)
MathJax.config.sre = {
  domain: 'clearspeak',
  style: 'default',
  // Custom rules can be added through SRE configuration
  customRules: {
    'custom-notation': 'custom speech pattern'
  }
};

Multilingual Support

// Configure for different languages
MathJax.config.sre = {
  domain: 'mathspeak',
  style: 'default',
  locale: 'es',  // Spanish
  // Available locales: en, es, fr, de, it, etc.
};

// Language-specific speech patterns
const languageConfigs = {
  en: { domain: 'clearspeak', style: 'default' },
  es: { domain: 'mathspeak', style: 'default' },
  fr: { domain: 'mathspeak', style: 'brief' },
  de: { domain: 'mathspeak', style: 'default' }
};

// Apply language configuration
const userLang = navigator.language.substring(0, 2);
MathJax.config.sre = languageConfigs[userLang] || languageConfigs.en;

Braille Output

// Enable experimental braille support
MathJax.config.options = {
  a11y: {
    braille: true
  },
  sre: {
    modality: 'braille',
    domain: 'mathspeak'
  }
};

Testing Accessibility

Accessibility Validation

// Test accessibility features
function testAccessibility() {
  // Check if assistive MathML is generated
  const mathElements = document.querySelectorAll('[role="img"]');
  console.log(`Found ${mathElements.length} accessible math elements`);
  
  // Check aria-labels
  mathElements.forEach((element, index) => {
    const label = element.getAttribute('aria-label');
    console.log(`Element ${index}: ${label || 'No aria-label'}`);
  });
  
  // Test speech generation
  if (window.SRE) {
    const testExpr = 'x^2 + y^2 = z^2';
    const speech = window.SRE.toSpeech(testExpr);
    console.log(`Speech output: ${speech}`);
  }
}

// Run accessibility tests
MathJax.whenReady(testAccessibility);

Screen Reader Testing

// Simulate screen reader interaction
function simulateScreenReader() {
  const mathElements = document.querySelectorAll('.mjx-chtml, .mjx-svg');
  
  mathElements.forEach(element => {
    // Check for proper ARIA attributes
    const role = element.getAttribute('role');
    const label = element.getAttribute('aria-label');
    const describedBy = element.getAttribute('aria-describedby');
    
    console.log('Accessibility attributes:', {
      role,
      label,
      describedBy
    });
    
    // Test focus management
    element.tabIndex = 0;
    element.addEventListener('focus', () => {
      console.log('Math element focused:', label);
    });
  });
}

// Apply screen reader simulation
MathJax.typesetPromise().then(simulateScreenReader);

Performance Considerations

Selective Accessibility

// Enable accessibility only when needed
const hasScreenReader = window.navigator.userAgent.includes('NVDA') ||
                       window.navigator.userAgent.includes('JAWS') ||
                       window.speechSynthesis;

if (hasScreenReader) {
  MathJax.config.options.enableAssistiveMml = true;
  MathJax.config.options.enableExplorer = true;
  MathJax.config.loader.load.push('a11y/semantic-enrich', 'a11y/speech');
}

Lazy Loading Accessibility

// Load accessibility features on demand
function enableAccessibility() {
  return MathJax.loader.load('a11y/semantic-enrich', 'a11y/speech', 'a11y/explorer')
    .then(() => {
      MathJax.config.options.enableAssistiveMml = true;
      MathJax.config.options.enableExplorer = true;
      
      // Re-process existing math
      return MathJax.typesetPromise();
    });
}

// Enable on user request or detection
document.getElementById('enable-accessibility').addEventListener('click', enableAccessibility);

docs

accessibility.md

document-rendering.md

extensions.md

index.md

initialization.md

input-processing.md

output-formats.md

tile.json