itutor-mathlive
Version:
Beautifully typeset math made easy
598 lines (515 loc) • 115 kB
HTML
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8"><title>core/mathAtom.js - MathLive Docs</title><meta name="description" content="Beautifully typeset math made easy"><meta name="keywords" content="latex, tex, math, typesetting, documentation, docs">
<meta name="viewport" content="width=device-width, initial-scale=1">
<script src="scripts/prettify/prettify.js"></script>
<script src="scripts/prettify/lang-css.js"></script>
<!--[if lt IE 9]>
<script src="//html5shiv.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
<link href="https://fonts.googleapis.com/css?family=Source+Code+Pro:400,700|Source+Sans+Pro:400,400i,700,900" rel="stylesheet">
<style>pre.prettyprint{background: #35434e;}</style>
<link type="text/css" rel="stylesheet" href="styles/prettify-tomorrow-night.css">
<link type="text/css" rel="stylesheet" href="styles/jsdoc-default.css">
<link type="text/css" rel="stylesheet" href="styles/custom.css">
</head>
<body>
<div class="forkme"><a href="https://github.com/arnog/mathlive"><img style="position: absolute; top: 0; right: 0; border: 0; z-index:1;" src="https://camo.githubusercontent.com/52760788cde945287fbb584134c4cbc2bc36f904/68747470733a2f2f73332e616d617a6f6e6177732e636f6d2f6769746875622f726962626f6e732f666f726b6d655f72696768745f77686974655f6666666666662e706e67" alt="Fork me on GitHub" data-canonical-src="https://s3.amazonaws.com/github/ribbons/forkme_right_white_ffffff.png"></a></div>
<section role="navigation">
<input type="checkbox" id="nav-trigger" class="nav-trigger" />
<label for="nav-trigger" class="navicon-button x">
<div class="navicon"></div>
</label>
<label for="nav-trigger" class="overlay"></label>
<nav id="nav">
<h3 class="group-title home"><a href="index.html">MathLive Docs</a></h3><input class="search" placeholder="Search" type="text"><div class="list"><h3 class="group-title">Tutorials</h3><ul><li><a href="tutorial-CONTRIBUTOR_GUIDE.html">Contributor Guide</a></li><li><a href="tutorial-MASTON.html">MASTON</a></li><li><a href="tutorial-USAGE_GUIDE.html">Usage Guide</a></li></ul><h3 class="group-title">Classes</h3><ul><li class="private"><a href="Context.html" class="className">Context</a><ul class='methods private'><li data-type='method' class='private'><a href="Context.html#clone" class="methodName">clone</a></li><li data-type='method' class='private'><a href="Context.html#cloneWith" class="methodName">cloneWith</a></li><li data-type='method' class='private'><a href="Context.html#getBackgroundColor" class="methodName">getBackgroundColor</a></li><li data-type='method' class='private'><a href="Context.html#getColor" class="methodName">getColor</a></li><li data-type='method' class='private'><a href="Context.html#setMathstyle" class="methodName">setMathstyle</a></li><li data-type='method' class='private'><a href="Context.html#withMathstyle" class="methodName">withMathstyle</a></li></ul></li><li><a href="EditableMathlist.html" class="className">EditableMathlist</a><ul class='methods'><li data-type='method'><a href="EditableMathlist.html#_addCell" class="methodName">_addCell</a></li><li data-type='method'><a href="EditableMathlist.html#_deleteAtoms" class="methodName">_deleteAtoms</a></li><li data-type='method'><a href="EditableMathlist.html#addColumnAfter_" class="methodName">addColumnAfter_</a></li><li data-type='method'><a href="EditableMathlist.html#addColumnBefore_" class="methodName">addColumnBefore_</a></li><li data-type='method'><a href="EditableMathlist.html#addRowAfter_" class="methodName">addRowAfter_</a></li><li data-type='method'><a href="EditableMathlist.html#addRowBefore_" class="methodName">addRowBefore_</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#ancestor" class="methodName">ancestor</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#anchor" class="methodName">anchor</a></li><li data-type='method'><a href="EditableMathlist.html#applyStyle" class="methodName">applyStyle</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#commandOffsets" class="methodName">commandOffsets</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#commitCommandStringBeforeInsertionPoint" class="methodName">commitCommandStringBeforeInsertionPoint</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#contains" class="methodName">contains</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#decorateCommandStringAroundInsertionPoint" class="methodName">decorateCommandStringAroundInsertionPoint</a></li><li data-type='method'><a href="EditableMathlist.html#delete" class="methodName">delete</a></li><li data-type='method'><a href="EditableMathlist.html#delete_" class="methodName">delete_</a></li><li data-type='method'><a href="EditableMathlist.html#deleteAll_" class="methodName">deleteAll_</a></li><li data-type='method'><a href="EditableMathlist.html#deleteNextChar_" class="methodName">deleteNextChar_</a></li><li data-type='method'><a href="EditableMathlist.html#deleteNextWord_" class="methodName">deleteNextWord_</a></li><li data-type='method'><a href="EditableMathlist.html#deletePreviousChar_" class="methodName">deletePreviousChar_</a></li><li data-type='method'><a href="EditableMathlist.html#deletePreviousWord_" class="methodName">deletePreviousWord_</a></li><li data-type='method'><a href="EditableMathlist.html#deleteToGroupEnd_" class="methodName">deleteToGroupEnd_</a></li><li data-type='method'><a href="EditableMathlist.html#deleteToGroupStart_" class="methodName">deleteToGroupStart_</a></li><li data-type='method'><a href="EditableMathlist.html#deleteToMathFieldEnd_" class="methodName">deleteToMathFieldEnd_</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#endOffset" class="methodName">endOffset</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#extend" class="methodName">extend</a></li><li data-type='method'><a href="EditableMathlist.html#extendDown_" class="methodName">extendDown_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToGroupEnd_" class="methodName">extendToGroupEnd_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToGroupStart_" class="methodName">extendToGroupStart_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToMathFieldEnd_" class="methodName">extendToMathFieldEnd_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToMathFieldStart_" class="methodName">extendToMathFieldStart_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToNextBoundary_" class="methodName">extendToNextBoundary_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToNextChar_" class="methodName">extendToNextChar_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToNextWord_" class="methodName">extendToNextWord_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToPreviousBoundary_" class="methodName">extendToPreviousBoundary_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToPreviousChar_" class="methodName">extendToPreviousChar_</a></li><li data-type='method'><a href="EditableMathlist.html#extendToPreviousWord_" class="methodName">extendToPreviousWord_</a></li><li data-type='method'><a href="EditableMathlist.html#extendUp_" class="methodName">extendUp_</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#extractCharactersBeforeInsertionPoint" class="methodName">extractCharactersBeforeInsertionPoint</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#extractCommandStringAroundInsertionPoint" class="methodName">extractCommandStringAroundInsertionPoint</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#extractContents" class="methodName">extractContents</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#extractContentsOrdInGroupBeforeInsertionPoint" class="methodName">extractContentsOrdInGroupBeforeInsertionPoint</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#filter" class="methodName">filter</a></li><li data-type='method'><a href="EditableMathlist.html#insert" class="methodName">insert</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#insertFirstAtom" class="methodName">insertFirstAtom</a></li><li data-type='method'><a href="EditableMathlist.html#isCollapsed" class="methodName">isCollapsed</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#jump" class="methodName">jump</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#leap" class="methodName">leap</a></li><li data-type='method'><a href="EditableMathlist.html#moveAfterParent_" class="methodName">moveAfterParent_</a></li><li data-type='method'><a href="EditableMathlist.html#moveBeforeParent_" class="methodName">moveBeforeParent_</a></li><li data-type='method'><a href="EditableMathlist.html#moveDown_" class="methodName">moveDown_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToGroupEnd_" class="methodName">moveToGroupEnd_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToGroupStart_" class="methodName">moveToGroupStart_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToMathFieldEnd_" class="methodName">moveToMathFieldEnd_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToMathFieldStart_" class="methodName">moveToMathFieldStart_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToNextChar_" class="methodName">moveToNextChar_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToNextPlaceholder_" class="methodName">moveToNextPlaceholder_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToNextWord_" class="methodName">moveToNextWord_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToOpposite_" class="methodName">moveToOpposite_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToPreviousChar_" class="methodName">moveToPreviousChar_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToPreviousPlaceholder_" class="methodName">moveToPreviousPlaceholder_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToPreviousWord_" class="methodName">moveToPreviousWord_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToSubscript_" class="methodName">moveToSubscript_</a></li><li data-type='method'><a href="EditableMathlist.html#moveToSuperscript_" class="methodName">moveToSuperscript_</a></li><li data-type='method'><a href="EditableMathlist.html#moveUp_" class="methodName">moveUp_</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#next" class="methodName">next</a></li><li data-type='method'><a href="EditableMathlist.html#selectAll_" class="methodName">selectAll_</a></li><li data-type='method'><a href="EditableMathlist.html#selectGroup_" class="methodName">selectGroup_</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#setExtent" class="methodName">setExtent</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#setRange" class="methodName">setRange</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#setSelection" class="methodName">setSelection</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#sibling" class="methodName">sibling</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#siblings" class="methodName">siblings</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#skip" class="methodName">skip</a></li><li data-type='method'><a href="EditableMathlist.html#speakAll_" class="methodName">speakAll_</a></li><li data-type='method'><a href="EditableMathlist.html#speakAllWithSynchronizedHighlighting_" class="methodName">speakAllWithSynchronizedHighlighting_</a></li><li data-type='method'><a href="EditableMathlist.html#speakGroup_" class="methodName">speakGroup_</a></li><li data-type='method'><a href="EditableMathlist.html#speakLeftSibling_" class="methodName">speakLeftSibling_</a></li><li data-type='method'><a href="EditableMathlist.html#speakParent_" class="methodName">speakParent_</a></li><li data-type='method'><a href="EditableMathlist.html#speakRightSibling_" class="methodName">speakRightSibling_</a></li><li data-type='method'><a href="EditableMathlist.html#speakSelection_" class="methodName">speakSelection_</a></li><li data-type='method'><a href="EditableMathlist.html#speakSelectionWithSynchronizedHighlighting_" class="methodName">speakSelectionWithSynchronizedHighlighting_</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#startOffset" class="methodName">startOffset</a></li><li data-type='method' class='private'><a href="EditableMathlist.html#toString" class="methodName">toString</a></li><li data-type='method'><a href="EditableMathlist.html#transpose_" class="methodName">transpose_</a></li></ul></li><li class="private"><a href="Lexer.html" class="className">Lexer</a><ul class='methods private'><li data-type='method' class='private'><a href="Lexer.html#end" class="methodName">end</a></li><li data-type='method' class='private'><a href="Lexer.html#get" class="methodName">get</a></li><li data-type='method' class='private'><a href="Lexer.html#isWhiteSpace" class="methodName">isWhiteSpace</a></li><li data-type='method' class='private'><a href="Lexer.html#makeToken" class="methodName">makeToken</a></li><li data-type='method' class='private'><a href="Lexer.html#peek" class="methodName">peek</a></li><li data-type='method' class='private'><a href="Lexer.html#scan" class="methodName">scan</a></li></ul></li><li class="private"><a href="MathAtom.html" class="className">MathAtom</a><ul class='methods private'><li data-type='method' class='private'><a href="MathAtom.html#.toSpeakableText" class="methodName">toSpeakableText</a></li><li data-type='method' class='private'><a href="MathAtom.html#bind" class="methodName">bind</a></li><li data-type='method' class='private'><a href="MathAtom.html#decompose" class="methodName">decompose</a></li><li data-type='method' class='private'><a href="MathAtom.html#decomposeGenfrac" class="methodName">decomposeGenfrac</a></li><li data-type='method' class='private'><a href="MathAtom.html#decomposeLeftright" class="methodName">decomposeLeftright</a></li><li data-type='method' class='private'><a href="MathAtom.html#decomposeLine" class="methodName">decomposeLine</a></li><li data-type='method' class='private'><a href="MathAtom.html#decomposeRule" class="methodName">decomposeRule</a></li><li data-type='method' class='private'><a href="MathAtom.html#filter" class="methodName">filter</a></li><li data-type='method' class='private'><a href="MathAtom.html#makeSpan" class="methodName">makeSpan</a></li></ul></li><li><a href="MathField.html" class="className">MathField</a><ul class='methods'><li data-type='method' class='private'><a href="MathField.html#_getCaretPosition" class="methodName">_getCaretPosition</a></li><li data-type='method' class='private'><a href="MathField.html#_onKeystroke" class="methodName">_onKeystroke</a></li><li data-type='method' class='private'><a href="MathField.html#complete_" class="methodName">complete_</a></li><li data-type='method'><a href="MathField.html#el" class="methodName">el</a></li><li data-type='method' class='private'><a href="MathField.html#enterCommandMode_" class="methodName">enterCommandMode_</a></li><li data-type='method'><a href="MathField.html#insert" class="methodName">insert</a></li><li data-type='method'><a href="MathField.html#keystroke" class="methodName">keystroke</a></li><li data-type='method'><a href="MathField.html#latex" class="methodName">latex</a></li><li data-type='method'><a href="MathField.html#perform" class="methodName">perform</a></li><li data-type='method'><a href="MathField.html#perform" class="methodName">perform</a></li><li data-type='method' class='private'><a href="MathField.html#render" class="methodName">render</a></li><li data-type='method'><a href="MathField.html#revertToOriginalContent" class="methodName">revertToOriginalContent</a></li><li data-type='method'><a href="MathField.html#selectedText" class="methodName">selectedText</a></li><li data-type='method'><a href="MathField.html#selectionAtEnd" class="methodName">selectionAtEnd</a></li><li data-type='method'><a href="MathField.html#selectionAtStart" class="methodName">selectionAtStart</a></li><li data-type='method'><a href="MathField.html#selectionDepth" class="methodName">selectionDepth</a></li><li data-type='method'><a href="MathField.html#selectionIsCollapsed" class="methodName">selectionIsCollapsed</a></li><li data-type='method'><a href="MathField.html#setConfig" class="methodName">setConfig</a></li><li data-type='method'><a href="MathField.html#text" class="methodName">text</a></li><li data-type='method'><a href="MathField.html#typedText" class="methodName">typedText</a></li></ul></li><li class="private"><a href="module-mathstyle.Mathstyle.html" class="className">Mathstyle</a></li><li class="private"><a href="Parser.html" class="className">Parser</a><ul class='methods private'><li data-type='method' class='private'><a href="Parser.html#end" class="methodName">end</a></li><li data-type='method' class='private'><a href="Parser.html#hasLiteral" class="methodName">hasLiteral</a></li><li data-type='method' class='private'><a href="Parser.html#hasLiteralPattern" class="methodName">hasLiteralPattern</a></li><li data-type='method' class='private'><a href="Parser.html#hasToken" class="methodName">hasToken</a></li><li data-type='method' class='private'><a href="Parser.html#lastMathAtom" class="methodName">lastMathAtom</a></li><li data-type='method' class='private'><a href="Parser.html#parseAtom" class="methodName">parseAtom</a></li><li data-type='method' class='private'><a href="Parser.html#parseKeyword" class="methodName">parseKeyword</a></li><li data-type='method' class='private'><a href="Parser.html#parseLimits" class="methodName">parseLimits</a></li><li data-type='method' class='private'><a href="Parser.html#parseSupSub" class="methodName">parseSupSub</a></li><li data-type='method' class='private'><a href="Parser.html#parseToken" class="methodName">parseToken</a></li><li data-type='method' class='private'><a href="Parser.html#scanArg" class="methodName">scanArg</a></li><li data-type='method' class='private'><a href="Parser.html#scanColor" class="methodName">scanColor</a></li><li data-type='method' class='private'><a href="Parser.html#scanDelim" class="methodName">scanDelim</a></li><li data-type='method' class='private'><a href="Parser.html#scanDimen" class="methodName">scanDimen</a></li><li data-type='method' class='private'><a href="Parser.html#scanEnvironment" class="methodName">scanEnvironment</a></li><li data-type='method' class='private'><a href="Parser.html#scanGroup" class="methodName">scanGroup</a></li><li data-type='method' class='private'><a href="Parser.html#scanImplicitGroup" class="methodName">scanImplicitGroup</a></li><li data-type='method' class='private'><a href="Parser.html#scanLeftRight" class="methodName">scanLeftRight</a></li><li data-type='method' class='private'><a href="Parser.html#scanModeSet" class="methodName">scanModeSet</a></li><li data-type='method' class='private'><a href="Parser.html#scanModeShift" class="methodName">scanModeShift</a></li><li data-type='method' class='private'><a href="Parser.html#scanNumber" class="methodName">scanNumber</a></li><li data-type='method' class='private'><a href="Parser.html#scanString" class="methodName">scanString</a></li><li data-type='method' class='private'><a href="Parser.html#scanToken" class="methodName">scanToken</a></li></ul></li><li class="private"><a href="Span.html" class="className">Span</a></li><li class="private"><a href="Token.html" class="className">Token</a></li><li class="private"><a href="UndoManager.html" class="className">UndoManager</a><ul class='methods private'><li data-type='method' class='private'><a href="UndoManager.html#canRedo" class="methodName">canRedo</a></li><li data-type='method' class='private'><a href="UndoManager.html#canUndo" class="methodName">canUndo</a></li><li data-type='method' class='private'><a href="UndoManager.html#redo" class="methodName">redo</a></li><li data-type='method' class='private'><a href="UndoManager.html#snapshot" class="methodName">snapshot</a></li><li data-type='method' class='private'><a href="UndoManager.html#undo" class="methodName">undo</a></li></ul></li></ul><h3 class="group-title">Modules</h3><ul><li class="private"><a href="module-color.html" class="className">color</a><ul class='methods private'><li data-type='method' class='private'><a href="module-color.html#.stringToColor" class="methodName">stringToColor</a></li></ul></li><li class="private"><a href="module-definitions.html" class="className">definitions</a><ul class='methods private'><li data-type='method' class='private'><a href="module-definitions.html#.defineEnvironment" class="methodName">defineEnvironment</a></li><li data-type='method' class='private'><a href="module-definitions.html#.defineFunction" class="methodName">defineFunction</a></li><li data-type='method' class='private'><a href="module-definitions.html#.defineSymbol" class="methodName">defineSymbol</a></li><li data-type='method' class='private'><a href="module-definitions.html#.defineSymbolRange" class="methodName">defineSymbolRange</a></li><li data-type='method' class='private'><a href="module-definitions.html#.defineSymbols" class="methodName">defineSymbols</a></li><li data-type='method' class='private'><a href="module-definitions.html#.frequency" class="methodName">frequency</a></li><li data-type='method' class='private'><a href="module-definitions.html#.getInfo" class="methodName">getInfo</a></li><li data-type='method' class='private'><a href="module-definitions.html#.matchCodepoint" class="methodName">matchCodepoint</a></li><li data-type='method' class='private'><a href="module-definitions.html#.matchFunction" class="methodName">matchFunction</a></li><li data-type='method' class='private'><a href="module-definitions.html#.parseParamTemplateArgument" class="methodName">parseParamTemplateArgument</a></li><li data-type='method' class='private'><a href="module-definitions.html#.suggest" class="methodName">suggest</a></li></ul></li><li class="private"><a href="module-delimiters.html" class="className">delimiters</a><ul class='methods private'><li data-type='method' class='private'><a href="module-delimiters.html#.makeCustomSizedDelim" class="methodName">makeCustomSizedDelim</a></li><li data-type='method' class='private'><a href="module-delimiters.html#.makeInner" class="methodName">makeInner</a></li><li data-type='method' class='private'><a href="module-delimiters.html#.makeLargeDelim" class="methodName">makeLargeDelim</a></li><li data-type='method' class='private'><a href="module-delimiters.html#.makeLeftRightDelim" class="methodName">makeLeftRightDelim</a></li><li data-type='method' class='private'><a href="module-delimiters.html#.makeNullFence" class="methodName">makeNullFence</a></li><li data-type='method' class='private'><a href="module-delimiters.html#.makeSizedDelim" class="methodName">makeSizedDelim</a></li><li data-type='method' class='private'><a href="module-delimiters.html#.makeSmallDelim" class="methodName">makeSmallDelim</a></li><li data-type='method' class='private'><a href="module-delimiters.html#.makeStackedDelim" class="methodName">makeStackedDelim</a></li><li data-type='method' class='private'><a href="module-delimiters.html#.traverseSequence" class="methodName">traverseSequence</a></li></ul></li><li class="private"><a href="module-editor_editableMathlist.html" class="className">editor/editableMathlist</a><ul class='methods private'><li data-type='method' class='private'><a href="module-editor_editableMathlist.html#~atomContains" class="methodName">atomContains</a></li></ul></li><li class="private"><a href="module-editor_keyboard.html" class="className">editor/keyboard</a><ul class='methods private'><li data-type='method' class='private'><a href="module-editor_keyboard.html#.delegateKeyboardEvents" class="methodName">delegateKeyboardEvents</a></li><li data-type='method' class='private'><a href="module-editor_keyboard.html#.keyboardEventToString" class="methodName">keyboardEventToString</a></li></ul></li><li class="private"><a href="module-editor_mathfield.html" class="className">editor/mathfield</a><ul class='methods private'><li data-type='method' class='private'><a href="module-editor_mathfield.html#nearestElementFromPoint" class="methodName">nearestElementFromPoint</a></li></ul></li><li class="private"><a href="module-editor_mathpath.html" class="className">editor/mathpath</a><ul class='methods private'><li data-type='method' class='private'><a href="module-editor_mathpath.html#.pathCommonAncestor" class="methodName">pathCommonAncestor</a></li><li data-type='method' class='private'><a href="module-editor_mathpath.html#.pathDistance" class="methodName">pathDistance</a></li><li data-type='method' class='private'><a href="module-editor_mathpath.html#.pathFromString" class="methodName">pathFromString</a></li><li data-type='method' class='private'><a href="module-editor_mathpath.html#.pathToString" class="methodName">pathToString</a></li></ul></li><li class="private"><a href="module-editor_shortcuts.html" class="className">editor/shortcuts</a><ul class='methods private'><li data-type='method' class='private'><a href="module-editor_shortcuts.html#.match" class="methodName">match</a></li><li data-type='method' class='private'><a href="module-editor_shortcuts.html#.matchKeystroke" class="methodName">matchKeystroke</a></li><li data-type='method' class='private'><a href="module-editor_shortcuts.html#.platform" class="methodName">platform</a></li><li data-type='method' class='private'><a href="module-editor_shortcuts.html#.stringify" class="methodName">stringify</a></li></ul></li><li class="private"><a href="module-fontMetrics.html" class="className">fontMetrics</a><ul class='methods private'><li data-type='method' class='private'><a href="module-fontMetrics.html#.getCharacterMetrics" class="methodName">getCharacterMetrics</a></li></ul></li><li class="private"><a href="module-lexer.html" class="className">lexer</a><ul class='methods private'><li data-type='method' class='private'><a href="module-lexer.html#.tokenize" class="methodName">tokenize</a></li></ul></li><li class="private"><a href="module-mathAtom.html" class="className">mathAtom</a><ul class='methods private'><li data-type='method' class='private'><a href="module-mathAtom.html#.decompose" class="methodName">decompose</a></li><li data-type='method' class='private'><a href="module-mathAtom.html#.getFontName" class="methodName">getFontName</a></li><li data-type='method' class='private'><a href="module-mathAtom.html#.makeColGap" class="methodName">makeColGap</a></li><li data-type='method' class='private'><a href="module-mathAtom.html#.makeColOfRepeatingElements" class="methodName">makeColOfRepeatingElements</a></li><li data-type='method' class='private'><a href="module-mathAtom.html#.makeStack" class="methodName">makeStack</a></li></ul></li><li><a href="module-mathlive.html" class="className">mathlive</a><ul class='methods'><li data-type='method'><a href="module-mathlive.html#latexToAST" class="methodName">latexToAST</a></li><li data-type='method'><a href="module-mathlive.html#latexToMarkup" class="methodName">latexToMarkup</a></li><li data-type='method'><a href="module-mathlive.html#latexToMathML" class="methodName">latexToMathML</a></li><li data-type='method'><a href="module-mathlive.html#latexToSpeakableText" class="methodName">latexToSpeakableText</a></li><li data-type='method'><a href="module-mathlive.html#makeMathField" class="methodName">makeMathField</a></li><li data-type='method'><a href="module-mathlive.html#pauseReadAloud" class="methodName">pauseReadAloud</a></li><li data-type='method'><a href="module-mathlive.html#playReadAloud" class="methodName">playReadAloud</a></li><li data-type='method'><a href="module-mathlive.html#readAloud" class="methodName">readAloud</a></li><li data-type='method'><a href="module-mathlive.html#readAloudStatus" class="methodName">readAloudStatus</a></li><li data-type='method'><a href="module-mathlive.html#renderMathInDocument" class="methodName">renderMathInDocument</a></li><li data-type='method'><a href="module-mathlive.html#renderMathInElement" class="methodName">renderMathInElement</a></li><li data-type='method'><a href="module-mathlive.html#resumeReadAloud" class="methodName">resumeReadAloud</a></li><li data-type='method'><a href="module-mathlive.html#revertToOriginalContent" class="methodName">revertToOriginalContent</a></li><li data-type='method'><a href="module-mathlive.html#revertToOriginalContent" class="methodName">revertToOriginalContent</a></li></ul></li><li class="private"><a href="module-mathstyle.html" class="className">mathstyle</a><ul class='methods private'><li data-type='method' class='private'><a href="module-mathstyle.html#.toMathstyle" class="methodName">toMathstyle</a></li></ul></li><li class="private"><a href="module-span.html" class="className">span</a><ul class='methods private'><li data-type='method' class='private'><a href="module-span.html#.coalesce" class="methodName">coalesce</a></li><li data-type='method' class='private'><a href="module-span.html#.makeFontSizer" class="methodName">makeFontSizer</a></li><li data-type='method' class='private'><a href="module-span.html#.makeHlist" class="methodName">makeHlist</a></li><li data-type='method' class='private'><a href="module-span.html#.makeSpan" class="methodName">makeSpan</a></li><li data-type='method' class='private'><a href="module-span.html#.makeSpanOfType" class="methodName">makeSpanOfType</a></li><li data-type='method' class='private'><a href="module-span.html#.makeSymbol" class="methodName">makeSymbol</a></li><li data-type='method' class='private'><a href="module-span.html#.makeVlist" class="methodName">makeVlist</a></li><li data-type='method' class='private'><a href="module-span.html#.toString" class="methodName">toString</a></li></ul></li></ul><label class="checkbox"><input id="toggle-private" type="checkbox" onclick="
if (!document.getElementById('toggle-private').checked) {
document.documentElement.classList.add('no-private')
writeCookie('symbol-access', 'no-private')
} else {
document.documentElement.classList.remove('no-private')
writeCookie('symbol-access', 'private')
}
">Include Private Symbols</input></label></div>
<footer role="contentInfo">
Made with <a href="https://github.com/jsdoc3/jsdoc">JSDoc 3.5.5</a>.
</footer>
</nav>
</section>
<main id="main">
<h1 class="page-title">core/mathAtom.js</h1>
<section>
<article>
<pre class="prettyprint source linenums">
<code>/*global require:false*/
/*global define:false*/
/**
*
* See {@linkcode MathAtom}
* @module mathAtom
* @private
*/
define([
'mathlive/core/mathstyle',
'mathlive/core/context',
'mathlive/core/fontMetrics',
'mathlive/core/span',
'mathlive/core/delimiters'],
function(Mathstyle, Context, FontMetricsModule, Span, Delimiters) {
const makeSpan = Span.makeSpan;
const makeOrd = Span.makeOrd;
const makeInner = Span.makeInner;
const makeHlist = Span.makeHlist;
const makeVlist = Span.makeVlist;
const FONTMETRICS = FontMetricsModule.metrics;
const getCharacterMetrics = FontMetricsModule.getCharacterMetrics;
/**
* An atom is an object encapsulating an elementary mathematical unit,
* independent of its graphical representation.
*
* It keeps track of the content, while the dimensions, position and style
* are tracked by Span objects which are created by the `decompose()` functions.
*
* @param {string} mode
* @param {string} type
* @param {string|MathAtom[]} body
* @param {?string} [fontFamily="main"]
* @param {?Object} [extras=null] A set of additional properties to append to
* the atom
* @return {MathAtom}
* @property {string} mode `'display'`, `'command'`, etc...
* @property {string} type - Type can be one of:
* - `mord`: ordinary symbol, e.g. `x`, `\alpha`
* - `textord`: ordinary characters used in text mode
* - `mop`: operators, including special functions, `\sin`, `\sum`, `\cap`.
* - `mbin`: binary operator: `+`, `*`, etc...
* - `mrel`: relational operator: `=`, `\ne`, etc...
* - `mpunct`: punctuation: `,`, `:`, etc...
* - `mopen`: opening fence: `(`, `\langle`, etc...
* - `mclose`: closing fence: `)`, `\rangle`, etc...
* - `minner`: special layout cases, overlap, `\left...\right`
*
* In addition to these basic types, which correspond to the TeX atom types,
* some atoms represent more complex compounds, including:
* - `space` and `spacing`: blank space between atoms
* - `mathstyle`: to change the math style used: `display` or `text`.
* The layout rules are different for each, the latter being more compact and
* intended to be incorporated with surrounding non-math text.
* - `root`: a group, which has no parent (only one per formula)
* - `group`: a simple group of atoms, for example from a `{...}`
* - `font`: set the font used. Used by `\mathbb`, `\mathbb`, etc...
* - `sizing`: set the size of the font used
* - `color`: set the foreground color
* - `rule`: draw a line, for the `\rule` command
* - `line`: used by `\overline` and `\underline` commands
* - `box`: a border drawn around an expression and change its background color
* - `overlap`: display a symbol _over_ another
* - `overunder`: displays an annotation above or below a symbol
* - `array`: a group, which has children arranged in rows. Used
* by environments such as `matrix`, `cases`, etc...
* - `genfrac`: a generalized fraction: a numerator and denominator, separated
* by an optional line, and surrounded by optional fences
* - `surd`: a surd, aka root
* - `leftright`: used by the `\left` and `\right` commands
* - `delim`: some delimiter
* - `sizeddelim`: a delimiter that can grow
*
* The following types are used by the editor:
* - `command` indicate a command being entered. The text is displayed in
* blue in the editor.
* - `error`: indicate a command that is unknown, for example `\xyzy`. The text
* is displayed with a wavy red underline in the editor.
* - `placeholder`: indicate a temporary item. Placeholders are displayed
* as a dashed square in the editor.
* - `first`: a special, empty, atom put as the first atom in math lists in
* order to be able to position the caret before the first element. Aside from
* the caret, they display nothing.
*
* @property {string} fontFamily
* @property {string|MathAtom[]} body
* @property {MathAtom[]} superscript
* @property {MathAtom[]} subscript
* @property {MathAtom[]} numer
* @property {MathAtom[]} denom
* @property {boolean} captureSelection if true, this atom does not let its
* children be selected. Used by the `\enclose` annotations, for example.
* @property {boolean} skipBoundary if true, when the caret reaches the
* first position in this element's body, it automatically moves to the
* outside of the element. Conversely, when the caret reaches the position
* right after this element, it automatically moves to the last position
* inside this element.
* @class MathAtom
* @global
* @private
*/
function MathAtom(mode, type, body, fontFamily, extras) {
this.mode = mode;
this.type = type;
this.body = body;
this.fontFamily = fontFamily;
// Append all the properties in extras to this
// This can override the type, value, etc...
if (extras) {
for (const p in extras) {
if (extras.hasOwnProperty(p)) {
this[p] = extras[p];
}
}
}
// Determine which font family to use.
// Note that the type, fontFamily and body could have been overridden
// by 'extras', so don't check against the parameter ('type') but
// the value in the object ('this.type').
if (this.type !== 'textord' && this.fontFamily === 'main' &&
typeof this.body === 'string' && this.body.length === 1) {
if (AUTO_ITALIC_REGEX.test(this.body)) {
// Auto italicize alphabetic and lowercase greek symbols
// in math mode (European style, American style would not
// italicize greek letters, but it's TeX's default behavior)
this.fontFamily = 'mathit';
}
}
if (this.type === 'textord' && this.fontFamily === 'main') {
this.fontFamily = 'mathrm';
}
// if (!italic && type === 'textord' && (mode === 'displaymath' || mode === 'inlinemath')) {
// fontFamily = 'mathit'; // This is important to get \prime to render correctly
// }
if (this.fontFamily === 'main') {
this.fontFamily = 'mathrm';
} else if (fontFamily === 'ams') {
this.fontFamily = 'amsrm';
}
}
MathAtom.prototype.getInitialBaseElement = function () {
// if (this.type === 'leftright') {
// return this;
// }
let result = this;
if (Array.isArray(this.body) && this.body.length > 0) {
for (let i = 0; i < this.body.length; i++) {
if (this.body[i].type !== 'first') {
result = this.body[i].getInitialBaseElement();
break;
}
}
}
return result;
}
MathAtom.prototype.getFinalBaseElement = function () {
if (Array.isArray(this.body) && this.body.length > 0) {
return this.body[this.body.length - 1].getFinalBaseElement();
}
return this;
}
MathAtom.prototype.isCharacterBox = function () {
const base = this.getInitialBaseElement();
return base.type === 'mord' ||
base.type === 'minner' || base.type === 'mbin' ||
base.type === 'mrel' || base.type === 'mpunct' ||
base.type === 'mopen' || base.type === 'mclose' ||
base.type === 'textord';
}
MathAtom.prototype.forEach = function (cb) {
cb(this);
if (Array.isArray(this.body)) {
for (const atom of this.body) if (atom) atom.forEach(cb);
} else if (this.body && typeof this.body === 'object') {
cb(this.body);
}
if (this.superscript) {
for (const atom of this.superscript) if (atom) atom.forEach(cb);
}
if (this.subscript) {
for (const atom of this.subscript) if (atom) atom.forEach(cb);
}
if (this.overscript) {
for (const atom of this.overscript) if (atom) atom.forEach(cb);
}
if (this.underscript) {
for (const atom of this.underscript) if (atom) atom.forEach(cb);
}
if (this.numer) {
for (const atom of this.numer) if (atom) atom.forEach(cb);
}
if (this.denom) {
for (const atom of this.denom) if (atom) atom.forEach(cb);
}
if (this.index) {
for (const atom of this.index) if (atom) atom.forEach(cb);
}
if (this.array) {
for (const row of this.array) {
for (const cell of row) {
for (const atom of cell) atom.forEach(cb);
}
}
}
}
/**
* Iterate over all the child atoms of this atom, this included,
* and return an array of all the atoms for which the predicate callback
* is true.
*
* @return {MathAtom[]}
* @method MathAtom#filter
*/
MathAtom.prototype.filter = function (cb) {
let result = [];
if (cb(this)) result.push(this);
for (const relation of ['body', 'superscript', 'subscript',
'overscript', 'underscript',
'numer', 'denom', 'index']) {
if (Array.isArray(this[relation])) {
for (const atom of this[relation]) {
if (atom) result = result.concat(atom.filter(cb));
}
}
}
if (Array.isArray(this.array)) {
for (const row of this.array) {
for (const cell of row) {
if (cell) result = result.concat(cell.filter(cb));
}
}
}
return result;
}
MathAtom.prototype.decomposeGroup = function(context) {
// The scope of the context is this group, so make a copy of it
// so that any changes to it will be discarded when finished
// with this group.
// Note that the mathstyle property is optional and could be undefined
// If that's the case, withMathstyle() returns a clone of the
// context with the same mathstyle.
const localContext = context.withMathstyle(this.mathstyle);
return makeOrd(decompose(localContext, this.body));
}
/**
* Used in `decomposeArray` to create a column separator span.
*
* @param {number} width
* @memberof module:mathAtom
* @private
*/
function makeColGap(width) {
const separator = makeSpan('\u200b', 'arraycolsep');
separator.setWidth(width, 'em');
return separator;
}
/**
* Used in decomposeArray to create a column of repeating elements.
* @memberof module:mathAtom
* @private
*/
function makeColOfRepeatingElements(context, body, offset, elem) {
const col = [];
for (const row of body) {
const cell = makeSpan(decompose(context, elem));
cell.depth = row.depth;
cell.height = row.height;
col.push(cell);
col.push(row.pos - offset);
}
return makeVlist(context, col, 'individualShift');
}
MathAtom.prototype.decomposeArray = function(context) {
// See http://tug.ctan.org/macros/latex/base/ltfsstrc.dtx
// and http://tug.ctan.org/macros/latex/base/lttab.dtx
let colFormat = this.colFormat;
if (colFormat && colFormat.length === 0) {
colFormat = [{align:'l'}];
}
if (!colFormat) {
colFormat = [{align:'l'}, {align:'l'}, {align:'l'},
{align:'l'}, {align:'l'}, {align:'l'}, {align:'l'}, {align:'l'},
{align:'l'}, {align:'l'}]
}
// Fold the array so that there are no more columns of content than
// there are columns prescribed by the column format.
const array = [];
let colMax = 0; // Maximum number of columns of content
for (const colSpec of colFormat) {
if (colSpec.align) colMax++;
}
for (const row of this.array) {
let colIndex = 0;
while (colIndex < row.length) {
const newRow = [];
const lastCol = Math.min(row.length, colIndex + colMax);
while (colIndex < lastCol) {
newRow.push(row[colIndex++]);
}
array.push(newRow);
}
}
// If the last row is empty, ignore it.
if (array[array.length - 1].length === 1 &&
array[array.length - 1][0].length === 0) {
array.pop();
}
const mathstyle = Mathstyle.toMathstyle(this.mathstyle) ||
context.mathstyle;
// Row spacing
// Default \arraystretch from lttab.dtx
const arraystretch = this.arraystretch || 1;
const arrayskip = arraystretch * FONTMETRICS.baselineskip;
const arstrutHeight = 0.7 * arrayskip;
const arstrutDepth = 0.3 * arrayskip; // \@arstrutbox in lttab.dtx
let totalHeight = 0;
let nc = 0;
const body = [];
const nr = array.length;
for (let r = 0; r < nr; ++r) {
const inrow = array[r];
nc = Math.max(nc, inrow.length);
let height = arstrutHeight; // \@array adds an \@arstrut
let depth = arstrutDepth; // to each row (via the template)
const outrow = [];
for (let c = 0; c < inrow.length; ++c) {
const localContext = context.withMathstyle(this.mathstyle || 'auto');
const cell = decompose(localContext, inrow[c]) || [];
const elt = [makeOrd(null)].concat(cell);
depth = Math.max(depth, Span.depth(elt));
height = Math.max(height, Span.height(elt));
outrow.push(elt);
}
let jot = r === nr - 1 ? 0 : (this.jot || 0);
if (this.rowGaps && this.rowGaps[r]) {
jot = this.rowGaps[r];
if (jot > 0) { // \@argarraycr
jot += arstrutDepth;
if (depth < jot) {
depth = jot; // \@xargarraycr
}
jot = 0;
}
}
outrow.height = height;
outrow.depth = depth;
totalHeight += height;
outrow.pos = totalHeight;
totalHeight += depth + jot; // \@yargarraycr
body.push(outrow);
}
const offset = totalHeight / 2 + mathstyle.metrics.axisHeight;
const contentCols = [];
for (let colIndex = 0; colIndex < nc; colIndex++) {
const col = [];
for (const row of body) {
const elem = row[colIndex];
if (!elem) {
continue;
}
elem.depth = row.depth;
elem.height = row.height;
col.push(elem);
col.push(row.pos - offset);
}
if (col.length > 0) {
contentCols.push(makeVlist(context, col, 'individualShift'));
}
}
// Iterate over each column description.
// Each `colDesc` will indicate whether to insert a gap, a rule or
// a column from 'contentCols'
const cols = [];
let prevColContent = false;
let prevColRule = false;
let currentContentCol = 0
let firstColumn = !this.lFence;
for (const colDesc of colFormat) {
if (colDesc.align && currentContentCol >= contentCols.length) {
break;
} else if (colDesc.align && currentContentCol < contentCols.length) {
// If an alignment is specified, insert a column of content
if (prevColContent) {
// If no gap was provided, insert a default gap between
// consecutive columns of content
cols.push(makeColGap(2 * FONTMETRICS.arraycolsep));
} else if (prevColRule || firstColumn) {
// If the previous column was a rule or this is the first column
// add a smaller gap
cols.push(makeColGap(FONTMETRICS.arraycolsep));
}
cols.push(makeSpan(contentCols[currentContentCol],
'col-align-' + colDesc.align));
currentContentCol++;
prevColContent = true;
prevColRule = false;
firstColumn = false;
} else if (typeof colDesc.gap !== 'undefined') {
// Something to insert in between columns of content
if (typeof colDesc.gap === 'number') {
// It's a number, indicating how much space, in em,
// to leave in between columns
cols.push(makeColGap(colDesc.gap));
} else {
// It's a mathlist
// Create a column made up of the mathlist
// as many times as there are rows.
cols.push(makeColOfRepeatingElements(context, body, offset, colDesc.gap));
}
prevColContent = false;
prevColRule = false;
firstColumn = false;
} else if (colDesc.rule) {
// It's a rule.
const separator = makeSpan(null, 'vertical-separator');
separator.setStyle('height', totalHeight, 'em');
// result.setTop((1 - context.mathstyle.sizeMultiplier) *
// context.mathstyle.metrics.axisHeight);
separator.setStyle('margin-top',
3 * context.mathstyle.metrics.axisHeight - offset, 'em');
separator.setStyle('vertical-align', 'top');
// separator.setStyle('display', 'inline-block');
let gap = 0;
if (prevColRule) {
gap = FONTMETRICS.doubleRuleSep - FONTMETRICS.arrayrulewidth;
} else if (prevColContent) {
gap = FONTMETRICS.arraycolsep - FONTMETRICS.arrayrulewidth;
}
separator.setLeft(gap, 'em');
cols.push(separator);
prevColContent = false;
prevColRule = true;
firstColumn = false;
}
}
if (prevColContent && !this.rFence) {
// If the last column was content, add a small gap
cols.push(makeColGap(FONTMETRICS.arraycolsep));
}
if ((!this.lFence || this.lFence === '.') &&
(!this.rFence || this.rFence === '.')) {
// There are no delimiters around the array, just return what
// we've built so far.
return makeOrd(cols, 'mtable');
}
// There is at least one delimiter. Wrap the core of the array with
// appropriate left and right delimiters
// const inner = makeSpan(makeSpan(cols, 'mtable'), 'mord');
const inner = makeSpan(cols, 'mtable');
const innerHeight = Span.height(inner);
const innerDepth = Span.depth(inner);
return makeOrd([
this.bind(context, Delimiters.makeLeftRightDelim(
'mopen', this.lFence, innerHeight, innerDepth, context)),
inner,
this.bind(context, Delimiters.makeLeftRightDelim(
'mclose', this.rFence, innerHeight, innerDepth, context))
]);
}
/**
* GENFRAC -- Generalized fraction
*
* Decompose fractions, binomials, and in general anything made
* of two expressions on top of each other, optionally separated by a bar,
* and optionally surrounded by fences (parentheses, brackets, etc...)
*
* Depending on the type of fraction the mathstyle is either
* display math or inline math (which is indicated by 'textstyle'). This value can
* also be set to 'auto', which indicates it should use the current mathstyle
*
* @method MathAtom#de