diff --git a/.gitignore b/.gitignore index d1c1dbe..3c3629e 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1 @@ node_modules -bundle.js diff --git a/bundle.js b/bundle.js new file mode 100644 index 0000000..cc23752 --- /dev/null +++ b/bundle.js @@ -0,0 +1,18137 @@ +(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o 0 ? state.src.charCodeAt(start - 1) : 0x20; + + if (pos >= max) { + can_open = false; + } + + pos += delimLength; + + count = pos - start; + + // treat end of the line as a whitespace + nextChar = pos < max ? state.src.charCodeAt(pos) : 0x20; + + isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)); + isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)); + + isLastWhiteSpace = isWhiteSpace(lastChar); + isNextWhiteSpace = isWhiteSpace(nextChar); + + if (isNextWhiteSpace) { + left_flanking = false; + } else if (isNextPunctChar) { + if (!(isLastWhiteSpace || isLastPunctChar)) { + left_flanking = false; + } + } + + if (isLastWhiteSpace) { + right_flanking = false; + } else if (isLastPunctChar) { + if (!(isNextWhiteSpace || isNextPunctChar)) { + right_flanking = false; + } + } + + can_open = left_flanking; + can_close = right_flanking; + + return { + can_open: can_open, + can_close: can_close, + delims: count + }; +} + + +function makeMath_inline(open, close) { + return function math_inline(state, silent) { + var startCount, + found, + res, + token, + closeDelim, + max = state.posMax, + start = state.pos, + openDelim = state.src.slice(start, start + open.length); + + if (openDelim !== open) { return false; } + if (silent) { return false; } // Don’t run any pairs in validation mode + + res = scanDelims(state, start, openDelim.length); + startCount = res.delims; + + if (!res.can_open) { + state.pos += startCount; + // Earlier we checked !silent, but this implementation does not need it + state.pending += state.src.slice(start, state.pos); + return true; + } + + state.pos = start + open.length; + + while (state.pos < max) { + closeDelim = state.src.slice(state.pos, state.pos + close.length); + if (closeDelim === close) { + res = scanDelims(state, state.pos, close.length); + if (res.can_close) { + found = true; + break; + } + } + + state.md.inline.skipToken(state); + } + + if (!found) { + // Parser failed to find ending tag, so it is not a valid math + state.pos = start; + return false; + } + + // Found! + state.posMax = state.pos; + state.pos = start + close.length; + + // Earlier we checked !silent, but this implementation does not need it + token = state.push('math_inline', 'math', 0); + token.content = state.src.slice(state.pos, state.posMax); + token.markup = open; + + state.pos = state.posMax + close.length; + state.posMax = max; + + return true; + }; +} + +function makeMath_block(open, close) { + return function math_block(state, startLine, endLine, silent) { + var openDelim, len, params, nextLine, token, firstLine, lastLine, lastLinePos, + haveEndMarker = false, + pos = state.bMarks[startLine] + state.tShift[startLine], + max = state.eMarks[startLine]; + + if (pos + open.length > max) { return false; } + + openDelim = state.src.slice(pos, pos + open.length); + + if (openDelim !== open) { return false; } + + pos += open.length; + firstLine = state.src.slice(pos, max); + + // Since start is found, we can report success here in validation mode + if (silent) { return true; } + + if (firstLine.trim().slice(-close.length) === close) { + // Single line expression + firstLine = firstLine.trim().slice(0, -close.length); + haveEndMarker = true; + } + + // search end of block + nextLine = startLine; + + for (;;) { + if (haveEndMarker) { break; } + + nextLine++; + + if (nextLine >= endLine) { + // unclosed block should be autoclosed by end of document. + // also block seems to be autoclosed by end of parent + break; + } + + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + + if (pos < max && state.tShift[nextLine] < state.blkIndent) { + // non-empty line with negative indent should stop the list: + break; + } + + if (state.src.slice(pos, max).trim().slice(-close.length) !== close) { + continue; + } + + if (state.tShift[nextLine] - state.blkIndent >= 4) { + // closing block math should be indented less then 4 spaces + continue; + } + + lastLinePos = state.src.slice(0, max).lastIndexOf(close); + lastLine = state.src.slice(pos, lastLinePos); + + pos += lastLine.length + close.length; + + // make sure tail has spaces only + pos = state.skipSpaces(pos); + + if (pos < max) { continue; } + + // found! + haveEndMarker = true; + } + + // If math block has heading spaces, they should be removed from its inner block + len = state.tShift[startLine]; + + state.line = nextLine + (haveEndMarker ? 1 : 0); + + token = state.push('math_block', 'math', 0); + token.block = true; + token.content = (firstLine && firstLine.trim() ? firstLine + '\n' : '') + + state.getLines(startLine + 1, nextLine, len, true) + + (lastLine && lastLine.trim() ? lastLine : ''); + token.info = params; + token.map = [ startLine, state.line ]; + token.markup = open; + + return true; + }; +} + + +module.exports = function math_plugin(md) { + // Default options + + var inlineOpen = '$', + inlineClose = '$', + blockOpen = '$$', + blockClose = '$$'; + // set KaTeX as the renderer for markdown-it-simplemath + var katexInline = function(latex){ + return katex.renderToString(latex, {"displayMode" : false}); + }; + + var inlineRenderer = function(tokens, idx){ + return katexInline(tokens[idx].content); + }; + + var katexBlock = function(latex){ + return katex.renderToString(latex, {"displayMode" : true}); + } + + var blockRenderer = function(tokens, idx){ + return katexBlock(tokens[idx].content) + '\n'; + } + + var math_inline = makeMath_inline(inlineOpen, inlineClose); + var math_block = makeMath_block(blockOpen, blockClose); + + md.inline.ruler.before('escape', 'math_inline', math_inline); + md.block.ruler.after('blockquote', 'math_block', math_block, { + alt: [ 'paragraph', 'reference', 'blockquote', 'list' ] + }); + md.renderer.rules.math_inline = inlineRenderer; + md.renderer.rules.math_block = blockRenderer; +}; + +},{"katex":4}],3:[function(require,module,exports){ +module.exports={"Aacute":"\u00C1","aacute":"\u00E1","Abreve":"\u0102","abreve":"\u0103","ac":"\u223E","acd":"\u223F","acE":"\u223E\u0333","Acirc":"\u00C2","acirc":"\u00E2","acute":"\u00B4","Acy":"\u0410","acy":"\u0430","AElig":"\u00C6","aelig":"\u00E6","af":"\u2061","Afr":"\uD835\uDD04","afr":"\uD835\uDD1E","Agrave":"\u00C0","agrave":"\u00E0","alefsym":"\u2135","aleph":"\u2135","Alpha":"\u0391","alpha":"\u03B1","Amacr":"\u0100","amacr":"\u0101","amalg":"\u2A3F","amp":"&","AMP":"&","andand":"\u2A55","And":"\u2A53","and":"\u2227","andd":"\u2A5C","andslope":"\u2A58","andv":"\u2A5A","ang":"\u2220","ange":"\u29A4","angle":"\u2220","angmsdaa":"\u29A8","angmsdab":"\u29A9","angmsdac":"\u29AA","angmsdad":"\u29AB","angmsdae":"\u29AC","angmsdaf":"\u29AD","angmsdag":"\u29AE","angmsdah":"\u29AF","angmsd":"\u2221","angrt":"\u221F","angrtvb":"\u22BE","angrtvbd":"\u299D","angsph":"\u2222","angst":"\u00C5","angzarr":"\u237C","Aogon":"\u0104","aogon":"\u0105","Aopf":"\uD835\uDD38","aopf":"\uD835\uDD52","apacir":"\u2A6F","ap":"\u2248","apE":"\u2A70","ape":"\u224A","apid":"\u224B","apos":"'","ApplyFunction":"\u2061","approx":"\u2248","approxeq":"\u224A","Aring":"\u00C5","aring":"\u00E5","Ascr":"\uD835\uDC9C","ascr":"\uD835\uDCB6","Assign":"\u2254","ast":"*","asymp":"\u2248","asympeq":"\u224D","Atilde":"\u00C3","atilde":"\u00E3","Auml":"\u00C4","auml":"\u00E4","awconint":"\u2233","awint":"\u2A11","backcong":"\u224C","backepsilon":"\u03F6","backprime":"\u2035","backsim":"\u223D","backsimeq":"\u22CD","Backslash":"\u2216","Barv":"\u2AE7","barvee":"\u22BD","barwed":"\u2305","Barwed":"\u2306","barwedge":"\u2305","bbrk":"\u23B5","bbrktbrk":"\u23B6","bcong":"\u224C","Bcy":"\u0411","bcy":"\u0431","bdquo":"\u201E","becaus":"\u2235","because":"\u2235","Because":"\u2235","bemptyv":"\u29B0","bepsi":"\u03F6","bernou":"\u212C","Bernoullis":"\u212C","Beta":"\u0392","beta":"\u03B2","beth":"\u2136","between":"\u226C","Bfr":"\uD835\uDD05","bfr":"\uD835\uDD1F","bigcap":"\u22C2","bigcirc":"\u25EF","bigcup":"\u22C3","bigodot":"\u2A00","bigoplus":"\u2A01","bigotimes":"\u2A02","bigsqcup":"\u2A06","bigstar":"\u2605","bigtriangledown":"\u25BD","bigtriangleup":"\u25B3","biguplus":"\u2A04","bigvee":"\u22C1","bigwedge":"\u22C0","bkarow":"\u290D","blacklozenge":"\u29EB","blacksquare":"\u25AA","blacktriangle":"\u25B4","blacktriangledown":"\u25BE","blacktriangleleft":"\u25C2","blacktriangleright":"\u25B8","blank":"\u2423","blk12":"\u2592","blk14":"\u2591","blk34":"\u2593","block":"\u2588","bne":"=\u20E5","bnequiv":"\u2261\u20E5","bNot":"\u2AED","bnot":"\u2310","Bopf":"\uD835\uDD39","bopf":"\uD835\uDD53","bot":"\u22A5","bottom":"\u22A5","bowtie":"\u22C8","boxbox":"\u29C9","boxdl":"\u2510","boxdL":"\u2555","boxDl":"\u2556","boxDL":"\u2557","boxdr":"\u250C","boxdR":"\u2552","boxDr":"\u2553","boxDR":"\u2554","boxh":"\u2500","boxH":"\u2550","boxhd":"\u252C","boxHd":"\u2564","boxhD":"\u2565","boxHD":"\u2566","boxhu":"\u2534","boxHu":"\u2567","boxhU":"\u2568","boxHU":"\u2569","boxminus":"\u229F","boxplus":"\u229E","boxtimes":"\u22A0","boxul":"\u2518","boxuL":"\u255B","boxUl":"\u255C","boxUL":"\u255D","boxur":"\u2514","boxuR":"\u2558","boxUr":"\u2559","boxUR":"\u255A","boxv":"\u2502","boxV":"\u2551","boxvh":"\u253C","boxvH":"\u256A","boxVh":"\u256B","boxVH":"\u256C","boxvl":"\u2524","boxvL":"\u2561","boxVl":"\u2562","boxVL":"\u2563","boxvr":"\u251C","boxvR":"\u255E","boxVr":"\u255F","boxVR":"\u2560","bprime":"\u2035","breve":"\u02D8","Breve":"\u02D8","brvbar":"\u00A6","bscr":"\uD835\uDCB7","Bscr":"\u212C","bsemi":"\u204F","bsim":"\u223D","bsime":"\u22CD","bsolb":"\u29C5","bsol":"\\","bsolhsub":"\u27C8","bull":"\u2022","bullet":"\u2022","bump":"\u224E","bumpE":"\u2AAE","bumpe":"\u224F","Bumpeq":"\u224E","bumpeq":"\u224F","Cacute":"\u0106","cacute":"\u0107","capand":"\u2A44","capbrcup":"\u2A49","capcap":"\u2A4B","cap":"\u2229","Cap":"\u22D2","capcup":"\u2A47","capdot":"\u2A40","CapitalDifferentialD":"\u2145","caps":"\u2229\uFE00","caret":"\u2041","caron":"\u02C7","Cayleys":"\u212D","ccaps":"\u2A4D","Ccaron":"\u010C","ccaron":"\u010D","Ccedil":"\u00C7","ccedil":"\u00E7","Ccirc":"\u0108","ccirc":"\u0109","Cconint":"\u2230","ccups":"\u2A4C","ccupssm":"\u2A50","Cdot":"\u010A","cdot":"\u010B","cedil":"\u00B8","Cedilla":"\u00B8","cemptyv":"\u29B2","cent":"\u00A2","centerdot":"\u00B7","CenterDot":"\u00B7","cfr":"\uD835\uDD20","Cfr":"\u212D","CHcy":"\u0427","chcy":"\u0447","check":"\u2713","checkmark":"\u2713","Chi":"\u03A7","chi":"\u03C7","circ":"\u02C6","circeq":"\u2257","circlearrowleft":"\u21BA","circlearrowright":"\u21BB","circledast":"\u229B","circledcirc":"\u229A","circleddash":"\u229D","CircleDot":"\u2299","circledR":"\u00AE","circledS":"\u24C8","CircleMinus":"\u2296","CirclePlus":"\u2295","CircleTimes":"\u2297","cir":"\u25CB","cirE":"\u29C3","cire":"\u2257","cirfnint":"\u2A10","cirmid":"\u2AEF","cirscir":"\u29C2","ClockwiseContourIntegral":"\u2232","CloseCurlyDoubleQuote":"\u201D","CloseCurlyQuote":"\u2019","clubs":"\u2663","clubsuit":"\u2663","colon":":","Colon":"\u2237","Colone":"\u2A74","colone":"\u2254","coloneq":"\u2254","comma":",","commat":"@","comp":"\u2201","compfn":"\u2218","complement":"\u2201","complexes":"\u2102","cong":"\u2245","congdot":"\u2A6D","Congruent":"\u2261","conint":"\u222E","Conint":"\u222F","ContourIntegral":"\u222E","copf":"\uD835\uDD54","Copf":"\u2102","coprod":"\u2210","Coproduct":"\u2210","copy":"\u00A9","COPY":"\u00A9","copysr":"\u2117","CounterClockwiseContourIntegral":"\u2233","crarr":"\u21B5","cross":"\u2717","Cross":"\u2A2F","Cscr":"\uD835\uDC9E","cscr":"\uD835\uDCB8","csub":"\u2ACF","csube":"\u2AD1","csup":"\u2AD0","csupe":"\u2AD2","ctdot":"\u22EF","cudarrl":"\u2938","cudarrr":"\u2935","cuepr":"\u22DE","cuesc":"\u22DF","cularr":"\u21B6","cularrp":"\u293D","cupbrcap":"\u2A48","cupcap":"\u2A46","CupCap":"\u224D","cup":"\u222A","Cup":"\u22D3","cupcup":"\u2A4A","cupdot":"\u228D","cupor":"\u2A45","cups":"\u222A\uFE00","curarr":"\u21B7","curarrm":"\u293C","curlyeqprec":"\u22DE","curlyeqsucc":"\u22DF","curlyvee":"\u22CE","curlywedge":"\u22CF","curren":"\u00A4","curvearrowleft":"\u21B6","curvearrowright":"\u21B7","cuvee":"\u22CE","cuwed":"\u22CF","cwconint":"\u2232","cwint":"\u2231","cylcty":"\u232D","dagger":"\u2020","Dagger":"\u2021","daleth":"\u2138","darr":"\u2193","Darr":"\u21A1","dArr":"\u21D3","dash":"\u2010","Dashv":"\u2AE4","dashv":"\u22A3","dbkarow":"\u290F","dblac":"\u02DD","Dcaron":"\u010E","dcaron":"\u010F","Dcy":"\u0414","dcy":"\u0434","ddagger":"\u2021","ddarr":"\u21CA","DD":"\u2145","dd":"\u2146","DDotrahd":"\u2911","ddotseq":"\u2A77","deg":"\u00B0","Del":"\u2207","Delta":"\u0394","delta":"\u03B4","demptyv":"\u29B1","dfisht":"\u297F","Dfr":"\uD835\uDD07","dfr":"\uD835\uDD21","dHar":"\u2965","dharl":"\u21C3","dharr":"\u21C2","DiacriticalAcute":"\u00B4","DiacriticalDot":"\u02D9","DiacriticalDoubleAcute":"\u02DD","DiacriticalGrave":"`","DiacriticalTilde":"\u02DC","diam":"\u22C4","diamond":"\u22C4","Diamond":"\u22C4","diamondsuit":"\u2666","diams":"\u2666","die":"\u00A8","DifferentialD":"\u2146","digamma":"\u03DD","disin":"\u22F2","div":"\u00F7","divide":"\u00F7","divideontimes":"\u22C7","divonx":"\u22C7","DJcy":"\u0402","djcy":"\u0452","dlcorn":"\u231E","dlcrop":"\u230D","dollar":"$","Dopf":"\uD835\uDD3B","dopf":"\uD835\uDD55","Dot":"\u00A8","dot":"\u02D9","DotDot":"\u20DC","doteq":"\u2250","doteqdot":"\u2251","DotEqual":"\u2250","dotminus":"\u2238","dotplus":"\u2214","dotsquare":"\u22A1","doublebarwedge":"\u2306","DoubleContourIntegral":"\u222F","DoubleDot":"\u00A8","DoubleDownArrow":"\u21D3","DoubleLeftArrow":"\u21D0","DoubleLeftRightArrow":"\u21D4","DoubleLeftTee":"\u2AE4","DoubleLongLeftArrow":"\u27F8","DoubleLongLeftRightArrow":"\u27FA","DoubleLongRightArrow":"\u27F9","DoubleRightArrow":"\u21D2","DoubleRightTee":"\u22A8","DoubleUpArrow":"\u21D1","DoubleUpDownArrow":"\u21D5","DoubleVerticalBar":"\u2225","DownArrowBar":"\u2913","downarrow":"\u2193","DownArrow":"\u2193","Downarrow":"\u21D3","DownArrowUpArrow":"\u21F5","DownBreve":"\u0311","downdownarrows":"\u21CA","downharpoonleft":"\u21C3","downharpoonright":"\u21C2","DownLeftRightVector":"\u2950","DownLeftTeeVector":"\u295E","DownLeftVectorBar":"\u2956","DownLeftVector":"\u21BD","DownRightTeeVector":"\u295F","DownRightVectorBar":"\u2957","DownRightVector":"\u21C1","DownTeeArrow":"\u21A7","DownTee":"\u22A4","drbkarow":"\u2910","drcorn":"\u231F","drcrop":"\u230C","Dscr":"\uD835\uDC9F","dscr":"\uD835\uDCB9","DScy":"\u0405","dscy":"\u0455","dsol":"\u29F6","Dstrok":"\u0110","dstrok":"\u0111","dtdot":"\u22F1","dtri":"\u25BF","dtrif":"\u25BE","duarr":"\u21F5","duhar":"\u296F","dwangle":"\u29A6","DZcy":"\u040F","dzcy":"\u045F","dzigrarr":"\u27FF","Eacute":"\u00C9","eacute":"\u00E9","easter":"\u2A6E","Ecaron":"\u011A","ecaron":"\u011B","Ecirc":"\u00CA","ecirc":"\u00EA","ecir":"\u2256","ecolon":"\u2255","Ecy":"\u042D","ecy":"\u044D","eDDot":"\u2A77","Edot":"\u0116","edot":"\u0117","eDot":"\u2251","ee":"\u2147","efDot":"\u2252","Efr":"\uD835\uDD08","efr":"\uD835\uDD22","eg":"\u2A9A","Egrave":"\u00C8","egrave":"\u00E8","egs":"\u2A96","egsdot":"\u2A98","el":"\u2A99","Element":"\u2208","elinters":"\u23E7","ell":"\u2113","els":"\u2A95","elsdot":"\u2A97","Emacr":"\u0112","emacr":"\u0113","empty":"\u2205","emptyset":"\u2205","EmptySmallSquare":"\u25FB","emptyv":"\u2205","EmptyVerySmallSquare":"\u25AB","emsp13":"\u2004","emsp14":"\u2005","emsp":"\u2003","ENG":"\u014A","eng":"\u014B","ensp":"\u2002","Eogon":"\u0118","eogon":"\u0119","Eopf":"\uD835\uDD3C","eopf":"\uD835\uDD56","epar":"\u22D5","eparsl":"\u29E3","eplus":"\u2A71","epsi":"\u03B5","Epsilon":"\u0395","epsilon":"\u03B5","epsiv":"\u03F5","eqcirc":"\u2256","eqcolon":"\u2255","eqsim":"\u2242","eqslantgtr":"\u2A96","eqslantless":"\u2A95","Equal":"\u2A75","equals":"=","EqualTilde":"\u2242","equest":"\u225F","Equilibrium":"\u21CC","equiv":"\u2261","equivDD":"\u2A78","eqvparsl":"\u29E5","erarr":"\u2971","erDot":"\u2253","escr":"\u212F","Escr":"\u2130","esdot":"\u2250","Esim":"\u2A73","esim":"\u2242","Eta":"\u0397","eta":"\u03B7","ETH":"\u00D0","eth":"\u00F0","Euml":"\u00CB","euml":"\u00EB","euro":"\u20AC","excl":"!","exist":"\u2203","Exists":"\u2203","expectation":"\u2130","exponentiale":"\u2147","ExponentialE":"\u2147","fallingdotseq":"\u2252","Fcy":"\u0424","fcy":"\u0444","female":"\u2640","ffilig":"\uFB03","fflig":"\uFB00","ffllig":"\uFB04","Ffr":"\uD835\uDD09","ffr":"\uD835\uDD23","filig":"\uFB01","FilledSmallSquare":"\u25FC","FilledVerySmallSquare":"\u25AA","fjlig":"fj","flat":"\u266D","fllig":"\uFB02","fltns":"\u25B1","fnof":"\u0192","Fopf":"\uD835\uDD3D","fopf":"\uD835\uDD57","forall":"\u2200","ForAll":"\u2200","fork":"\u22D4","forkv":"\u2AD9","Fouriertrf":"\u2131","fpartint":"\u2A0D","frac12":"\u00BD","frac13":"\u2153","frac14":"\u00BC","frac15":"\u2155","frac16":"\u2159","frac18":"\u215B","frac23":"\u2154","frac25":"\u2156","frac34":"\u00BE","frac35":"\u2157","frac38":"\u215C","frac45":"\u2158","frac56":"\u215A","frac58":"\u215D","frac78":"\u215E","frasl":"\u2044","frown":"\u2322","fscr":"\uD835\uDCBB","Fscr":"\u2131","gacute":"\u01F5","Gamma":"\u0393","gamma":"\u03B3","Gammad":"\u03DC","gammad":"\u03DD","gap":"\u2A86","Gbreve":"\u011E","gbreve":"\u011F","Gcedil":"\u0122","Gcirc":"\u011C","gcirc":"\u011D","Gcy":"\u0413","gcy":"\u0433","Gdot":"\u0120","gdot":"\u0121","ge":"\u2265","gE":"\u2267","gEl":"\u2A8C","gel":"\u22DB","geq":"\u2265","geqq":"\u2267","geqslant":"\u2A7E","gescc":"\u2AA9","ges":"\u2A7E","gesdot":"\u2A80","gesdoto":"\u2A82","gesdotol":"\u2A84","gesl":"\u22DB\uFE00","gesles":"\u2A94","Gfr":"\uD835\uDD0A","gfr":"\uD835\uDD24","gg":"\u226B","Gg":"\u22D9","ggg":"\u22D9","gimel":"\u2137","GJcy":"\u0403","gjcy":"\u0453","gla":"\u2AA5","gl":"\u2277","glE":"\u2A92","glj":"\u2AA4","gnap":"\u2A8A","gnapprox":"\u2A8A","gne":"\u2A88","gnE":"\u2269","gneq":"\u2A88","gneqq":"\u2269","gnsim":"\u22E7","Gopf":"\uD835\uDD3E","gopf":"\uD835\uDD58","grave":"`","GreaterEqual":"\u2265","GreaterEqualLess":"\u22DB","GreaterFullEqual":"\u2267","GreaterGreater":"\u2AA2","GreaterLess":"\u2277","GreaterSlantEqual":"\u2A7E","GreaterTilde":"\u2273","Gscr":"\uD835\uDCA2","gscr":"\u210A","gsim":"\u2273","gsime":"\u2A8E","gsiml":"\u2A90","gtcc":"\u2AA7","gtcir":"\u2A7A","gt":">","GT":">","Gt":"\u226B","gtdot":"\u22D7","gtlPar":"\u2995","gtquest":"\u2A7C","gtrapprox":"\u2A86","gtrarr":"\u2978","gtrdot":"\u22D7","gtreqless":"\u22DB","gtreqqless":"\u2A8C","gtrless":"\u2277","gtrsim":"\u2273","gvertneqq":"\u2269\uFE00","gvnE":"\u2269\uFE00","Hacek":"\u02C7","hairsp":"\u200A","half":"\u00BD","hamilt":"\u210B","HARDcy":"\u042A","hardcy":"\u044A","harrcir":"\u2948","harr":"\u2194","hArr":"\u21D4","harrw":"\u21AD","Hat":"^","hbar":"\u210F","Hcirc":"\u0124","hcirc":"\u0125","hearts":"\u2665","heartsuit":"\u2665","hellip":"\u2026","hercon":"\u22B9","hfr":"\uD835\uDD25","Hfr":"\u210C","HilbertSpace":"\u210B","hksearow":"\u2925","hkswarow":"\u2926","hoarr":"\u21FF","homtht":"\u223B","hookleftarrow":"\u21A9","hookrightarrow":"\u21AA","hopf":"\uD835\uDD59","Hopf":"\u210D","horbar":"\u2015","HorizontalLine":"\u2500","hscr":"\uD835\uDCBD","Hscr":"\u210B","hslash":"\u210F","Hstrok":"\u0126","hstrok":"\u0127","HumpDownHump":"\u224E","HumpEqual":"\u224F","hybull":"\u2043","hyphen":"\u2010","Iacute":"\u00CD","iacute":"\u00ED","ic":"\u2063","Icirc":"\u00CE","icirc":"\u00EE","Icy":"\u0418","icy":"\u0438","Idot":"\u0130","IEcy":"\u0415","iecy":"\u0435","iexcl":"\u00A1","iff":"\u21D4","ifr":"\uD835\uDD26","Ifr":"\u2111","Igrave":"\u00CC","igrave":"\u00EC","ii":"\u2148","iiiint":"\u2A0C","iiint":"\u222D","iinfin":"\u29DC","iiota":"\u2129","IJlig":"\u0132","ijlig":"\u0133","Imacr":"\u012A","imacr":"\u012B","image":"\u2111","ImaginaryI":"\u2148","imagline":"\u2110","imagpart":"\u2111","imath":"\u0131","Im":"\u2111","imof":"\u22B7","imped":"\u01B5","Implies":"\u21D2","incare":"\u2105","in":"\u2208","infin":"\u221E","infintie":"\u29DD","inodot":"\u0131","intcal":"\u22BA","int":"\u222B","Int":"\u222C","integers":"\u2124","Integral":"\u222B","intercal":"\u22BA","Intersection":"\u22C2","intlarhk":"\u2A17","intprod":"\u2A3C","InvisibleComma":"\u2063","InvisibleTimes":"\u2062","IOcy":"\u0401","iocy":"\u0451","Iogon":"\u012E","iogon":"\u012F","Iopf":"\uD835\uDD40","iopf":"\uD835\uDD5A","Iota":"\u0399","iota":"\u03B9","iprod":"\u2A3C","iquest":"\u00BF","iscr":"\uD835\uDCBE","Iscr":"\u2110","isin":"\u2208","isindot":"\u22F5","isinE":"\u22F9","isins":"\u22F4","isinsv":"\u22F3","isinv":"\u2208","it":"\u2062","Itilde":"\u0128","itilde":"\u0129","Iukcy":"\u0406","iukcy":"\u0456","Iuml":"\u00CF","iuml":"\u00EF","Jcirc":"\u0134","jcirc":"\u0135","Jcy":"\u0419","jcy":"\u0439","Jfr":"\uD835\uDD0D","jfr":"\uD835\uDD27","jmath":"\u0237","Jopf":"\uD835\uDD41","jopf":"\uD835\uDD5B","Jscr":"\uD835\uDCA5","jscr":"\uD835\uDCBF","Jsercy":"\u0408","jsercy":"\u0458","Jukcy":"\u0404","jukcy":"\u0454","Kappa":"\u039A","kappa":"\u03BA","kappav":"\u03F0","Kcedil":"\u0136","kcedil":"\u0137","Kcy":"\u041A","kcy":"\u043A","Kfr":"\uD835\uDD0E","kfr":"\uD835\uDD28","kgreen":"\u0138","KHcy":"\u0425","khcy":"\u0445","KJcy":"\u040C","kjcy":"\u045C","Kopf":"\uD835\uDD42","kopf":"\uD835\uDD5C","Kscr":"\uD835\uDCA6","kscr":"\uD835\uDCC0","lAarr":"\u21DA","Lacute":"\u0139","lacute":"\u013A","laemptyv":"\u29B4","lagran":"\u2112","Lambda":"\u039B","lambda":"\u03BB","lang":"\u27E8","Lang":"\u27EA","langd":"\u2991","langle":"\u27E8","lap":"\u2A85","Laplacetrf":"\u2112","laquo":"\u00AB","larrb":"\u21E4","larrbfs":"\u291F","larr":"\u2190","Larr":"\u219E","lArr":"\u21D0","larrfs":"\u291D","larrhk":"\u21A9","larrlp":"\u21AB","larrpl":"\u2939","larrsim":"\u2973","larrtl":"\u21A2","latail":"\u2919","lAtail":"\u291B","lat":"\u2AAB","late":"\u2AAD","lates":"\u2AAD\uFE00","lbarr":"\u290C","lBarr":"\u290E","lbbrk":"\u2772","lbrace":"{","lbrack":"[","lbrke":"\u298B","lbrksld":"\u298F","lbrkslu":"\u298D","Lcaron":"\u013D","lcaron":"\u013E","Lcedil":"\u013B","lcedil":"\u013C","lceil":"\u2308","lcub":"{","Lcy":"\u041B","lcy":"\u043B","ldca":"\u2936","ldquo":"\u201C","ldquor":"\u201E","ldrdhar":"\u2967","ldrushar":"\u294B","ldsh":"\u21B2","le":"\u2264","lE":"\u2266","LeftAngleBracket":"\u27E8","LeftArrowBar":"\u21E4","leftarrow":"\u2190","LeftArrow":"\u2190","Leftarrow":"\u21D0","LeftArrowRightArrow":"\u21C6","leftarrowtail":"\u21A2","LeftCeiling":"\u2308","LeftDoubleBracket":"\u27E6","LeftDownTeeVector":"\u2961","LeftDownVectorBar":"\u2959","LeftDownVector":"\u21C3","LeftFloor":"\u230A","leftharpoondown":"\u21BD","leftharpoonup":"\u21BC","leftleftarrows":"\u21C7","leftrightarrow":"\u2194","LeftRightArrow":"\u2194","Leftrightarrow":"\u21D4","leftrightarrows":"\u21C6","leftrightharpoons":"\u21CB","leftrightsquigarrow":"\u21AD","LeftRightVector":"\u294E","LeftTeeArrow":"\u21A4","LeftTee":"\u22A3","LeftTeeVector":"\u295A","leftthreetimes":"\u22CB","LeftTriangleBar":"\u29CF","LeftTriangle":"\u22B2","LeftTriangleEqual":"\u22B4","LeftUpDownVector":"\u2951","LeftUpTeeVector":"\u2960","LeftUpVectorBar":"\u2958","LeftUpVector":"\u21BF","LeftVectorBar":"\u2952","LeftVector":"\u21BC","lEg":"\u2A8B","leg":"\u22DA","leq":"\u2264","leqq":"\u2266","leqslant":"\u2A7D","lescc":"\u2AA8","les":"\u2A7D","lesdot":"\u2A7F","lesdoto":"\u2A81","lesdotor":"\u2A83","lesg":"\u22DA\uFE00","lesges":"\u2A93","lessapprox":"\u2A85","lessdot":"\u22D6","lesseqgtr":"\u22DA","lesseqqgtr":"\u2A8B","LessEqualGreater":"\u22DA","LessFullEqual":"\u2266","LessGreater":"\u2276","lessgtr":"\u2276","LessLess":"\u2AA1","lesssim":"\u2272","LessSlantEqual":"\u2A7D","LessTilde":"\u2272","lfisht":"\u297C","lfloor":"\u230A","Lfr":"\uD835\uDD0F","lfr":"\uD835\uDD29","lg":"\u2276","lgE":"\u2A91","lHar":"\u2962","lhard":"\u21BD","lharu":"\u21BC","lharul":"\u296A","lhblk":"\u2584","LJcy":"\u0409","ljcy":"\u0459","llarr":"\u21C7","ll":"\u226A","Ll":"\u22D8","llcorner":"\u231E","Lleftarrow":"\u21DA","llhard":"\u296B","lltri":"\u25FA","Lmidot":"\u013F","lmidot":"\u0140","lmoustache":"\u23B0","lmoust":"\u23B0","lnap":"\u2A89","lnapprox":"\u2A89","lne":"\u2A87","lnE":"\u2268","lneq":"\u2A87","lneqq":"\u2268","lnsim":"\u22E6","loang":"\u27EC","loarr":"\u21FD","lobrk":"\u27E6","longleftarrow":"\u27F5","LongLeftArrow":"\u27F5","Longleftarrow":"\u27F8","longleftrightarrow":"\u27F7","LongLeftRightArrow":"\u27F7","Longleftrightarrow":"\u27FA","longmapsto":"\u27FC","longrightarrow":"\u27F6","LongRightArrow":"\u27F6","Longrightarrow":"\u27F9","looparrowleft":"\u21AB","looparrowright":"\u21AC","lopar":"\u2985","Lopf":"\uD835\uDD43","lopf":"\uD835\uDD5D","loplus":"\u2A2D","lotimes":"\u2A34","lowast":"\u2217","lowbar":"_","LowerLeftArrow":"\u2199","LowerRightArrow":"\u2198","loz":"\u25CA","lozenge":"\u25CA","lozf":"\u29EB","lpar":"(","lparlt":"\u2993","lrarr":"\u21C6","lrcorner":"\u231F","lrhar":"\u21CB","lrhard":"\u296D","lrm":"\u200E","lrtri":"\u22BF","lsaquo":"\u2039","lscr":"\uD835\uDCC1","Lscr":"\u2112","lsh":"\u21B0","Lsh":"\u21B0","lsim":"\u2272","lsime":"\u2A8D","lsimg":"\u2A8F","lsqb":"[","lsquo":"\u2018","lsquor":"\u201A","Lstrok":"\u0141","lstrok":"\u0142","ltcc":"\u2AA6","ltcir":"\u2A79","lt":"<","LT":"<","Lt":"\u226A","ltdot":"\u22D6","lthree":"\u22CB","ltimes":"\u22C9","ltlarr":"\u2976","ltquest":"\u2A7B","ltri":"\u25C3","ltrie":"\u22B4","ltrif":"\u25C2","ltrPar":"\u2996","lurdshar":"\u294A","luruhar":"\u2966","lvertneqq":"\u2268\uFE00","lvnE":"\u2268\uFE00","macr":"\u00AF","male":"\u2642","malt":"\u2720","maltese":"\u2720","Map":"\u2905","map":"\u21A6","mapsto":"\u21A6","mapstodown":"\u21A7","mapstoleft":"\u21A4","mapstoup":"\u21A5","marker":"\u25AE","mcomma":"\u2A29","Mcy":"\u041C","mcy":"\u043C","mdash":"\u2014","mDDot":"\u223A","measuredangle":"\u2221","MediumSpace":"\u205F","Mellintrf":"\u2133","Mfr":"\uD835\uDD10","mfr":"\uD835\uDD2A","mho":"\u2127","micro":"\u00B5","midast":"*","midcir":"\u2AF0","mid":"\u2223","middot":"\u00B7","minusb":"\u229F","minus":"\u2212","minusd":"\u2238","minusdu":"\u2A2A","MinusPlus":"\u2213","mlcp":"\u2ADB","mldr":"\u2026","mnplus":"\u2213","models":"\u22A7","Mopf":"\uD835\uDD44","mopf":"\uD835\uDD5E","mp":"\u2213","mscr":"\uD835\uDCC2","Mscr":"\u2133","mstpos":"\u223E","Mu":"\u039C","mu":"\u03BC","multimap":"\u22B8","mumap":"\u22B8","nabla":"\u2207","Nacute":"\u0143","nacute":"\u0144","nang":"\u2220\u20D2","nap":"\u2249","napE":"\u2A70\u0338","napid":"\u224B\u0338","napos":"\u0149","napprox":"\u2249","natural":"\u266E","naturals":"\u2115","natur":"\u266E","nbsp":"\u00A0","nbump":"\u224E\u0338","nbumpe":"\u224F\u0338","ncap":"\u2A43","Ncaron":"\u0147","ncaron":"\u0148","Ncedil":"\u0145","ncedil":"\u0146","ncong":"\u2247","ncongdot":"\u2A6D\u0338","ncup":"\u2A42","Ncy":"\u041D","ncy":"\u043D","ndash":"\u2013","nearhk":"\u2924","nearr":"\u2197","neArr":"\u21D7","nearrow":"\u2197","ne":"\u2260","nedot":"\u2250\u0338","NegativeMediumSpace":"\u200B","NegativeThickSpace":"\u200B","NegativeThinSpace":"\u200B","NegativeVeryThinSpace":"\u200B","nequiv":"\u2262","nesear":"\u2928","nesim":"\u2242\u0338","NestedGreaterGreater":"\u226B","NestedLessLess":"\u226A","NewLine":"\n","nexist":"\u2204","nexists":"\u2204","Nfr":"\uD835\uDD11","nfr":"\uD835\uDD2B","ngE":"\u2267\u0338","nge":"\u2271","ngeq":"\u2271","ngeqq":"\u2267\u0338","ngeqslant":"\u2A7E\u0338","nges":"\u2A7E\u0338","nGg":"\u22D9\u0338","ngsim":"\u2275","nGt":"\u226B\u20D2","ngt":"\u226F","ngtr":"\u226F","nGtv":"\u226B\u0338","nharr":"\u21AE","nhArr":"\u21CE","nhpar":"\u2AF2","ni":"\u220B","nis":"\u22FC","nisd":"\u22FA","niv":"\u220B","NJcy":"\u040A","njcy":"\u045A","nlarr":"\u219A","nlArr":"\u21CD","nldr":"\u2025","nlE":"\u2266\u0338","nle":"\u2270","nleftarrow":"\u219A","nLeftarrow":"\u21CD","nleftrightarrow":"\u21AE","nLeftrightarrow":"\u21CE","nleq":"\u2270","nleqq":"\u2266\u0338","nleqslant":"\u2A7D\u0338","nles":"\u2A7D\u0338","nless":"\u226E","nLl":"\u22D8\u0338","nlsim":"\u2274","nLt":"\u226A\u20D2","nlt":"\u226E","nltri":"\u22EA","nltrie":"\u22EC","nLtv":"\u226A\u0338","nmid":"\u2224","NoBreak":"\u2060","NonBreakingSpace":"\u00A0","nopf":"\uD835\uDD5F","Nopf":"\u2115","Not":"\u2AEC","not":"\u00AC","NotCongruent":"\u2262","NotCupCap":"\u226D","NotDoubleVerticalBar":"\u2226","NotElement":"\u2209","NotEqual":"\u2260","NotEqualTilde":"\u2242\u0338","NotExists":"\u2204","NotGreater":"\u226F","NotGreaterEqual":"\u2271","NotGreaterFullEqual":"\u2267\u0338","NotGreaterGreater":"\u226B\u0338","NotGreaterLess":"\u2279","NotGreaterSlantEqual":"\u2A7E\u0338","NotGreaterTilde":"\u2275","NotHumpDownHump":"\u224E\u0338","NotHumpEqual":"\u224F\u0338","notin":"\u2209","notindot":"\u22F5\u0338","notinE":"\u22F9\u0338","notinva":"\u2209","notinvb":"\u22F7","notinvc":"\u22F6","NotLeftTriangleBar":"\u29CF\u0338","NotLeftTriangle":"\u22EA","NotLeftTriangleEqual":"\u22EC","NotLess":"\u226E","NotLessEqual":"\u2270","NotLessGreater":"\u2278","NotLessLess":"\u226A\u0338","NotLessSlantEqual":"\u2A7D\u0338","NotLessTilde":"\u2274","NotNestedGreaterGreater":"\u2AA2\u0338","NotNestedLessLess":"\u2AA1\u0338","notni":"\u220C","notniva":"\u220C","notnivb":"\u22FE","notnivc":"\u22FD","NotPrecedes":"\u2280","NotPrecedesEqual":"\u2AAF\u0338","NotPrecedesSlantEqual":"\u22E0","NotReverseElement":"\u220C","NotRightTriangleBar":"\u29D0\u0338","NotRightTriangle":"\u22EB","NotRightTriangleEqual":"\u22ED","NotSquareSubset":"\u228F\u0338","NotSquareSubsetEqual":"\u22E2","NotSquareSuperset":"\u2290\u0338","NotSquareSupersetEqual":"\u22E3","NotSubset":"\u2282\u20D2","NotSubsetEqual":"\u2288","NotSucceeds":"\u2281","NotSucceedsEqual":"\u2AB0\u0338","NotSucceedsSlantEqual":"\u22E1","NotSucceedsTilde":"\u227F\u0338","NotSuperset":"\u2283\u20D2","NotSupersetEqual":"\u2289","NotTilde":"\u2241","NotTildeEqual":"\u2244","NotTildeFullEqual":"\u2247","NotTildeTilde":"\u2249","NotVerticalBar":"\u2224","nparallel":"\u2226","npar":"\u2226","nparsl":"\u2AFD\u20E5","npart":"\u2202\u0338","npolint":"\u2A14","npr":"\u2280","nprcue":"\u22E0","nprec":"\u2280","npreceq":"\u2AAF\u0338","npre":"\u2AAF\u0338","nrarrc":"\u2933\u0338","nrarr":"\u219B","nrArr":"\u21CF","nrarrw":"\u219D\u0338","nrightarrow":"\u219B","nRightarrow":"\u21CF","nrtri":"\u22EB","nrtrie":"\u22ED","nsc":"\u2281","nsccue":"\u22E1","nsce":"\u2AB0\u0338","Nscr":"\uD835\uDCA9","nscr":"\uD835\uDCC3","nshortmid":"\u2224","nshortparallel":"\u2226","nsim":"\u2241","nsime":"\u2244","nsimeq":"\u2244","nsmid":"\u2224","nspar":"\u2226","nsqsube":"\u22E2","nsqsupe":"\u22E3","nsub":"\u2284","nsubE":"\u2AC5\u0338","nsube":"\u2288","nsubset":"\u2282\u20D2","nsubseteq":"\u2288","nsubseteqq":"\u2AC5\u0338","nsucc":"\u2281","nsucceq":"\u2AB0\u0338","nsup":"\u2285","nsupE":"\u2AC6\u0338","nsupe":"\u2289","nsupset":"\u2283\u20D2","nsupseteq":"\u2289","nsupseteqq":"\u2AC6\u0338","ntgl":"\u2279","Ntilde":"\u00D1","ntilde":"\u00F1","ntlg":"\u2278","ntriangleleft":"\u22EA","ntrianglelefteq":"\u22EC","ntriangleright":"\u22EB","ntrianglerighteq":"\u22ED","Nu":"\u039D","nu":"\u03BD","num":"#","numero":"\u2116","numsp":"\u2007","nvap":"\u224D\u20D2","nvdash":"\u22AC","nvDash":"\u22AD","nVdash":"\u22AE","nVDash":"\u22AF","nvge":"\u2265\u20D2","nvgt":">\u20D2","nvHarr":"\u2904","nvinfin":"\u29DE","nvlArr":"\u2902","nvle":"\u2264\u20D2","nvlt":"<\u20D2","nvltrie":"\u22B4\u20D2","nvrArr":"\u2903","nvrtrie":"\u22B5\u20D2","nvsim":"\u223C\u20D2","nwarhk":"\u2923","nwarr":"\u2196","nwArr":"\u21D6","nwarrow":"\u2196","nwnear":"\u2927","Oacute":"\u00D3","oacute":"\u00F3","oast":"\u229B","Ocirc":"\u00D4","ocirc":"\u00F4","ocir":"\u229A","Ocy":"\u041E","ocy":"\u043E","odash":"\u229D","Odblac":"\u0150","odblac":"\u0151","odiv":"\u2A38","odot":"\u2299","odsold":"\u29BC","OElig":"\u0152","oelig":"\u0153","ofcir":"\u29BF","Ofr":"\uD835\uDD12","ofr":"\uD835\uDD2C","ogon":"\u02DB","Ograve":"\u00D2","ograve":"\u00F2","ogt":"\u29C1","ohbar":"\u29B5","ohm":"\u03A9","oint":"\u222E","olarr":"\u21BA","olcir":"\u29BE","olcross":"\u29BB","oline":"\u203E","olt":"\u29C0","Omacr":"\u014C","omacr":"\u014D","Omega":"\u03A9","omega":"\u03C9","Omicron":"\u039F","omicron":"\u03BF","omid":"\u29B6","ominus":"\u2296","Oopf":"\uD835\uDD46","oopf":"\uD835\uDD60","opar":"\u29B7","OpenCurlyDoubleQuote":"\u201C","OpenCurlyQuote":"\u2018","operp":"\u29B9","oplus":"\u2295","orarr":"\u21BB","Or":"\u2A54","or":"\u2228","ord":"\u2A5D","order":"\u2134","orderof":"\u2134","ordf":"\u00AA","ordm":"\u00BA","origof":"\u22B6","oror":"\u2A56","orslope":"\u2A57","orv":"\u2A5B","oS":"\u24C8","Oscr":"\uD835\uDCAA","oscr":"\u2134","Oslash":"\u00D8","oslash":"\u00F8","osol":"\u2298","Otilde":"\u00D5","otilde":"\u00F5","otimesas":"\u2A36","Otimes":"\u2A37","otimes":"\u2297","Ouml":"\u00D6","ouml":"\u00F6","ovbar":"\u233D","OverBar":"\u203E","OverBrace":"\u23DE","OverBracket":"\u23B4","OverParenthesis":"\u23DC","para":"\u00B6","parallel":"\u2225","par":"\u2225","parsim":"\u2AF3","parsl":"\u2AFD","part":"\u2202","PartialD":"\u2202","Pcy":"\u041F","pcy":"\u043F","percnt":"%","period":".","permil":"\u2030","perp":"\u22A5","pertenk":"\u2031","Pfr":"\uD835\uDD13","pfr":"\uD835\uDD2D","Phi":"\u03A6","phi":"\u03C6","phiv":"\u03D5","phmmat":"\u2133","phone":"\u260E","Pi":"\u03A0","pi":"\u03C0","pitchfork":"\u22D4","piv":"\u03D6","planck":"\u210F","planckh":"\u210E","plankv":"\u210F","plusacir":"\u2A23","plusb":"\u229E","pluscir":"\u2A22","plus":"+","plusdo":"\u2214","plusdu":"\u2A25","pluse":"\u2A72","PlusMinus":"\u00B1","plusmn":"\u00B1","plussim":"\u2A26","plustwo":"\u2A27","pm":"\u00B1","Poincareplane":"\u210C","pointint":"\u2A15","popf":"\uD835\uDD61","Popf":"\u2119","pound":"\u00A3","prap":"\u2AB7","Pr":"\u2ABB","pr":"\u227A","prcue":"\u227C","precapprox":"\u2AB7","prec":"\u227A","preccurlyeq":"\u227C","Precedes":"\u227A","PrecedesEqual":"\u2AAF","PrecedesSlantEqual":"\u227C","PrecedesTilde":"\u227E","preceq":"\u2AAF","precnapprox":"\u2AB9","precneqq":"\u2AB5","precnsim":"\u22E8","pre":"\u2AAF","prE":"\u2AB3","precsim":"\u227E","prime":"\u2032","Prime":"\u2033","primes":"\u2119","prnap":"\u2AB9","prnE":"\u2AB5","prnsim":"\u22E8","prod":"\u220F","Product":"\u220F","profalar":"\u232E","profline":"\u2312","profsurf":"\u2313","prop":"\u221D","Proportional":"\u221D","Proportion":"\u2237","propto":"\u221D","prsim":"\u227E","prurel":"\u22B0","Pscr":"\uD835\uDCAB","pscr":"\uD835\uDCC5","Psi":"\u03A8","psi":"\u03C8","puncsp":"\u2008","Qfr":"\uD835\uDD14","qfr":"\uD835\uDD2E","qint":"\u2A0C","qopf":"\uD835\uDD62","Qopf":"\u211A","qprime":"\u2057","Qscr":"\uD835\uDCAC","qscr":"\uD835\uDCC6","quaternions":"\u210D","quatint":"\u2A16","quest":"?","questeq":"\u225F","quot":"\"","QUOT":"\"","rAarr":"\u21DB","race":"\u223D\u0331","Racute":"\u0154","racute":"\u0155","radic":"\u221A","raemptyv":"\u29B3","rang":"\u27E9","Rang":"\u27EB","rangd":"\u2992","range":"\u29A5","rangle":"\u27E9","raquo":"\u00BB","rarrap":"\u2975","rarrb":"\u21E5","rarrbfs":"\u2920","rarrc":"\u2933","rarr":"\u2192","Rarr":"\u21A0","rArr":"\u21D2","rarrfs":"\u291E","rarrhk":"\u21AA","rarrlp":"\u21AC","rarrpl":"\u2945","rarrsim":"\u2974","Rarrtl":"\u2916","rarrtl":"\u21A3","rarrw":"\u219D","ratail":"\u291A","rAtail":"\u291C","ratio":"\u2236","rationals":"\u211A","rbarr":"\u290D","rBarr":"\u290F","RBarr":"\u2910","rbbrk":"\u2773","rbrace":"}","rbrack":"]","rbrke":"\u298C","rbrksld":"\u298E","rbrkslu":"\u2990","Rcaron":"\u0158","rcaron":"\u0159","Rcedil":"\u0156","rcedil":"\u0157","rceil":"\u2309","rcub":"}","Rcy":"\u0420","rcy":"\u0440","rdca":"\u2937","rdldhar":"\u2969","rdquo":"\u201D","rdquor":"\u201D","rdsh":"\u21B3","real":"\u211C","realine":"\u211B","realpart":"\u211C","reals":"\u211D","Re":"\u211C","rect":"\u25AD","reg":"\u00AE","REG":"\u00AE","ReverseElement":"\u220B","ReverseEquilibrium":"\u21CB","ReverseUpEquilibrium":"\u296F","rfisht":"\u297D","rfloor":"\u230B","rfr":"\uD835\uDD2F","Rfr":"\u211C","rHar":"\u2964","rhard":"\u21C1","rharu":"\u21C0","rharul":"\u296C","Rho":"\u03A1","rho":"\u03C1","rhov":"\u03F1","RightAngleBracket":"\u27E9","RightArrowBar":"\u21E5","rightarrow":"\u2192","RightArrow":"\u2192","Rightarrow":"\u21D2","RightArrowLeftArrow":"\u21C4","rightarrowtail":"\u21A3","RightCeiling":"\u2309","RightDoubleBracket":"\u27E7","RightDownTeeVector":"\u295D","RightDownVectorBar":"\u2955","RightDownVector":"\u21C2","RightFloor":"\u230B","rightharpoondown":"\u21C1","rightharpoonup":"\u21C0","rightleftarrows":"\u21C4","rightleftharpoons":"\u21CC","rightrightarrows":"\u21C9","rightsquigarrow":"\u219D","RightTeeArrow":"\u21A6","RightTee":"\u22A2","RightTeeVector":"\u295B","rightthreetimes":"\u22CC","RightTriangleBar":"\u29D0","RightTriangle":"\u22B3","RightTriangleEqual":"\u22B5","RightUpDownVector":"\u294F","RightUpTeeVector":"\u295C","RightUpVectorBar":"\u2954","RightUpVector":"\u21BE","RightVectorBar":"\u2953","RightVector":"\u21C0","ring":"\u02DA","risingdotseq":"\u2253","rlarr":"\u21C4","rlhar":"\u21CC","rlm":"\u200F","rmoustache":"\u23B1","rmoust":"\u23B1","rnmid":"\u2AEE","roang":"\u27ED","roarr":"\u21FE","robrk":"\u27E7","ropar":"\u2986","ropf":"\uD835\uDD63","Ropf":"\u211D","roplus":"\u2A2E","rotimes":"\u2A35","RoundImplies":"\u2970","rpar":")","rpargt":"\u2994","rppolint":"\u2A12","rrarr":"\u21C9","Rrightarrow":"\u21DB","rsaquo":"\u203A","rscr":"\uD835\uDCC7","Rscr":"\u211B","rsh":"\u21B1","Rsh":"\u21B1","rsqb":"]","rsquo":"\u2019","rsquor":"\u2019","rthree":"\u22CC","rtimes":"\u22CA","rtri":"\u25B9","rtrie":"\u22B5","rtrif":"\u25B8","rtriltri":"\u29CE","RuleDelayed":"\u29F4","ruluhar":"\u2968","rx":"\u211E","Sacute":"\u015A","sacute":"\u015B","sbquo":"\u201A","scap":"\u2AB8","Scaron":"\u0160","scaron":"\u0161","Sc":"\u2ABC","sc":"\u227B","sccue":"\u227D","sce":"\u2AB0","scE":"\u2AB4","Scedil":"\u015E","scedil":"\u015F","Scirc":"\u015C","scirc":"\u015D","scnap":"\u2ABA","scnE":"\u2AB6","scnsim":"\u22E9","scpolint":"\u2A13","scsim":"\u227F","Scy":"\u0421","scy":"\u0441","sdotb":"\u22A1","sdot":"\u22C5","sdote":"\u2A66","searhk":"\u2925","searr":"\u2198","seArr":"\u21D8","searrow":"\u2198","sect":"\u00A7","semi":";","seswar":"\u2929","setminus":"\u2216","setmn":"\u2216","sext":"\u2736","Sfr":"\uD835\uDD16","sfr":"\uD835\uDD30","sfrown":"\u2322","sharp":"\u266F","SHCHcy":"\u0429","shchcy":"\u0449","SHcy":"\u0428","shcy":"\u0448","ShortDownArrow":"\u2193","ShortLeftArrow":"\u2190","shortmid":"\u2223","shortparallel":"\u2225","ShortRightArrow":"\u2192","ShortUpArrow":"\u2191","shy":"\u00AD","Sigma":"\u03A3","sigma":"\u03C3","sigmaf":"\u03C2","sigmav":"\u03C2","sim":"\u223C","simdot":"\u2A6A","sime":"\u2243","simeq":"\u2243","simg":"\u2A9E","simgE":"\u2AA0","siml":"\u2A9D","simlE":"\u2A9F","simne":"\u2246","simplus":"\u2A24","simrarr":"\u2972","slarr":"\u2190","SmallCircle":"\u2218","smallsetminus":"\u2216","smashp":"\u2A33","smeparsl":"\u29E4","smid":"\u2223","smile":"\u2323","smt":"\u2AAA","smte":"\u2AAC","smtes":"\u2AAC\uFE00","SOFTcy":"\u042C","softcy":"\u044C","solbar":"\u233F","solb":"\u29C4","sol":"/","Sopf":"\uD835\uDD4A","sopf":"\uD835\uDD64","spades":"\u2660","spadesuit":"\u2660","spar":"\u2225","sqcap":"\u2293","sqcaps":"\u2293\uFE00","sqcup":"\u2294","sqcups":"\u2294\uFE00","Sqrt":"\u221A","sqsub":"\u228F","sqsube":"\u2291","sqsubset":"\u228F","sqsubseteq":"\u2291","sqsup":"\u2290","sqsupe":"\u2292","sqsupset":"\u2290","sqsupseteq":"\u2292","square":"\u25A1","Square":"\u25A1","SquareIntersection":"\u2293","SquareSubset":"\u228F","SquareSubsetEqual":"\u2291","SquareSuperset":"\u2290","SquareSupersetEqual":"\u2292","SquareUnion":"\u2294","squarf":"\u25AA","squ":"\u25A1","squf":"\u25AA","srarr":"\u2192","Sscr":"\uD835\uDCAE","sscr":"\uD835\uDCC8","ssetmn":"\u2216","ssmile":"\u2323","sstarf":"\u22C6","Star":"\u22C6","star":"\u2606","starf":"\u2605","straightepsilon":"\u03F5","straightphi":"\u03D5","strns":"\u00AF","sub":"\u2282","Sub":"\u22D0","subdot":"\u2ABD","subE":"\u2AC5","sube":"\u2286","subedot":"\u2AC3","submult":"\u2AC1","subnE":"\u2ACB","subne":"\u228A","subplus":"\u2ABF","subrarr":"\u2979","subset":"\u2282","Subset":"\u22D0","subseteq":"\u2286","subseteqq":"\u2AC5","SubsetEqual":"\u2286","subsetneq":"\u228A","subsetneqq":"\u2ACB","subsim":"\u2AC7","subsub":"\u2AD5","subsup":"\u2AD3","succapprox":"\u2AB8","succ":"\u227B","succcurlyeq":"\u227D","Succeeds":"\u227B","SucceedsEqual":"\u2AB0","SucceedsSlantEqual":"\u227D","SucceedsTilde":"\u227F","succeq":"\u2AB0","succnapprox":"\u2ABA","succneqq":"\u2AB6","succnsim":"\u22E9","succsim":"\u227F","SuchThat":"\u220B","sum":"\u2211","Sum":"\u2211","sung":"\u266A","sup1":"\u00B9","sup2":"\u00B2","sup3":"\u00B3","sup":"\u2283","Sup":"\u22D1","supdot":"\u2ABE","supdsub":"\u2AD8","supE":"\u2AC6","supe":"\u2287","supedot":"\u2AC4","Superset":"\u2283","SupersetEqual":"\u2287","suphsol":"\u27C9","suphsub":"\u2AD7","suplarr":"\u297B","supmult":"\u2AC2","supnE":"\u2ACC","supne":"\u228B","supplus":"\u2AC0","supset":"\u2283","Supset":"\u22D1","supseteq":"\u2287","supseteqq":"\u2AC6","supsetneq":"\u228B","supsetneqq":"\u2ACC","supsim":"\u2AC8","supsub":"\u2AD4","supsup":"\u2AD6","swarhk":"\u2926","swarr":"\u2199","swArr":"\u21D9","swarrow":"\u2199","swnwar":"\u292A","szlig":"\u00DF","Tab":"\t","target":"\u2316","Tau":"\u03A4","tau":"\u03C4","tbrk":"\u23B4","Tcaron":"\u0164","tcaron":"\u0165","Tcedil":"\u0162","tcedil":"\u0163","Tcy":"\u0422","tcy":"\u0442","tdot":"\u20DB","telrec":"\u2315","Tfr":"\uD835\uDD17","tfr":"\uD835\uDD31","there4":"\u2234","therefore":"\u2234","Therefore":"\u2234","Theta":"\u0398","theta":"\u03B8","thetasym":"\u03D1","thetav":"\u03D1","thickapprox":"\u2248","thicksim":"\u223C","ThickSpace":"\u205F\u200A","ThinSpace":"\u2009","thinsp":"\u2009","thkap":"\u2248","thksim":"\u223C","THORN":"\u00DE","thorn":"\u00FE","tilde":"\u02DC","Tilde":"\u223C","TildeEqual":"\u2243","TildeFullEqual":"\u2245","TildeTilde":"\u2248","timesbar":"\u2A31","timesb":"\u22A0","times":"\u00D7","timesd":"\u2A30","tint":"\u222D","toea":"\u2928","topbot":"\u2336","topcir":"\u2AF1","top":"\u22A4","Topf":"\uD835\uDD4B","topf":"\uD835\uDD65","topfork":"\u2ADA","tosa":"\u2929","tprime":"\u2034","trade":"\u2122","TRADE":"\u2122","triangle":"\u25B5","triangledown":"\u25BF","triangleleft":"\u25C3","trianglelefteq":"\u22B4","triangleq":"\u225C","triangleright":"\u25B9","trianglerighteq":"\u22B5","tridot":"\u25EC","trie":"\u225C","triminus":"\u2A3A","TripleDot":"\u20DB","triplus":"\u2A39","trisb":"\u29CD","tritime":"\u2A3B","trpezium":"\u23E2","Tscr":"\uD835\uDCAF","tscr":"\uD835\uDCC9","TScy":"\u0426","tscy":"\u0446","TSHcy":"\u040B","tshcy":"\u045B","Tstrok":"\u0166","tstrok":"\u0167","twixt":"\u226C","twoheadleftarrow":"\u219E","twoheadrightarrow":"\u21A0","Uacute":"\u00DA","uacute":"\u00FA","uarr":"\u2191","Uarr":"\u219F","uArr":"\u21D1","Uarrocir":"\u2949","Ubrcy":"\u040E","ubrcy":"\u045E","Ubreve":"\u016C","ubreve":"\u016D","Ucirc":"\u00DB","ucirc":"\u00FB","Ucy":"\u0423","ucy":"\u0443","udarr":"\u21C5","Udblac":"\u0170","udblac":"\u0171","udhar":"\u296E","ufisht":"\u297E","Ufr":"\uD835\uDD18","ufr":"\uD835\uDD32","Ugrave":"\u00D9","ugrave":"\u00F9","uHar":"\u2963","uharl":"\u21BF","uharr":"\u21BE","uhblk":"\u2580","ulcorn":"\u231C","ulcorner":"\u231C","ulcrop":"\u230F","ultri":"\u25F8","Umacr":"\u016A","umacr":"\u016B","uml":"\u00A8","UnderBar":"_","UnderBrace":"\u23DF","UnderBracket":"\u23B5","UnderParenthesis":"\u23DD","Union":"\u22C3","UnionPlus":"\u228E","Uogon":"\u0172","uogon":"\u0173","Uopf":"\uD835\uDD4C","uopf":"\uD835\uDD66","UpArrowBar":"\u2912","uparrow":"\u2191","UpArrow":"\u2191","Uparrow":"\u21D1","UpArrowDownArrow":"\u21C5","updownarrow":"\u2195","UpDownArrow":"\u2195","Updownarrow":"\u21D5","UpEquilibrium":"\u296E","upharpoonleft":"\u21BF","upharpoonright":"\u21BE","uplus":"\u228E","UpperLeftArrow":"\u2196","UpperRightArrow":"\u2197","upsi":"\u03C5","Upsi":"\u03D2","upsih":"\u03D2","Upsilon":"\u03A5","upsilon":"\u03C5","UpTeeArrow":"\u21A5","UpTee":"\u22A5","upuparrows":"\u21C8","urcorn":"\u231D","urcorner":"\u231D","urcrop":"\u230E","Uring":"\u016E","uring":"\u016F","urtri":"\u25F9","Uscr":"\uD835\uDCB0","uscr":"\uD835\uDCCA","utdot":"\u22F0","Utilde":"\u0168","utilde":"\u0169","utri":"\u25B5","utrif":"\u25B4","uuarr":"\u21C8","Uuml":"\u00DC","uuml":"\u00FC","uwangle":"\u29A7","vangrt":"\u299C","varepsilon":"\u03F5","varkappa":"\u03F0","varnothing":"\u2205","varphi":"\u03D5","varpi":"\u03D6","varpropto":"\u221D","varr":"\u2195","vArr":"\u21D5","varrho":"\u03F1","varsigma":"\u03C2","varsubsetneq":"\u228A\uFE00","varsubsetneqq":"\u2ACB\uFE00","varsupsetneq":"\u228B\uFE00","varsupsetneqq":"\u2ACC\uFE00","vartheta":"\u03D1","vartriangleleft":"\u22B2","vartriangleright":"\u22B3","vBar":"\u2AE8","Vbar":"\u2AEB","vBarv":"\u2AE9","Vcy":"\u0412","vcy":"\u0432","vdash":"\u22A2","vDash":"\u22A8","Vdash":"\u22A9","VDash":"\u22AB","Vdashl":"\u2AE6","veebar":"\u22BB","vee":"\u2228","Vee":"\u22C1","veeeq":"\u225A","vellip":"\u22EE","verbar":"|","Verbar":"\u2016","vert":"|","Vert":"\u2016","VerticalBar":"\u2223","VerticalLine":"|","VerticalSeparator":"\u2758","VerticalTilde":"\u2240","VeryThinSpace":"\u200A","Vfr":"\uD835\uDD19","vfr":"\uD835\uDD33","vltri":"\u22B2","vnsub":"\u2282\u20D2","vnsup":"\u2283\u20D2","Vopf":"\uD835\uDD4D","vopf":"\uD835\uDD67","vprop":"\u221D","vrtri":"\u22B3","Vscr":"\uD835\uDCB1","vscr":"\uD835\uDCCB","vsubnE":"\u2ACB\uFE00","vsubne":"\u228A\uFE00","vsupnE":"\u2ACC\uFE00","vsupne":"\u228B\uFE00","Vvdash":"\u22AA","vzigzag":"\u299A","Wcirc":"\u0174","wcirc":"\u0175","wedbar":"\u2A5F","wedge":"\u2227","Wedge":"\u22C0","wedgeq":"\u2259","weierp":"\u2118","Wfr":"\uD835\uDD1A","wfr":"\uD835\uDD34","Wopf":"\uD835\uDD4E","wopf":"\uD835\uDD68","wp":"\u2118","wr":"\u2240","wreath":"\u2240","Wscr":"\uD835\uDCB2","wscr":"\uD835\uDCCC","xcap":"\u22C2","xcirc":"\u25EF","xcup":"\u22C3","xdtri":"\u25BD","Xfr":"\uD835\uDD1B","xfr":"\uD835\uDD35","xharr":"\u27F7","xhArr":"\u27FA","Xi":"\u039E","xi":"\u03BE","xlarr":"\u27F5","xlArr":"\u27F8","xmap":"\u27FC","xnis":"\u22FB","xodot":"\u2A00","Xopf":"\uD835\uDD4F","xopf":"\uD835\uDD69","xoplus":"\u2A01","xotime":"\u2A02","xrarr":"\u27F6","xrArr":"\u27F9","Xscr":"\uD835\uDCB3","xscr":"\uD835\uDCCD","xsqcup":"\u2A06","xuplus":"\u2A04","xutri":"\u25B3","xvee":"\u22C1","xwedge":"\u22C0","Yacute":"\u00DD","yacute":"\u00FD","YAcy":"\u042F","yacy":"\u044F","Ycirc":"\u0176","ycirc":"\u0177","Ycy":"\u042B","ycy":"\u044B","yen":"\u00A5","Yfr":"\uD835\uDD1C","yfr":"\uD835\uDD36","YIcy":"\u0407","yicy":"\u0457","Yopf":"\uD835\uDD50","yopf":"\uD835\uDD6A","Yscr":"\uD835\uDCB4","yscr":"\uD835\uDCCE","YUcy":"\u042E","yucy":"\u044E","yuml":"\u00FF","Yuml":"\u0178","Zacute":"\u0179","zacute":"\u017A","Zcaron":"\u017D","zcaron":"\u017E","Zcy":"\u0417","zcy":"\u0437","Zdot":"\u017B","zdot":"\u017C","zeetrf":"\u2128","ZeroWidthSpace":"\u200B","Zeta":"\u0396","zeta":"\u03B6","zfr":"\uD835\uDD37","Zfr":"\u2128","ZHcy":"\u0416","zhcy":"\u0436","zigrarr":"\u21DD","zopf":"\uD835\uDD6B","Zopf":"\u2124","Zscr":"\uD835\uDCB5","zscr":"\uD835\uDCCF","zwj":"\u200D","zwnj":"\u200C"} +},{}],4:[function(require,module,exports){ +/** + * This is the main entry point for KaTeX. Here, we expose functions for + * rendering expressions either to DOM nodes or to markup strings. + * + * We also expose the ParseError class to check if errors thrown from KaTeX are + * errors in the expression, or errors in javascript handling. + */ + +var ParseError = require("./src/ParseError"); +var Settings = require("./src/Settings"); + +var buildTree = require("./src/buildTree"); +var parseTree = require("./src/parseTree"); +var utils = require("./src/utils"); + +/** + * Parse and build an expression, and place that expression in the DOM node + * given. + */ +var render = function(expression, baseNode, options) { + utils.clearNode(baseNode); + + var settings = new Settings(options); + + var tree = parseTree(expression, settings); + var node = buildTree(tree, expression, settings).toNode(); + + baseNode.appendChild(node); +}; + +// KaTeX's styles don't work properly in quirks mode. Print out an error, and +// disable rendering. +if (typeof document !== "undefined") { + if (document.compatMode !== "CSS1Compat") { + typeof console !== "undefined" && console.warn( + "Warning: KaTeX doesn't work in quirks mode. Make sure your " + + "website has a suitable doctype."); + + render = function() { + throw new ParseError("KaTeX doesn't work in quirks mode."); + }; + } +} + +/** + * Parse and build an expression, and return the markup for that. + */ +var renderToString = function(expression, options) { + var settings = new Settings(options); + + var tree = parseTree(expression, settings); + return buildTree(tree, expression, settings).toMarkup(); +}; + +/** + * Parse an expression and return the parse tree. + */ +var generateParseTree = function(expression, options) { + var settings = new Settings(options); + return parseTree(expression, settings); +}; + +module.exports = { + render: render, + renderToString: renderToString, + /** + * NOTE: This method is not currently recommended for public use. + * The internal tree representation is unstable and is very likely + * to change. Use at your own risk. + */ + __parse: generateParseTree, + ParseError: ParseError +}; + +},{"./src/ParseError":7,"./src/Settings":9,"./src/buildTree":14,"./src/parseTree":23,"./src/utils":25}],5:[function(require,module,exports){ +/** + * The Lexer class handles tokenizing the input in various ways. Since our + * parser expects us to be able to backtrack, the lexer allows lexing from any + * given starting point. + * + * Its main exposed function is the `lex` function, which takes a position to + * lex from and a type of token to lex. It defers to the appropriate `_innerLex` + * function. + * + * The various `_innerLex` functions perform the actual lexing of different + * kinds. + */ + +var matchAt = require("match-at"); + +var ParseError = require("./ParseError"); + +// The main lexer class +function Lexer(input) { + this._input = input; +} + +// The resulting token returned from `lex`. +function Token(text, data, position) { + this.text = text; + this.data = data; + this.position = position; +} + +// "normal" types of tokens. These are tokens which can be matched by a simple +// regex +var mathNormals = [ + /[/|@.""`0-9a-zA-Z]/, // ords + /[*+-]/, // bins + /[=<>:]/, // rels + /[,;]/, // punctuation + /['\^_{}]/, // misc + /[(\[]/, // opens + /[)\]?!]/, // closes + /~/, // spacing + /&/, // horizontal alignment + /\\\\/ // line break +]; + +// These are "normal" tokens like above, but should instead be parsed in text +// mode. +var textNormals = [ + /[a-zA-Z0-9`!@*()-=+\[\]'";:?\/.,]/, // ords + /[{}]/, // grouping + /~/, // spacing + /&/, // horizontal alignment + /\\\\/ // line break +]; + +// Regexes for matching whitespace +var whitespaceRegex = /\s*/; +var whitespaceConcatRegex = / +|\\ +/; + +// This regex matches any other TeX function, which is a backslash followed by a +// word or a single symbol +var anyFunc = /\\(?:[a-zA-Z]+|.)/; + +/** + * This function lexes a single normal token. It takes a position, a list of + * "normal" tokens to try, and whether it should completely ignore whitespace or + * not. + */ +Lexer.prototype._innerLex = function(pos, normals, ignoreWhitespace) { + var input = this._input; + var whitespace; + + if (ignoreWhitespace) { + // Get rid of whitespace. + whitespace = matchAt(whitespaceRegex, input, pos)[0]; + pos += whitespace.length; + } else { + // Do the funky concatenation of whitespace that happens in text mode. + whitespace = matchAt(whitespaceConcatRegex, input, pos); + if (whitespace !== null) { + return new Token(" ", null, pos + whitespace[0].length); + } + } + + // If there's no more input to parse, return an EOF token + if (pos === input.length) { + return new Token("EOF", null, pos); + } + + var match; + if ((match = matchAt(anyFunc, input, pos))) { + // If we match a function token, return it + return new Token(match[0], null, pos + match[0].length); + } else { + // Otherwise, we look through the normal token regexes and see if it's + // one of them. + for (var i = 0; i < normals.length; i++) { + var normal = normals[i]; + + if ((match = matchAt(normal, input, pos))) { + // If it is, return it + return new Token( + match[0], null, pos + match[0].length); + } + } + } + + throw new ParseError( + "Unexpected character: '" + input[pos] + "'", + this, pos); +}; + +// A regex to match a CSS color (like #ffffff or BlueViolet) +var cssColor = /#[a-z0-9]+|[a-z]+/i; + +/** + * This function lexes a CSS color. + */ +Lexer.prototype._innerLexColor = function(pos) { + var input = this._input; + + // Ignore whitespace + var whitespace = matchAt(whitespaceRegex, input, pos)[0]; + pos += whitespace.length; + + var match; + if ((match = matchAt(cssColor, input, pos))) { + // If we look like a color, return a color + return new Token(match[0], null, pos + match[0].length); + } else { + throw new ParseError("Invalid color", this, pos); + } +}; + +// A regex to match a dimension. Dimensions look like +// "1.2em" or ".4pt" or "1 ex" +var sizeRegex = /(-?)\s*(\d+(?:\.\d*)?|\.\d+)\s*([a-z]{2})/; + +/** + * This function lexes a dimension. + */ +Lexer.prototype._innerLexSize = function(pos) { + var input = this._input; + + // Ignore whitespace + var whitespace = matchAt(whitespaceRegex, input, pos)[0]; + pos += whitespace.length; + + var match; + if ((match = matchAt(sizeRegex, input, pos))) { + var unit = match[3]; + // We only currently handle "em" and "ex" units + if (unit !== "em" && unit !== "ex") { + throw new ParseError("Invalid unit: '" + unit + "'", this, pos); + } + return new Token(match[0], { + number: +(match[1] + match[2]), + unit: unit + }, pos + match[0].length); + } + + throw new ParseError("Invalid size", this, pos); +}; + +/** + * This function lexes a string of whitespace. + */ +Lexer.prototype._innerLexWhitespace = function(pos) { + var input = this._input; + + var whitespace = matchAt(whitespaceRegex, input, pos)[0]; + pos += whitespace.length; + + return new Token(whitespace[0], null, pos); +}; + +/** + * This function lexes a single token starting at `pos` and of the given mode. + * Based on the mode, we defer to one of the `_innerLex` functions. + */ +Lexer.prototype.lex = function(pos, mode) { + if (mode === "math") { + return this._innerLex(pos, mathNormals, true); + } else if (mode === "text") { + return this._innerLex(pos, textNormals, false); + } else if (mode === "color") { + return this._innerLexColor(pos); + } else if (mode === "size") { + return this._innerLexSize(pos); + } else if (mode === "whitespace") { + return this._innerLexWhitespace(pos); + } +}; + +module.exports = Lexer; + +},{"./ParseError":7,"match-at":80}],6:[function(require,module,exports){ +/** + * This file contains information about the options that the Parser carries + * around with it while parsing. Data is held in an `Options` object, and when + * recursing, a new `Options` object can be created with the `.with*` and + * `.reset` functions. + */ + +/** + * This is the main options class. It contains the style, size, color, and font + * of the current parse level. It also contains the style and size of the parent + * parse level, so size changes can be handled efficiently. + * + * Each of the `.with*` and `.reset` functions passes its current style and size + * as the parentStyle and parentSize of the new options class, so parent + * handling is taken care of automatically. + */ +function Options(data) { + this.style = data.style; + this.color = data.color; + this.size = data.size; + this.phantom = data.phantom; + this.font = data.font; + + if (data.parentStyle === undefined) { + this.parentStyle = data.style; + } else { + this.parentStyle = data.parentStyle; + } + + if (data.parentSize === undefined) { + this.parentSize = data.size; + } else { + this.parentSize = data.parentSize; + } +} + +/** + * Returns a new options object with the same properties as "this". Properties + * from "extension" will be copied to the new options object. + */ +Options.prototype.extend = function(extension) { + var data = { + style: this.style, + size: this.size, + color: this.color, + parentStyle: this.style, + parentSize: this.size, + phantom: this.phantom, + font: this.font + }; + + for (var key in extension) { + if (extension.hasOwnProperty(key)) { + data[key] = extension[key]; + } + } + + return new Options(data); +}; + +/** + * Create a new options object with the given style. + */ +Options.prototype.withStyle = function(style) { + return this.extend({ + style: style + }); +}; + +/** + * Create a new options object with the given size. + */ +Options.prototype.withSize = function(size) { + return this.extend({ + size: size + }); +}; + +/** + * Create a new options object with the given color. + */ +Options.prototype.withColor = function(color) { + return this.extend({ + color: color + }); +}; + +/** + * Create a new options object with "phantom" set to true. + */ +Options.prototype.withPhantom = function() { + return this.extend({ + phantom: true + }); +}; + +/** + * Create a new options objects with the give font. + */ +Options.prototype.withFont = function(font) { + return this.extend({ + font: font + }); +}; + +/** + * Create a new options object with the same style, size, and color. This is + * used so that parent style and size changes are handled correctly. + */ +Options.prototype.reset = function() { + return this.extend({}); +}; + +/** + * A map of color names to CSS colors. + * TODO(emily): Remove this when we have real macros + */ +var colorMap = { + "katex-blue": "#6495ed", + "katex-orange": "#ffa500", + "katex-pink": "#ff00af", + "katex-red": "#df0030", + "katex-green": "#28ae7b", + "katex-gray": "gray", + "katex-purple": "#9d38bd", + "katex-blueA": "#c7e9f1", + "katex-blueB": "#9cdceb", + "katex-blueC": "#58c4dd", + "katex-blueD": "#29abca", + "katex-blueE": "#1c758a", + "katex-tealA": "#acead7", + "katex-tealB": "#76ddc0", + "katex-tealC": "#5cd0b3", + "katex-tealD": "#55c1a7", + "katex-tealE": "#49a88f", + "katex-greenA": "#c9e2ae", + "katex-greenB": "#a6cf8c", + "katex-greenC": "#83c167", + "katex-greenD": "#77b05d", + "katex-greenE": "#699c52", + "katex-goldA": "#f7c797", + "katex-goldB": "#f9b775", + "katex-goldC": "#f0ac5f", + "katex-goldD": "#e1a158", + "katex-goldE": "#c78d46", + "katex-redA": "#f7a1a3", + "katex-redB": "#ff8080", + "katex-redC": "#fc6255", + "katex-redD": "#e65a4c", + "katex-redE": "#cf5044", + "katex-maroonA": "#ecabc1", + "katex-maroonB": "#ec92ab", + "katex-maroonC": "#c55f73", + "katex-maroonD": "#a24d61", + "katex-maroonE": "#94424f", + "katex-purpleA": "#caa3e8", + "katex-purpleB": "#b189c6", + "katex-purpleC": "#9a72ac", + "katex-purpleD": "#715582", + "katex-purpleE": "#644172", + "katex-mintA": "#f5f9e8", + "katex-mintB": "#edf2df", + "katex-mintC": "#e0e5cc", + "katex-grayA": "#fdfdfd", + "katex-grayB": "#f7f7f7", + "katex-grayC": "#eeeeee", + "katex-grayD": "#dddddd", + "katex-grayE": "#cccccc", + "katex-grayF": "#aaaaaa", + "katex-grayG": "#999999", + "katex-grayH": "#555555", + "katex-grayI": "#333333", + "katex-kaBlue": "#314453", + "katex-kaGreen": "#639b24" +}; + +/** + * Gets the CSS color of the current options object, accounting for the + * `colorMap`. + */ +Options.prototype.getColor = function() { + if (this.phantom) { + return "transparent"; + } else { + return colorMap[this.color] || this.color; + } +}; + +module.exports = Options; + +},{}],7:[function(require,module,exports){ +/** + * This is the ParseError class, which is the main error thrown by KaTeX + * functions when something has gone wrong. This is used to distinguish internal + * errors from errors in the expression that the user provided. + */ +function ParseError(message, lexer, position) { + var error = "KaTeX parse error: " + message; + + if (lexer !== undefined && position !== undefined) { + // If we have the input and a position, make the error a bit fancier + + // Prepend some information + error += " at position " + position + ": "; + + // Get the input + var input = lexer._input; + // Insert a combining underscore at the correct position + input = input.slice(0, position) + "\u0332" + + input.slice(position); + + // Extract some context from the input and add it to the error + var begin = Math.max(0, position - 15); + var end = position + 15; + error += input.slice(begin, end); + } + + // Some hackery to make ParseError a prototype of Error + // See http://stackoverflow.com/a/8460753 + var self = new Error(error); + self.name = "ParseError"; + self.__proto__ = ParseError.prototype; + + self.position = position; + return self; +} + +// More hackery +ParseError.prototype.__proto__ = Error.prototype; + +module.exports = ParseError; + +},{}],8:[function(require,module,exports){ +var functions = require("./functions"); +var environments = require("./environments"); +var Lexer = require("./Lexer"); +var symbols = require("./symbols"); +var utils = require("./utils"); + +var parseData = require("./parseData"); +var ParseError = require("./ParseError"); + +/** + * This file contains the parser used to parse out a TeX expression from the + * input. Since TeX isn't context-free, standard parsers don't work particularly + * well. + * + * The strategy of this parser is as such: + * + * The main functions (the `.parse...` ones) take a position in the current + * parse string to parse tokens from. The lexer (found in Lexer.js, stored at + * this.lexer) also supports pulling out tokens at arbitrary places. When + * individual tokens are needed at a position, the lexer is called to pull out a + * token, which is then used. + * + * The main functions also take a mode that the parser is currently in + * (currently "math" or "text"), which denotes whether the current environment + * is a math-y one or a text-y one (e.g. inside \text). Currently, this serves + * to limit the functions which can be used in text mode. + * + * The main functions then return an object which contains the useful data that + * was parsed at its given point, and a new position at the end of the parsed + * data. The main functions can call each other and continue the parsing by + * using the returned position as a new starting point. + * + * There are also extra `.handle...` functions, which pull out some reused + * functionality into self-contained functions. + * + * The earlier functions return `ParseResult`s, which contain a ParseNode and a + * new position. + * + * The later functions (which are called deeper in the parse) sometimes return + * ParseFuncOrArgument, which contain a ParseResult as well as some data about + * whether the parsed object is a function which is missing some arguments, or a + * standalone object which can be used as an argument to another function. + */ + +/** + * Main Parser class + */ +function Parser(input, settings) { + // Make a new lexer + this.lexer = new Lexer(input); + // Store the settings for use in parsing + this.settings = settings; +} + +var ParseNode = parseData.ParseNode; +var ParseResult = parseData.ParseResult; + +/** + * An initial function (without its arguments), or an argument to a function. + * The `result` argument should be a ParseResult. + */ +function ParseFuncOrArgument(result, isFunction) { + this.result = result; + // Is this a function (i.e. is it something defined in functions.js)? + this.isFunction = isFunction; +} + +/** + * Checks a result to make sure it has the right type, and throws an + * appropriate error otherwise. + */ +Parser.prototype.expect = function(result, text) { + if (result.text !== text) { + throw new ParseError( + "Expected '" + text + "', got '" + result.text + "'", + this.lexer, result.position + ); + } +}; + +/** + * Main parsing function, which parses an entire input. + * + * @return {?Array.} + */ +Parser.prototype.parse = function(input) { + // Try to parse the input + var parse = this.parseInput(0, "math"); + return parse.result; +}; + +/** + * Parses an entire input tree. + */ +Parser.prototype.parseInput = function(pos, mode) { + // Parse an expression + var expression = this.parseExpression(pos, mode, false); + // If we succeeded, make sure there's an EOF at the end + this.expect(expression.peek, "EOF"); + return expression; +}; + +var endOfExpression = ["}", "\\end", "\\right", "&", "\\\\", "\\cr"]; + +/** + * Parses an "expression", which is a list of atoms. + * + * @param {boolean} breakOnInfix Should the parsing stop when we hit infix + * nodes? This happens when functions have higher precendence + * than infix nodes in implicit parses. + * + * @param {?string} breakOnToken The token that the expression should end with, + * or `null` if something else should end the expression. + * + * @return {ParseResult} + */ +Parser.prototype.parseExpression = function(pos, mode, breakOnInfix, breakOnToken) { + var body = []; + var lex = null; + // Keep adding atoms to the body until we can't parse any more atoms (either + // we reached the end, a }, or a \right) + while (true) { + lex = this.lexer.lex(pos, mode); + if (endOfExpression.indexOf(lex.text) !== -1) { + break; + } + if (breakOnToken && lex.text === breakOnToken) { + break; + } + var atom = this.parseAtom(pos, mode); + if (!atom) { + if (!this.settings.throwOnError && lex.text[0] === "\\") { + var errorNode = this.handleUnsupportedCmd(lex.text, mode); + body.push(errorNode); + + pos = lex.position; + continue; + } + + break; + } + if (breakOnInfix && atom.result.type === "infix") { + break; + } + body.push(atom.result); + pos = atom.position; + } + var res = new ParseResult(this.handleInfixNodes(body, mode), pos); + res.peek = lex; + return res; +}; + +/** + * Rewrites infix operators such as \over with corresponding commands such + * as \frac. + * + * There can only be one infix operator per group. If there's more than one + * then the expression is ambiguous. This can be resolved by adding {}. + * + * @returns {Array} + */ +Parser.prototype.handleInfixNodes = function (body, mode) { + var overIndex = -1; + var func; + var funcName; + + for (var i = 0; i < body.length; i++) { + var node = body[i]; + if (node.type === "infix") { + if (overIndex !== -1) { + throw new ParseError("only one infix operator per group", + this.lexer, -1); + } + overIndex = i; + funcName = node.value.replaceWith; + func = functions.funcs[funcName]; + } + } + + if (overIndex !== -1) { + var numerNode, denomNode; + + var numerBody = body.slice(0, overIndex); + var denomBody = body.slice(overIndex + 1); + + if (numerBody.length === 1 && numerBody[0].type === "ordgroup") { + numerNode = numerBody[0]; + } else { + numerNode = new ParseNode("ordgroup", numerBody, mode); + } + + if (denomBody.length === 1 && denomBody[0].type === "ordgroup") { + denomNode = denomBody[0]; + } else { + denomNode = new ParseNode("ordgroup", denomBody, mode); + } + + var value = func.handler(funcName, numerNode, denomNode); + return [new ParseNode(value.type, value, mode)]; + } else { + return body; + } +}; + +// The greediness of a superscript or subscript +var SUPSUB_GREEDINESS = 1; + +/** + * Handle a subscript or superscript with nice errors. + */ +Parser.prototype.handleSupSubscript = function(pos, mode, symbol, name) { + var group = this.parseGroup(pos, mode); + + if (!group) { + var lex = this.lexer.lex(pos, mode); + + if (!this.settings.throwOnError && lex.text[0] === "\\") { + return new ParseResult( + this.handleUnsupportedCmd(lex.text, mode), + lex.position); + } else { + throw new ParseError( + "Expected group after '" + symbol + "'", this.lexer, pos); + } + } else if (group.isFunction) { + // ^ and _ have a greediness, so handle interactions with functions' + // greediness + var funcGreediness = functions.funcs[group.result.result].greediness; + if (funcGreediness > SUPSUB_GREEDINESS) { + return this.parseFunction(pos, mode); + } else { + throw new ParseError( + "Got function '" + group.result.result + "' with no arguments " + + "as " + name, + this.lexer, pos); + } + } else { + return group.result; + } +}; + +/** + * Converts the textual input of an unsupported command into a text node + * contained within a color node whose color is determined by errorColor + */ + Parser.prototype.handleUnsupportedCmd = function(text, mode) { + var textordArray = []; + + for (var i = 0; i < text.length; i++) { + textordArray.push(new ParseNode("textord", text[i], "text")); + } + + var textNode = new ParseNode( + "text", + { + body: textordArray, + type: "text" + }, + mode); + + var colorNode = new ParseNode( + "color", + { + color: this.settings.errorColor, + value: [textNode], + type: "color" + }, + mode); + + return colorNode; + }; + +/** + * Parses a group with optional super/subscripts. + * + * @return {?ParseResult} + */ +Parser.prototype.parseAtom = function(pos, mode) { + // The body of an atom is an implicit group, so that things like + // \left(x\right)^2 work correctly. + var base = this.parseImplicitGroup(pos, mode); + + // In text mode, we don't have superscripts or subscripts + if (mode === "text") { + return base; + } + + // Handle an empty base + var currPos; + if (!base) { + currPos = pos; + base = undefined; + } else { + currPos = base.position; + } + + var superscript; + var subscript; + var result; + while (true) { + // Lex the first token + var lex = this.lexer.lex(currPos, mode); + + if (lex.text === "\\limits" || lex.text === "\\nolimits") { + // We got a limit control + if (!base || base.result.type !== "op") { + throw new ParseError("Limit controls must follow a math operator", + this.lexer, currPos); + } + else { + var limits = lex.text === "\\limits"; + base.result.value.limits = limits; + base.result.value.alwaysHandleSupSub = true; + currPos = lex.position; + } + } else if (lex.text === "^") { + // We got a superscript start + if (superscript) { + throw new ParseError( + "Double superscript", this.lexer, currPos); + } + result = this.handleSupSubscript( + lex.position, mode, lex.text, "superscript"); + currPos = result.position; + superscript = result.result; + } else if (lex.text === "_") { + // We got a subscript start + if (subscript) { + throw new ParseError( + "Double subscript", this.lexer, currPos); + } + result = this.handleSupSubscript( + lex.position, mode, lex.text, "subscript"); + currPos = result.position; + subscript = result.result; + } else if (lex.text === "'") { + // We got a prime + var prime = new ParseNode("textord", "\\prime", mode); + + // Many primes can be grouped together, so we handle this here + var primes = [prime]; + currPos = lex.position; + // Keep lexing tokens until we get something that's not a prime + while ((lex = this.lexer.lex(currPos, mode)).text === "'") { + // For each one, add another prime to the list + primes.push(prime); + currPos = lex.position; + } + // Put them into an ordgroup as the superscript + superscript = new ParseNode("ordgroup", primes, mode); + } else { + // If it wasn't ^, _, or ', stop parsing super/subscripts + break; + } + } + + if (superscript || subscript) { + // If we got either a superscript or subscript, create a supsub + return new ParseResult( + new ParseNode("supsub", { + base: base && base.result, + sup: superscript, + sub: subscript + }, mode), + currPos); + } else { + // Otherwise return the original body + return base; + } +}; + +// A list of the size-changing functions, for use in parseImplicitGroup +var sizeFuncs = [ + "\\tiny", "\\scriptsize", "\\footnotesize", "\\small", "\\normalsize", + "\\large", "\\Large", "\\LARGE", "\\huge", "\\Huge" +]; + +// A list of the style-changing functions, for use in parseImplicitGroup +var styleFuncs = [ + "\\displaystyle", "\\textstyle", "\\scriptstyle", "\\scriptscriptstyle" +]; + +/** + * Parses an implicit group, which is a group that starts at the end of a + * specified, and ends right before a higher explicit group ends, or at EOL. It + * is used for functions that appear to affect the current style, like \Large or + * \textrm, where instead of keeping a style we just pretend that there is an + * implicit grouping after it until the end of the group. E.g. + * small text {\Large large text} small text again + * It is also used for \left and \right to get the correct grouping. + * + * @return {?ParseResult} + */ +Parser.prototype.parseImplicitGroup = function(pos, mode) { + var start = this.parseSymbol(pos, mode); + + if (!start || !start.result) { + // If we didn't get anything we handle, fall back to parseFunction + return this.parseFunction(pos, mode); + } + + var func = start.result.result; + var body; + + if (func === "\\left") { + // If we see a left: + // Parse the entire left function (including the delimiter) + var left = this.parseFunction(pos, mode); + // Parse out the implicit body + body = this.parseExpression(left.position, mode, false); + // Check the next token + this.expect(body.peek, "\\right"); + var right = this.parseFunction(body.position, mode); + return new ParseResult( + new ParseNode("leftright", { + body: body.result, + left: left.result.value.value, + right: right.result.value.value + }, mode), + right.position); + } else if (func === "\\begin") { + // begin...end is similar to left...right + var begin = this.parseFunction(pos, mode); + var envName = begin.result.value.name; + if (!environments.hasOwnProperty(envName)) { + throw new ParseError( + "No such environment: " + envName, + this.lexer, begin.result.value.namepos); + } + // Build the environment object. Arguments and other information will + // be made available to the begin and end methods using properties. + var env = environments[envName]; + var args = [null, mode, envName]; + var newPos = this.parseArguments( + begin.position, mode, "\\begin{" + envName + "}", env, args); + args[0] = newPos; + var result = env.handler.apply(this, args); + var endLex = this.lexer.lex(result.position, mode); + this.expect(endLex, "\\end"); + var end = this.parseFunction(result.position, mode); + if (end.result.value.name !== envName) { + throw new ParseError( + "Mismatch: \\begin{" + envName + "} matched " + + "by \\end{" + end.result.value.name + "}", + this.lexer, end.namepos); + } + result.position = end.position; + return result; + } else if (utils.contains(sizeFuncs, func)) { + // If we see a sizing function, parse out the implict body + body = this.parseExpression(start.result.position, mode, false); + return new ParseResult( + new ParseNode("sizing", { + // Figure out what size to use based on the list of functions above + size: "size" + (utils.indexOf(sizeFuncs, func) + 1), + value: body.result + }, mode), + body.position); + } else if (utils.contains(styleFuncs, func)) { + // If we see a styling function, parse out the implict body + body = this.parseExpression(start.result.position, mode, true); + return new ParseResult( + new ParseNode("styling", { + // Figure out what style to use by pulling out the style from + // the function name + style: func.slice(1, func.length - 5), + value: body.result + }, mode), + body.position); + } else { + // Defer to parseFunction if it's not a function we handle + return this.parseFunction(pos, mode); + } +}; + +/** + * Parses an entire function, including its base and all of its arguments + * + * @return {?ParseResult} + */ +Parser.prototype.parseFunction = function(pos, mode) { + var baseGroup = this.parseGroup(pos, mode); + + if (baseGroup) { + if (baseGroup.isFunction) { + var func = baseGroup.result.result; + var funcData = functions.funcs[func]; + if (mode === "text" && !funcData.allowedInText) { + throw new ParseError( + "Can't use function '" + func + "' in text mode", + this.lexer, baseGroup.position); + } + + var args = [func]; + var newPos = this.parseArguments( + baseGroup.result.position, mode, func, funcData, args); + var result = functions.funcs[func].handler.apply(this, args); + return new ParseResult( + new ParseNode(result.type, result, mode), + newPos); + } else { + return baseGroup.result; + } + } else { + return null; + } +}; + + +/** + * Parses the arguments of a function or environment + * + * @param {string} func "\name" or "\begin{name}" + * @param {{numArgs:number,numOptionalArgs:number|undefined}} funcData + * @param {Array} args list of arguments to which new ones will be pushed + * @return the position after all arguments have been parsed + */ +Parser.prototype.parseArguments = function(pos, mode, func, funcData, args) { + var totalArgs = funcData.numArgs + funcData.numOptionalArgs; + if (totalArgs === 0) { + return pos; + } + + var newPos = pos; + var baseGreediness = funcData.greediness; + var positions = [newPos]; + + for (var i = 0; i < totalArgs; i++) { + var argType = funcData.argTypes && funcData.argTypes[i]; + var arg; + if (i < funcData.numOptionalArgs) { + if (argType) { + arg = this.parseSpecialGroup(newPos, argType, mode, true); + } else { + arg = this.parseOptionalGroup(newPos, mode); + } + if (!arg) { + args.push(null); + positions.push(newPos); + continue; + } + } else { + if (argType) { + arg = this.parseSpecialGroup(newPos, argType, mode); + } else { + arg = this.parseGroup(newPos, mode); + } + if (!arg) { + var lex = this.lexer.lex(newPos, mode); + + if (!this.settings.throwOnError && lex.text[0] === "\\") { + arg = new ParseFuncOrArgument( + new ParseResult( + this.handleUnsupportedCmd(lex.text, mode), + lex.position), + false); + } else { + throw new ParseError( + "Expected group after '" + func + "'", this.lexer, pos); + } + } + } + var argNode; + if (arg.isFunction) { + var argGreediness = + functions.funcs[arg.result.result].greediness; + if (argGreediness > baseGreediness) { + argNode = this.parseFunction(newPos, mode); + } else { + throw new ParseError( + "Got function '" + arg.result.result + "' as " + + "argument to '" + func + "'", + this.lexer, arg.result.position - 1); + } + } else { + argNode = arg.result; + } + args.push(argNode.result); + positions.push(argNode.position); + newPos = argNode.position; + } + + args.push(positions); + + return newPos; +}; + + +/** + * Parses a group when the mode is changing. Takes a position, a new mode, and + * an outer mode that is used to parse the outside. + * + * @return {?ParseFuncOrArgument} + */ +Parser.prototype.parseSpecialGroup = function(pos, mode, outerMode, optional) { + // Handle `original` argTypes + if (mode === "original") { + mode = outerMode; + } + + if (mode === "color" || mode === "size") { + // color and size modes are special because they should have braces and + // should only lex a single symbol inside + var openBrace = this.lexer.lex(pos, outerMode); + if (optional && openBrace.text !== "[") { + // optional arguments should return null if they don't exist + return null; + } + this.expect(openBrace, optional ? "[" : "{"); + var inner = this.lexer.lex(openBrace.position, mode); + var data; + if (mode === "color") { + data = inner.text; + } else { + data = inner.data; + } + var closeBrace = this.lexer.lex(inner.position, outerMode); + this.expect(closeBrace, optional ? "]" : "}"); + return new ParseFuncOrArgument( + new ParseResult( + new ParseNode(mode, data, outerMode), + closeBrace.position), + false); + } else if (mode === "text") { + // text mode is special because it should ignore the whitespace before + // it + var whitespace = this.lexer.lex(pos, "whitespace"); + pos = whitespace.position; + } + + if (optional) { + return this.parseOptionalGroup(pos, mode); + } else { + return this.parseGroup(pos, mode); + } +}; + +/** + * Parses a group, which is either a single nucleus (like "x") or an expression + * in braces (like "{x+y}") + * + * @return {?ParseFuncOrArgument} + */ +Parser.prototype.parseGroup = function(pos, mode) { + var start = this.lexer.lex(pos, mode); + // Try to parse an open brace + if (start.text === "{") { + // If we get a brace, parse an expression + var expression = this.parseExpression(start.position, mode, false); + // Make sure we get a close brace + var closeBrace = this.lexer.lex(expression.position, mode); + this.expect(closeBrace, "}"); + return new ParseFuncOrArgument( + new ParseResult( + new ParseNode("ordgroup", expression.result, mode), + closeBrace.position), + false); + } else { + // Otherwise, just return a nucleus + return this.parseSymbol(pos, mode); + } +}; + +/** + * Parses a group, which is an expression in brackets (like "[x+y]") + * + * @return {?ParseFuncOrArgument} + */ +Parser.prototype.parseOptionalGroup = function(pos, mode) { + var start = this.lexer.lex(pos, mode); + // Try to parse an open bracket + if (start.text === "[") { + // If we get a brace, parse an expression + var expression = this.parseExpression(start.position, mode, false, "]"); + // Make sure we get a close bracket + var closeBracket = this.lexer.lex(expression.position, mode); + this.expect(closeBracket, "]"); + return new ParseFuncOrArgument( + new ParseResult( + new ParseNode("ordgroup", expression.result, mode), + closeBracket.position), + false); + } else { + // Otherwise, return null, + return null; + } +}; + +/** + * Parse a single symbol out of the string. Here, we handle both the functions + * we have defined, as well as the single character symbols + * + * @return {?ParseFuncOrArgument} + */ +Parser.prototype.parseSymbol = function(pos, mode) { + var nucleus = this.lexer.lex(pos, mode); + + if (functions.funcs[nucleus.text]) { + // If there exists a function with this name, we return the function and + // say that it is a function. + return new ParseFuncOrArgument( + new ParseResult(nucleus.text, nucleus.position), + true); + } else if (symbols[mode][nucleus.text]) { + // Otherwise if this is a no-argument function, find the type it + // corresponds to in the symbols map + return new ParseFuncOrArgument( + new ParseResult( + new ParseNode(symbols[mode][nucleus.text].group, + nucleus.text, mode), + nucleus.position), + false); + } else { + return null; + } +}; + +Parser.prototype.ParseNode = ParseNode; + +module.exports = Parser; + +},{"./Lexer":5,"./ParseError":7,"./environments":17,"./functions":20,"./parseData":22,"./symbols":24,"./utils":25}],9:[function(require,module,exports){ +/** + * This is a module for storing settings passed into KaTeX. It correctly handles + * default settings. + */ + +/** + * Helper function for getting a default value if the value is undefined + */ +function get(option, defaultValue) { + return option === undefined ? defaultValue : option; +} + +/** + * The main Settings object + * + * The current options stored are: + * - displayMode: Whether the expression should be typeset by default in + * textstyle or displaystyle (default false) + */ +function Settings(options) { + // allow null options + options = options || {}; + this.displayMode = get(options.displayMode, false); + this.throwOnError = get(options.throwOnError, true); + this.errorColor = get(options.errorColor, "#cc0000"); +} + +module.exports = Settings; + +},{}],10:[function(require,module,exports){ +/** + * This file contains information and classes for the various kinds of styles + * used in TeX. It provides a generic `Style` class, which holds information + * about a specific style. It then provides instances of all the different kinds + * of styles possible, and provides functions to move between them and get + * information about them. + */ + +/** + * The main style class. Contains a unique id for the style, a size (which is + * the same for cramped and uncramped version of a style), a cramped flag, and a + * size multiplier, which gives the size difference between a style and + * textstyle. + */ +function Style(id, size, multiplier, cramped) { + this.id = id; + this.size = size; + this.cramped = cramped; + this.sizeMultiplier = multiplier; +} + +/** + * Get the style of a superscript given a base in the current style. + */ +Style.prototype.sup = function() { + return styles[sup[this.id]]; +}; + +/** + * Get the style of a subscript given a base in the current style. + */ +Style.prototype.sub = function() { + return styles[sub[this.id]]; +}; + +/** + * Get the style of a fraction numerator given the fraction in the current + * style. + */ +Style.prototype.fracNum = function() { + return styles[fracNum[this.id]]; +}; + +/** + * Get the style of a fraction denominator given the fraction in the current + * style. + */ +Style.prototype.fracDen = function() { + return styles[fracDen[this.id]]; +}; + +/** + * Get the cramped version of a style (in particular, cramping a cramped style + * doesn't change the style). + */ +Style.prototype.cramp = function() { + return styles[cramp[this.id]]; +}; + +/** + * HTML class name, like "displaystyle cramped" + */ +Style.prototype.cls = function() { + return sizeNames[this.size] + (this.cramped ? " cramped" : " uncramped"); +}; + +/** + * HTML Reset class name, like "reset-textstyle" + */ +Style.prototype.reset = function() { + return resetNames[this.size]; +}; + +// IDs of the different styles +var D = 0; +var Dc = 1; +var T = 2; +var Tc = 3; +var S = 4; +var Sc = 5; +var SS = 6; +var SSc = 7; + +// String names for the different sizes +var sizeNames = [ + "displaystyle textstyle", + "textstyle", + "scriptstyle", + "scriptscriptstyle" +]; + +// Reset names for the different sizes +var resetNames = [ + "reset-textstyle", + "reset-textstyle", + "reset-scriptstyle", + "reset-scriptscriptstyle" +]; + +// Instances of the different styles +var styles = [ + new Style(D, 0, 1.0, false), + new Style(Dc, 0, 1.0, true), + new Style(T, 1, 1.0, false), + new Style(Tc, 1, 1.0, true), + new Style(S, 2, 0.7, false), + new Style(Sc, 2, 0.7, true), + new Style(SS, 3, 0.5, false), + new Style(SSc, 3, 0.5, true) +]; + +// Lookup tables for switching from one style to another +var sup = [S, Sc, S, Sc, SS, SSc, SS, SSc]; +var sub = [Sc, Sc, Sc, Sc, SSc, SSc, SSc, SSc]; +var fracNum = [T, Tc, S, Sc, SS, SSc, SS, SSc]; +var fracDen = [Tc, Tc, Sc, Sc, SSc, SSc, SSc, SSc]; +var cramp = [Dc, Dc, Tc, Tc, Sc, Sc, SSc, SSc]; + +// We only export some of the styles. Also, we don't export the `Style` class so +// no more styles can be generated. +module.exports = { + DISPLAY: styles[D], + TEXT: styles[T], + SCRIPT: styles[S], + SCRIPTSCRIPT: styles[SS] +}; + +},{}],11:[function(require,module,exports){ +/** + * This module contains general functions that can be used for building + * different kinds of domTree nodes in a consistent manner. + */ + +var domTree = require("./domTree"); +var fontMetrics = require("./fontMetrics"); +var symbols = require("./symbols"); +var utils = require("./utils"); + +var greekCapitals = [ + "\\Gamma", + "\\Delta", + "\\Theta", + "\\Lambda", + "\\Xi", + "\\Pi", + "\\Sigma", + "\\Upsilon", + "\\Phi", + "\\Psi", + "\\Omega" +]; + +var dotlessLetters = [ + "\u0131", // dotless i, \imath + "\u0237" // dotless j, \jmath +]; + +/** + * Makes a symbolNode after translation via the list of symbols in symbols.js. + * Correctly pulls out metrics for the character, and optionally takes a list of + * classes to be attached to the node. + */ +var makeSymbol = function(value, style, mode, color, classes) { + // Replace the value with its replaced value from symbol.js + if (symbols[mode][value] && symbols[mode][value].replace) { + value = symbols[mode][value].replace; + } + + var metrics = fontMetrics.getCharacterMetrics(value, style); + + var symbolNode; + if (metrics) { + symbolNode = new domTree.symbolNode( + value, metrics.height, metrics.depth, metrics.italic, metrics.skew, + classes); + } else { + // TODO(emily): Figure out a good way to only print this in development + typeof console !== "undefined" && console.warn( + "No character metrics for '" + value + "' in style '" + + style + "'"); + symbolNode = new domTree.symbolNode(value, 0, 0, 0, 0, classes); + } + + if (color) { + symbolNode.style.color = color; + } + + return symbolNode; +}; + +/** + * Makes a symbol in Main-Regular or AMS-Regular. + * Used for rel, bin, open, close, inner, and punct. + */ +var mathsym = function(value, mode, color, classes) { + // Decide what font to render the symbol in by its entry in the symbols + // table. + // Have a special case for when the value = \ because the \ is used as a + // textord in unsupported command errors but cannot be parsed as a regular + // text ordinal and is therefore not present as a symbol in the symbols + // table for text + if (value === "\\" || symbols[mode][value].font === "main") { + return makeSymbol(value, "Main-Regular", mode, color, classes); + } else { + return makeSymbol( + value, "AMS-Regular", mode, color, classes.concat(["amsrm"])); + } +}; + +/** + * Makes a symbol in the default font for mathords and textords. + */ +var mathDefault = function(value, mode, color, classes, type) { + if (type === "mathord") { + return mathit(value, mode, color, classes); + } else if (type === "textord") { + return makeSymbol( + value, "Main-Regular", mode, color, classes.concat(["mathrm"])); + } else { + throw new Error("unexpected type: " + type + " in mathDefault"); + } +}; + +/** + * Makes a symbol in the italic math font. + */ +var mathit = function(value, mode, color, classes) { + if (/[0-9]/.test(value.charAt(0)) || + // glyphs for \imath and \jmath do not exist in Math-Italic so we + // need to use Main-Italic instead + utils.contains(dotlessLetters, value) || + utils.contains(greekCapitals, value)) { + return makeSymbol( + value, "Main-Italic", mode, color, classes.concat(["mainit"])); + } else { + return makeSymbol( + value, "Math-Italic", mode, color, classes.concat(["mathit"])); + } +}; + +/** + * Makes either a mathord or textord in the correct font and color. + */ +var makeOrd = function(group, options, type) { + var mode = group.mode; + var value = group.value; + if (symbols[mode][value] && symbols[mode][value].replace) { + value = symbols[mode][value].replace; + } + + var classes = ["mord"]; + var color = options.getColor(); + + var font = options.font; + if (font) { + if (font === "mathit" || utils.contains(dotlessLetters, value)) { + return mathit(value, mode, color, classes); + } else { + var fontName = fontMap[font].fontName; + if (fontMetrics.getCharacterMetrics(value, fontName)) { + return makeSymbol(value, fontName, mode, color, classes.concat([font])); + } else { + return mathDefault(value, mode, color, classes, type); + } + } + } else { + return mathDefault(value, mode, color, classes, type); + } +}; + +/** + * Calculate the height, depth, and maxFontSize of an element based on its + * children. + */ +var sizeElementFromChildren = function(elem) { + var height = 0; + var depth = 0; + var maxFontSize = 0; + + if (elem.children) { + for (var i = 0; i < elem.children.length; i++) { + if (elem.children[i].height > height) { + height = elem.children[i].height; + } + if (elem.children[i].depth > depth) { + depth = elem.children[i].depth; + } + if (elem.children[i].maxFontSize > maxFontSize) { + maxFontSize = elem.children[i].maxFontSize; + } + } + } + + elem.height = height; + elem.depth = depth; + elem.maxFontSize = maxFontSize; +}; + +/** + * Makes a span with the given list of classes, list of children, and color. + */ +var makeSpan = function(classes, children, color) { + var span = new domTree.span(classes, children); + + sizeElementFromChildren(span); + + if (color) { + span.style.color = color; + } + + return span; +}; + +/** + * Makes a document fragment with the given list of children. + */ +var makeFragment = function(children) { + var fragment = new domTree.documentFragment(children); + + sizeElementFromChildren(fragment); + + return fragment; +}; + +/** + * Makes an element placed in each of the vlist elements to ensure that each + * element has the same max font size. To do this, we create a zero-width space + * with the correct font size. + */ +var makeFontSizer = function(options, fontSize) { + var fontSizeInner = makeSpan([], [new domTree.symbolNode("\u200b")]); + fontSizeInner.style.fontSize = (fontSize / options.style.sizeMultiplier) + "em"; + + var fontSizer = makeSpan( + ["fontsize-ensurer", "reset-" + options.size, "size5"], + [fontSizeInner]); + + return fontSizer; +}; + +/** + * Makes a vertical list by stacking elements and kerns on top of each other. + * Allows for many different ways of specifying the positioning method. + * + * Arguments: + * - children: A list of child or kern nodes to be stacked on top of each other + * (i.e. the first element will be at the bottom, and the last at + * the top). Element nodes are specified as + * {type: "elem", elem: node} + * while kern nodes are specified as + * {type: "kern", size: size} + * - positionType: The method by which the vlist should be positioned. Valid + * values are: + * - "individualShift": The children list only contains elem + * nodes, and each node contains an extra + * "shift" value of how much it should be + * shifted (note that shifting is always + * moving downwards). positionData is + * ignored. + * - "top": The positionData specifies the topmost point of + * the vlist (note this is expected to be a height, + * so positive values move up) + * - "bottom": The positionData specifies the bottommost point + * of the vlist (note this is expected to be a + * depth, so positive values move down + * - "shift": The vlist will be positioned such that its + * baseline is positionData away from the baseline + * of the first child. Positive values move + * downwards. + * - "firstBaseline": The vlist will be positioned such that + * its baseline is aligned with the + * baseline of the first child. + * positionData is ignored. (this is + * equivalent to "shift" with + * positionData=0) + * - positionData: Data used in different ways depending on positionType + * - options: An Options object + * + */ +var makeVList = function(children, positionType, positionData, options) { + var depth; + var currPos; + var i; + if (positionType === "individualShift") { + var oldChildren = children; + children = [oldChildren[0]]; + + // Add in kerns to the list of children to get each element to be + // shifted to the correct specified shift + depth = -oldChildren[0].shift - oldChildren[0].elem.depth; + currPos = depth; + for (i = 1; i < oldChildren.length; i++) { + var diff = -oldChildren[i].shift - currPos - + oldChildren[i].elem.depth; + var size = diff - + (oldChildren[i - 1].elem.height + + oldChildren[i - 1].elem.depth); + + currPos = currPos + diff; + + children.push({type: "kern", size: size}); + children.push(oldChildren[i]); + } + } else if (positionType === "top") { + // We always start at the bottom, so calculate the bottom by adding up + // all the sizes + var bottom = positionData; + for (i = 0; i < children.length; i++) { + if (children[i].type === "kern") { + bottom -= children[i].size; + } else { + bottom -= children[i].elem.height + children[i].elem.depth; + } + } + depth = bottom; + } else if (positionType === "bottom") { + depth = -positionData; + } else if (positionType === "shift") { + depth = -children[0].elem.depth - positionData; + } else if (positionType === "firstBaseline") { + depth = -children[0].elem.depth; + } else { + depth = 0; + } + + // Make the fontSizer + var maxFontSize = 0; + for (i = 0; i < children.length; i++) { + if (children[i].type === "elem") { + maxFontSize = Math.max(maxFontSize, children[i].elem.maxFontSize); + } + } + var fontSizer = makeFontSizer(options, maxFontSize); + + // Create a new list of actual children at the correct offsets + var realChildren = []; + currPos = depth; + for (i = 0; i < children.length; i++) { + if (children[i].type === "kern") { + currPos += children[i].size; + } else { + var child = children[i].elem; + + var shift = -child.depth - currPos; + currPos += child.height + child.depth; + + var childWrap = makeSpan([], [fontSizer, child]); + childWrap.height -= shift; + childWrap.depth += shift; + childWrap.style.top = shift + "em"; + + realChildren.push(childWrap); + } + } + + // Add in an element at the end with no offset to fix the calculation of + // baselines in some browsers (namely IE, sometimes safari) + var baselineFix = makeSpan( + ["baseline-fix"], [fontSizer, new domTree.symbolNode("\u200b")]); + realChildren.push(baselineFix); + + var vlist = makeSpan(["vlist"], realChildren); + // Fix the final height and depth, in case there were kerns at the ends + // since the makeSpan calculation won't take that in to account. + vlist.height = Math.max(currPos, vlist.height); + vlist.depth = Math.max(-depth, vlist.depth); + return vlist; +}; + +// A table of size -> font size for the different sizing functions +var sizingMultiplier = { + size1: 0.5, + size2: 0.7, + size3: 0.8, + size4: 0.9, + size5: 1.0, + size6: 1.2, + size7: 1.44, + size8: 1.73, + size9: 2.07, + size10: 2.49 +}; + +// A map of spacing functions to their attributes, like size and corresponding +// CSS class +var spacingFunctions = { + "\\qquad": { + size: "2em", + className: "qquad" + }, + "\\quad": { + size: "1em", + className: "quad" + }, + "\\enspace": { + size: "0.5em", + className: "enspace" + }, + "\\;": { + size: "0.277778em", + className: "thickspace" + }, + "\\:": { + size: "0.22222em", + className: "mediumspace" + }, + "\\,": { + size: "0.16667em", + className: "thinspace" + }, + "\\!": { + size: "-0.16667em", + className: "negativethinspace" + } +}; + +/** + * Maps TeX font commands to objects containing: + * - variant: string used for "mathvariant" attribute in buildMathML.js + * - fontName: the "style" parameter to fontMetrics.getCharacterMetrics + */ +// A map between tex font commands an MathML mathvariant attribute values +var fontMap = { + // styles + "mathbf": { + variant: "bold", + fontName: "Main-Bold" + }, + "mathrm": { + variant: "normal", + fontName: "Main-Regular" + }, + + // "mathit" is missing because it requires the use of two fonts: Main-Italic + // and Math-Italic. This is handled by a special case in makeOrd which ends + // up calling mathit. + + // families + "mathbb": { + variant: "double-struck", + fontName: "AMS-Regular" + }, + "mathcal": { + variant: "script", + fontName: "Caligraphic-Regular" + }, + "mathfrak": { + variant: "fraktur", + fontName: "Fraktur-Regular" + }, + "mathscr": { + variant: "script", + fontName: "Script-Regular" + }, + "mathsf": { + variant: "sans-serif", + fontName: "SansSerif-Regular" + }, + "mathtt": { + variant: "monospace", + fontName: "Typewriter-Regular" + } +}; + +module.exports = { + fontMap: fontMap, + makeSymbol: makeSymbol, + mathsym: mathsym, + makeSpan: makeSpan, + makeFragment: makeFragment, + makeVList: makeVList, + makeOrd: makeOrd, + sizingMultiplier: sizingMultiplier, + spacingFunctions: spacingFunctions +}; + +},{"./domTree":16,"./fontMetrics":18,"./symbols":24,"./utils":25}],12:[function(require,module,exports){ +/** + * This file does the main work of building a domTree structure from a parse + * tree. The entry point is the `buildHTML` function, which takes a parse tree. + * Then, the buildExpression, buildGroup, and various groupTypes functions are + * called, to produce a final HTML tree. + */ + +var ParseError = require("./ParseError"); +var Style = require("./Style"); + +var buildCommon = require("./buildCommon"); +var delimiter = require("./delimiter"); +var domTree = require("./domTree"); +var fontMetrics = require("./fontMetrics"); +var utils = require("./utils"); + +var makeSpan = buildCommon.makeSpan; + +/** + * Take a list of nodes, build them in order, and return a list of the built + * nodes. This function handles the `prev` node correctly, and passes the + * previous element from the list as the prev of the next element. + */ +var buildExpression = function(expression, options, prev) { + var groups = []; + for (var i = 0; i < expression.length; i++) { + var group = expression[i]; + groups.push(buildGroup(group, options, prev)); + prev = group; + } + return groups; +}; + +// List of types used by getTypeOfGroup, +// see https://github.com/Khan/KaTeX/wiki/Examining-TeX#group-types +var groupToType = { + mathord: "mord", + textord: "mord", + bin: "mbin", + rel: "mrel", + text: "mord", + open: "mopen", + close: "mclose", + inner: "minner", + genfrac: "mord", + array: "mord", + spacing: "mord", + punct: "mpunct", + ordgroup: "mord", + op: "mop", + katex: "mord", + overline: "mord", + rule: "mord", + leftright: "minner", + sqrt: "mord", + accent: "mord" +}; + +/** + * Gets the final math type of an expression, given its group type. This type is + * used to determine spacing between elements, and affects bin elements by + * causing them to change depending on what types are around them. This type + * must be attached to the outermost node of an element as a CSS class so that + * spacing with its surrounding elements works correctly. + * + * Some elements can be mapped one-to-one from group type to math type, and + * those are listed in the `groupToType` table. + * + * Others (usually elements that wrap around other elements) often have + * recursive definitions, and thus call `getTypeOfGroup` on their inner + * elements. + */ +var getTypeOfGroup = function(group) { + if (group == null) { + // Like when typesetting $^3$ + return groupToType.mathord; + } else if (group.type === "supsub") { + return getTypeOfGroup(group.value.base); + } else if (group.type === "llap" || group.type === "rlap") { + return getTypeOfGroup(group.value); + } else if (group.type === "color") { + return getTypeOfGroup(group.value.value); + } else if (group.type === "sizing") { + return getTypeOfGroup(group.value.value); + } else if (group.type === "styling") { + return getTypeOfGroup(group.value.value); + } else if (group.type === "delimsizing") { + return groupToType[group.value.delimType]; + } else { + return groupToType[group.type]; + } +}; + +/** + * Sometimes, groups perform special rules when they have superscripts or + * subscripts attached to them. This function lets the `supsub` group know that + * its inner element should handle the superscripts and subscripts instead of + * handling them itself. + */ +var shouldHandleSupSub = function(group, options) { + if (!group) { + return false; + } else if (group.type === "op") { + // Operators handle supsubs differently when they have limits + // (e.g. `\displaystyle\sum_2^3`) + return group.value.limits && + (options.style.size === Style.DISPLAY.size || group.value.alwaysHandleSupSub); + } else if (group.type === "accent") { + return isCharacterBox(group.value.base); + } else { + return null; + } +}; + +/** + * Sometimes we want to pull out the innermost element of a group. In most + * cases, this will just be the group itself, but when ordgroups and colors have + * a single element, we want to pull that out. + */ +var getBaseElem = function(group) { + if (!group) { + return false; + } else if (group.type === "ordgroup") { + if (group.value.length === 1) { + return getBaseElem(group.value[0]); + } else { + return group; + } + } else if (group.type === "color") { + if (group.value.value.length === 1) { + return getBaseElem(group.value.value[0]); + } else { + return group; + } + } else { + return group; + } +}; + +/** + * TeXbook algorithms often reference "character boxes", which are simply groups + * with a single character in them. To decide if something is a character box, + * we find its innermost group, and see if it is a single character. + */ +var isCharacterBox = function(group) { + var baseElem = getBaseElem(group); + + // These are all they types of groups which hold single characters + return baseElem.type === "mathord" || + baseElem.type === "textord" || + baseElem.type === "bin" || + baseElem.type === "rel" || + baseElem.type === "inner" || + baseElem.type === "open" || + baseElem.type === "close" || + baseElem.type === "punct"; +}; + +var makeNullDelimiter = function(options) { + return makeSpan([ + "sizing", "reset-" + options.size, "size5", + options.style.reset(), Style.TEXT.cls(), + "nulldelimiter" + ]); +}; + +/** + * This is a map of group types to the function used to handle that type. + * Simpler types come at the beginning, while complicated types come afterwards. + */ +var groupTypes = { + mathord: function(group, options, prev) { + return buildCommon.makeOrd(group, options, "mathord"); + }, + + textord: function(group, options, prev) { + return buildCommon.makeOrd(group, options, "textord"); + }, + + bin: function(group, options, prev) { + var className = "mbin"; + // Pull out the most recent element. Do some special handling to find + // things at the end of a \color group. Note that we don't use the same + // logic for ordgroups (which count as ords). + var prevAtom = prev; + while (prevAtom && prevAtom.type === "color") { + var atoms = prevAtom.value.value; + prevAtom = atoms[atoms.length - 1]; + } + // See TeXbook pg. 442-446, Rules 5 and 6, and the text before Rule 19. + // Here, we determine whether the bin should turn into an ord. We + // currently only apply Rule 5. + if (!prev || utils.contains(["mbin", "mopen", "mrel", "mop", "mpunct"], + getTypeOfGroup(prevAtom))) { + group.type = "textord"; + className = "mord"; + } + + return buildCommon.mathsym( + group.value, group.mode, options.getColor(), [className]); + }, + + rel: function(group, options, prev) { + return buildCommon.mathsym( + group.value, group.mode, options.getColor(), ["mrel"]); + }, + + open: function(group, options, prev) { + return buildCommon.mathsym( + group.value, group.mode, options.getColor(), ["mopen"]); + }, + + close: function(group, options, prev) { + return buildCommon.mathsym( + group.value, group.mode, options.getColor(), ["mclose"]); + }, + + inner: function(group, options, prev) { + return buildCommon.mathsym( + group.value, group.mode, options.getColor(), ["minner"]); + }, + + punct: function(group, options, prev) { + return buildCommon.mathsym( + group.value, group.mode, options.getColor(), ["mpunct"]); + }, + + ordgroup: function(group, options, prev) { + return makeSpan( + ["mord", options.style.cls()], + buildExpression(group.value, options.reset()) + ); + }, + + text: function(group, options, prev) { + return makeSpan(["text", "mord", options.style.cls()], + buildExpression(group.value.body, options.reset())); + }, + + color: function(group, options, prev) { + var elements = buildExpression( + group.value.value, + options.withColor(group.value.color), + prev + ); + + // \color isn't supposed to affect the type of the elements it contains. + // To accomplish this, we wrap the results in a fragment, so the inner + // elements will be able to directly interact with their neighbors. For + // example, `\color{red}{2 +} 3` has the same spacing as `2 + 3` + return new buildCommon.makeFragment(elements); + }, + + supsub: function(group, options, prev) { + // Superscript and subscripts are handled in the TeXbook on page + // 445-446, rules 18(a-f). + + // Here is where we defer to the inner group if it should handle + // superscripts and subscripts itself. + if (shouldHandleSupSub(group.value.base, options)) { + return groupTypes[group.value.base.type](group, options, prev); + } + + var base = buildGroup(group.value.base, options.reset()); + var supmid, submid, sup, sub; + + if (group.value.sup) { + sup = buildGroup(group.value.sup, + options.withStyle(options.style.sup())); + supmid = makeSpan( + [options.style.reset(), options.style.sup().cls()], [sup]); + } + + if (group.value.sub) { + sub = buildGroup(group.value.sub, + options.withStyle(options.style.sub())); + submid = makeSpan( + [options.style.reset(), options.style.sub().cls()], [sub]); + } + + // Rule 18a + var supShift, subShift; + if (isCharacterBox(group.value.base)) { + supShift = 0; + subShift = 0; + } else { + supShift = base.height - fontMetrics.metrics.supDrop; + subShift = base.depth + fontMetrics.metrics.subDrop; + } + + // Rule 18c + var minSupShift; + if (options.style === Style.DISPLAY) { + minSupShift = fontMetrics.metrics.sup1; + } else if (options.style.cramped) { + minSupShift = fontMetrics.metrics.sup3; + } else { + minSupShift = fontMetrics.metrics.sup2; + } + + // scriptspace is a font-size-independent size, so scale it + // appropriately + var multiplier = Style.TEXT.sizeMultiplier * + options.style.sizeMultiplier; + var scriptspace = + (0.5 / fontMetrics.metrics.ptPerEm) / multiplier + "em"; + + var supsub; + if (!group.value.sup) { + // Rule 18b + subShift = Math.max( + subShift, fontMetrics.metrics.sub1, + sub.height - 0.8 * fontMetrics.metrics.xHeight); + + supsub = buildCommon.makeVList([ + {type: "elem", elem: submid} + ], "shift", subShift, options); + + supsub.children[0].style.marginRight = scriptspace; + + // Subscripts shouldn't be shifted by the base's italic correction. + // Account for that by shifting the subscript back the appropriate + // amount. Note we only do this when the base is a single symbol. + if (base instanceof domTree.symbolNode) { + supsub.children[0].style.marginLeft = -base.italic + "em"; + } + } else if (!group.value.sub) { + // Rule 18c, d + supShift = Math.max(supShift, minSupShift, + sup.depth + 0.25 * fontMetrics.metrics.xHeight); + + supsub = buildCommon.makeVList([ + {type: "elem", elem: supmid} + ], "shift", -supShift, options); + + supsub.children[0].style.marginRight = scriptspace; + } else { + supShift = Math.max( + supShift, minSupShift, + sup.depth + 0.25 * fontMetrics.metrics.xHeight); + subShift = Math.max(subShift, fontMetrics.metrics.sub2); + + var ruleWidth = fontMetrics.metrics.defaultRuleThickness; + + // Rule 18e + if ((supShift - sup.depth) - (sub.height - subShift) < + 4 * ruleWidth) { + subShift = 4 * ruleWidth - (supShift - sup.depth) + sub.height; + var psi = 0.8 * fontMetrics.metrics.xHeight - + (supShift - sup.depth); + if (psi > 0) { + supShift += psi; + subShift -= psi; + } + } + + supsub = buildCommon.makeVList([ + {type: "elem", elem: submid, shift: subShift}, + {type: "elem", elem: supmid, shift: -supShift} + ], "individualShift", null, options); + + // See comment above about subscripts not being shifted + if (base instanceof domTree.symbolNode) { + supsub.children[0].style.marginLeft = -base.italic + "em"; + } + + supsub.children[0].style.marginRight = scriptspace; + supsub.children[1].style.marginRight = scriptspace; + } + + return makeSpan([getTypeOfGroup(group.value.base)], + [base, supsub]); + }, + + genfrac: function(group, options, prev) { + // Fractions are handled in the TeXbook on pages 444-445, rules 15(a-e). + // Figure out what style this fraction should be in based on the + // function used + var fstyle = options.style; + if (group.value.size === "display") { + fstyle = Style.DISPLAY; + } else if (group.value.size === "text") { + fstyle = Style.TEXT; + } + + var nstyle = fstyle.fracNum(); + var dstyle = fstyle.fracDen(); + + var numer = buildGroup(group.value.numer, options.withStyle(nstyle)); + var numerreset = makeSpan([fstyle.reset(), nstyle.cls()], [numer]); + + var denom = buildGroup(group.value.denom, options.withStyle(dstyle)); + var denomreset = makeSpan([fstyle.reset(), dstyle.cls()], [denom]); + + var ruleWidth; + if (group.value.hasBarLine) { + ruleWidth = fontMetrics.metrics.defaultRuleThickness / + options.style.sizeMultiplier; + } else { + ruleWidth = 0; + } + + // Rule 15b + var numShift; + var clearance; + var denomShift; + if (fstyle.size === Style.DISPLAY.size) { + numShift = fontMetrics.metrics.num1; + if (ruleWidth > 0) { + clearance = 3 * ruleWidth; + } else { + clearance = 7 * fontMetrics.metrics.defaultRuleThickness; + } + denomShift = fontMetrics.metrics.denom1; + } else { + if (ruleWidth > 0) { + numShift = fontMetrics.metrics.num2; + clearance = ruleWidth; + } else { + numShift = fontMetrics.metrics.num3; + clearance = 3 * fontMetrics.metrics.defaultRuleThickness; + } + denomShift = fontMetrics.metrics.denom2; + } + + var frac; + if (ruleWidth === 0) { + // Rule 15c + var candiateClearance = + (numShift - numer.depth) - (denom.height - denomShift); + if (candiateClearance < clearance) { + numShift += 0.5 * (clearance - candiateClearance); + denomShift += 0.5 * (clearance - candiateClearance); + } + + frac = buildCommon.makeVList([ + {type: "elem", elem: denomreset, shift: denomShift}, + {type: "elem", elem: numerreset, shift: -numShift} + ], "individualShift", null, options); + } else { + // Rule 15d + var axisHeight = fontMetrics.metrics.axisHeight; + + if ((numShift - numer.depth) - (axisHeight + 0.5 * ruleWidth) < + clearance) { + numShift += + clearance - ((numShift - numer.depth) - + (axisHeight + 0.5 * ruleWidth)); + } + + if ((axisHeight - 0.5 * ruleWidth) - (denom.height - denomShift) < + clearance) { + denomShift += + clearance - ((axisHeight - 0.5 * ruleWidth) - + (denom.height - denomShift)); + } + + var mid = makeSpan( + [options.style.reset(), Style.TEXT.cls(), "frac-line"]); + // Manually set the height of the line because its height is + // created in CSS + mid.height = ruleWidth; + + var midShift = -(axisHeight - 0.5 * ruleWidth); + + frac = buildCommon.makeVList([ + {type: "elem", elem: denomreset, shift: denomShift}, + {type: "elem", elem: mid, shift: midShift}, + {type: "elem", elem: numerreset, shift: -numShift} + ], "individualShift", null, options); + } + + // Since we manually change the style sometimes (with \dfrac or \tfrac), + // account for the possible size change here. + frac.height *= fstyle.sizeMultiplier / options.style.sizeMultiplier; + frac.depth *= fstyle.sizeMultiplier / options.style.sizeMultiplier; + + // Rule 15e + var delimSize; + if (fstyle.size === Style.DISPLAY.size) { + delimSize = fontMetrics.metrics.delim1; + } else { + delimSize = fontMetrics.metrics.getDelim2(fstyle); + } + + var leftDelim, rightDelim; + if (group.value.leftDelim == null) { + leftDelim = makeNullDelimiter(options); + } else { + leftDelim = delimiter.customSizedDelim( + group.value.leftDelim, delimSize, true, + options.withStyle(fstyle), group.mode); + } + if (group.value.rightDelim == null) { + rightDelim = makeNullDelimiter(options); + } else { + rightDelim = delimiter.customSizedDelim( + group.value.rightDelim, delimSize, true, + options.withStyle(fstyle), group.mode); + } + + return makeSpan( + ["mord", options.style.reset(), fstyle.cls()], + [leftDelim, makeSpan(["mfrac"], [frac]), rightDelim], + options.getColor()); + }, + + array: function(group, options, prev) { + var r, c; + var nr = group.value.body.length; + var nc = 0; + var body = new Array(nr); + + // Horizontal spacing + var pt = 1 / fontMetrics.metrics.ptPerEm; + var arraycolsep = 5 * pt; // \arraycolsep in article.cls + + // Vertical spacing + var baselineskip = 12 * pt; // see size10.clo + // Default \arraystretch from lttab.dtx + // TODO(gagern): may get redefined once we have user-defined macros + var arraystretch = utils.deflt(group.value.arraystretch, 1); + var arrayskip = arraystretch * baselineskip; + var arstrutHeight = 0.7 * arrayskip; // \strutbox in ltfsstrc.dtx and + var arstrutDepth = 0.3 * arrayskip; // \@arstrutbox in lttab.dtx + + var totalHeight = 0; + for (r = 0; r < group.value.body.length; ++r) { + var inrow = group.value.body[r]; + var height = arstrutHeight; // \@array adds an \@arstrut + var depth = arstrutDepth; // to each tow (via the template) + + if (nc < inrow.length) { + nc = inrow.length; + } + + var outrow = new Array(inrow.length); + for (c = 0; c < inrow.length; ++c) { + var elt = buildGroup(inrow[c], options); + if (depth < elt.depth) { + depth = elt.depth; + } + if (height < elt.height) { + height = elt.height; + } + outrow[c] = elt; + } + + var gap = 0; + if (group.value.rowGaps[r]) { + gap = group.value.rowGaps[r].value; + switch (gap.unit) { + case "em": + gap = gap.number; + break; + case "ex": + gap = gap.number * fontMetrics.metrics.emPerEx; + break; + default: + console.error("Can't handle unit " + gap.unit); + gap = 0; + } + if (gap > 0) { // \@argarraycr + gap += arstrutDepth; + if (depth < gap) { + depth = gap; // \@xargarraycr + } + gap = 0; + } + } + + outrow.height = height; + outrow.depth = depth; + totalHeight += height; + outrow.pos = totalHeight; + totalHeight += depth + gap; // \@yargarraycr + body[r] = outrow; + } + + var offset = totalHeight / 2 + fontMetrics.metrics.axisHeight; + var colDescriptions = group.value.cols || []; + var cols = []; + var colSep; + var colDescrNum; + for (c = 0, colDescrNum = 0; + // Continue while either there are more columns or more column + // descriptions, so trailing separators don't get lost. + c < nc || colDescrNum < colDescriptions.length; + ++c, ++colDescrNum) { + + var colDescr = colDescriptions[colDescrNum] || {}; + + var firstSeparator = true; + while (colDescr.type === "separator") { + // If there is more than one separator in a row, add a space + // between them. + if (!firstSeparator) { + colSep = makeSpan(["arraycolsep"], []); + colSep.style.width = + fontMetrics.metrics.doubleRuleSep + "em"; + cols.push(colSep); + } + + if (colDescr.separator === "|") { + var separator = makeSpan( + ["vertical-separator"], + []); + separator.style.height = totalHeight + "em"; + separator.style.verticalAlign = + -(totalHeight - offset) + "em"; + + cols.push(separator); + } else { + throw new ParseError( + "Invalid separator type: " + colDescr.separator); + } + + colDescrNum++; + colDescr = colDescriptions[colDescrNum] || {}; + firstSeparator = false; + } + + if (c >= nc) { + continue; + } + + var sepwidth; + if (c > 0 || group.value.hskipBeforeAndAfter) { + sepwidth = utils.deflt(colDescr.pregap, arraycolsep); + if (sepwidth !== 0) { + colSep = makeSpan(["arraycolsep"], []); + colSep.style.width = sepwidth + "em"; + cols.push(colSep); + } + } + + var col = []; + for (r = 0; r < nr; ++r) { + var row = body[r]; + var elem = row[c]; + if (!elem) { + continue; + } + var shift = row.pos - offset; + elem.depth = row.depth; + elem.height = row.height; + col.push({type: "elem", elem: elem, shift: shift}); + } + + col = buildCommon.makeVList(col, "individualShift", null, options); + col = makeSpan( + ["col-align-" + (colDescr.align || "c")], + [col]); + cols.push(col); + + if (c < nc - 1 || group.value.hskipBeforeAndAfter) { + sepwidth = utils.deflt(colDescr.postgap, arraycolsep); + if (sepwidth !== 0) { + colSep = makeSpan(["arraycolsep"], []); + colSep.style.width = sepwidth + "em"; + cols.push(colSep); + } + } + } + body = makeSpan(["mtable"], cols); + return makeSpan(["mord"], [body], options.getColor()); + }, + + spacing: function(group, options, prev) { + if (group.value === "\\ " || group.value === "\\space" || + group.value === " " || group.value === "~") { + // Spaces are generated by adding an actual space. Each of these + // things has an entry in the symbols table, so these will be turned + // into appropriate outputs. + return makeSpan( + ["mord", "mspace"], + [buildCommon.mathsym(group.value, group.mode)] + ); + } else { + // Other kinds of spaces are of arbitrary width. We use CSS to + // generate these. + return makeSpan( + ["mord", "mspace", + buildCommon.spacingFunctions[group.value].className]); + } + }, + + llap: function(group, options, prev) { + var inner = makeSpan( + ["inner"], [buildGroup(group.value.body, options.reset())]); + var fix = makeSpan(["fix"], []); + return makeSpan( + ["llap", options.style.cls()], [inner, fix]); + }, + + rlap: function(group, options, prev) { + var inner = makeSpan( + ["inner"], [buildGroup(group.value.body, options.reset())]); + var fix = makeSpan(["fix"], []); + return makeSpan( + ["rlap", options.style.cls()], [inner, fix]); + }, + + op: function(group, options, prev) { + // Operators are handled in the TeXbook pg. 443-444, rule 13(a). + var supGroup; + var subGroup; + var hasLimits = false; + if (group.type === "supsub" ) { + // If we have limits, supsub will pass us its group to handle. Pull + // out the superscript and subscript and set the group to the op in + // its base. + supGroup = group.value.sup; + subGroup = group.value.sub; + group = group.value.base; + hasLimits = true; + } + + // Most operators have a large successor symbol, but these don't. + var noSuccessor = [ + "\\smallint" + ]; + + var large = false; + if (options.style.size === Style.DISPLAY.size && + group.value.symbol && + !utils.contains(noSuccessor, group.value.body)) { + + // Most symbol operators get larger in displaystyle (rule 13) + large = true; + } + + var base; + var baseShift = 0; + var slant = 0; + if (group.value.symbol) { + // If this is a symbol, create the symbol. + var style = large ? "Size2-Regular" : "Size1-Regular"; + base = buildCommon.makeSymbol( + group.value.body, style, "math", options.getColor(), + ["op-symbol", large ? "large-op" : "small-op", "mop"]); + + // Shift the symbol so its center lies on the axis (rule 13). It + // appears that our fonts have the centers of the symbols already + // almost on the axis, so these numbers are very small. Note we + // don't actually apply this here, but instead it is used either in + // the vlist creation or separately when there are no limits. + baseShift = (base.height - base.depth) / 2 - + fontMetrics.metrics.axisHeight * + options.style.sizeMultiplier; + + // The slant of the symbol is just its italic correction. + slant = base.italic; + } else { + // Otherwise, this is a text operator. Build the text from the + // operator's name. + // TODO(emily): Add a space in the middle of some of these + // operators, like \limsup + var output = []; + for (var i = 1; i < group.value.body.length; i++) { + output.push(buildCommon.mathsym(group.value.body[i], group.mode)); + } + base = makeSpan(["mop"], output, options.getColor()); + } + + if (hasLimits) { + // IE 8 clips \int if it is in a display: inline-block. We wrap it + // in a new span so it is an inline, and works. + base = makeSpan([], [base]); + + var supmid, supKern, submid, subKern; + // We manually have to handle the superscripts and subscripts. This, + // aside from the kern calculations, is copied from supsub. + if (supGroup) { + var sup = buildGroup( + supGroup, options.withStyle(options.style.sup())); + supmid = makeSpan( + [options.style.reset(), options.style.sup().cls()], [sup]); + + supKern = Math.max( + fontMetrics.metrics.bigOpSpacing1, + fontMetrics.metrics.bigOpSpacing3 - sup.depth); + } + + if (subGroup) { + var sub = buildGroup( + subGroup, options.withStyle(options.style.sub())); + submid = makeSpan( + [options.style.reset(), options.style.sub().cls()], + [sub]); + + subKern = Math.max( + fontMetrics.metrics.bigOpSpacing2, + fontMetrics.metrics.bigOpSpacing4 - sub.height); + } + + // Build the final group as a vlist of the possible subscript, base, + // and possible superscript. + var finalGroup, top, bottom; + if (!supGroup) { + top = base.height - baseShift; + + finalGroup = buildCommon.makeVList([ + {type: "kern", size: fontMetrics.metrics.bigOpSpacing5}, + {type: "elem", elem: submid}, + {type: "kern", size: subKern}, + {type: "elem", elem: base} + ], "top", top, options); + + // Here, we shift the limits by the slant of the symbol. Note + // that we are supposed to shift the limits by 1/2 of the slant, + // but since we are centering the limits adding a full slant of + // margin will shift by 1/2 that. + finalGroup.children[0].style.marginLeft = -slant + "em"; + } else if (!subGroup) { + bottom = base.depth + baseShift; + + finalGroup = buildCommon.makeVList([ + {type: "elem", elem: base}, + {type: "kern", size: supKern}, + {type: "elem", elem: supmid}, + {type: "kern", size: fontMetrics.metrics.bigOpSpacing5} + ], "bottom", bottom, options); + + // See comment above about slants + finalGroup.children[1].style.marginLeft = slant + "em"; + } else if (!supGroup && !subGroup) { + // This case probably shouldn't occur (this would mean the + // supsub was sending us a group with no superscript or + // subscript) but be safe. + return base; + } else { + bottom = fontMetrics.metrics.bigOpSpacing5 + + submid.height + submid.depth + + subKern + + base.depth + baseShift; + + finalGroup = buildCommon.makeVList([ + {type: "kern", size: fontMetrics.metrics.bigOpSpacing5}, + {type: "elem", elem: submid}, + {type: "kern", size: subKern}, + {type: "elem", elem: base}, + {type: "kern", size: supKern}, + {type: "elem", elem: supmid}, + {type: "kern", size: fontMetrics.metrics.bigOpSpacing5} + ], "bottom", bottom, options); + + // See comment above about slants + finalGroup.children[0].style.marginLeft = -slant + "em"; + finalGroup.children[2].style.marginLeft = slant + "em"; + } + + return makeSpan(["mop", "op-limits"], [finalGroup]); + } else { + if (group.value.symbol) { + base.style.top = baseShift + "em"; + } + + return base; + } + }, + + katex: function(group, options, prev) { + // The KaTeX logo. The offsets for the K and a were chosen to look + // good, but the offsets for the T, E, and X were taken from the + // definition of \TeX in TeX (see TeXbook pg. 356) + var k = makeSpan( + ["k"], [buildCommon.mathsym("K", group.mode)]); + var a = makeSpan( + ["a"], [buildCommon.mathsym("A", group.mode)]); + + a.height = (a.height + 0.2) * 0.75; + a.depth = (a.height - 0.2) * 0.75; + + var t = makeSpan( + ["t"], [buildCommon.mathsym("T", group.mode)]); + var e = makeSpan( + ["e"], [buildCommon.mathsym("E", group.mode)]); + + e.height = (e.height - 0.2155); + e.depth = (e.depth + 0.2155); + + var x = makeSpan( + ["x"], [buildCommon.mathsym("X", group.mode)]); + + return makeSpan( + ["katex-logo", "mord"], [k, a, t, e, x], options.getColor()); + }, + + overline: function(group, options, prev) { + // Overlines are handled in the TeXbook pg 443, Rule 9. + + // Build the inner group in the cramped style. + var innerGroup = buildGroup(group.value.body, + options.withStyle(options.style.cramp())); + + var ruleWidth = fontMetrics.metrics.defaultRuleThickness / + options.style.sizeMultiplier; + + // Create the line above the body + var line = makeSpan( + [options.style.reset(), Style.TEXT.cls(), "overline-line"]); + line.height = ruleWidth; + line.maxFontSize = 1.0; + + // Generate the vlist, with the appropriate kerns + var vlist = buildCommon.makeVList([ + {type: "elem", elem: innerGroup}, + {type: "kern", size: 3 * ruleWidth}, + {type: "elem", elem: line}, + {type: "kern", size: ruleWidth} + ], "firstBaseline", null, options); + + return makeSpan(["overline", "mord"], [vlist], options.getColor()); + }, + + sqrt: function(group, options, prev) { + // Square roots are handled in the TeXbook pg. 443, Rule 11. + + // First, we do the same steps as in overline to build the inner group + // and line + var inner = buildGroup(group.value.body, + options.withStyle(options.style.cramp())); + + var ruleWidth = fontMetrics.metrics.defaultRuleThickness / + options.style.sizeMultiplier; + + var line = makeSpan( + [options.style.reset(), Style.TEXT.cls(), "sqrt-line"], [], + options.getColor()); + line.height = ruleWidth; + line.maxFontSize = 1.0; + + var phi = ruleWidth; + if (options.style.id < Style.TEXT.id) { + phi = fontMetrics.metrics.xHeight; + } + + // Calculate the clearance between the body and line + var lineClearance = ruleWidth + phi / 4; + + var innerHeight = + (inner.height + inner.depth) * options.style.sizeMultiplier; + var minDelimiterHeight = innerHeight + lineClearance + ruleWidth; + + // Create a \surd delimiter of the required minimum size + var delim = makeSpan(["sqrt-sign"], [ + delimiter.customSizedDelim("\\surd", minDelimiterHeight, + false, options, group.mode)], + options.getColor()); + + var delimDepth = (delim.height + delim.depth) - ruleWidth; + + // Adjust the clearance based on the delimiter size + if (delimDepth > inner.height + inner.depth + lineClearance) { + lineClearance = + (lineClearance + delimDepth - inner.height - inner.depth) / 2; + } + + // Shift the delimiter so that its top lines up with the top of the line + var delimShift = -(inner.height + lineClearance + ruleWidth) + delim.height; + delim.style.top = delimShift + "em"; + delim.height -= delimShift; + delim.depth += delimShift; + + // We add a special case here, because even when `inner` is empty, we + // still get a line. So, we use a simple heuristic to decide if we + // should omit the body entirely. (note this doesn't work for something + // like `\sqrt{\rlap{x}}`, but if someone is doing that they deserve for + // it not to work. + var body; + if (inner.height === 0 && inner.depth === 0) { + body = makeSpan(); + } else { + body = buildCommon.makeVList([ + {type: "elem", elem: inner}, + {type: "kern", size: lineClearance}, + {type: "elem", elem: line}, + {type: "kern", size: ruleWidth} + ], "firstBaseline", null, options); + } + + if (!group.value.index) { + return makeSpan(["sqrt", "mord"], [delim, body]); + } else { + // Handle the optional root index + + // The index is always in scriptscript style + var root = buildGroup( + group.value.index, + options.withStyle(Style.SCRIPTSCRIPT)); + var rootWrap = makeSpan( + [options.style.reset(), Style.SCRIPTSCRIPT.cls()], + [root]); + + // Figure out the height and depth of the inner part + var innerRootHeight = Math.max(delim.height, body.height); + var innerRootDepth = Math.max(delim.depth, body.depth); + + // The amount the index is shifted by. This is taken from the TeX + // source, in the definition of `\r@@t`. + var toShift = 0.6 * (innerRootHeight - innerRootDepth); + + // Build a VList with the superscript shifted up correctly + var rootVList = buildCommon.makeVList( + [{type: "elem", elem: rootWrap}], + "shift", -toShift, options); + // Add a class surrounding it so we can add on the appropriate + // kerning + var rootVListWrap = makeSpan(["root"], [rootVList]); + + return makeSpan(["sqrt", "mord"], [rootVListWrap, delim, body]); + } + }, + + sizing: function(group, options, prev) { + // Handle sizing operators like \Huge. Real TeX doesn't actually allow + // these functions inside of math expressions, so we do some special + // handling. + var inner = buildExpression(group.value.value, + options.withSize(group.value.size), prev); + + var span = makeSpan(["mord"], + [makeSpan(["sizing", "reset-" + options.size, group.value.size, + options.style.cls()], + inner)]); + + // Calculate the correct maxFontSize manually + var fontSize = buildCommon.sizingMultiplier[group.value.size]; + span.maxFontSize = fontSize * options.style.sizeMultiplier; + + return span; + }, + + styling: function(group, options, prev) { + // Style changes are handled in the TeXbook on pg. 442, Rule 3. + + // Figure out what style we're changing to. + var style = { + "display": Style.DISPLAY, + "text": Style.TEXT, + "script": Style.SCRIPT, + "scriptscript": Style.SCRIPTSCRIPT + }; + + var newStyle = style[group.value.style]; + + // Build the inner expression in the new style. + var inner = buildExpression( + group.value.value, options.withStyle(newStyle), prev); + + return makeSpan([options.style.reset(), newStyle.cls()], inner); + }, + + font: function(group, options, prev) { + var font = group.value.font; + return buildGroup(group.value.body, options.withFont(font), prev); + }, + + delimsizing: function(group, options, prev) { + var delim = group.value.value; + + if (delim === ".") { + // Empty delimiters still count as elements, even though they don't + // show anything. + return makeSpan([groupToType[group.value.delimType]]); + } + + // Use delimiter.sizedDelim to generate the delimiter. + return makeSpan( + [groupToType[group.value.delimType]], + [delimiter.sizedDelim( + delim, group.value.size, options, group.mode)]); + }, + + leftright: function(group, options, prev) { + // Build the inner expression + var inner = buildExpression(group.value.body, options.reset()); + + var innerHeight = 0; + var innerDepth = 0; + + // Calculate its height and depth + for (var i = 0; i < inner.length; i++) { + innerHeight = Math.max(inner[i].height, innerHeight); + innerDepth = Math.max(inner[i].depth, innerDepth); + } + + // The size of delimiters is the same, regardless of what style we are + // in. Thus, to correctly calculate the size of delimiter we need around + // a group, we scale down the inner size based on the size. + innerHeight *= options.style.sizeMultiplier; + innerDepth *= options.style.sizeMultiplier; + + var leftDelim; + if (group.value.left === ".") { + // Empty delimiters in \left and \right make null delimiter spaces. + leftDelim = makeNullDelimiter(options); + } else { + // Otherwise, use leftRightDelim to generate the correct sized + // delimiter. + leftDelim = delimiter.leftRightDelim( + group.value.left, innerHeight, innerDepth, options, + group.mode); + } + // Add it to the beginning of the expression + inner.unshift(leftDelim); + + var rightDelim; + // Same for the right delimiter + if (group.value.right === ".") { + rightDelim = makeNullDelimiter(options); + } else { + rightDelim = delimiter.leftRightDelim( + group.value.right, innerHeight, innerDepth, options, + group.mode); + } + // Add it to the end of the expression. + inner.push(rightDelim); + + return makeSpan( + ["minner", options.style.cls()], inner, options.getColor()); + }, + + rule: function(group, options, prev) { + // Make an empty span for the rule + var rule = makeSpan(["mord", "rule"], [], options.getColor()); + + // Calculate the shift, width, and height of the rule, and account for units + var shift = 0; + if (group.value.shift) { + shift = group.value.shift.number; + if (group.value.shift.unit === "ex") { + shift *= fontMetrics.metrics.xHeight; + } + } + + var width = group.value.width.number; + if (group.value.width.unit === "ex") { + width *= fontMetrics.metrics.xHeight; + } + + var height = group.value.height.number; + if (group.value.height.unit === "ex") { + height *= fontMetrics.metrics.xHeight; + } + + // The sizes of rules are absolute, so make it larger if we are in a + // smaller style. + shift /= options.style.sizeMultiplier; + width /= options.style.sizeMultiplier; + height /= options.style.sizeMultiplier; + + // Style the rule to the right size + rule.style.borderRightWidth = width + "em"; + rule.style.borderTopWidth = height + "em"; + rule.style.bottom = shift + "em"; + + // Record the height and width + rule.width = width; + rule.height = height + shift; + rule.depth = -shift; + + return rule; + }, + + accent: function(group, options, prev) { + // Accents are handled in the TeXbook pg. 443, rule 12. + var base = group.value.base; + + var supsubGroup; + if (group.type === "supsub") { + // If our base is a character box, and we have superscripts and + // subscripts, the supsub will defer to us. In particular, we want + // to attach the superscripts and subscripts to the inner body (so + // that the position of the superscripts and subscripts won't be + // affected by the height of the accent). We accomplish this by + // sticking the base of the accent into the base of the supsub, and + // rendering that, while keeping track of where the accent is. + + // The supsub group is the group that was passed in + var supsub = group; + // The real accent group is the base of the supsub group + group = supsub.value.base; + // The character box is the base of the accent group + base = group.value.base; + // Stick the character box into the base of the supsub group + supsub.value.base = base; + + // Rerender the supsub group with its new base, and store that + // result. + supsubGroup = buildGroup( + supsub, options.reset(), prev); + } + + // Build the base group + var body = buildGroup( + base, options.withStyle(options.style.cramp())); + + // Calculate the skew of the accent. This is based on the line "If the + // nucleus is not a single character, let s = 0; otherwise set s to the + // kern amount for the nucleus followed by the \skewchar of its font." + // Note that our skew metrics are just the kern between each character + // and the skewchar. + var skew; + if (isCharacterBox(base)) { + // If the base is a character box, then we want the skew of the + // innermost character. To do that, we find the innermost character: + var baseChar = getBaseElem(base); + // Then, we render its group to get the symbol inside it + var baseGroup = buildGroup( + baseChar, options.withStyle(options.style.cramp())); + // Finally, we pull the skew off of the symbol. + skew = baseGroup.skew; + // Note that we now throw away baseGroup, because the layers we + // removed with getBaseElem might contain things like \color which + // we can't get rid of. + // TODO(emily): Find a better way to get the skew + } else { + skew = 0; + } + + // calculate the amount of space between the body and the accent + var clearance = Math.min(body.height, fontMetrics.metrics.xHeight); + + // Build the accent + var accent = buildCommon.makeSymbol( + group.value.accent, "Main-Regular", "math", options.getColor()); + // Remove the italic correction of the accent, because it only serves to + // shift the accent over to a place we don't want. + accent.italic = 0; + + // The \vec character that the fonts use is a combining character, and + // thus shows up much too far to the left. To account for this, we add a + // specific class which shifts the accent over to where we want it. + // TODO(emily): Fix this in a better way, like by changing the font + var vecClass = group.value.accent === "\\vec" ? "accent-vec" : null; + + var accentBody = makeSpan(["accent-body", vecClass], [ + makeSpan([], [accent])]); + + accentBody = buildCommon.makeVList([ + {type: "elem", elem: body}, + {type: "kern", size: -clearance}, + {type: "elem", elem: accentBody} + ], "firstBaseline", null, options); + + // Shift the accent over by the skew. Note we shift by twice the skew + // because we are centering the accent, so by adding 2*skew to the left, + // we shift it to the right by 1*skew. + accentBody.children[1].style.marginLeft = 2 * skew + "em"; + + var accentWrap = makeSpan(["mord", "accent"], [accentBody]); + + if (supsubGroup) { + // Here, we replace the "base" child of the supsub with our newly + // generated accent. + supsubGroup.children[0] = accentWrap; + + // Since we don't rerun the height calculation after replacing the + // accent, we manually recalculate height. + supsubGroup.height = Math.max(accentWrap.height, supsubGroup.height); + + // Accents should always be ords, even when their innards are not. + supsubGroup.classes[0] = "mord"; + + return supsubGroup; + } else { + return accentWrap; + } + }, + + phantom: function(group, options, prev) { + var elements = buildExpression( + group.value.value, + options.withPhantom(), + prev + ); + + // \phantom isn't supposed to affect the elements it contains. + // See "color" for more details. + return new buildCommon.makeFragment(elements); + } +}; + +/** + * buildGroup is the function that takes a group and calls the correct groupType + * function for it. It also handles the interaction of size and style changes + * between parents and children. + */ +var buildGroup = function(group, options, prev) { + if (!group) { + return makeSpan(); + } + + if (groupTypes[group.type]) { + // Call the groupTypes function + var groupNode = groupTypes[group.type](group, options, prev); + var multiplier; + + // If the style changed between the parent and the current group, + // account for the size difference + if (options.style !== options.parentStyle) { + multiplier = options.style.sizeMultiplier / + options.parentStyle.sizeMultiplier; + + groupNode.height *= multiplier; + groupNode.depth *= multiplier; + } + + // If the size changed between the parent and the current group, account + // for that size difference. + if (options.size !== options.parentSize) { + multiplier = buildCommon.sizingMultiplier[options.size] / + buildCommon.sizingMultiplier[options.parentSize]; + + groupNode.height *= multiplier; + groupNode.depth *= multiplier; + } + + return groupNode; + } else { + throw new ParseError( + "Got group of unknown type: '" + group.type + "'"); + } +}; + +/** + * Take an entire parse tree, and build it into an appropriate set of HTML + * nodes. + */ +var buildHTML = function(tree, options) { + // buildExpression is destructive, so we need to make a clone + // of the incoming tree so that it isn't accidentally changed + tree = JSON.parse(JSON.stringify(tree)); + + // Build the expression contained in the tree + var expression = buildExpression(tree, options); + var body = makeSpan(["base", options.style.cls()], expression); + + // Add struts, which ensure that the top of the HTML element falls at the + // height of the expression, and the bottom of the HTML element falls at the + // depth of the expression. + var topStrut = makeSpan(["strut"]); + var bottomStrut = makeSpan(["strut", "bottom"]); + + topStrut.style.height = body.height + "em"; + bottomStrut.style.height = (body.height + body.depth) + "em"; + // We'd like to use `vertical-align: top` but in IE 9 this lowers the + // baseline of the box to the bottom of this strut (instead staying in the + // normal place) so we use an absolute value for vertical-align instead + bottomStrut.style.verticalAlign = -body.depth + "em"; + + // Wrap the struts and body together + var htmlNode = makeSpan(["katex-html"], [topStrut, bottomStrut, body]); + + htmlNode.setAttribute("aria-hidden", "true"); + + return htmlNode; +}; + +module.exports = buildHTML; + +},{"./ParseError":7,"./Style":10,"./buildCommon":11,"./delimiter":15,"./domTree":16,"./fontMetrics":18,"./utils":25}],13:[function(require,module,exports){ +/** + * This file converts a parse tree into a cooresponding MathML tree. The main + * entry point is the `buildMathML` function, which takes a parse tree from the + * parser. + */ + +var buildCommon = require("./buildCommon"); +var fontMetrics = require("./fontMetrics"); +var mathMLTree = require("./mathMLTree"); +var ParseError = require("./ParseError"); +var symbols = require("./symbols"); +var utils = require("./utils"); + +var makeSpan = buildCommon.makeSpan; +var fontMap = buildCommon.fontMap; + +/** + * Takes a symbol and converts it into a MathML text node after performing + * optional replacement from symbols.js. + */ +var makeText = function(text, mode) { + if (symbols[mode][text] && symbols[mode][text].replace) { + text = symbols[mode][text].replace; + } + + return new mathMLTree.TextNode(text); +}; + +/** + * Returns the math variant as a string or null if none is required. + */ +var getVariant = function(group, options) { + var font = options.font; + if (!font) { + return null; + } + + var mode = group.mode; + if (font === "mathit") { + return "italic"; + } + + var value = group.value; + if (utils.contains(["\\imath", "\\jmath"], value)) { + return null; + } + + if (symbols[mode][value] && symbols[mode][value].replace) { + value = symbols[mode][value].replace; + } + + var fontName = fontMap[font].fontName; + if (fontMetrics.getCharacterMetrics(value, fontName)) { + return fontMap[options.font].variant; + } + + return null; +}; + +/** + * Functions for handling the different types of groups found in the parse + * tree. Each function should take a parse group and return a MathML node. + */ +var groupTypes = { + mathord: function(group, options) { + var node = new mathMLTree.MathNode( + "mi", + [makeText(group.value, group.mode)]); + + var variant = getVariant(group, options); + if (variant) { + node.setAttribute("mathvariant", variant); + } + return node; + }, + + textord: function(group, options) { + var text = makeText(group.value, group.mode); + + var variant = getVariant(group, options) || "normal"; + + var node; + if (/[0-9]/.test(group.value)) { + // TODO(kevinb) merge adjacent nodes + // do it as a post processing step + node = new mathMLTree.MathNode("mn", [text]); + if (options.font) { + node.setAttribute("mathvariant", variant); + } + } else { + node = new mathMLTree.MathNode("mi", [text]); + node.setAttribute("mathvariant", variant); + } + + return node; + }, + + bin: function(group) { + var node = new mathMLTree.MathNode( + "mo", [makeText(group.value, group.mode)]); + + return node; + }, + + rel: function(group) { + var node = new mathMLTree.MathNode( + "mo", [makeText(group.value, group.mode)]); + + return node; + }, + + open: function(group) { + var node = new mathMLTree.MathNode( + "mo", [makeText(group.value, group.mode)]); + + return node; + }, + + close: function(group) { + var node = new mathMLTree.MathNode( + "mo", [makeText(group.value, group.mode)]); + + return node; + }, + + inner: function(group) { + var node = new mathMLTree.MathNode( + "mo", [makeText(group.value, group.mode)]); + + return node; + }, + + punct: function(group) { + var node = new mathMLTree.MathNode( + "mo", [makeText(group.value, group.mode)]); + + node.setAttribute("separator", "true"); + + return node; + }, + + ordgroup: function(group, options) { + var inner = buildExpression(group.value, options); + + var node = new mathMLTree.MathNode("mrow", inner); + + return node; + }, + + text: function(group, options) { + var inner = buildExpression(group.value.body, options); + + var node = new mathMLTree.MathNode("mtext", inner); + + return node; + }, + + color: function(group, options) { + var inner = buildExpression(group.value.value, options); + + var node = new mathMLTree.MathNode("mstyle", inner); + + node.setAttribute("mathcolor", group.value.color); + + return node; + }, + + supsub: function(group, options) { + var children = [buildGroup(group.value.base, options)]; + + if (group.value.sub) { + children.push(buildGroup(group.value.sub, options)); + } + + if (group.value.sup) { + children.push(buildGroup(group.value.sup, options)); + } + + var nodeType; + if (!group.value.sub) { + nodeType = "msup"; + } else if (!group.value.sup) { + nodeType = "msub"; + } else { + nodeType = "msubsup"; + } + + var node = new mathMLTree.MathNode(nodeType, children); + + return node; + }, + + genfrac: function(group, options) { + var node = new mathMLTree.MathNode( + "mfrac", + [buildGroup(group.value.numer, options), + buildGroup(group.value.denom, options)]); + + if (!group.value.hasBarLine) { + node.setAttribute("linethickness", "0px"); + } + + if (group.value.leftDelim != null || group.value.rightDelim != null) { + var withDelims = []; + + if (group.value.leftDelim != null) { + var leftOp = new mathMLTree.MathNode( + "mo", [new mathMLTree.TextNode(group.value.leftDelim)]); + + leftOp.setAttribute("fence", "true"); + + withDelims.push(leftOp); + } + + withDelims.push(node); + + if (group.value.rightDelim != null) { + var rightOp = new mathMLTree.MathNode( + "mo", [new mathMLTree.TextNode(group.value.rightDelim)]); + + rightOp.setAttribute("fence", "true"); + + withDelims.push(rightOp); + } + + var outerNode = new mathMLTree.MathNode("mrow", withDelims); + + return outerNode; + } + + return node; + }, + + array: function(group, options) { + return new mathMLTree.MathNode( + "mtable", group.value.body.map(function(row) { + return new mathMLTree.MathNode( + "mtr", row.map(function(cell) { + return new mathMLTree.MathNode( + "mtd", [buildGroup(cell, options)]); + })); + })); + }, + + sqrt: function(group, options) { + var node; + if (group.value.index) { + node = new mathMLTree.MathNode( + "mroot", [ + buildGroup(group.value.body, options), + buildGroup(group.value.index, options) + ]); + } else { + node = new mathMLTree.MathNode( + "msqrt", [buildGroup(group.value.body, options)]); + } + + return node; + }, + + leftright: function(group, options) { + var inner = buildExpression(group.value.body, options); + + if (group.value.left !== ".") { + var leftNode = new mathMLTree.MathNode( + "mo", [makeText(group.value.left, group.mode)]); + + leftNode.setAttribute("fence", "true"); + + inner.unshift(leftNode); + } + + if (group.value.right !== ".") { + var rightNode = new mathMLTree.MathNode( + "mo", [makeText(group.value.right, group.mode)]); + + rightNode.setAttribute("fence", "true"); + + inner.push(rightNode); + } + + var outerNode = new mathMLTree.MathNode("mrow", inner); + + return outerNode; + }, + + accent: function(group, options) { + var accentNode = new mathMLTree.MathNode( + "mo", [makeText(group.value.accent, group.mode)]); + + var node = new mathMLTree.MathNode( + "mover", + [buildGroup(group.value.base, options), + accentNode]); + + node.setAttribute("accent", "true"); + + return node; + }, + + spacing: function(group) { + var node; + + if (group.value === "\\ " || group.value === "\\space" || + group.value === " " || group.value === "~") { + node = new mathMLTree.MathNode( + "mtext", [new mathMLTree.TextNode("\u00a0")]); + } else { + node = new mathMLTree.MathNode("mspace"); + + node.setAttribute( + "width", buildCommon.spacingFunctions[group.value].size); + } + + return node; + }, + + op: function(group) { + var node; + + // TODO(emily): handle big operators using the `largeop` attribute + + if (group.value.symbol) { + // This is a symbol. Just add the symbol. + node = new mathMLTree.MathNode( + "mo", [makeText(group.value.body, group.mode)]); + } else { + // This is a text operator. Add all of the characters from the + // operator's name. + // TODO(emily): Add a space in the middle of some of these + // operators, like \limsup. + node = new mathMLTree.MathNode( + "mi", [new mathMLTree.TextNode(group.value.body.slice(1))]); + } + + return node; + }, + + katex: function(group) { + var node = new mathMLTree.MathNode( + "mtext", [new mathMLTree.TextNode("KaTeX")]); + + return node; + }, + + font: function(group, options) { + var font = group.value.font; + return buildGroup(group.value.body, options.withFont(font)); + }, + + delimsizing: function(group) { + var children = []; + + if (group.value.value !== ".") { + children.push(makeText(group.value.value, group.mode)); + } + + var node = new mathMLTree.MathNode("mo", children); + + if (group.value.delimType === "open" || + group.value.delimType === "close") { + // Only some of the delimsizing functions act as fences, and they + // return "open" or "close" delimTypes. + node.setAttribute("fence", "true"); + } else { + // Explicitly disable fencing if it's not a fence, to override the + // defaults. + node.setAttribute("fence", "false"); + } + + return node; + }, + + styling: function(group, options) { + var inner = buildExpression(group.value.value, options); + + var node = new mathMLTree.MathNode("mstyle", inner); + + var styleAttributes = { + "display": ["0", "true"], + "text": ["0", "false"], + "script": ["1", "false"], + "scriptscript": ["2", "false"] + }; + + var attr = styleAttributes[group.value.style]; + + node.setAttribute("scriptlevel", attr[0]); + node.setAttribute("displaystyle", attr[1]); + + return node; + }, + + sizing: function(group, options) { + var inner = buildExpression(group.value.value, options); + + var node = new mathMLTree.MathNode("mstyle", inner); + + // TODO(emily): This doesn't produce the correct size for nested size + // changes, because we don't keep state of what style we're currently + // in, so we can't reset the size to normal before changing it. Now + // that we're passing an options parameter we should be able to fix + // this. + node.setAttribute( + "mathsize", buildCommon.sizingMultiplier[group.value.size] + "em"); + + return node; + }, + + overline: function(group, options) { + var operator = new mathMLTree.MathNode( + "mo", [new mathMLTree.TextNode("\u203e")]); + operator.setAttribute("stretchy", "true"); + + var node = new mathMLTree.MathNode( + "mover", + [buildGroup(group.value.body, options), + operator]); + node.setAttribute("accent", "true"); + + return node; + }, + + rule: function(group) { + // TODO(emily): Figure out if there's an actual way to draw black boxes + // in MathML. + var node = new mathMLTree.MathNode("mrow"); + + return node; + }, + + llap: function(group, options) { + var node = new mathMLTree.MathNode( + "mpadded", [buildGroup(group.value.body, options)]); + + node.setAttribute("lspace", "-1width"); + node.setAttribute("width", "0px"); + + return node; + }, + + rlap: function(group, options) { + var node = new mathMLTree.MathNode( + "mpadded", [buildGroup(group.value.body, options)]); + + node.setAttribute("width", "0px"); + + return node; + }, + + phantom: function(group, options, prev) { + var inner = buildExpression(group.value.value, options); + return new mathMLTree.MathNode("mphantom", inner); + } +}; + +/** + * Takes a list of nodes, builds them, and returns a list of the generated + * MathML nodes. A little simpler than the HTML version because we don't do any + * previous-node handling. + */ +var buildExpression = function(expression, options) { + var groups = []; + for (var i = 0; i < expression.length; i++) { + var group = expression[i]; + groups.push(buildGroup(group, options)); + } + return groups; +}; + +/** + * Takes a group from the parser and calls the appropriate groupTypes function + * on it to produce a MathML node. + */ +var buildGroup = function(group, options) { + if (!group) { + return new mathMLTree.MathNode("mrow"); + } + + if (groupTypes[group.type]) { + // Call the groupTypes function + return groupTypes[group.type](group, options); + } else { + throw new ParseError( + "Got group of unknown type: '" + group.type + "'"); + } +}; + +/** + * Takes a full parse tree and settings and builds a MathML representation of + * it. In particular, we put the elements from building the parse tree into a + * tag so we can also include that TeX source as an annotation. + * + * Note that we actually return a domTree element with a `` inside it so + * we can do appropriate styling. + */ +var buildMathML = function(tree, texExpression, options) { + var expression = buildExpression(tree, options); + + // Wrap up the expression in an mrow so it is presented in the semantics + // tag correctly. + var wrapper = new mathMLTree.MathNode("mrow", expression); + + // Build a TeX annotation of the source + var annotation = new mathMLTree.MathNode( + "annotation", [new mathMLTree.TextNode(texExpression)]); + + annotation.setAttribute("encoding", "application/x-tex"); + + var semantics = new mathMLTree.MathNode( + "semantics", [wrapper, annotation]); + + var math = new mathMLTree.MathNode("math", [semantics]); + + // You can't style nodes, so we wrap the node in a span. + return makeSpan(["katex-mathml"], [math]); +}; + +module.exports = buildMathML; + +},{"./ParseError":7,"./buildCommon":11,"./fontMetrics":18,"./mathMLTree":21,"./symbols":24,"./utils":25}],14:[function(require,module,exports){ +var buildHTML = require("./buildHTML"); +var buildMathML = require("./buildMathML"); +var buildCommon = require("./buildCommon"); +var Options = require("./Options"); +var Settings = require("./Settings"); +var Style = require("./Style"); + +var makeSpan = buildCommon.makeSpan; + +var buildTree = function(tree, expression, settings) { + settings = settings || new Settings({}); + + var startStyle = Style.TEXT; + if (settings.displayMode) { + startStyle = Style.DISPLAY; + } + + // Setup the default options + var options = new Options({ + style: startStyle, + size: "size5" + }); + + // `buildHTML` sometimes messes with the parse tree (like turning bins -> + // ords), so we build the MathML version first. + var mathMLNode = buildMathML(tree, expression, options); + var htmlNode = buildHTML(tree, options); + + var katexNode = makeSpan(["katex"], [ + mathMLNode, htmlNode + ]); + + if (settings.displayMode) { + return makeSpan(["katex-display"], [katexNode]); + } else { + return katexNode; + } +}; + +module.exports = buildTree; + +},{"./Options":6,"./Settings":9,"./Style":10,"./buildCommon":11,"./buildHTML":12,"./buildMathML":13}],15:[function(require,module,exports){ +/** + * This file deals with creating delimiters of various sizes. The TeXbook + * discusses these routines on page 441-442, in the "Another subroutine sets box + * x to a specified variable delimiter" paragraph. + * + * There are three main routines here. `makeSmallDelim` makes a delimiter in the + * normal font, but in either text, script, or scriptscript style. + * `makeLargeDelim` makes a delimiter in textstyle, but in one of the Size1, + * Size2, Size3, or Size4 fonts. `makeStackedDelim` makes a delimiter out of + * smaller pieces that are stacked on top of one another. + * + * The functions take a parameter `center`, which determines if the delimiter + * should be centered around the axis. + * + * Then, there are three exposed functions. `sizedDelim` makes a delimiter in + * one of the given sizes. This is used for things like `\bigl`. + * `customSizedDelim` makes a delimiter with a given total height+depth. It is + * called in places like `\sqrt`. `leftRightDelim` makes an appropriate + * delimiter which surrounds an expression of a given height an depth. It is + * used in `\left` and `\right`. + */ + +var ParseError = require("./ParseError"); +var Style = require("./Style"); + +var buildCommon = require("./buildCommon"); +var fontMetrics = require("./fontMetrics"); +var symbols = require("./symbols"); +var utils = require("./utils"); + +var makeSpan = buildCommon.makeSpan; + +/** + * Get the metrics for a given symbol and font, after transformation (i.e. + * after following replacement from symbols.js) + */ +var getMetrics = function(symbol, font) { + if (symbols.math[symbol] && symbols.math[symbol].replace) { + return fontMetrics.getCharacterMetrics( + symbols.math[symbol].replace, font); + } else { + return fontMetrics.getCharacterMetrics( + symbol, font); + } +}; + +/** + * Builds a symbol in the given font size (note size is an integer) + */ +var mathrmSize = function(value, size, mode) { + return buildCommon.makeSymbol(value, "Size" + size + "-Regular", mode); +}; + +/** + * Puts a delimiter span in a given style, and adds appropriate height, depth, + * and maxFontSizes. + */ +var styleWrap = function(delim, toStyle, options) { + var span = makeSpan( + ["style-wrap", options.style.reset(), toStyle.cls()], [delim]); + + var multiplier = toStyle.sizeMultiplier / options.style.sizeMultiplier; + + span.height *= multiplier; + span.depth *= multiplier; + span.maxFontSize = toStyle.sizeMultiplier; + + return span; +}; + +/** + * Makes a small delimiter. This is a delimiter that comes in the Main-Regular + * font, but is restyled to either be in textstyle, scriptstyle, or + * scriptscriptstyle. + */ +var makeSmallDelim = function(delim, style, center, options, mode) { + var text = buildCommon.makeSymbol(delim, "Main-Regular", mode); + + var span = styleWrap(text, style, options); + + if (center) { + var shift = + (1 - options.style.sizeMultiplier / style.sizeMultiplier) * + fontMetrics.metrics.axisHeight; + + span.style.top = shift + "em"; + span.height -= shift; + span.depth += shift; + } + + return span; +}; + +/** + * Makes a large delimiter. This is a delimiter that comes in the Size1, Size2, + * Size3, or Size4 fonts. It is always rendered in textstyle. + */ +var makeLargeDelim = function(delim, size, center, options, mode) { + var inner = mathrmSize(delim, size, mode); + + var span = styleWrap( + makeSpan(["delimsizing", "size" + size], + [inner], options.getColor()), + Style.TEXT, options); + + if (center) { + var shift = (1 - options.style.sizeMultiplier) * + fontMetrics.metrics.axisHeight; + + span.style.top = shift + "em"; + span.height -= shift; + span.depth += shift; + } + + return span; +}; + +/** + * Make an inner span with the given offset and in the given font. This is used + * in `makeStackedDelim` to make the stacking pieces for the delimiter. + */ +var makeInner = function(symbol, font, mode) { + var sizeClass; + // Apply the correct CSS class to choose the right font. + if (font === "Size1-Regular") { + sizeClass = "delim-size1"; + } else if (font === "Size4-Regular") { + sizeClass = "delim-size4"; + } + + var inner = makeSpan( + ["delimsizinginner", sizeClass], + [makeSpan([], [buildCommon.makeSymbol(symbol, font, mode)])]); + + // Since this will be passed into `makeVList` in the end, wrap the element + // in the appropriate tag that VList uses. + return {type: "elem", elem: inner}; +}; + +/** + * Make a stacked delimiter out of a given delimiter, with the total height at + * least `heightTotal`. This routine is mentioned on page 442 of the TeXbook. + */ +var makeStackedDelim = function(delim, heightTotal, center, options, mode) { + // There are four parts, the top, an optional middle, a repeated part, and a + // bottom. + var top, middle, repeat, bottom; + top = repeat = bottom = delim; + middle = null; + // Also keep track of what font the delimiters are in + var font = "Size1-Regular"; + + // We set the parts and font based on the symbol. Note that we use + // '\u23d0' instead of '|' and '\u2016' instead of '\\|' for the + // repeats of the arrows + if (delim === "\\uparrow") { + repeat = bottom = "\u23d0"; + } else if (delim === "\\Uparrow") { + repeat = bottom = "\u2016"; + } else if (delim === "\\downarrow") { + top = repeat = "\u23d0"; + } else if (delim === "\\Downarrow") { + top = repeat = "\u2016"; + } else if (delim === "\\updownarrow") { + top = "\\uparrow"; + repeat = "\u23d0"; + bottom = "\\downarrow"; + } else if (delim === "\\Updownarrow") { + top = "\\Uparrow"; + repeat = "\u2016"; + bottom = "\\Downarrow"; + } else if (delim === "[" || delim === "\\lbrack") { + top = "\u23a1"; + repeat = "\u23a2"; + bottom = "\u23a3"; + font = "Size4-Regular"; + } else if (delim === "]" || delim === "\\rbrack") { + top = "\u23a4"; + repeat = "\u23a5"; + bottom = "\u23a6"; + font = "Size4-Regular"; + } else if (delim === "\\lfloor") { + repeat = top = "\u23a2"; + bottom = "\u23a3"; + font = "Size4-Regular"; + } else if (delim === "\\lceil") { + top = "\u23a1"; + repeat = bottom = "\u23a2"; + font = "Size4-Regular"; + } else if (delim === "\\rfloor") { + repeat = top = "\u23a5"; + bottom = "\u23a6"; + font = "Size4-Regular"; + } else if (delim === "\\rceil") { + top = "\u23a4"; + repeat = bottom = "\u23a5"; + font = "Size4-Regular"; + } else if (delim === "(") { + top = "\u239b"; + repeat = "\u239c"; + bottom = "\u239d"; + font = "Size4-Regular"; + } else if (delim === ")") { + top = "\u239e"; + repeat = "\u239f"; + bottom = "\u23a0"; + font = "Size4-Regular"; + } else if (delim === "\\{" || delim === "\\lbrace") { + top = "\u23a7"; + middle = "\u23a8"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\}" || delim === "\\rbrace") { + top = "\u23ab"; + middle = "\u23ac"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\lgroup") { + top = "\u23a7"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\rgroup") { + top = "\u23ab"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\lmoustache") { + top = "\u23a7"; + bottom = "\u23ad"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\rmoustache") { + top = "\u23ab"; + bottom = "\u23a9"; + repeat = "\u23aa"; + font = "Size4-Regular"; + } else if (delim === "\\surd") { + top = "\ue001"; + bottom = "\u23b7"; + repeat = "\ue000"; + font = "Size4-Regular"; + } + + // Get the metrics of the four sections + var topMetrics = getMetrics(top, font); + var topHeightTotal = topMetrics.height + topMetrics.depth; + var repeatMetrics = getMetrics(repeat, font); + var repeatHeightTotal = repeatMetrics.height + repeatMetrics.depth; + var bottomMetrics = getMetrics(bottom, font); + var bottomHeightTotal = bottomMetrics.height + bottomMetrics.depth; + var middleHeightTotal = 0; + var middleFactor = 1; + if (middle !== null) { + var middleMetrics = getMetrics(middle, font); + middleHeightTotal = middleMetrics.height + middleMetrics.depth; + middleFactor = 2; // repeat symmetrically above and below middle + } + + // Calcuate the minimal height that the delimiter can have. + // It is at least the size of the top, bottom, and optional middle combined. + var minHeight = topHeightTotal + bottomHeightTotal + middleHeightTotal; + + // Compute the number of copies of the repeat symbol we will need + var repeatCount = Math.ceil( + (heightTotal - minHeight) / (middleFactor * repeatHeightTotal)); + + // Compute the total height of the delimiter including all the symbols + var realHeightTotal = + minHeight + repeatCount * middleFactor * repeatHeightTotal; + + // The center of the delimiter is placed at the center of the axis. Note + // that in this context, "center" means that the delimiter should be + // centered around the axis in the current style, while normally it is + // centered around the axis in textstyle. + var axisHeight = fontMetrics.metrics.axisHeight; + if (center) { + axisHeight *= options.style.sizeMultiplier; + } + // Calculate the depth + var depth = realHeightTotal / 2 - axisHeight; + + // Now, we start building the pieces that will go into the vlist + + // Keep a list of the inner pieces + var inners = []; + + // Add the bottom symbol + inners.push(makeInner(bottom, font, mode)); + + var i; + if (middle === null) { + // Add that many symbols + for (i = 0; i < repeatCount; i++) { + inners.push(makeInner(repeat, font, mode)); + } + } else { + // When there is a middle bit, we need the middle part and two repeated + // sections + for (i = 0; i < repeatCount; i++) { + inners.push(makeInner(repeat, font, mode)); + } + inners.push(makeInner(middle, font, mode)); + for (i = 0; i < repeatCount; i++) { + inners.push(makeInner(repeat, font, mode)); + } + } + + // Add the top symbol + inners.push(makeInner(top, font, mode)); + + // Finally, build the vlist + var inner = buildCommon.makeVList(inners, "bottom", depth, options); + + return styleWrap( + makeSpan(["delimsizing", "mult"], [inner], options.getColor()), + Style.TEXT, options); +}; + +// There are three kinds of delimiters, delimiters that stack when they become +// too large +var stackLargeDelimiters = [ + "(", ")", "[", "\\lbrack", "]", "\\rbrack", + "\\{", "\\lbrace", "\\}", "\\rbrace", + "\\lfloor", "\\rfloor", "\\lceil", "\\rceil", + "\\surd" +]; + +// delimiters that always stack +var stackAlwaysDelimiters = [ + "\\uparrow", "\\downarrow", "\\updownarrow", + "\\Uparrow", "\\Downarrow", "\\Updownarrow", + "|", "\\|", "\\vert", "\\Vert", + "\\lvert", "\\rvert", "\\lVert", "\\rVert", + "\\lgroup", "\\rgroup", "\\lmoustache", "\\rmoustache" +]; + +// and delimiters that never stack +var stackNeverDelimiters = [ + "<", ">", "\\langle", "\\rangle", "/", "\\backslash" +]; + +// Metrics of the different sizes. Found by looking at TeX's output of +// $\bigl| // \Bigl| \biggl| \Biggl| \showlists$ +// Used to create stacked delimiters of appropriate sizes in makeSizedDelim. +var sizeToMaxHeight = [0, 1.2, 1.8, 2.4, 3.0]; + +/** + * Used to create a delimiter of a specific size, where `size` is 1, 2, 3, or 4. + */ +var makeSizedDelim = function(delim, size, options, mode) { + // < and > turn into \langle and \rangle in delimiters + if (delim === "<") { + delim = "\\langle"; + } else if (delim === ">") { + delim = "\\rangle"; + } + + // Sized delimiters are never centered. + if (utils.contains(stackLargeDelimiters, delim) || + utils.contains(stackNeverDelimiters, delim)) { + return makeLargeDelim(delim, size, false, options, mode); + } else if (utils.contains(stackAlwaysDelimiters, delim)) { + return makeStackedDelim( + delim, sizeToMaxHeight[size], false, options, mode); + } else { + throw new ParseError("Illegal delimiter: '" + delim + "'"); + } +}; + +/** + * There are three different sequences of delimiter sizes that the delimiters + * follow depending on the kind of delimiter. This is used when creating custom + * sized delimiters to decide whether to create a small, large, or stacked + * delimiter. + * + * In real TeX, these sequences aren't explicitly defined, but are instead + * defined inside the font metrics. Since there are only three sequences that + * are possible for the delimiters that TeX defines, it is easier to just encode + * them explicitly here. + */ + +// Delimiters that never stack try small delimiters and large delimiters only +var stackNeverDelimiterSequence = [ + {type: "small", style: Style.SCRIPTSCRIPT}, + {type: "small", style: Style.SCRIPT}, + {type: "small", style: Style.TEXT}, + {type: "large", size: 1}, + {type: "large", size: 2}, + {type: "large", size: 3}, + {type: "large", size: 4} +]; + +// Delimiters that always stack try the small delimiters first, then stack +var stackAlwaysDelimiterSequence = [ + {type: "small", style: Style.SCRIPTSCRIPT}, + {type: "small", style: Style.SCRIPT}, + {type: "small", style: Style.TEXT}, + {type: "stack"} +]; + +// Delimiters that stack when large try the small and then large delimiters, and +// stack afterwards +var stackLargeDelimiterSequence = [ + {type: "small", style: Style.SCRIPTSCRIPT}, + {type: "small", style: Style.SCRIPT}, + {type: "small", style: Style.TEXT}, + {type: "large", size: 1}, + {type: "large", size: 2}, + {type: "large", size: 3}, + {type: "large", size: 4}, + {type: "stack"} +]; + +/** + * Get the font used in a delimiter based on what kind of delimiter it is. + */ +var delimTypeToFont = function(type) { + if (type.type === "small") { + return "Main-Regular"; + } else if (type.type === "large") { + return "Size" + type.size + "-Regular"; + } else if (type.type === "stack") { + return "Size4-Regular"; + } +}; + +/** + * Traverse a sequence of types of delimiters to decide what kind of delimiter + * should be used to create a delimiter of the given height+depth. + */ +var traverseSequence = function(delim, height, sequence, options) { + // Here, we choose the index we should start at in the sequences. In smaller + // sizes (which correspond to larger numbers in style.size) we start earlier + // in the sequence. Thus, scriptscript starts at index 3-3=0, script starts + // at index 3-2=1, text starts at 3-1=2, and display starts at min(2,3-0)=2 + var start = Math.min(2, 3 - options.style.size); + for (var i = start; i < sequence.length; i++) { + if (sequence[i].type === "stack") { + // This is always the last delimiter, so we just break the loop now. + break; + } + + var metrics = getMetrics(delim, delimTypeToFont(sequence[i])); + var heightDepth = metrics.height + metrics.depth; + + // Small delimiters are scaled down versions of the same font, so we + // account for the style change size. + + if (sequence[i].type === "small") { + heightDepth *= sequence[i].style.sizeMultiplier; + } + + // Check if the delimiter at this size works for the given height. + if (heightDepth > height) { + return sequence[i]; + } + } + + // If we reached the end of the sequence, return the last sequence element. + return sequence[sequence.length - 1]; +}; + +/** + * Make a delimiter of a given height+depth, with optional centering. Here, we + * traverse the sequences, and create a delimiter that the sequence tells us to. + */ +var makeCustomSizedDelim = function(delim, height, center, options, mode) { + if (delim === "<") { + delim = "\\langle"; + } else if (delim === ">") { + delim = "\\rangle"; + } + + // Decide what sequence to use + var sequence; + if (utils.contains(stackNeverDelimiters, delim)) { + sequence = stackNeverDelimiterSequence; + } else if (utils.contains(stackLargeDelimiters, delim)) { + sequence = stackLargeDelimiterSequence; + } else { + sequence = stackAlwaysDelimiterSequence; + } + + // Look through the sequence + var delimType = traverseSequence(delim, height, sequence, options); + + // Depending on the sequence element we decided on, call the appropriate + // function. + if (delimType.type === "small") { + return makeSmallDelim(delim, delimType.style, center, options, mode); + } else if (delimType.type === "large") { + return makeLargeDelim(delim, delimType.size, center, options, mode); + } else if (delimType.type === "stack") { + return makeStackedDelim(delim, height, center, options, mode); + } +}; + +/** + * Make a delimiter for use with `\left` and `\right`, given a height and depth + * of an expression that the delimiters surround. + */ +var makeLeftRightDelim = function(delim, height, depth, options, mode) { + // We always center \left/\right delimiters, so the axis is always shifted + var axisHeight = + fontMetrics.metrics.axisHeight * options.style.sizeMultiplier; + + // Taken from TeX source, tex.web, function make_left_right + var delimiterFactor = 901; + var delimiterExtend = 5.0 / fontMetrics.metrics.ptPerEm; + + var maxDistFromAxis = Math.max( + height - axisHeight, depth + axisHeight); + + var totalHeight = Math.max( + // In real TeX, calculations are done using integral values which are + // 65536 per pt, or 655360 per em. So, the division here truncates in + // TeX but doesn't here, producing different results. If we wanted to + // exactly match TeX's calculation, we could do + // Math.floor(655360 * maxDistFromAxis / 500) * + // delimiterFactor / 655360 + // (To see the difference, compare + // x^{x^{\left(\rule{0.1em}{0.68em}\right)}} + // in TeX and KaTeX) + maxDistFromAxis / 500 * delimiterFactor, + 2 * maxDistFromAxis - delimiterExtend); + + // Finally, we defer to `makeCustomSizedDelim` with our calculated total + // height + return makeCustomSizedDelim(delim, totalHeight, true, options, mode); +}; + +module.exports = { + sizedDelim: makeSizedDelim, + customSizedDelim: makeCustomSizedDelim, + leftRightDelim: makeLeftRightDelim +}; + +},{"./ParseError":7,"./Style":10,"./buildCommon":11,"./fontMetrics":18,"./symbols":24,"./utils":25}],16:[function(require,module,exports){ +/** + * These objects store the data about the DOM nodes we create, as well as some + * extra data. They can then be transformed into real DOM nodes with the + * `toNode` function or HTML markup using `toMarkup`. They are useful for both + * storing extra properties on the nodes, as well as providing a way to easily + * work with the DOM. + * + * Similar functions for working with MathML nodes exist in mathMLTree.js. + */ + +var utils = require("./utils"); + +/** + * Create an HTML className based on a list of classes. In addition to joining + * with spaces, we also remove null or empty classes. + */ +var createClass = function(classes) { + classes = classes.slice(); + for (var i = classes.length - 1; i >= 0; i--) { + if (!classes[i]) { + classes.splice(i, 1); + } + } + + return classes.join(" "); +}; + +/** + * This node represents a span node, with a className, a list of children, and + * an inline style. It also contains information about its height, depth, and + * maxFontSize. + */ +function span(classes, children, height, depth, maxFontSize, style) { + this.classes = classes || []; + this.children = children || []; + this.height = height || 0; + this.depth = depth || 0; + this.maxFontSize = maxFontSize || 0; + this.style = style || {}; + this.attributes = {}; +} + +/** + * Sets an arbitrary attribute on the span. Warning: use this wisely. Not all + * browsers support attributes the same, and having too many custom attributes + * is probably bad. + */ +span.prototype.setAttribute = function(attribute, value) { + this.attributes[attribute] = value; +}; + +/** + * Convert the span into an HTML node + */ +span.prototype.toNode = function() { + var span = document.createElement("span"); + + // Apply the class + span.className = createClass(this.classes); + + // Apply inline styles + for (var style in this.style) { + if (Object.prototype.hasOwnProperty.call(this.style, style)) { + span.style[style] = this.style[style]; + } + } + + // Apply attributes + for (var attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + span.setAttribute(attr, this.attributes[attr]); + } + } + + // Append the children, also as HTML nodes + for (var i = 0; i < this.children.length; i++) { + span.appendChild(this.children[i].toNode()); + } + + return span; +}; + +/** + * Convert the span into an HTML markup string + */ +span.prototype.toMarkup = function() { + var markup = " 0) { + span = document.createElement("span"); + span.style.marginRight = this.italic + "em"; + } + + if (this.classes.length > 0) { + span = span || document.createElement("span"); + span.className = createClass(this.classes); + } + + for (var style in this.style) { + if (this.style.hasOwnProperty(style)) { + span = span || document.createElement("span"); + span.style[style] = this.style[style]; + } + } + + if (span) { + span.appendChild(node); + return span; + } else { + return node; + } +}; + +/** + * Creates markup for a symbol node. + */ +symbolNode.prototype.toMarkup = function() { + // TODO(alpert): More duplication than I'd like from + // span.prototype.toMarkup and symbolNode.prototype.toNode... + var needsSpan = false; + + var markup = " 0) { + styles += "margin-right:" + this.italic + "em;"; + } + for (var style in this.style) { + if (this.style.hasOwnProperty(style)) { + styles += utils.hyphenate(style) + ":" + this.style[style] + ";"; + } + } + + if (styles) { + needsSpan = true; + markup += " style=\"" + utils.escape(styles) + "\""; + } + + var escaped = utils.escape(this.value); + if (needsSpan) { + markup += ">"; + markup += escaped; + markup += ""; + return markup; + } else { + return escaped; + } +}; + +module.exports = { + span: span, + documentFragment: documentFragment, + symbolNode: symbolNode +}; + +},{"./utils":25}],17:[function(require,module,exports){ +var fontMetrics = require("./fontMetrics"); +var parseData = require("./parseData"); +var ParseError = require("./ParseError"); + +var ParseNode = parseData.ParseNode; +var ParseResult = parseData.ParseResult; + +/** + * Parse the body of the environment, with rows delimited by \\ and + * columns delimited by &, and create a nested list in row-major order + * with one group per cell. + */ +function parseArray(parser, pos, mode, result) { + var row = [], body = [row], rowGaps = []; + while (true) { + var cell = parser.parseExpression(pos, mode, false, null); + row.push(new ParseNode("ordgroup", cell.result, mode)); + pos = cell.position; + var next = cell.peek.text; + if (next === "&") { + pos = cell.peek.position; + } else if (next === "\\end") { + break; + } else if (next === "\\\\" || next === "\\cr") { + var cr = parser.parseFunction(pos, mode); + rowGaps.push(cr.result.value.size); + pos = cr.position; + row = []; + body.push(row); + } else { + throw new ParseError("Expected & or \\\\ or \\end", + parser.lexer, cell.peek.position); + } + } + result.body = body; + result.rowGaps = rowGaps; + return new ParseResult(new ParseNode(result.type, result, mode), pos); +} + +/* + * An environment definition is very similar to a function definition. + * Each element of the following array may contain + * - names: The names associated with a function. This can be used to + * share one implementation between several similar environments. + * - numArgs: The number of arguments after the \begin{name} function. + * - argTypes: (optional) Just like for a function + * - allowedInText: (optional) Whether or not the environment is allowed inside + * text mode (default false) (not enforced yet) + * - numOptionalArgs: (optional) Just like for a function + * - handler: The function that is called to handle this environment. + * It will receive the following arguments: + * - pos: the current position of the parser. + * - mode: the current parsing mode. + * - envName: the name of the environment, one of the listed names. + * - [args]: the arguments passed to \begin. + * - positions: the positions associated with these arguments. + */ + +var environmentDefinitions = [ + + // Arrays are part of LaTeX, defined in lttab.dtx so its documentation + // is part of the source2e.pdf file of LaTeX2e source documentation. + { + names: ["array"], + numArgs: 1, + handler: function(pos, mode, envName, colalign, positions) { + var parser = this; + colalign = colalign.value.map ? colalign.value : [colalign]; + var cols = colalign.map(function(node) { + var ca = node.value; + if ("lcr".indexOf(ca) !== -1) { + return { + type: "align", + align: ca + }; + } else if (ca === "|") { + return { + type: "separator", + separator: "|" + }; + } + throw new ParseError( + "Unknown column alignment: " + node.value, + parser.lexer, positions[1]); + }); + var res = { + type: "array", + cols: cols, + hskipBeforeAndAfter: true // \@preamble in lttab.dtx + }; + res = parseArray(parser, pos, mode, res); + return res; + } + }, + + // The matrix environments of amsmath builds on the array environment + // of LaTeX, which is discussed above. + { + names: [ + "matrix", + "pmatrix", + "bmatrix", + "Bmatrix", + "vmatrix", + "Vmatrix" + ], + handler: function(pos, mode, envName) { + var delimiters = { + "matrix": null, + "pmatrix": ["(", ")"], + "bmatrix": ["[", "]"], + "Bmatrix": ["\\{", "\\}"], + "vmatrix": ["|", "|"], + "Vmatrix": ["\\Vert", "\\Vert"] + }[envName]; + var res = { + type: "array", + hskipBeforeAndAfter: false // \hskip -\arraycolsep in amsmath + }; + res = parseArray(this, pos, mode, res); + if (delimiters) { + res.result = new ParseNode("leftright", { + body: [res.result], + left: delimiters[0], + right: delimiters[1] + }, mode); + } + return res; + } + }, + + // A cases environment (in amsmath.sty) is almost equivalent to + // \def\arraystretch{1.2}% + // \left\{\begin{array}{@{}l@{\quad}l@{}} … \end{array}\right. + { + names: ["cases"], + handler: function(pos, mode, envName) { + var res = { + type: "array", + arraystretch: 1.2, + cols: [{ + type: "align", + align: "l", + pregap: 0, + postgap: fontMetrics.metrics.quad + }, { + type: "align", + align: "l", + pregap: 0, + postgap: 0 + }] + }; + res = parseArray(this, pos, mode, res); + res.result = new ParseNode("leftright", { + body: [res.result], + left: "\\{", + right: "." + }, mode); + return res; + } + } +]; + +module.exports = (function() { + // nested function so we don't leak i and j into the module scope + var exports = {}; + for (var i = 0; i < environmentDefinitions.length; ++i) { + var def = environmentDefinitions[i]; + def.greediness = 1; + def.allowedInText = !!def.allowedInText; + def.numArgs = def.numArgs || 0; + def.numOptionalArgs = def.numOptionalArgs || 0; + for (var j = 0; j < def.names.length; ++j) { + exports[def.names[j]] = def; + } + } + return exports; +})(); + +},{"./ParseError":7,"./fontMetrics":18,"./parseData":22}],18:[function(require,module,exports){ +/* jshint unused:false */ + +var Style = require("./Style"); + +/** + * This file contains metrics regarding fonts and individual symbols. The sigma + * and xi variables, as well as the metricMap map contain data extracted from + * TeX, TeX font metrics, and the TTF files. These data are then exposed via the + * `metrics` variable and the getCharacterMetrics function. + */ + +// These font metrics are extracted from TeX by using +// \font\a=cmmi10 +// \showthe\fontdimenX\a +// where X is the corresponding variable number. These correspond to the font +// parameters of the symbol fonts. In TeX, there are actually three sets of +// dimensions, one for each of textstyle, scriptstyle, and scriptscriptstyle, +// but we only use the textstyle ones, and scale certain dimensions accordingly. +// See the TeXbook, page 441. +var sigma1 = 0.025; +var sigma2 = 0; +var sigma3 = 0; +var sigma4 = 0; +var sigma5 = 0.431; +var sigma6 = 1; +var sigma7 = 0; +var sigma8 = 0.677; +var sigma9 = 0.394; +var sigma10 = 0.444; +var sigma11 = 0.686; +var sigma12 = 0.345; +var sigma13 = 0.413; +var sigma14 = 0.363; +var sigma15 = 0.289; +var sigma16 = 0.150; +var sigma17 = 0.247; +var sigma18 = 0.386; +var sigma19 = 0.050; +var sigma20 = 2.390; +var sigma21 = 1.01; +var sigma21Script = 0.81; +var sigma21ScriptScript = 0.71; +var sigma22 = 0.250; + +// These font metrics are extracted from TeX by using +// \font\a=cmex10 +// \showthe\fontdimenX\a +// where X is the corresponding variable number. These correspond to the font +// parameters of the extension fonts (family 3). See the TeXbook, page 441. +var xi1 = 0; +var xi2 = 0; +var xi3 = 0; +var xi4 = 0; +var xi5 = 0.431; +var xi6 = 1; +var xi7 = 0; +var xi8 = 0.04; +var xi9 = 0.111; +var xi10 = 0.166; +var xi11 = 0.2; +var xi12 = 0.6; +var xi13 = 0.1; + +// This value determines how large a pt is, for metrics which are defined in +// terms of pts. +// This value is also used in katex.less; if you change it make sure the values +// match. +var ptPerEm = 10.0; + +// The space between adjacent `|` columns in an array definition. From +// `\showthe\doublerulesep` in LaTeX. +var doubleRuleSep = 2.0 / ptPerEm; + +/** + * This is just a mapping from common names to real metrics + */ +var metrics = { + xHeight: sigma5, + quad: sigma6, + num1: sigma8, + num2: sigma9, + num3: sigma10, + denom1: sigma11, + denom2: sigma12, + sup1: sigma13, + sup2: sigma14, + sup3: sigma15, + sub1: sigma16, + sub2: sigma17, + supDrop: sigma18, + subDrop: sigma19, + axisHeight: sigma22, + defaultRuleThickness: xi8, + bigOpSpacing1: xi9, + bigOpSpacing2: xi10, + bigOpSpacing3: xi11, + bigOpSpacing4: xi12, + bigOpSpacing5: xi13, + ptPerEm: ptPerEm, + emPerEx: sigma5 / sigma6, + doubleRuleSep: doubleRuleSep, + + // TODO(alpert): Missing parallel structure here. We should probably add + // style-specific metrics for all of these. + delim1: sigma20, + getDelim2: function(style) { + if (style.size === Style.TEXT.size) { + return sigma21; + } else if (style.size === Style.SCRIPT.size) { + return sigma21Script; + } else if (style.size === Style.SCRIPTSCRIPT.size) { + return sigma21ScriptScript; + } + throw new Error("Unexpected style size: " + style.size); + } +}; + +// This map contains a mapping from font name and character code to character +// metrics, including height, depth, italic correction, and skew (kern from the +// character to the corresponding \skewchar) +// This map is generated via `make metrics`. It should not be changed manually. +var metricMap = require("./fontMetricsData"); + +/** + * This function is a convience function for looking up information in the + * metricMap table. It takes a character as a string, and a style + */ +var getCharacterMetrics = function(character, style) { + return metricMap[style][character.charCodeAt(0)]; +}; + +module.exports = { + metrics: metrics, + getCharacterMetrics: getCharacterMetrics +}; + +},{"./Style":10,"./fontMetricsData":19}],19:[function(require,module,exports){ +module.exports = { +"AMS-Regular": { + "65": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "70": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "72": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "74": {"depth": 0.16667, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "79": {"depth": 0.16667, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "80": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "81": {"depth": 0.16667, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "89": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "165": {"depth": 0.0, "height": 0.675, "italic": 0.025, "skew": 0.0}, + "174": {"depth": 0.15559, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "240": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "295": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "710": {"depth": 0.0, "height": 0.825, "italic": 0.0, "skew": 0.0}, + "732": {"depth": 0.0, "height": 0.9, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.825, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.9, "italic": 0.0, "skew": 0.0}, + "989": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "1008": {"depth": 0.0, "height": 0.43056, "italic": 0.04028, "skew": 0.0}, + "8245": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8463": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8487": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8498": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8502": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8503": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8504": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8513": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8592": {"depth": -0.03598, "height": 0.46402, "italic": 0.0, "skew": 0.0}, + "8594": {"depth": -0.03598, "height": 0.46402, "italic": 0.0, "skew": 0.0}, + "8602": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8603": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8606": {"depth": 0.01354, "height": 0.52239, "italic": 0.0, "skew": 0.0}, + "8608": {"depth": 0.01354, "height": 0.52239, "italic": 0.0, "skew": 0.0}, + "8610": {"depth": 0.01354, "height": 0.52239, "italic": 0.0, "skew": 0.0}, + "8611": {"depth": 0.01354, "height": 0.52239, "italic": 0.0, "skew": 0.0}, + "8619": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8620": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8621": {"depth": -0.13313, "height": 0.37788, "italic": 0.0, "skew": 0.0}, + "8622": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8624": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8625": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8630": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "8631": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "8634": {"depth": 0.08198, "height": 0.58198, "italic": 0.0, "skew": 0.0}, + "8635": {"depth": 0.08198, "height": 0.58198, "italic": 0.0, "skew": 0.0}, + "8638": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8639": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8642": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8643": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8644": {"depth": 0.1808, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8646": {"depth": 0.1808, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8647": {"depth": 0.1808, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8648": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8649": {"depth": 0.1808, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8650": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8651": {"depth": 0.01354, "height": 0.52239, "italic": 0.0, "skew": 0.0}, + "8652": {"depth": 0.01354, "height": 0.52239, "italic": 0.0, "skew": 0.0}, + "8653": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8654": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8655": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8666": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "8667": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "8669": {"depth": -0.13313, "height": 0.37788, "italic": 0.0, "skew": 0.0}, + "8672": {"depth": -0.064, "height": 0.437, "italic": 0, "skew": 0}, + "8674": {"depth": -0.064, "height": 0.437, "italic": 0, "skew": 0}, + "8705": {"depth": 0.0, "height": 0.825, "italic": 0.0, "skew": 0.0}, + "8708": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8709": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "8717": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "8722": {"depth": -0.03598, "height": 0.46402, "italic": 0.0, "skew": 0.0}, + "8724": {"depth": 0.08198, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8726": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "8733": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8736": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8737": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8738": {"depth": 0.03517, "height": 0.52239, "italic": 0.0, "skew": 0.0}, + "8739": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "8740": {"depth": 0.25142, "height": 0.74111, "italic": 0.0, "skew": 0.0}, + "8741": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "8742": {"depth": 0.25142, "height": 0.74111, "italic": 0.0, "skew": 0.0}, + "8756": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8757": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8764": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8765": {"depth": -0.13313, "height": 0.37788, "italic": 0.0, "skew": 0.0}, + "8769": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8770": {"depth": -0.03625, "height": 0.46375, "italic": 0.0, "skew": 0.0}, + "8774": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8776": {"depth": -0.01688, "height": 0.48312, "italic": 0.0, "skew": 0.0}, + "8778": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "8782": {"depth": 0.06062, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8783": {"depth": 0.06062, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8785": {"depth": 0.08198, "height": 0.58198, "italic": 0.0, "skew": 0.0}, + "8786": {"depth": 0.08198, "height": 0.58198, "italic": 0.0, "skew": 0.0}, + "8787": {"depth": 0.08198, "height": 0.58198, "italic": 0.0, "skew": 0.0}, + "8790": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8791": {"depth": 0.22958, "height": 0.72958, "italic": 0.0, "skew": 0.0}, + "8796": {"depth": 0.08198, "height": 0.91667, "italic": 0.0, "skew": 0.0}, + "8806": {"depth": 0.25583, "height": 0.75583, "italic": 0.0, "skew": 0.0}, + "8807": {"depth": 0.25583, "height": 0.75583, "italic": 0.0, "skew": 0.0}, + "8808": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "8809": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "8812": {"depth": 0.25583, "height": 0.75583, "italic": 0.0, "skew": 0.0}, + "8814": {"depth": 0.20576, "height": 0.70576, "italic": 0.0, "skew": 0.0}, + "8815": {"depth": 0.20576, "height": 0.70576, "italic": 0.0, "skew": 0.0}, + "8816": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8817": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8818": {"depth": 0.22958, "height": 0.72958, "italic": 0.0, "skew": 0.0}, + "8819": {"depth": 0.22958, "height": 0.72958, "italic": 0.0, "skew": 0.0}, + "8822": {"depth": 0.1808, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8823": {"depth": 0.1808, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8828": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "8829": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "8830": {"depth": 0.22958, "height": 0.72958, "italic": 0.0, "skew": 0.0}, + "8831": {"depth": 0.22958, "height": 0.72958, "italic": 0.0, "skew": 0.0}, + "8832": {"depth": 0.20576, "height": 0.70576, "italic": 0.0, "skew": 0.0}, + "8833": {"depth": 0.20576, "height": 0.70576, "italic": 0.0, "skew": 0.0}, + "8840": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8841": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8842": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "8843": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "8847": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8848": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8858": {"depth": 0.08198, "height": 0.58198, "italic": 0.0, "skew": 0.0}, + "8859": {"depth": 0.08198, "height": 0.58198, "italic": 0.0, "skew": 0.0}, + "8861": {"depth": 0.08198, "height": 0.58198, "italic": 0.0, "skew": 0.0}, + "8862": {"depth": 0.0, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8863": {"depth": 0.0, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8864": {"depth": 0.0, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8865": {"depth": 0.0, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "8872": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8873": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8874": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8876": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8877": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8878": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8879": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8882": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8883": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8884": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "8885": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "8888": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8890": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "8891": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8892": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8901": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8903": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "8905": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "8906": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "8907": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8908": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8909": {"depth": -0.03598, "height": 0.46402, "italic": 0.0, "skew": 0.0}, + "8910": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8911": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8912": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8913": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8914": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8915": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8916": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8918": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8919": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8920": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8921": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "8922": {"depth": 0.38569, "height": 0.88569, "italic": 0.0, "skew": 0.0}, + "8923": {"depth": 0.38569, "height": 0.88569, "italic": 0.0, "skew": 0.0}, + "8926": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "8927": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "8928": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8929": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8934": {"depth": 0.23222, "height": 0.74111, "italic": 0.0, "skew": 0.0}, + "8935": {"depth": 0.23222, "height": 0.74111, "italic": 0.0, "skew": 0.0}, + "8936": {"depth": 0.23222, "height": 0.74111, "italic": 0.0, "skew": 0.0}, + "8937": {"depth": 0.23222, "height": 0.74111, "italic": 0.0, "skew": 0.0}, + "8938": {"depth": 0.20576, "height": 0.70576, "italic": 0.0, "skew": 0.0}, + "8939": {"depth": 0.20576, "height": 0.70576, "italic": 0.0, "skew": 0.0}, + "8940": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8941": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "8994": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8995": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "9416": {"depth": 0.15559, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "9484": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "9488": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "9492": {"depth": 0.0, "height": 0.37788, "italic": 0.0, "skew": 0.0}, + "9496": {"depth": 0.0, "height": 0.37788, "italic": 0.0, "skew": 0.0}, + "9585": {"depth": 0.19444, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "9586": {"depth": 0.19444, "height": 0.74111, "italic": 0.0, "skew": 0.0}, + "9632": {"depth": 0.0, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "9633": {"depth": 0.0, "height": 0.675, "italic": 0.0, "skew": 0.0}, + "9650": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "9651": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "9654": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "9660": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "9661": {"depth": 0.0, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "9664": {"depth": 0.03517, "height": 0.54986, "italic": 0.0, "skew": 0.0}, + "9674": {"depth": 0.11111, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "9733": {"depth": 0.19444, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "10003": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "10016": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "10731": {"depth": 0.11111, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "10846": {"depth": 0.19444, "height": 0.75583, "italic": 0.0, "skew": 0.0}, + "10877": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "10878": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "10885": {"depth": 0.25583, "height": 0.75583, "italic": 0.0, "skew": 0.0}, + "10886": {"depth": 0.25583, "height": 0.75583, "italic": 0.0, "skew": 0.0}, + "10887": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "10888": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "10889": {"depth": 0.26167, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "10890": {"depth": 0.26167, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "10891": {"depth": 0.48256, "height": 0.98256, "italic": 0.0, "skew": 0.0}, + "10892": {"depth": 0.48256, "height": 0.98256, "italic": 0.0, "skew": 0.0}, + "10901": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "10902": {"depth": 0.13667, "height": 0.63667, "italic": 0.0, "skew": 0.0}, + "10933": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "10934": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "10935": {"depth": 0.26167, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "10936": {"depth": 0.26167, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "10937": {"depth": 0.26167, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "10938": {"depth": 0.26167, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "10949": {"depth": 0.25583, "height": 0.75583, "italic": 0.0, "skew": 0.0}, + "10950": {"depth": 0.25583, "height": 0.75583, "italic": 0.0, "skew": 0.0}, + "10955": {"depth": 0.28481, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "10956": {"depth": 0.28481, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "57350": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "57351": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "57352": {"depth": 0.08167, "height": 0.58167, "italic": 0.0, "skew": 0.0}, + "57353": {"depth": 0.0, "height": 0.43056, "italic": 0.04028, "skew": 0.0}, + "57356": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "57357": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "57358": {"depth": 0.41951, "height": 0.91951, "italic": 0.0, "skew": 0.0}, + "57359": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "57360": {"depth": 0.30274, "height": 0.79383, "italic": 0.0, "skew": 0.0}, + "57361": {"depth": 0.41951, "height": 0.91951, "italic": 0.0, "skew": 0.0}, + "57366": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "57367": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "57368": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "57369": {"depth": 0.25142, "height": 0.75726, "italic": 0.0, "skew": 0.0}, + "57370": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "57371": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0} +}, +"Caligraphic-Regular": { + "48": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "49": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "50": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "51": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "52": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "53": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "54": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "55": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "56": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "57": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.19445}, + "66": {"depth": 0.0, "height": 0.68333, "italic": 0.03041, "skew": 0.13889}, + "67": {"depth": 0.0, "height": 0.68333, "italic": 0.05834, "skew": 0.13889}, + "68": {"depth": 0.0, "height": 0.68333, "italic": 0.02778, "skew": 0.08334}, + "69": {"depth": 0.0, "height": 0.68333, "italic": 0.08944, "skew": 0.11111}, + "70": {"depth": 0.0, "height": 0.68333, "italic": 0.09931, "skew": 0.11111}, + "71": {"depth": 0.09722, "height": 0.68333, "italic": 0.0593, "skew": 0.11111}, + "72": {"depth": 0.0, "height": 0.68333, "italic": 0.00965, "skew": 0.11111}, + "73": {"depth": 0.0, "height": 0.68333, "italic": 0.07382, "skew": 0.0}, + "74": {"depth": 0.09722, "height": 0.68333, "italic": 0.18472, "skew": 0.16667}, + "75": {"depth": 0.0, "height": 0.68333, "italic": 0.01445, "skew": 0.05556}, + "76": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.13889}, + "77": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.13889}, + "78": {"depth": 0.0, "height": 0.68333, "italic": 0.14736, "skew": 0.08334}, + "79": {"depth": 0.0, "height": 0.68333, "italic": 0.02778, "skew": 0.11111}, + "80": {"depth": 0.0, "height": 0.68333, "italic": 0.08222, "skew": 0.08334}, + "81": {"depth": 0.09722, "height": 0.68333, "italic": 0.0, "skew": 0.11111}, + "82": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.08334}, + "83": {"depth": 0.0, "height": 0.68333, "italic": 0.075, "skew": 0.13889}, + "84": {"depth": 0.0, "height": 0.68333, "italic": 0.25417, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.68333, "italic": 0.09931, "skew": 0.08334}, + "86": {"depth": 0.0, "height": 0.68333, "italic": 0.08222, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.68333, "italic": 0.08222, "skew": 0.08334}, + "88": {"depth": 0.0, "height": 0.68333, "italic": 0.14643, "skew": 0.13889}, + "89": {"depth": 0.09722, "height": 0.68333, "italic": 0.08222, "skew": 0.08334}, + "90": {"depth": 0.0, "height": 0.68333, "italic": 0.07944, "skew": 0.13889} +}, +"Fraktur-Regular": { + "33": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "34": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "38": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "39": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "40": {"depth": 0.24982, "height": 0.74947, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 0.24982, "height": 0.74947, "italic": 0.0, "skew": 0.0}, + "42": {"depth": 0.0, "height": 0.62119, "italic": 0.0, "skew": 0.0}, + "43": {"depth": 0.08319, "height": 0.58283, "italic": 0.0, "skew": 0.0}, + "44": {"depth": 0.0, "height": 0.10803, "italic": 0.0, "skew": 0.0}, + "45": {"depth": 0.08319, "height": 0.58283, "italic": 0.0, "skew": 0.0}, + "46": {"depth": 0.0, "height": 0.10803, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.24982, "height": 0.74947, "italic": 0.0, "skew": 0.0}, + "48": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "49": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "50": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "51": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "52": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "53": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "54": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "55": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "56": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "57": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "58": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "59": {"depth": 0.12604, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "61": {"depth": -0.13099, "height": 0.36866, "italic": 0.0, "skew": 0.0}, + "63": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "70": {"depth": 0.12604, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "72": {"depth": 0.06302, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "74": {"depth": 0.12604, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "79": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "80": {"depth": 0.18906, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "81": {"depth": 0.03781, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "89": {"depth": 0.18906, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "90": {"depth": 0.12604, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 0.24982, "height": 0.74947, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 0.24982, "height": 0.74947, "italic": 0.0, "skew": 0.0}, + "94": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "97": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "100": {"depth": 0.0, "height": 0.62119, "italic": 0.0, "skew": 0.0}, + "101": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "102": {"depth": 0.18906, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "103": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "104": {"depth": 0.18906, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "106": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "109": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "112": {"depth": 0.18906, "height": 0.52396, "italic": 0.0, "skew": 0.0}, + "113": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "114": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "115": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "116": {"depth": 0.0, "height": 0.62119, "italic": 0.0, "skew": 0.0}, + "117": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "118": {"depth": 0.0, "height": 0.52396, "italic": 0.0, "skew": 0.0}, + "119": {"depth": 0.0, "height": 0.52396, "italic": 0.0, "skew": 0.0}, + "120": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "121": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "122": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "8216": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "8217": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "58112": {"depth": 0.0, "height": 0.62119, "italic": 0.0, "skew": 0.0}, + "58113": {"depth": 0.0, "height": 0.62119, "italic": 0.0, "skew": 0.0}, + "58114": {"depth": 0.18906, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "58115": {"depth": 0.18906, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "58116": {"depth": 0.18906, "height": 0.47534, "italic": 0.0, "skew": 0.0}, + "58117": {"depth": 0.0, "height": 0.69141, "italic": 0.0, "skew": 0.0}, + "58118": {"depth": 0.0, "height": 0.62119, "italic": 0.0, "skew": 0.0}, + "58119": {"depth": 0.0, "height": 0.47534, "italic": 0.0, "skew": 0.0} +}, +"Main-Bold": { + "33": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "34": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "35": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "36": {"depth": 0.05556, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "37": {"depth": 0.05556, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "38": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "39": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "40": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "42": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "43": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "44": {"depth": 0.19444, "height": 0.15556, "italic": 0.0, "skew": 0.0}, + "45": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "46": {"depth": 0.0, "height": 0.15556, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "48": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "49": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "50": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "51": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "52": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "53": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "54": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "55": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "56": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "57": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "58": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "59": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "60": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "61": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "62": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "63": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "64": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "70": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "72": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "74": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "79": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "80": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "81": {"depth": 0.19444, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.68611, "italic": 0.01597, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.68611, "italic": 0.01597, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "89": {"depth": 0.0, "height": 0.68611, "italic": 0.02875, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "92": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "94": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "95": {"depth": 0.31, "height": 0.13444, "italic": 0.03194, "skew": 0.0}, + "96": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "97": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "100": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "101": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "102": {"depth": 0.0, "height": 0.69444, "italic": 0.10903, "skew": 0.0}, + "103": {"depth": 0.19444, "height": 0.44444, "italic": 0.01597, "skew": 0.0}, + "104": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "106": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "109": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "112": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "113": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "114": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "115": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "116": {"depth": 0.0, "height": 0.63492, "italic": 0.0, "skew": 0.0}, + "117": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "118": {"depth": 0.0, "height": 0.44444, "italic": 0.01597, "skew": 0.0}, + "119": {"depth": 0.0, "height": 0.44444, "italic": 0.01597, "skew": 0.0}, + "120": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "121": {"depth": 0.19444, "height": 0.44444, "italic": 0.01597, "skew": 0.0}, + "122": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "123": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "124": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "125": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "126": {"depth": 0.35, "height": 0.34444, "italic": 0.0, "skew": 0.0}, + "168": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "172": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "175": {"depth": 0.0, "height": 0.59611, "italic": 0.0, "skew": 0.0}, + "176": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "177": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "180": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "215": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "247": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "305": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "567": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "710": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "711": {"depth": 0.0, "height": 0.63194, "italic": 0.0, "skew": 0.0}, + "713": {"depth": 0.0, "height": 0.59611, "italic": 0.0, "skew": 0.0}, + "714": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "715": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "728": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "729": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "730": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "732": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "768": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "769": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "772": {"depth": 0.0, "height": 0.59611, "italic": 0.0, "skew": 0.0}, + "774": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "775": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "776": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "778": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "779": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "780": {"depth": 0.0, "height": 0.63194, "italic": 0.0, "skew": 0.0}, + "824": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "915": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "916": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "920": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "923": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "926": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "928": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "931": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "933": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "934": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "936": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "937": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "8211": {"depth": 0.0, "height": 0.44444, "italic": 0.03194, "skew": 0.0}, + "8212": {"depth": 0.0, "height": 0.44444, "italic": 0.03194, "skew": 0.0}, + "8216": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8217": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8220": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8221": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8224": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8225": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8242": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8407": {"depth": 0.0, "height": 0.72444, "italic": 0.15486, "skew": 0.0}, + "8463": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8465": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8467": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8472": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "8476": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8501": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8592": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8593": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8594": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8595": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8596": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8597": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8598": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8599": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8600": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8601": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8636": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8637": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8640": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8641": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8656": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8657": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8658": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8659": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8660": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8661": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8704": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8706": {"depth": 0.0, "height": 0.69444, "italic": 0.06389, "skew": 0.0}, + "8707": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8709": {"depth": 0.05556, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8711": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "8712": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "8715": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "8722": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "8723": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "8725": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8726": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8727": {"depth": -0.02778, "height": 0.47222, "italic": 0.0, "skew": 0.0}, + "8728": {"depth": -0.02639, "height": 0.47361, "italic": 0.0, "skew": 0.0}, + "8729": {"depth": -0.02639, "height": 0.47361, "italic": 0.0, "skew": 0.0}, + "8730": {"depth": 0.18, "height": 0.82, "italic": 0.0, "skew": 0.0}, + "8733": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "8734": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "8736": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8739": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8741": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8743": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8744": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8745": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8746": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8747": {"depth": 0.19444, "height": 0.69444, "italic": 0.12778, "skew": 0.0}, + "8764": {"depth": -0.10889, "height": 0.39111, "italic": 0.0, "skew": 0.0}, + "8768": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8771": {"depth": 0.00222, "height": 0.50222, "italic": 0.0, "skew": 0.0}, + "8776": {"depth": 0.02444, "height": 0.52444, "italic": 0.0, "skew": 0.0}, + "8781": {"depth": 0.00222, "height": 0.50222, "italic": 0.0, "skew": 0.0}, + "8801": {"depth": 0.00222, "height": 0.50222, "italic": 0.0, "skew": 0.0}, + "8804": {"depth": 0.19667, "height": 0.69667, "italic": 0.0, "skew": 0.0}, + "8805": {"depth": 0.19667, "height": 0.69667, "italic": 0.0, "skew": 0.0}, + "8810": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "8811": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "8826": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "8827": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "8834": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "8835": {"depth": 0.08556, "height": 0.58556, "italic": 0.0, "skew": 0.0}, + "8838": {"depth": 0.19667, "height": 0.69667, "italic": 0.0, "skew": 0.0}, + "8839": {"depth": 0.19667, "height": 0.69667, "italic": 0.0, "skew": 0.0}, + "8846": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8849": {"depth": 0.19667, "height": 0.69667, "italic": 0.0, "skew": 0.0}, + "8850": {"depth": 0.19667, "height": 0.69667, "italic": 0.0, "skew": 0.0}, + "8851": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8852": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8853": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "8854": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "8855": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "8856": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "8857": {"depth": 0.13333, "height": 0.63333, "italic": 0.0, "skew": 0.0}, + "8866": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8867": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8868": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8869": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8900": {"depth": -0.02639, "height": 0.47361, "italic": 0.0, "skew": 0.0}, + "8901": {"depth": -0.02639, "height": 0.47361, "italic": 0.0, "skew": 0.0}, + "8902": {"depth": -0.02778, "height": 0.47222, "italic": 0.0, "skew": 0.0}, + "8968": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8969": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8970": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8971": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8994": {"depth": -0.13889, "height": 0.36111, "italic": 0.0, "skew": 0.0}, + "8995": {"depth": -0.13889, "height": 0.36111, "italic": 0.0, "skew": 0.0}, + "9651": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9657": {"depth": -0.02778, "height": 0.47222, "italic": 0.0, "skew": 0.0}, + "9661": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9667": {"depth": -0.02778, "height": 0.47222, "italic": 0.0, "skew": 0.0}, + "9711": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9824": {"depth": 0.12963, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9825": {"depth": 0.12963, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9826": {"depth": 0.12963, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9827": {"depth": 0.12963, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9837": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "9838": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9839": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "10216": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "10217": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "10815": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "10927": {"depth": 0.19667, "height": 0.69667, "italic": 0.0, "skew": 0.0}, + "10928": {"depth": 0.19667, "height": 0.69667, "italic": 0.0, "skew": 0.0} +}, +"Main-Italic": { + "33": {"depth": 0.0, "height": 0.69444, "italic": 0.12417, "skew": 0.0}, + "34": {"depth": 0.0, "height": 0.69444, "italic": 0.06961, "skew": 0.0}, + "35": {"depth": 0.19444, "height": 0.69444, "italic": 0.06616, "skew": 0.0}, + "37": {"depth": 0.05556, "height": 0.75, "italic": 0.13639, "skew": 0.0}, + "38": {"depth": 0.0, "height": 0.69444, "italic": 0.09694, "skew": 0.0}, + "39": {"depth": 0.0, "height": 0.69444, "italic": 0.12417, "skew": 0.0}, + "40": {"depth": 0.25, "height": 0.75, "italic": 0.16194, "skew": 0.0}, + "41": {"depth": 0.25, "height": 0.75, "italic": 0.03694, "skew": 0.0}, + "42": {"depth": 0.0, "height": 0.75, "italic": 0.14917, "skew": 0.0}, + "43": {"depth": 0.05667, "height": 0.56167, "italic": 0.03694, "skew": 0.0}, + "44": {"depth": 0.19444, "height": 0.10556, "italic": 0.0, "skew": 0.0}, + "45": {"depth": 0.0, "height": 0.43056, "italic": 0.02826, "skew": 0.0}, + "46": {"depth": 0.0, "height": 0.10556, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.25, "height": 0.75, "italic": 0.16194, "skew": 0.0}, + "48": {"depth": 0.0, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "49": {"depth": 0.0, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "50": {"depth": 0.0, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "51": {"depth": 0.0, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "52": {"depth": 0.19444, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "53": {"depth": 0.0, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "54": {"depth": 0.0, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "55": {"depth": 0.19444, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "56": {"depth": 0.0, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "57": {"depth": 0.0, "height": 0.64444, "italic": 0.13556, "skew": 0.0}, + "58": {"depth": 0.0, "height": 0.43056, "italic": 0.0582, "skew": 0.0}, + "59": {"depth": 0.19444, "height": 0.43056, "italic": 0.0582, "skew": 0.0}, + "61": {"depth": -0.13313, "height": 0.36687, "italic": 0.06616, "skew": 0.0}, + "63": {"depth": 0.0, "height": 0.69444, "italic": 0.1225, "skew": 0.0}, + "64": {"depth": 0.0, "height": 0.69444, "italic": 0.09597, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.68333, "italic": 0.10257, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.68333, "italic": 0.14528, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.68333, "italic": 0.09403, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.68333, "italic": 0.12028, "skew": 0.0}, + "70": {"depth": 0.0, "height": 0.68333, "italic": 0.13305, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.68333, "italic": 0.08722, "skew": 0.0}, + "72": {"depth": 0.0, "height": 0.68333, "italic": 0.16389, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.68333, "italic": 0.15806, "skew": 0.0}, + "74": {"depth": 0.0, "height": 0.68333, "italic": 0.14028, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.68333, "italic": 0.14528, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.68333, "italic": 0.16389, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.68333, "italic": 0.16389, "skew": 0.0}, + "79": {"depth": 0.0, "height": 0.68333, "italic": 0.09403, "skew": 0.0}, + "80": {"depth": 0.0, "height": 0.68333, "italic": 0.10257, "skew": 0.0}, + "81": {"depth": 0.19444, "height": 0.68333, "italic": 0.09403, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.68333, "italic": 0.03868, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.68333, "italic": 0.11972, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.68333, "italic": 0.13305, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.68333, "italic": 0.16389, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.68333, "italic": 0.18361, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.68333, "italic": 0.18361, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.68333, "italic": 0.15806, "skew": 0.0}, + "89": {"depth": 0.0, "height": 0.68333, "italic": 0.19383, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.68333, "italic": 0.14528, "skew": 0.0}, + "91": {"depth": 0.25, "height": 0.75, "italic": 0.1875, "skew": 0.0}, + "93": {"depth": 0.25, "height": 0.75, "italic": 0.10528, "skew": 0.0}, + "94": {"depth": 0.0, "height": 0.69444, "italic": 0.06646, "skew": 0.0}, + "95": {"depth": 0.31, "height": 0.12056, "italic": 0.09208, "skew": 0.0}, + "97": {"depth": 0.0, "height": 0.43056, "italic": 0.07671, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.69444, "italic": 0.06312, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.43056, "italic": 0.05653, "skew": 0.0}, + "100": {"depth": 0.0, "height": 0.69444, "italic": 0.10333, "skew": 0.0}, + "101": {"depth": 0.0, "height": 0.43056, "italic": 0.07514, "skew": 0.0}, + "102": {"depth": 0.19444, "height": 0.69444, "italic": 0.21194, "skew": 0.0}, + "103": {"depth": 0.19444, "height": 0.43056, "italic": 0.08847, "skew": 0.0}, + "104": {"depth": 0.0, "height": 0.69444, "italic": 0.07671, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.65536, "italic": 0.1019, "skew": 0.0}, + "106": {"depth": 0.19444, "height": 0.65536, "italic": 0.14467, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.69444, "italic": 0.10764, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.69444, "italic": 0.10333, "skew": 0.0}, + "109": {"depth": 0.0, "height": 0.43056, "italic": 0.07671, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.43056, "italic": 0.07671, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.43056, "italic": 0.06312, "skew": 0.0}, + "112": {"depth": 0.19444, "height": 0.43056, "italic": 0.06312, "skew": 0.0}, + "113": {"depth": 0.19444, "height": 0.43056, "italic": 0.08847, "skew": 0.0}, + "114": {"depth": 0.0, "height": 0.43056, "italic": 0.10764, "skew": 0.0}, + "115": {"depth": 0.0, "height": 0.43056, "italic": 0.08208, "skew": 0.0}, + "116": {"depth": 0.0, "height": 0.61508, "italic": 0.09486, "skew": 0.0}, + "117": {"depth": 0.0, "height": 0.43056, "italic": 0.07671, "skew": 0.0}, + "118": {"depth": 0.0, "height": 0.43056, "italic": 0.10764, "skew": 0.0}, + "119": {"depth": 0.0, "height": 0.43056, "italic": 0.10764, "skew": 0.0}, + "120": {"depth": 0.0, "height": 0.43056, "italic": 0.12042, "skew": 0.0}, + "121": {"depth": 0.19444, "height": 0.43056, "italic": 0.08847, "skew": 0.0}, + "122": {"depth": 0.0, "height": 0.43056, "italic": 0.12292, "skew": 0.0}, + "126": {"depth": 0.35, "height": 0.31786, "italic": 0.11585, "skew": 0.0}, + "163": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "305": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.02778}, + "567": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "768": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "769": {"depth": 0.0, "height": 0.69444, "italic": 0.09694, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.69444, "italic": 0.06646, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.66786, "italic": 0.11585, "skew": 0.0}, + "772": {"depth": 0.0, "height": 0.56167, "italic": 0.10333, "skew": 0.0}, + "774": {"depth": 0.0, "height": 0.69444, "italic": 0.10806, "skew": 0.0}, + "775": {"depth": 0.0, "height": 0.66786, "italic": 0.11752, "skew": 0.0}, + "776": {"depth": 0.0, "height": 0.66786, "italic": 0.10474, "skew": 0.0}, + "778": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "779": {"depth": 0.0, "height": 0.69444, "italic": 0.1225, "skew": 0.0}, + "780": {"depth": 0.0, "height": 0.62847, "italic": 0.08295, "skew": 0.0}, + "915": {"depth": 0.0, "height": 0.68333, "italic": 0.13305, "skew": 0.0}, + "916": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "920": {"depth": 0.0, "height": 0.68333, "italic": 0.09403, "skew": 0.0}, + "923": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "926": {"depth": 0.0, "height": 0.68333, "italic": 0.15294, "skew": 0.0}, + "928": {"depth": 0.0, "height": 0.68333, "italic": 0.16389, "skew": 0.0}, + "931": {"depth": 0.0, "height": 0.68333, "italic": 0.12028, "skew": 0.0}, + "933": {"depth": 0.0, "height": 0.68333, "italic": 0.11111, "skew": 0.0}, + "934": {"depth": 0.0, "height": 0.68333, "italic": 0.05986, "skew": 0.0}, + "936": {"depth": 0.0, "height": 0.68333, "italic": 0.11111, "skew": 0.0}, + "937": {"depth": 0.0, "height": 0.68333, "italic": 0.10257, "skew": 0.0}, + "8211": {"depth": 0.0, "height": 0.43056, "italic": 0.09208, "skew": 0.0}, + "8212": {"depth": 0.0, "height": 0.43056, "italic": 0.09208, "skew": 0.0}, + "8216": {"depth": 0.0, "height": 0.69444, "italic": 0.12417, "skew": 0.0}, + "8217": {"depth": 0.0, "height": 0.69444, "italic": 0.12417, "skew": 0.0}, + "8220": {"depth": 0.0, "height": 0.69444, "italic": 0.1685, "skew": 0.0}, + "8221": {"depth": 0.0, "height": 0.69444, "italic": 0.06961, "skew": 0.0}, + "8463": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0} +}, +"Main-Regular": { + "32": {"depth": 0.0, "height": 0.0, "italic": 0, "skew": 0}, + "33": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "34": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "35": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "36": {"depth": 0.05556, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "37": {"depth": 0.05556, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "38": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "39": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "40": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "42": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "43": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "44": {"depth": 0.19444, "height": 0.10556, "italic": 0.0, "skew": 0.0}, + "45": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "46": {"depth": 0.0, "height": 0.10556, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "48": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "49": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "50": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "51": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "52": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "53": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "54": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "55": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "56": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "57": {"depth": 0.0, "height": 0.64444, "italic": 0.0, "skew": 0.0}, + "58": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "59": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "60": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "61": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "62": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "63": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "64": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "70": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "72": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "74": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "79": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "80": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "81": {"depth": 0.19444, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.68333, "italic": 0.01389, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.68333, "italic": 0.01389, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "89": {"depth": 0.0, "height": 0.68333, "italic": 0.025, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "92": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "94": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "95": {"depth": 0.31, "height": 0.12056, "italic": 0.02778, "skew": 0.0}, + "96": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "97": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "100": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "101": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "102": {"depth": 0.0, "height": 0.69444, "italic": 0.07778, "skew": 0.0}, + "103": {"depth": 0.19444, "height": 0.43056, "italic": 0.01389, "skew": 0.0}, + "104": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.66786, "italic": 0.0, "skew": 0.0}, + "106": {"depth": 0.19444, "height": 0.66786, "italic": 0.0, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "109": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "112": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "113": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "114": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "115": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "116": {"depth": 0.0, "height": 0.61508, "italic": 0.0, "skew": 0.0}, + "117": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "118": {"depth": 0.0, "height": 0.43056, "italic": 0.01389, "skew": 0.0}, + "119": {"depth": 0.0, "height": 0.43056, "italic": 0.01389, "skew": 0.0}, + "120": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "121": {"depth": 0.19444, "height": 0.43056, "italic": 0.01389, "skew": 0.0}, + "122": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "123": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "124": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "125": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "126": {"depth": 0.35, "height": 0.31786, "italic": 0.0, "skew": 0.0}, + "160": {"depth": 0.0, "height": 0.0, "italic": 0, "skew": 0}, + "168": {"depth": 0.0, "height": 0.66786, "italic": 0.0, "skew": 0.0}, + "172": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "175": {"depth": 0.0, "height": 0.56778, "italic": 0.0, "skew": 0.0}, + "176": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "177": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "180": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "215": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "247": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "305": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "567": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "710": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "711": {"depth": 0.0, "height": 0.62847, "italic": 0.0, "skew": 0.0}, + "713": {"depth": 0.0, "height": 0.56778, "italic": 0.0, "skew": 0.0}, + "714": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "715": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "728": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "729": {"depth": 0.0, "height": 0.66786, "italic": 0.0, "skew": 0.0}, + "730": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "732": {"depth": 0.0, "height": 0.66786, "italic": 0.0, "skew": 0.0}, + "768": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "769": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.66786, "italic": 0.0, "skew": 0.0}, + "772": {"depth": 0.0, "height": 0.56778, "italic": 0.0, "skew": 0.0}, + "774": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "775": {"depth": 0.0, "height": 0.66786, "italic": 0.0, "skew": 0.0}, + "776": {"depth": 0.0, "height": 0.66786, "italic": 0.0, "skew": 0.0}, + "778": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "779": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "780": {"depth": 0.0, "height": 0.62847, "italic": 0.0, "skew": 0.0}, + "824": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "915": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "916": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "920": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "923": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "926": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "928": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "931": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "933": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "934": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "936": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "937": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "8211": {"depth": 0.0, "height": 0.43056, "italic": 0.02778, "skew": 0.0}, + "8212": {"depth": 0.0, "height": 0.43056, "italic": 0.02778, "skew": 0.0}, + "8216": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8217": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8220": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8221": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8224": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8225": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8230": {"depth": 0.0, "height": 0.12, "italic": 0, "skew": 0}, + "8242": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8407": {"depth": 0.0, "height": 0.71444, "italic": 0.15382, "skew": 0.0}, + "8463": {"depth": 0.0, "height": 0.68889, "italic": 0.0, "skew": 0.0}, + "8465": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8467": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.11111}, + "8472": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.11111}, + "8476": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8501": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8592": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8593": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8594": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8595": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8596": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8597": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8598": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8599": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8600": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8601": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8614": {"depth": 0.011, "height": 0.511, "italic": 0, "skew": 0}, + "8617": {"depth": 0.011, "height": 0.511, "italic": 0, "skew": 0}, + "8618": {"depth": 0.011, "height": 0.511, "italic": 0, "skew": 0}, + "8636": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8637": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8640": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8641": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8652": {"depth": 0.011, "height": 0.671, "italic": 0, "skew": 0}, + "8656": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8657": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8658": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8659": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8660": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8661": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8704": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8706": {"depth": 0.0, "height": 0.69444, "italic": 0.05556, "skew": 0.08334}, + "8707": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8709": {"depth": 0.05556, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8711": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "8712": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8715": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8722": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "8723": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "8725": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8726": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8727": {"depth": -0.03472, "height": 0.46528, "italic": 0.0, "skew": 0.0}, + "8728": {"depth": -0.05555, "height": 0.44445, "italic": 0.0, "skew": 0.0}, + "8729": {"depth": -0.05555, "height": 0.44445, "italic": 0.0, "skew": 0.0}, + "8730": {"depth": 0.2, "height": 0.8, "italic": 0.0, "skew": 0.0}, + "8733": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "8734": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "8736": {"depth": 0.0, "height": 0.69224, "italic": 0.0, "skew": 0.0}, + "8739": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8741": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8743": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8744": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8745": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8746": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8747": {"depth": 0.19444, "height": 0.69444, "italic": 0.11111, "skew": 0.0}, + "8764": {"depth": -0.13313, "height": 0.36687, "italic": 0.0, "skew": 0.0}, + "8768": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8771": {"depth": -0.03625, "height": 0.46375, "italic": 0.0, "skew": 0.0}, + "8773": {"depth": -0.022, "height": 0.589, "italic": 0, "skew": 0}, + "8776": {"depth": -0.01688, "height": 0.48312, "italic": 0.0, "skew": 0.0}, + "8781": {"depth": -0.03625, "height": 0.46375, "italic": 0.0, "skew": 0.0}, + "8784": {"depth": -0.133, "height": 0.67, "italic": 0, "skew": 0}, + "8800": {"depth": 0.215, "height": 0.716, "italic": 0, "skew": 0}, + "8801": {"depth": -0.03625, "height": 0.46375, "italic": 0.0, "skew": 0.0}, + "8804": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "8805": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "8810": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8811": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8826": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8827": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8834": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8835": {"depth": 0.0391, "height": 0.5391, "italic": 0.0, "skew": 0.0}, + "8838": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "8839": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "8846": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8849": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "8850": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "8851": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8852": {"depth": 0.0, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "8853": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "8854": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "8855": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "8856": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "8857": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "8866": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8867": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8868": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8869": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8872": {"depth": 0.249, "height": 0.75, "italic": 0, "skew": 0}, + "8900": {"depth": -0.05555, "height": 0.44445, "italic": 0.0, "skew": 0.0}, + "8901": {"depth": -0.05555, "height": 0.44445, "italic": 0.0, "skew": 0.0}, + "8902": {"depth": -0.03472, "height": 0.46528, "italic": 0.0, "skew": 0.0}, + "8904": {"depth": 0.005, "height": 0.505, "italic": 0, "skew": 0}, + "8942": {"depth": 0.03, "height": 0.9, "italic": 0, "skew": 0}, + "8943": {"depth": -0.19, "height": 0.31, "italic": 0, "skew": 0}, + "8945": {"depth": -0.1, "height": 0.82, "italic": 0, "skew": 0}, + "8968": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8969": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8970": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8971": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8994": {"depth": -0.14236, "height": 0.35764, "italic": 0.0, "skew": 0.0}, + "8995": {"depth": -0.14236, "height": 0.35764, "italic": 0.0, "skew": 0.0}, + "9136": {"depth": 0.244, "height": 0.744, "italic": 0, "skew": 0}, + "9137": {"depth": 0.244, "height": 0.744, "italic": 0, "skew": 0}, + "9651": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9657": {"depth": -0.03472, "height": 0.46528, "italic": 0.0, "skew": 0.0}, + "9661": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9667": {"depth": -0.03472, "height": 0.46528, "italic": 0.0, "skew": 0.0}, + "9711": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9824": {"depth": 0.12963, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9825": {"depth": 0.12963, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9826": {"depth": 0.12963, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9827": {"depth": 0.12963, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9837": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "9838": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "9839": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "10216": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "10217": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "10222": {"depth": 0.244, "height": 0.744, "italic": 0, "skew": 0}, + "10223": {"depth": 0.244, "height": 0.744, "italic": 0, "skew": 0}, + "10229": {"depth": 0.011, "height": 0.511, "italic": 0, "skew": 0}, + "10230": {"depth": 0.011, "height": 0.511, "italic": 0, "skew": 0}, + "10231": {"depth": 0.011, "height": 0.511, "italic": 0, "skew": 0}, + "10232": {"depth": 0.024, "height": 0.525, "italic": 0, "skew": 0}, + "10233": {"depth": 0.024, "height": 0.525, "italic": 0, "skew": 0}, + "10234": {"depth": 0.024, "height": 0.525, "italic": 0, "skew": 0}, + "10236": {"depth": 0.011, "height": 0.511, "italic": 0, "skew": 0}, + "10815": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.0}, + "10927": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0}, + "10928": {"depth": 0.13597, "height": 0.63597, "italic": 0.0, "skew": 0.0} +}, +"Math-BoldItalic": { + "47": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.68611, "italic": 0.04835, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.68611, "italic": 0.06979, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.68611, "italic": 0.03194, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.68611, "italic": 0.05451, "skew": 0.0}, + "70": {"depth": 0.0, "height": 0.68611, "italic": 0.15972, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "72": {"depth": 0.0, "height": 0.68611, "italic": 0.08229, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.68611, "italic": 0.07778, "skew": 0.0}, + "74": {"depth": 0.0, "height": 0.68611, "italic": 0.10069, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.68611, "italic": 0.06979, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.68611, "italic": 0.11424, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.68611, "italic": 0.11424, "skew": 0.0}, + "79": {"depth": 0.0, "height": 0.68611, "italic": 0.03194, "skew": 0.0}, + "80": {"depth": 0.0, "height": 0.68611, "italic": 0.15972, "skew": 0.0}, + "81": {"depth": 0.19444, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.68611, "italic": 0.00421, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.68611, "italic": 0.05382, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.68611, "italic": 0.15972, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.68611, "italic": 0.11424, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.68611, "italic": 0.25555, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.68611, "italic": 0.15972, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.68611, "italic": 0.07778, "skew": 0.0}, + "89": {"depth": 0.0, "height": 0.68611, "italic": 0.25555, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.68611, "italic": 0.06979, "skew": 0.0}, + "97": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "100": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "101": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "102": {"depth": 0.19444, "height": 0.69444, "italic": 0.11042, "skew": 0.0}, + "103": {"depth": 0.19444, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "104": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.69326, "italic": 0.0, "skew": 0.0}, + "106": {"depth": 0.19444, "height": 0.69326, "italic": 0.0622, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.69444, "italic": 0.01852, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.69444, "italic": 0.0088, "skew": 0.0}, + "109": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "112": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "113": {"depth": 0.19444, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "114": {"depth": 0.0, "height": 0.44444, "italic": 0.03194, "skew": 0.0}, + "115": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "116": {"depth": 0.0, "height": 0.63492, "italic": 0.0, "skew": 0.0}, + "117": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "118": {"depth": 0.0, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "119": {"depth": 0.0, "height": 0.44444, "italic": 0.02778, "skew": 0.0}, + "120": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "121": {"depth": 0.19444, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "122": {"depth": 0.0, "height": 0.44444, "italic": 0.04213, "skew": 0.0}, + "915": {"depth": 0.0, "height": 0.68611, "italic": 0.15972, "skew": 0.0}, + "916": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "920": {"depth": 0.0, "height": 0.68611, "italic": 0.03194, "skew": 0.0}, + "923": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "926": {"depth": 0.0, "height": 0.68611, "italic": 0.07458, "skew": 0.0}, + "928": {"depth": 0.0, "height": 0.68611, "italic": 0.08229, "skew": 0.0}, + "931": {"depth": 0.0, "height": 0.68611, "italic": 0.05451, "skew": 0.0}, + "933": {"depth": 0.0, "height": 0.68611, "italic": 0.15972, "skew": 0.0}, + "934": {"depth": 0.0, "height": 0.68611, "italic": 0.0, "skew": 0.0}, + "936": {"depth": 0.0, "height": 0.68611, "italic": 0.11653, "skew": 0.0}, + "937": {"depth": 0.0, "height": 0.68611, "italic": 0.04835, "skew": 0.0}, + "945": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "946": {"depth": 0.19444, "height": 0.69444, "italic": 0.03403, "skew": 0.0}, + "947": {"depth": 0.19444, "height": 0.44444, "italic": 0.06389, "skew": 0.0}, + "948": {"depth": 0.0, "height": 0.69444, "italic": 0.03819, "skew": 0.0}, + "949": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "950": {"depth": 0.19444, "height": 0.69444, "italic": 0.06215, "skew": 0.0}, + "951": {"depth": 0.19444, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "952": {"depth": 0.0, "height": 0.69444, "italic": 0.03194, "skew": 0.0}, + "953": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "954": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "955": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "956": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "957": {"depth": 0.0, "height": 0.44444, "italic": 0.06898, "skew": 0.0}, + "958": {"depth": 0.19444, "height": 0.69444, "italic": 0.03021, "skew": 0.0}, + "959": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "960": {"depth": 0.0, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "961": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "962": {"depth": 0.09722, "height": 0.44444, "italic": 0.07917, "skew": 0.0}, + "963": {"depth": 0.0, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "964": {"depth": 0.0, "height": 0.44444, "italic": 0.13472, "skew": 0.0}, + "965": {"depth": 0.0, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "966": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "967": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "968": {"depth": 0.19444, "height": 0.69444, "italic": 0.03704, "skew": 0.0}, + "969": {"depth": 0.0, "height": 0.44444, "italic": 0.03704, "skew": 0.0}, + "977": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "981": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "982": {"depth": 0.0, "height": 0.44444, "italic": 0.03194, "skew": 0.0}, + "1009": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "1013": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0} +}, +"Math-Italic": { + "47": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.13889}, + "66": {"depth": 0.0, "height": 0.68333, "italic": 0.05017, "skew": 0.08334}, + "67": {"depth": 0.0, "height": 0.68333, "italic": 0.07153, "skew": 0.08334}, + "68": {"depth": 0.0, "height": 0.68333, "italic": 0.02778, "skew": 0.05556}, + "69": {"depth": 0.0, "height": 0.68333, "italic": 0.05764, "skew": 0.08334}, + "70": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.08334}, + "71": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.08334}, + "72": {"depth": 0.0, "height": 0.68333, "italic": 0.08125, "skew": 0.05556}, + "73": {"depth": 0.0, "height": 0.68333, "italic": 0.07847, "skew": 0.11111}, + "74": {"depth": 0.0, "height": 0.68333, "italic": 0.09618, "skew": 0.16667}, + "75": {"depth": 0.0, "height": 0.68333, "italic": 0.07153, "skew": 0.05556}, + "76": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.02778}, + "77": {"depth": 0.0, "height": 0.68333, "italic": 0.10903, "skew": 0.08334}, + "78": {"depth": 0.0, "height": 0.68333, "italic": 0.10903, "skew": 0.08334}, + "79": {"depth": 0.0, "height": 0.68333, "italic": 0.02778, "skew": 0.08334}, + "80": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.08334}, + "81": {"depth": 0.19444, "height": 0.68333, "italic": 0.0, "skew": 0.08334}, + "82": {"depth": 0.0, "height": 0.68333, "italic": 0.00773, "skew": 0.08334}, + "83": {"depth": 0.0, "height": 0.68333, "italic": 0.05764, "skew": 0.08334}, + "84": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.08334}, + "85": {"depth": 0.0, "height": 0.68333, "italic": 0.10903, "skew": 0.02778}, + "86": {"depth": 0.0, "height": 0.68333, "italic": 0.22222, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.68333, "italic": 0.07847, "skew": 0.08334}, + "89": {"depth": 0.0, "height": 0.68333, "italic": 0.22222, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.68333, "italic": 0.07153, "skew": 0.08334}, + "97": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "100": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.16667}, + "101": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "102": {"depth": 0.19444, "height": 0.69444, "italic": 0.10764, "skew": 0.16667}, + "103": {"depth": 0.19444, "height": 0.43056, "italic": 0.03588, "skew": 0.02778}, + "104": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.65952, "italic": 0.0, "skew": 0.0}, + "106": {"depth": 0.19444, "height": 0.65952, "italic": 0.05724, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.69444, "italic": 0.03148, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.69444, "italic": 0.01968, "skew": 0.08334}, + "109": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "112": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "113": {"depth": 0.19444, "height": 0.43056, "italic": 0.03588, "skew": 0.08334}, + "114": {"depth": 0.0, "height": 0.43056, "italic": 0.02778, "skew": 0.05556}, + "115": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "116": {"depth": 0.0, "height": 0.61508, "italic": 0.0, "skew": 0.08334}, + "117": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.02778}, + "118": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.02778}, + "119": {"depth": 0.0, "height": 0.43056, "italic": 0.02691, "skew": 0.08334}, + "120": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.02778}, + "121": {"depth": 0.19444, "height": 0.43056, "italic": 0.03588, "skew": 0.05556}, + "122": {"depth": 0.0, "height": 0.43056, "italic": 0.04398, "skew": 0.05556}, + "915": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.08334}, + "916": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.16667}, + "920": {"depth": 0.0, "height": 0.68333, "italic": 0.02778, "skew": 0.08334}, + "923": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.16667}, + "926": {"depth": 0.0, "height": 0.68333, "italic": 0.07569, "skew": 0.08334}, + "928": {"depth": 0.0, "height": 0.68333, "italic": 0.08125, "skew": 0.05556}, + "931": {"depth": 0.0, "height": 0.68333, "italic": 0.05764, "skew": 0.08334}, + "933": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.05556}, + "934": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.08334}, + "936": {"depth": 0.0, "height": 0.68333, "italic": 0.11, "skew": 0.05556}, + "937": {"depth": 0.0, "height": 0.68333, "italic": 0.05017, "skew": 0.08334}, + "945": {"depth": 0.0, "height": 0.43056, "italic": 0.0037, "skew": 0.02778}, + "946": {"depth": 0.19444, "height": 0.69444, "italic": 0.05278, "skew": 0.08334}, + "947": {"depth": 0.19444, "height": 0.43056, "italic": 0.05556, "skew": 0.0}, + "948": {"depth": 0.0, "height": 0.69444, "italic": 0.03785, "skew": 0.05556}, + "949": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "950": {"depth": 0.19444, "height": 0.69444, "italic": 0.07378, "skew": 0.08334}, + "951": {"depth": 0.19444, "height": 0.43056, "italic": 0.03588, "skew": 0.05556}, + "952": {"depth": 0.0, "height": 0.69444, "italic": 0.02778, "skew": 0.08334}, + "953": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "954": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "955": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "956": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.02778}, + "957": {"depth": 0.0, "height": 0.43056, "italic": 0.06366, "skew": 0.02778}, + "958": {"depth": 0.19444, "height": 0.69444, "italic": 0.04601, "skew": 0.11111}, + "959": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "960": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.0}, + "961": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "962": {"depth": 0.09722, "height": 0.43056, "italic": 0.07986, "skew": 0.08334}, + "963": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.0}, + "964": {"depth": 0.0, "height": 0.43056, "italic": 0.1132, "skew": 0.02778}, + "965": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.02778}, + "966": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "967": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "968": {"depth": 0.19444, "height": 0.69444, "italic": 0.03588, "skew": 0.11111}, + "969": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.0}, + "977": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.08334}, + "981": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.08334}, + "982": {"depth": 0.0, "height": 0.43056, "italic": 0.02778, "skew": 0.0}, + "1009": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "1013": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556} +}, +"Math-Regular": { + "65": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.13889}, + "66": {"depth": 0.0, "height": 0.68333, "italic": 0.05017, "skew": 0.08334}, + "67": {"depth": 0.0, "height": 0.68333, "italic": 0.07153, "skew": 0.08334}, + "68": {"depth": 0.0, "height": 0.68333, "italic": 0.02778, "skew": 0.05556}, + "69": {"depth": 0.0, "height": 0.68333, "italic": 0.05764, "skew": 0.08334}, + "70": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.08334}, + "71": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.08334}, + "72": {"depth": 0.0, "height": 0.68333, "italic": 0.08125, "skew": 0.05556}, + "73": {"depth": 0.0, "height": 0.68333, "italic": 0.07847, "skew": 0.11111}, + "74": {"depth": 0.0, "height": 0.68333, "italic": 0.09618, "skew": 0.16667}, + "75": {"depth": 0.0, "height": 0.68333, "italic": 0.07153, "skew": 0.05556}, + "76": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.02778}, + "77": {"depth": 0.0, "height": 0.68333, "italic": 0.10903, "skew": 0.08334}, + "78": {"depth": 0.0, "height": 0.68333, "italic": 0.10903, "skew": 0.08334}, + "79": {"depth": 0.0, "height": 0.68333, "italic": 0.02778, "skew": 0.08334}, + "80": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.08334}, + "81": {"depth": 0.19444, "height": 0.68333, "italic": 0.0, "skew": 0.08334}, + "82": {"depth": 0.0, "height": 0.68333, "italic": 0.00773, "skew": 0.08334}, + "83": {"depth": 0.0, "height": 0.68333, "italic": 0.05764, "skew": 0.08334}, + "84": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.08334}, + "85": {"depth": 0.0, "height": 0.68333, "italic": 0.10903, "skew": 0.02778}, + "86": {"depth": 0.0, "height": 0.68333, "italic": 0.22222, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.68333, "italic": 0.07847, "skew": 0.08334}, + "89": {"depth": 0.0, "height": 0.68333, "italic": 0.22222, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.68333, "italic": 0.07153, "skew": 0.08334}, + "97": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "100": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.16667}, + "101": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "102": {"depth": 0.19444, "height": 0.69444, "italic": 0.10764, "skew": 0.16667}, + "103": {"depth": 0.19444, "height": 0.43056, "italic": 0.03588, "skew": 0.02778}, + "104": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.65952, "italic": 0.0, "skew": 0.0}, + "106": {"depth": 0.19444, "height": 0.65952, "italic": 0.05724, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.69444, "italic": 0.03148, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.69444, "italic": 0.01968, "skew": 0.08334}, + "109": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "112": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "113": {"depth": 0.19444, "height": 0.43056, "italic": 0.03588, "skew": 0.08334}, + "114": {"depth": 0.0, "height": 0.43056, "italic": 0.02778, "skew": 0.05556}, + "115": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "116": {"depth": 0.0, "height": 0.61508, "italic": 0.0, "skew": 0.08334}, + "117": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.02778}, + "118": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.02778}, + "119": {"depth": 0.0, "height": 0.43056, "italic": 0.02691, "skew": 0.08334}, + "120": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.02778}, + "121": {"depth": 0.19444, "height": 0.43056, "italic": 0.03588, "skew": 0.05556}, + "122": {"depth": 0.0, "height": 0.43056, "italic": 0.04398, "skew": 0.05556}, + "915": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.08334}, + "916": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.16667}, + "920": {"depth": 0.0, "height": 0.68333, "italic": 0.02778, "skew": 0.08334}, + "923": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.16667}, + "926": {"depth": 0.0, "height": 0.68333, "italic": 0.07569, "skew": 0.08334}, + "928": {"depth": 0.0, "height": 0.68333, "italic": 0.08125, "skew": 0.05556}, + "931": {"depth": 0.0, "height": 0.68333, "italic": 0.05764, "skew": 0.08334}, + "933": {"depth": 0.0, "height": 0.68333, "italic": 0.13889, "skew": 0.05556}, + "934": {"depth": 0.0, "height": 0.68333, "italic": 0.0, "skew": 0.08334}, + "936": {"depth": 0.0, "height": 0.68333, "italic": 0.11, "skew": 0.05556}, + "937": {"depth": 0.0, "height": 0.68333, "italic": 0.05017, "skew": 0.08334}, + "945": {"depth": 0.0, "height": 0.43056, "italic": 0.0037, "skew": 0.02778}, + "946": {"depth": 0.19444, "height": 0.69444, "italic": 0.05278, "skew": 0.08334}, + "947": {"depth": 0.19444, "height": 0.43056, "italic": 0.05556, "skew": 0.0}, + "948": {"depth": 0.0, "height": 0.69444, "italic": 0.03785, "skew": 0.05556}, + "949": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "950": {"depth": 0.19444, "height": 0.69444, "italic": 0.07378, "skew": 0.08334}, + "951": {"depth": 0.19444, "height": 0.43056, "italic": 0.03588, "skew": 0.05556}, + "952": {"depth": 0.0, "height": 0.69444, "italic": 0.02778, "skew": 0.08334}, + "953": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "954": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "955": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "956": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.02778}, + "957": {"depth": 0.0, "height": 0.43056, "italic": 0.06366, "skew": 0.02778}, + "958": {"depth": 0.19444, "height": 0.69444, "italic": 0.04601, "skew": 0.11111}, + "959": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "960": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.0}, + "961": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "962": {"depth": 0.09722, "height": 0.43056, "italic": 0.07986, "skew": 0.08334}, + "963": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.0}, + "964": {"depth": 0.0, "height": 0.43056, "italic": 0.1132, "skew": 0.02778}, + "965": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.02778}, + "966": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "967": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.05556}, + "968": {"depth": 0.19444, "height": 0.69444, "italic": 0.03588, "skew": 0.11111}, + "969": {"depth": 0.0, "height": 0.43056, "italic": 0.03588, "skew": 0.0}, + "977": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.08334}, + "981": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.08334}, + "982": {"depth": 0.0, "height": 0.43056, "italic": 0.02778, "skew": 0.0}, + "1009": {"depth": 0.19444, "height": 0.43056, "italic": 0.0, "skew": 0.08334}, + "1013": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.05556} +}, +"SansSerif-Regular": { + "33": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "34": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "35": {"depth": 0.19444, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "36": {"depth": 0.05556, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "37": {"depth": 0.05556, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "38": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "39": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "40": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "42": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "43": {"depth": 0.08333, "height": 0.58333, "italic": 0.0, "skew": 0.0}, + "44": {"depth": 0.125, "height": 0.08333, "italic": 0.0, "skew": 0.0}, + "45": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "46": {"depth": 0.0, "height": 0.08333, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "48": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "49": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "50": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "51": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "52": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "53": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "54": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "55": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "56": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "57": {"depth": 0.0, "height": 0.65556, "italic": 0.0, "skew": 0.0}, + "58": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "59": {"depth": 0.125, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "61": {"depth": -0.13, "height": 0.37, "italic": 0.0, "skew": 0.0}, + "63": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "64": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "70": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "72": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "74": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "79": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "80": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "81": {"depth": 0.125, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.69444, "italic": 0.01389, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.69444, "italic": 0.01389, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "89": {"depth": 0.0, "height": 0.69444, "italic": 0.025, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 0.25, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "94": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "95": {"depth": 0.35, "height": 0.09444, "italic": 0.02778, "skew": 0.0}, + "97": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "100": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "101": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "102": {"depth": 0.0, "height": 0.69444, "italic": 0.06944, "skew": 0.0}, + "103": {"depth": 0.19444, "height": 0.44444, "italic": 0.01389, "skew": 0.0}, + "104": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.67937, "italic": 0.0, "skew": 0.0}, + "106": {"depth": 0.19444, "height": 0.67937, "italic": 0.0, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "109": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "112": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "113": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "114": {"depth": 0.0, "height": 0.44444, "italic": 0.01389, "skew": 0.0}, + "115": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "116": {"depth": 0.0, "height": 0.57143, "italic": 0.0, "skew": 0.0}, + "117": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "118": {"depth": 0.0, "height": 0.44444, "italic": 0.01389, "skew": 0.0}, + "119": {"depth": 0.0, "height": 0.44444, "italic": 0.01389, "skew": 0.0}, + "120": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "121": {"depth": 0.19444, "height": 0.44444, "italic": 0.01389, "skew": 0.0}, + "122": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "126": {"depth": 0.35, "height": 0.32659, "italic": 0.0, "skew": 0.0}, + "305": {"depth": 0.0, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "567": {"depth": 0.19444, "height": 0.44444, "italic": 0.0, "skew": 0.0}, + "768": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "769": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.67659, "italic": 0.0, "skew": 0.0}, + "772": {"depth": 0.0, "height": 0.60889, "italic": 0.0, "skew": 0.0}, + "774": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "775": {"depth": 0.0, "height": 0.67937, "italic": 0.0, "skew": 0.0}, + "776": {"depth": 0.0, "height": 0.67937, "italic": 0.0, "skew": 0.0}, + "778": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "779": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "780": {"depth": 0.0, "height": 0.63194, "italic": 0.0, "skew": 0.0}, + "915": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "916": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "920": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "923": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "926": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "928": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "931": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "933": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "934": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "936": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "937": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8211": {"depth": 0.0, "height": 0.44444, "italic": 0.02778, "skew": 0.0}, + "8212": {"depth": 0.0, "height": 0.44444, "italic": 0.02778, "skew": 0.0}, + "8216": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8217": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8220": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "8221": {"depth": 0.0, "height": 0.69444, "italic": 0.0, "skew": 0.0} +}, +"Script-Regular": { + "65": {"depth": 0.0, "height": 0.7, "italic": 0.22925, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.7, "italic": 0.04087, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.7, "italic": 0.1689, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.7, "italic": 0.09371, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.7, "italic": 0.18583, "skew": 0.0}, + "70": {"depth": 0.0, "height": 0.7, "italic": 0.13634, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.7, "italic": 0.17322, "skew": 0.0}, + "72": {"depth": 0.0, "height": 0.7, "italic": 0.29694, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.7, "italic": 0.19189, "skew": 0.0}, + "74": {"depth": 0.27778, "height": 0.7, "italic": 0.19189, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.7, "italic": 0.31259, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.7, "italic": 0.19189, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.7, "italic": 0.15981, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.7, "italic": 0.3525, "skew": 0.0}, + "79": {"depth": 0.0, "height": 0.7, "italic": 0.08078, "skew": 0.0}, + "80": {"depth": 0.0, "height": 0.7, "italic": 0.08078, "skew": 0.0}, + "81": {"depth": 0.0, "height": 0.7, "italic": 0.03305, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.7, "italic": 0.06259, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.7, "italic": 0.19189, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.7, "italic": 0.29087, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.7, "italic": 0.25815, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.7, "italic": 0.27523, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.7, "italic": 0.27523, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.7, "italic": 0.26006, "skew": 0.0}, + "89": {"depth": 0.0, "height": 0.7, "italic": 0.2939, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.7, "italic": 0.24037, "skew": 0.0} +}, +"Size1-Regular": { + "40": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "92": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "123": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "125": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "710": {"depth": 0.0, "height": 0.72222, "italic": 0.0, "skew": 0.0}, + "732": {"depth": 0.0, "height": 0.72222, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.72222, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.72222, "italic": 0.0, "skew": 0.0}, + "8214": {"depth": -0.00099, "height": 0.601, "italic": 0.0, "skew": 0.0}, + "8593": {"depth": 1e-05, "height": 0.6, "italic": 0.0, "skew": 0.0}, + "8595": {"depth": 1e-05, "height": 0.6, "italic": 0.0, "skew": 0.0}, + "8657": {"depth": 1e-05, "height": 0.6, "italic": 0.0, "skew": 0.0}, + "8659": {"depth": 1e-05, "height": 0.6, "italic": 0.0, "skew": 0.0}, + "8719": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8720": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8721": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8730": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "8739": {"depth": -0.00599, "height": 0.606, "italic": 0.0, "skew": 0.0}, + "8741": {"depth": -0.00599, "height": 0.606, "italic": 0.0, "skew": 0.0}, + "8747": {"depth": 0.30612, "height": 0.805, "italic": 0.19445, "skew": 0.0}, + "8748": {"depth": 0.306, "height": 0.805, "italic": 0.19445, "skew": 0.0}, + "8749": {"depth": 0.306, "height": 0.805, "italic": 0.19445, "skew": 0.0}, + "8750": {"depth": 0.30612, "height": 0.805, "italic": 0.19445, "skew": 0.0}, + "8896": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8897": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8898": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8899": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8968": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "8969": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "8970": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "8971": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "9168": {"depth": -0.00099, "height": 0.601, "italic": 0.0, "skew": 0.0}, + "10216": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "10217": {"depth": 0.35001, "height": 0.85, "italic": 0.0, "skew": 0.0}, + "10752": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "10753": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "10754": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "10756": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "10758": {"depth": 0.25001, "height": 0.75, "italic": 0.0, "skew": 0.0} +}, +"Size2-Regular": { + "40": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "92": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "123": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "125": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "710": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "732": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8719": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "8720": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "8721": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "8730": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "8747": {"depth": 0.86225, "height": 1.36, "italic": 0.44445, "skew": 0.0}, + "8748": {"depth": 0.862, "height": 1.36, "italic": 0.44445, "skew": 0.0}, + "8749": {"depth": 0.862, "height": 1.36, "italic": 0.44445, "skew": 0.0}, + "8750": {"depth": 0.86225, "height": 1.36, "italic": 0.44445, "skew": 0.0}, + "8896": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "8897": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "8898": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "8899": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "8968": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "8969": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "8970": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "8971": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "10216": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "10217": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "10752": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "10753": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "10754": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "10756": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0}, + "10758": {"depth": 0.55001, "height": 1.05, "italic": 0.0, "skew": 0.0} +}, +"Size3-Regular": { + "40": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "92": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "123": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "125": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "710": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "732": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.75, "italic": 0.0, "skew": 0.0}, + "8730": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "8968": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "8969": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "8970": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "8971": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "10216": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0}, + "10217": {"depth": 0.95003, "height": 1.45, "italic": 0.0, "skew": 0.0} +}, +"Size4-Regular": { + "40": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "92": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "123": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "125": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "710": {"depth": 0.0, "height": 0.825, "italic": 0.0, "skew": 0.0}, + "732": {"depth": 0.0, "height": 0.825, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.825, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.825, "italic": 0.0, "skew": 0.0}, + "8730": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "8968": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "8969": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "8970": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "8971": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "9115": {"depth": 0.64502, "height": 1.155, "italic": 0.0, "skew": 0.0}, + "9116": {"depth": 1e-05, "height": 0.6, "italic": 0.0, "skew": 0.0}, + "9117": {"depth": 0.64502, "height": 1.155, "italic": 0.0, "skew": 0.0}, + "9118": {"depth": 0.64502, "height": 1.155, "italic": 0.0, "skew": 0.0}, + "9119": {"depth": 1e-05, "height": 0.6, "italic": 0.0, "skew": 0.0}, + "9120": {"depth": 0.64502, "height": 1.155, "italic": 0.0, "skew": 0.0}, + "9121": {"depth": 0.64502, "height": 1.155, "italic": 0.0, "skew": 0.0}, + "9122": {"depth": -0.00099, "height": 0.601, "italic": 0.0, "skew": 0.0}, + "9123": {"depth": 0.64502, "height": 1.155, "italic": 0.0, "skew": 0.0}, + "9124": {"depth": 0.64502, "height": 1.155, "italic": 0.0, "skew": 0.0}, + "9125": {"depth": -0.00099, "height": 0.601, "italic": 0.0, "skew": 0.0}, + "9126": {"depth": 0.64502, "height": 1.155, "italic": 0.0, "skew": 0.0}, + "9127": {"depth": 1e-05, "height": 0.9, "italic": 0.0, "skew": 0.0}, + "9128": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "9129": {"depth": 0.90001, "height": 0.0, "italic": 0.0, "skew": 0.0}, + "9130": {"depth": 0.0, "height": 0.3, "italic": 0.0, "skew": 0.0}, + "9131": {"depth": 1e-05, "height": 0.9, "italic": 0.0, "skew": 0.0}, + "9132": {"depth": 0.65002, "height": 1.15, "italic": 0.0, "skew": 0.0}, + "9133": {"depth": 0.90001, "height": 0.0, "italic": 0.0, "skew": 0.0}, + "9143": {"depth": 0.88502, "height": 0.915, "italic": 0.0, "skew": 0.0}, + "10216": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "10217": {"depth": 1.25003, "height": 1.75, "italic": 0.0, "skew": 0.0}, + "57344": {"depth": -0.00499, "height": 0.605, "italic": 0.0, "skew": 0.0}, + "57345": {"depth": -0.00499, "height": 0.605, "italic": 0.0, "skew": 0.0}, + "57680": {"depth": 0.0, "height": 0.12, "italic": 0.0, "skew": 0.0}, + "57681": {"depth": 0.0, "height": 0.12, "italic": 0.0, "skew": 0.0}, + "57682": {"depth": 0.0, "height": 0.12, "italic": 0.0, "skew": 0.0}, + "57683": {"depth": 0.0, "height": 0.12, "italic": 0.0, "skew": 0.0} +}, +"Typewriter-Regular": { + "33": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "34": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "35": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "36": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "37": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "38": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "39": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "40": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "41": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "42": {"depth": 0.0, "height": 0.52083, "italic": 0.0, "skew": 0.0}, + "43": {"depth": -0.08056, "height": 0.53055, "italic": 0.0, "skew": 0.0}, + "44": {"depth": 0.13889, "height": 0.125, "italic": 0.0, "skew": 0.0}, + "45": {"depth": -0.08056, "height": 0.53055, "italic": 0.0, "skew": 0.0}, + "46": {"depth": 0.0, "height": 0.125, "italic": 0.0, "skew": 0.0}, + "47": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "48": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "49": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "50": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "51": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "52": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "53": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "54": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "55": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "56": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "57": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "58": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "59": {"depth": 0.13889, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "60": {"depth": -0.05556, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "61": {"depth": -0.19549, "height": 0.41562, "italic": 0.0, "skew": 0.0}, + "62": {"depth": -0.05556, "height": 0.55556, "italic": 0.0, "skew": 0.0}, + "63": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "64": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "65": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "66": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "67": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "68": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "69": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "70": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "71": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "72": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "73": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "74": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "75": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "76": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "77": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "78": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "79": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "80": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "81": {"depth": 0.13889, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "82": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "83": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "84": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "85": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "86": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "87": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "88": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "89": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "90": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "91": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "92": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "93": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "94": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "95": {"depth": 0.09514, "height": 0.0, "italic": 0.0, "skew": 0.0}, + "96": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "97": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "98": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "99": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "100": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "101": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "102": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "103": {"depth": 0.22222, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "104": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "105": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "106": {"depth": 0.22222, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "107": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "108": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "109": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "110": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "111": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "112": {"depth": 0.22222, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "113": {"depth": 0.22222, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "114": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "115": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "116": {"depth": 0.0, "height": 0.55358, "italic": 0.0, "skew": 0.0}, + "117": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "118": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "119": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "120": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "121": {"depth": 0.22222, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "122": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "123": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "124": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "125": {"depth": 0.08333, "height": 0.69444, "italic": 0.0, "skew": 0.0}, + "126": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "127": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "305": {"depth": 0.0, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "567": {"depth": 0.22222, "height": 0.43056, "italic": 0.0, "skew": 0.0}, + "768": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "769": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "770": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "771": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "772": {"depth": 0.0, "height": 0.56555, "italic": 0.0, "skew": 0.0}, + "774": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "776": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "778": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "780": {"depth": 0.0, "height": 0.56597, "italic": 0.0, "skew": 0.0}, + "915": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "916": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "920": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "923": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "926": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "928": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "931": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "933": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "934": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "936": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "937": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "2018": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "2019": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0}, + "8242": {"depth": 0.0, "height": 0.61111, "italic": 0.0, "skew": 0.0} +}}; + +},{}],20:[function(require,module,exports){ +var utils = require("./utils"); +var ParseError = require("./ParseError"); + +// This file contains a list of functions that we parse. The functions map +// contains the following data: + +/* + * Keys are the name of the functions to parse + * The data contains the following keys: + * - numArgs: The number of arguments the function takes. + * - argTypes: (optional) An array corresponding to each argument of the + * function, giving the type of argument that should be parsed. Its + * length should be equal to `numArgs + numOptionalArgs`. Valid + * types: + * - "size": A size-like thing, such as "1em" or "5ex" + * - "color": An html color, like "#abc" or "blue" + * - "original": The same type as the environment that the + * function being parsed is in (e.g. used for the + * bodies of functions like \color where the first + * argument is special and the second argument is + * parsed normally) + * Other possible types (probably shouldn't be used) + * - "text": Text-like (e.g. \text) + * - "math": Normal math + * If undefined, this will be treated as an appropriate length + * array of "original" strings + * - greediness: (optional) The greediness of the function to use ungrouped + * arguments. + * + * E.g. if you have an expression + * \sqrt \frac 1 2 + * since \frac has greediness=2 vs \sqrt's greediness=1, \frac + * will use the two arguments '1' and '2' as its two arguments, + * then that whole function will be used as the argument to + * \sqrt. On the other hand, the expressions + * \frac \frac 1 2 3 + * and + * \frac \sqrt 1 2 + * will fail because \frac and \frac have equal greediness + * and \sqrt has a lower greediness than \frac respectively. To + * make these parse, we would have to change them to: + * \frac {\frac 1 2} 3 + * and + * \frac {\sqrt 1} 2 + * + * The default value is `1` + * - allowedInText: (optional) Whether or not the function is allowed inside + * text mode (default false) + * - numOptionalArgs: (optional) The number of optional arguments the function + * should parse. If the optional arguments aren't found, + * `null` will be passed to the handler in their place. + * (default 0) + * - handler: The function that is called to handle this function and its + * arguments. The arguments are: + * - func: the text of the function + * - [args]: the next arguments are the arguments to the function, + * of which there are numArgs of them + * - positions: the positions in the overall string of the function + * and the arguments. Should only be used to produce + * error messages + * The function should return an object with the following keys: + * - type: The type of element that this is. This is then used in + * buildHTML/buildMathML to determine which function + * should be called to build this node into a DOM node + * Any other data can be added to the object, which will be passed + * in to the function in buildHTML/buildMathML as `group.value`. + */ + +var functions = { + // A normal square root + "\\sqrt": { + numArgs: 1, + numOptionalArgs: 1, + handler: function(func, index, body, positions) { + return { + type: "sqrt", + body: body, + index: index + }; + } + }, + + // Some non-mathy text + "\\text": { + numArgs: 1, + argTypes: ["text"], + greediness: 2, + handler: function(func, body) { + // Since the corresponding buildHTML/buildMathML function expects a + // list of elements, we normalize for different kinds of arguments + // TODO(emily): maybe this should be done somewhere else + var inner; + if (body.type === "ordgroup") { + inner = body.value; + } else { + inner = [body]; + } + + return { + type: "text", + body: inner + }; + } + }, + + // A two-argument custom color + "\\color": { + numArgs: 2, + allowedInText: true, + greediness: 3, + argTypes: ["color", "original"], + handler: function(func, color, body) { + // Normalize the different kinds of bodies (see \text above) + var inner; + if (body.type === "ordgroup") { + inner = body.value; + } else { + inner = [body]; + } + + return { + type: "color", + color: color.value, + value: inner + }; + } + }, + + // An overline + "\\overline": { + numArgs: 1, + handler: function(func, body) { + return { + type: "overline", + body: body + }; + } + }, + + // A box of the width and height + "\\rule": { + numArgs: 2, + numOptionalArgs: 1, + argTypes: ["size", "size", "size"], + handler: function(func, shift, width, height) { + return { + type: "rule", + shift: shift && shift.value, + width: width.value, + height: height.value + }; + } + }, + + // A KaTeX logo + "\\KaTeX": { + numArgs: 0, + handler: function(func) { + return { + type: "katex" + }; + } + }, + + "\\phantom": { + numArgs: 1, + handler: function(func, body) { + var inner; + if (body.type === "ordgroup") { + inner = body.value; + } else { + inner = [body]; + } + + return { + type: "phantom", + value: inner + }; + } + } +}; + +// Extra data needed for the delimiter handler down below +var delimiterSizes = { + "\\bigl" : {type: "open", size: 1}, + "\\Bigl" : {type: "open", size: 2}, + "\\biggl": {type: "open", size: 3}, + "\\Biggl": {type: "open", size: 4}, + "\\bigr" : {type: "close", size: 1}, + "\\Bigr" : {type: "close", size: 2}, + "\\biggr": {type: "close", size: 3}, + "\\Biggr": {type: "close", size: 4}, + "\\bigm" : {type: "rel", size: 1}, + "\\Bigm" : {type: "rel", size: 2}, + "\\biggm": {type: "rel", size: 3}, + "\\Biggm": {type: "rel", size: 4}, + "\\big" : {type: "textord", size: 1}, + "\\Big" : {type: "textord", size: 2}, + "\\bigg" : {type: "textord", size: 3}, + "\\Bigg" : {type: "textord", size: 4} +}; + +var delimiters = [ + "(", ")", "[", "\\lbrack", "]", "\\rbrack", + "\\{", "\\lbrace", "\\}", "\\rbrace", + "\\lfloor", "\\rfloor", "\\lceil", "\\rceil", + "<", ">", "\\langle", "\\rangle", + "\\lvert", "\\rvert", "\\lVert", "\\rVert", + "\\lgroup", "\\rgroup", "\\lmoustache", "\\rmoustache", + "/", "\\backslash", + "|", "\\vert", "\\|", "\\Vert", + "\\uparrow", "\\Uparrow", + "\\downarrow", "\\Downarrow", + "\\updownarrow", "\\Updownarrow", + "." +]; + +var fontAliases = { + "\\Bbb": "\\mathbb", + "\\bold": "\\mathbf", + "\\frak": "\\mathfrak" +}; + +/* + * This is a list of functions which each have the same function but have + * different names so that we don't have to duplicate the data a bunch of times. + * Each element in the list is an object with the following keys: + * - funcs: A list of function names to be associated with the data + * - data: An objecty with the same data as in each value of the `function` + * table above + */ +var duplicatedFunctions = [ + // Single-argument color functions + { + funcs: [ + "\\blue", "\\orange", "\\pink", "\\red", + "\\green", "\\gray", "\\purple", + "\\blueA", "\\blueB", "\\blueC", "\\blueD", "\\blueE", + "\\tealA", "\\tealB", "\\tealC", "\\tealD", "\\tealE", + "\\greenA", "\\greenB", "\\greenC", "\\greenD", "\\greenE", + "\\goldA", "\\goldB", "\\goldC", "\\goldD", "\\goldE", + "\\redA", "\\redB", "\\redC", "\\redD", "\\redE", + "\\maroonA", "\\maroonB", "\\maroonC", "\\maroonD", "\\maroonE", + "\\purpleA", "\\purpleB", "\\purpleC", "\\purpleD", "\\purpleE", + "\\mintA", "\\mintB", "\\mintC", + "\\grayA", "\\grayB", "\\grayC", "\\grayD", "\\grayE", + "\\grayF", "\\grayG", "\\grayH", "\\grayI", + "\\kaBlue", "\\kaGreen" + ], + data: { + numArgs: 1, + allowedInText: true, + greediness: 3, + handler: function(func, body) { + var atoms; + if (body.type === "ordgroup") { + atoms = body.value; + } else { + atoms = [body]; + } + + return { + type: "color", + color: "katex-" + func.slice(1), + value: atoms + }; + } + } + }, + + // There are 2 flags for operators; whether they produce limits in + // displaystyle, and whether they are symbols and should grow in + // displaystyle. These four groups cover the four possible choices. + + // No limits, not symbols + { + funcs: [ + "\\arcsin", "\\arccos", "\\arctan", "\\arg", "\\cos", "\\cosh", + "\\cot", "\\coth", "\\csc", "\\deg", "\\dim", "\\exp", "\\hom", + "\\ker", "\\lg", "\\ln", "\\log", "\\sec", "\\sin", "\\sinh", + "\\tan","\\tanh" + ], + data: { + numArgs: 0, + handler: function(func) { + return { + type: "op", + limits: false, + symbol: false, + body: func + }; + } + } + }, + + // Limits, not symbols + { + funcs: [ + "\\det", "\\gcd", "\\inf", "\\lim", "\\liminf", "\\limsup", "\\max", + "\\min", "\\Pr", "\\sup" + ], + data: { + numArgs: 0, + handler: function(func) { + return { + type: "op", + limits: true, + symbol: false, + body: func + }; + } + } + }, + + // No limits, symbols + { + funcs: [ + "\\int", "\\iint", "\\iiint", "\\oint" + ], + data: { + numArgs: 0, + handler: function(func) { + return { + type: "op", + limits: false, + symbol: true, + body: func + }; + } + } + }, + + // Limits, symbols + { + funcs: [ + "\\coprod", "\\bigvee", "\\bigwedge", "\\biguplus", "\\bigcap", + "\\bigcup", "\\intop", "\\prod", "\\sum", "\\bigotimes", + "\\bigoplus", "\\bigodot", "\\bigsqcup", "\\smallint" + ], + data: { + numArgs: 0, + handler: function(func) { + return { + type: "op", + limits: true, + symbol: true, + body: func + }; + } + } + }, + + // Fractions + { + funcs: [ + "\\dfrac", "\\frac", "\\tfrac", + "\\dbinom", "\\binom", "\\tbinom" + ], + data: { + numArgs: 2, + greediness: 2, + handler: function(func, numer, denom) { + var hasBarLine; + var leftDelim = null; + var rightDelim = null; + var size = "auto"; + + switch (func) { + case "\\dfrac": + case "\\frac": + case "\\tfrac": + hasBarLine = true; + break; + case "\\dbinom": + case "\\binom": + case "\\tbinom": + hasBarLine = false; + leftDelim = "("; + rightDelim = ")"; + break; + default: + throw new Error("Unrecognized genfrac command"); + } + + switch (func) { + case "\\dfrac": + case "\\dbinom": + size = "display"; + break; + case "\\tfrac": + case "\\tbinom": + size = "text"; + break; + } + + return { + type: "genfrac", + numer: numer, + denom: denom, + hasBarLine: hasBarLine, + leftDelim: leftDelim, + rightDelim: rightDelim, + size: size + }; + } + } + }, + + // Left and right overlap functions + { + funcs: ["\\llap", "\\rlap"], + data: { + numArgs: 1, + allowedInText: true, + handler: function(func, body) { + return { + type: func.slice(1), + body: body + }; + } + } + }, + + // Delimiter functions + { + funcs: [ + "\\bigl", "\\Bigl", "\\biggl", "\\Biggl", + "\\bigr", "\\Bigr", "\\biggr", "\\Biggr", + "\\bigm", "\\Bigm", "\\biggm", "\\Biggm", + "\\big", "\\Big", "\\bigg", "\\Bigg", + "\\left", "\\right" + ], + data: { + numArgs: 1, + handler: function(func, delim, positions) { + if (!utils.contains(delimiters, delim.value)) { + throw new ParseError( + "Invalid delimiter: '" + delim.value + "' after '" + + func + "'", + this.lexer, positions[1]); + } + + // \left and \right are caught somewhere in Parser.js, which is + // why this data doesn't match what is in buildHTML. + if (func === "\\left" || func === "\\right") { + return { + type: "leftright", + value: delim.value + }; + } else { + return { + type: "delimsizing", + size: delimiterSizes[func].size, + delimType: delimiterSizes[func].type, + value: delim.value + }; + } + } + } + }, + + // Sizing functions (handled in Parser.js explicitly, hence no handler) + { + funcs: [ + "\\tiny", "\\scriptsize", "\\footnotesize", "\\small", + "\\normalsize", "\\large", "\\Large", "\\LARGE", "\\huge", "\\Huge" + ], + data: { + numArgs: 0 + } + }, + + // Style changing functions (handled in Parser.js explicitly, hence no + // handler) + { + funcs: [ + "\\displaystyle", "\\textstyle", "\\scriptstyle", + "\\scriptscriptstyle" + ], + data: { + numArgs: 0 + } + }, + + { + funcs: [ + // styles + "\\mathrm", "\\mathit", "\\mathbf", + + // families + "\\mathbb", "\\mathcal", "\\mathfrak", "\\mathscr", "\\mathsf", + "\\mathtt", + + // aliases + "\\Bbb", "\\bold", "\\frak" + ], + data: { + numArgs: 1, + handler: function (func, body) { + if (func in fontAliases) { + func = fontAliases[func]; + } + return { + type: "font", + font: func.slice(1), + body: body + }; + } + } + }, + + // Accents + { + funcs: [ + "\\acute", "\\grave", "\\ddot", "\\tilde", "\\bar", "\\breve", + "\\check", "\\hat", "\\vec", "\\dot" + // We don't support expanding accents yet + // "\\widetilde", "\\widehat" + ], + data: { + numArgs: 1, + handler: function(func, base) { + return { + type: "accent", + accent: func, + base: base + }; + } + } + }, + + // Infix generalized fractions + { + funcs: ["\\over", "\\choose"], + data: { + numArgs: 0, + handler: function (func) { + var replaceWith; + switch (func) { + case "\\over": + replaceWith = "\\frac"; + break; + case "\\choose": + replaceWith = "\\binom"; + break; + default: + throw new Error("Unrecognized infix genfrac command"); + } + return { + type: "infix", + replaceWith: replaceWith + }; + } + } + }, + + // Row breaks for aligned data + { + funcs: ["\\\\", "\\cr"], + data: { + numArgs: 0, + numOptionalArgs: 1, + argTypes: ["size"], + handler: function(func, size) { + return { + type: "cr", + size: size + }; + } + } + }, + + // Environment delimiters + { + funcs: ["\\begin", "\\end"], + data: { + numArgs: 1, + argTypes: ["text"], + handler: function(func, nameGroup, positions) { + if (nameGroup.type !== "ordgroup") { + throw new ParseError( + "Invalid environment name", + this.lexer, positions[1]); + } + var name = ""; + for (var i = 0; i < nameGroup.value.length; ++i) { + name += nameGroup.value[i].value; + } + return { + type: "environment", + name: name, + namepos: positions[1] + }; + } + } + } +]; + +var addFuncsWithData = function(funcs, data) { + for (var i = 0; i < funcs.length; i++) { + functions[funcs[i]] = data; + } +}; + +// Add all of the functions in duplicatedFunctions to the functions map +for (var i = 0; i < duplicatedFunctions.length; i++) { + addFuncsWithData(duplicatedFunctions[i].funcs, duplicatedFunctions[i].data); +} + +// Set default values of functions +for (var f in functions) { + if (functions.hasOwnProperty(f)) { + var func = functions[f]; + + functions[f] = { + numArgs: func.numArgs, + argTypes: func.argTypes, + greediness: (func.greediness === undefined) ? 1 : func.greediness, + allowedInText: func.allowedInText ? func.allowedInText : false, + numOptionalArgs: (func.numOptionalArgs === undefined) ? 0 : + func.numOptionalArgs, + handler: func.handler + }; + } +} + +module.exports = { + funcs: functions +}; + +},{"./ParseError":7,"./utils":25}],21:[function(require,module,exports){ +/** + * These objects store data about MathML nodes. This is the MathML equivalent + * of the types in domTree.js. Since MathML handles its own rendering, and + * since we're mainly using MathML to improve accessibility, we don't manage + * any of the styling state that the plain DOM nodes do. + * + * The `toNode` and `toMarkup` functions work simlarly to how they do in + * domTree.js, creating namespaced DOM nodes and HTML text markup respectively. + */ + +var utils = require("./utils"); + +/** + * This node represents a general purpose MathML node of any type. The + * constructor requires the type of node to create (for example, `"mo"` or + * `"mspace"`, corresponding to `` and `` tags). + */ +function MathNode(type, children) { + this.type = type; + this.attributes = {}; + this.children = children || []; +} + +/** + * Sets an attribute on a MathML node. MathML depends on attributes to convey a + * semantic content, so this is used heavily. + */ +MathNode.prototype.setAttribute = function(name, value) { + this.attributes[name] = value; +}; + +/** + * Converts the math node into a MathML-namespaced DOM element. + */ +MathNode.prototype.toNode = function() { + var node = document.createElementNS( + "http://www.w3.org/1998/Math/MathML", this.type); + + for (var attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + node.setAttribute(attr, this.attributes[attr]); + } + } + + for (var i = 0; i < this.children.length; i++) { + node.appendChild(this.children[i].toNode()); + } + + return node; +}; + +/** + * Converts the math node into an HTML markup string. + */ +MathNode.prototype.toMarkup = function() { + var markup = "<" + this.type; + + // Add the attributes + for (var attr in this.attributes) { + if (Object.prototype.hasOwnProperty.call(this.attributes, attr)) { + markup += " " + attr + "=\""; + markup += utils.escape(this.attributes[attr]); + markup += "\""; + } + } + + markup += ">"; + + for (var i = 0; i < this.children.length; i++) { + markup += this.children[i].toMarkup(); + } + + markup += ""; + + return markup; +}; + +/** + * This node represents a piece of text. + */ +function TextNode(text) { + this.text = text; +} + +/** + * Converts the text node into a DOM text node. + */ +TextNode.prototype.toNode = function() { + return document.createTextNode(this.text); +}; + +/** + * Converts the text node into HTML markup (which is just the text itself). + */ +TextNode.prototype.toMarkup = function() { + return utils.escape(this.text); +}; + +module.exports = { + MathNode: MathNode, + TextNode: TextNode +}; + +},{"./utils":25}],22:[function(require,module,exports){ +/** + * The resulting parse tree nodes of the parse tree. + */ +function ParseNode(type, value, mode) { + this.type = type; + this.value = value; + this.mode = mode; +} + +/** + * A result and final position returned by the `.parse...` functions. + * + */ +function ParseResult(result, newPosition, peek) { + this.result = result; + this.position = newPosition; +} + +module.exports = { + ParseNode: ParseNode, + ParseResult: ParseResult +}; + + +},{}],23:[function(require,module,exports){ +/** + * Provides a single function for parsing an expression using a Parser + * TODO(emily): Remove this + */ + +var Parser = require("./Parser"); + +/** + * Parses an expression using a Parser, then returns the parsed result. + */ +var parseTree = function(toParse, settings) { + var parser = new Parser(toParse, settings); + + return parser.parse(); +}; + +module.exports = parseTree; + +},{"./Parser":8}],24:[function(require,module,exports){ +/** + * This file holds a list of all no-argument functions and single-character + * symbols (like 'a' or ';'). + * + * For each of the symbols, there are three properties they can have: + * - font (required): the font to be used for this symbol. Either "main" (the + normal font), or "ams" (the ams fonts). + * - group (required): the ParseNode group type the symbol should have (i.e. + "textord", "mathord", etc). + See https://github.com/Khan/KaTeX/wiki/Examining-TeX#group-types + * - replace (optional): the character that this symbol or function should be + * replaced with (i.e. "\phi" has a replace value of "\u03d5", the phi + * character in the main font). + * + * The outermost map in the table indicates what mode the symbols should be + * accepted in (e.g. "math" or "text"). + */ + +var symbols = { + "math": { + // Relation Symbols + "\\equiv": { + font: "main", + group: "rel", + replace: "\u2261" + }, + "\\prec": { + font: "main", + group: "rel", + replace: "\u227a" + }, + "\\succ": { + font: "main", + group: "rel", + replace: "\u227b" + }, + "\\sim": { + font: "main", + group: "rel", + replace: "\u223c" + }, + "\\perp": { + font: "main", + group: "rel", + replace: "\u22a5" + }, + "\\preceq": { + font: "main", + group: "rel", + replace: "\u2aaf" + }, + "\\succeq": { + font: "main", + group: "rel", + replace: "\u2ab0" + }, + "\\simeq": { + font: "main", + group: "rel", + replace: "\u2243" + }, + "\\mid": { + font: "main", + group: "rel", + replace: "\u2223" + }, + "\\ll": { + font: "main", + group: "rel", + replace: "\u226a" + }, + "\\gg": { + font: "main", + group: "rel", + replace: "\u226b" + }, + "\\asymp": { + font: "main", + group: "rel", + replace: "\u224d" + }, + "\\parallel": { + font: "main", + group: "rel", + replace: "\u2225" + }, + "\\bowtie": { + font: "main", + group: "rel", + replace: "\u22c8" + }, + "\\smile": { + font: "main", + group: "rel", + replace: "\u2323" + }, + "\\sqsubseteq": { + font: "main", + group: "rel", + replace: "\u2291" + }, + "\\sqsupseteq": { + font: "main", + group: "rel", + replace: "\u2292" + }, + "\\doteq": { + font: "main", + group: "rel", + replace: "\u2250" + }, + "\\frown": { + font: "main", + group: "rel", + replace: "\u2322" + }, + "\\ni": { + font: "main", + group: "rel", + replace: "\u220b" + }, + "\\propto": { + font: "main", + group: "rel", + replace: "\u221d" + }, + "\\vdash": { + font: "main", + group: "rel", + replace: "\u22a2" + }, + "\\dashv": { + font: "main", + group: "rel", + replace: "\u22a3" + }, + "\\owns": { + font: "main", + group: "rel", + replace: "\u220b" + }, + + // Punctuation + "\\ldotp": { + font: "main", + group: "punct", + replace: "\u002e" + }, + "\\cdotp": { + font: "main", + group: "punct", + replace: "\u22c5" + }, + + // Misc Symbols + "\\#": { + font: "main", + group: "textord", + replace: "\u0023" + }, + "\\&": { + font: "main", + group: "textord", + replace: "\u0026" + }, + "\\aleph": { + font: "main", + group: "textord", + replace: "\u2135" + }, + "\\forall": { + font: "main", + group: "textord", + replace: "\u2200" + }, + "\\hbar": { + font: "main", + group: "textord", + replace: "\u210f" + }, + "\\exists": { + font: "main", + group: "textord", + replace: "\u2203" + }, + "\\nabla": { + font: "main", + group: "textord", + replace: "\u2207" + }, + "\\flat": { + font: "main", + group: "textord", + replace: "\u266d" + }, + "\\ell": { + font: "main", + group: "textord", + replace: "\u2113" + }, + "\\natural": { + font: "main", + group: "textord", + replace: "\u266e" + }, + "\\clubsuit": { + font: "main", + group: "textord", + replace: "\u2663" + }, + "\\wp": { + font: "main", + group: "textord", + replace: "\u2118" + }, + "\\sharp": { + font: "main", + group: "textord", + replace: "\u266f" + }, + "\\diamondsuit": { + font: "main", + group: "textord", + replace: "\u2662" + }, + "\\Re": { + font: "main", + group: "textord", + replace: "\u211c" + }, + "\\heartsuit": { + font: "main", + group: "textord", + replace: "\u2661" + }, + "\\Im": { + font: "main", + group: "textord", + replace: "\u2111" + }, + "\\spadesuit": { + font: "main", + group: "textord", + replace: "\u2660" + }, + + // Math and Text + "\\dag": { + font: "main", + group: "textord", + replace: "\u2020" + }, + "\\ddag": { + font: "main", + group: "textord", + replace: "\u2021" + }, + + // Large Delimiters + "\\rmoustache": { + font: "main", + group: "close", + replace: "\u23b1" + }, + "\\lmoustache": { + font: "main", + group: "open", + replace: "\u23b0" + }, + "\\rgroup": { + font: "main", + group: "close", + replace: "\u27ef" + }, + "\\lgroup": { + font: "main", + group: "open", + replace: "\u27ee" + }, + + // Binary Operators + "\\mp": { + font: "main", + group: "bin", + replace: "\u2213" + }, + "\\ominus": { + font: "main", + group: "bin", + replace: "\u2296" + }, + "\\uplus": { + font: "main", + group: "bin", + replace: "\u228e" + }, + "\\sqcap": { + font: "main", + group: "bin", + replace: "\u2293" + }, + "\\ast": { + font: "main", + group: "bin", + replace: "\u2217" + }, + "\\sqcup": { + font: "main", + group: "bin", + replace: "\u2294" + }, + "\\bigcirc": { + font: "main", + group: "bin", + replace: "\u25ef" + }, + "\\bullet": { + font: "main", + group: "bin", + replace: "\u2219" + }, + "\\ddagger": { + font: "main", + group: "bin", + replace: "\u2021" + }, + "\\wr": { + font: "main", + group: "bin", + replace: "\u2240" + }, + "\\amalg": { + font: "main", + group: "bin", + replace: "\u2a3f" + }, + + // Arrow Symbols + "\\longleftarrow": { + font: "main", + group: "rel", + replace: "\u27f5" + }, + "\\Leftarrow": { + font: "main", + group: "rel", + replace: "\u21d0" + }, + "\\Longleftarrow": { + font: "main", + group: "rel", + replace: "\u27f8" + }, + "\\longrightarrow": { + font: "main", + group: "rel", + replace: "\u27f6" + }, + "\\Rightarrow": { + font: "main", + group: "rel", + replace: "\u21d2" + }, + "\\Longrightarrow": { + font: "main", + group: "rel", + replace: "\u27f9" + }, + "\\leftrightarrow": { + font: "main", + group: "rel", + replace: "\u2194" + }, + "\\longleftrightarrow": { + font: "main", + group: "rel", + replace: "\u27f7" + }, + "\\Leftrightarrow": { + font: "main", + group: "rel", + replace: "\u21d4" + }, + "\\Longleftrightarrow": { + font: "main", + group: "rel", + replace: "\u27fa" + }, + "\\mapsto": { + font: "main", + group: "rel", + replace: "\u21a6" + }, + "\\longmapsto": { + font: "main", + group: "rel", + replace: "\u27fc" + }, + "\\nearrow": { + font: "main", + group: "rel", + replace: "\u2197" + }, + "\\hookleftarrow": { + font: "main", + group: "rel", + replace: "\u21a9" + }, + "\\hookrightarrow": { + font: "main", + group: "rel", + replace: "\u21aa" + }, + "\\searrow": { + font: "main", + group: "rel", + replace: "\u2198" + }, + "\\leftharpoonup": { + font: "main", + group: "rel", + replace: "\u21bc" + }, + "\\rightharpoonup": { + font: "main", + group: "rel", + replace: "\u21c0" + }, + "\\swarrow": { + font: "main", + group: "rel", + replace: "\u2199" + }, + "\\leftharpoondown": { + font: "main", + group: "rel", + replace: "\u21bd" + }, + "\\rightharpoondown": { + font: "main", + group: "rel", + replace: "\u21c1" + }, + "\\nwarrow": { + font: "main", + group: "rel", + replace: "\u2196" + }, + "\\rightleftharpoons": { + font: "main", + group: "rel", + replace: "\u21cc" + }, + + // AMS Negated Binary Relations + "\\nless": { + font: "ams", + group: "rel", + replace: "\u226e" + }, + "\\nleqslant": { + font: "ams", + group: "rel", + replace: "\ue010" + }, + "\\nleqq": { + font: "ams", + group: "rel", + replace: "\ue011" + }, + "\\lneq": { + font: "ams", + group: "rel", + replace: "\u2a87" + }, + "\\lneqq": { + font: "ams", + group: "rel", + replace: "\u2268" + }, + "\\lvertneqq": { + font: "ams", + group: "rel", + replace: "\ue00c" + }, + "\\lnsim": { + font: "ams", + group: "rel", + replace: "\u22e6" + }, + "\\lnapprox": { + font: "ams", + group: "rel", + replace: "\u2a89" + }, + "\\nprec": { + font: "ams", + group: "rel", + replace: "\u2280" + }, + "\\npreceq": { + font: "ams", + group: "rel", + replace: "\u22e0" + }, + "\\precnsim": { + font: "ams", + group: "rel", + replace: "\u22e8" + }, + "\\precnapprox": { + font: "ams", + group: "rel", + replace: "\u2ab9" + }, + "\\nsim": { + font: "ams", + group: "rel", + replace: "\u2241" + }, + "\\nshortmid": { + font: "ams", + group: "rel", + replace: "\ue006" + }, + "\\nmid": { + font: "ams", + group: "rel", + replace: "\u2224" + }, + "\\nvdash": { + font: "ams", + group: "rel", + replace: "\u22ac" + }, + "\\nvDash": { + font: "ams", + group: "rel", + replace: "\u22ad" + }, + "\\ntriangleleft": { + font: "ams", + group: "rel", + replace: "\u22ea" + }, + "\\ntrianglelefteq": { + font: "ams", + group: "rel", + replace: "\u22ec" + }, + "\\subsetneq": { + font: "ams", + group: "rel", + replace: "\u228a" + }, + "\\varsubsetneq": { + font: "ams", + group: "rel", + replace: "\ue01a" + }, + "\\subsetneqq": { + font: "ams", + group: "rel", + replace: "\u2acb" + }, + "\\varsubsetneqq": { + font: "ams", + group: "rel", + replace: "\ue017" + }, + "\\ngtr": { + font: "ams", + group: "rel", + replace: "\u226f" + }, + "\\ngeqslant": { + font: "ams", + group: "rel", + replace: "\ue00f" + }, + "\\ngeqq": { + font: "ams", + group: "rel", + replace: "\ue00e" + }, + "\\gneq": { + font: "ams", + group: "rel", + replace: "\u2a88" + }, + "\\gneqq": { + font: "ams", + group: "rel", + replace: "\u2269" + }, + "\\gvertneqq": { + font: "ams", + group: "rel", + replace: "\ue00d" + }, + "\\gnsim": { + font: "ams", + group: "rel", + replace: "\u22e7" + }, + "\\gnapprox": { + font: "ams", + group: "rel", + replace: "\u2a8a" + }, + "\\nsucc": { + font: "ams", + group: "rel", + replace: "\u2281" + }, + "\\nsucceq": { + font: "ams", + group: "rel", + replace: "\u22e1" + }, + "\\succnsim": { + font: "ams", + group: "rel", + replace: "\u22e9" + }, + "\\succnapprox": { + font: "ams", + group: "rel", + replace: "\u2aba" + }, + "\\ncong": { + font: "ams", + group: "rel", + replace: "\u2246" + }, + "\\nshortparallel": { + font: "ams", + group: "rel", + replace: "\ue007" + }, + "\\nparallel": { + font: "ams", + group: "rel", + replace: "\u2226" + }, + "\\nVDash": { + font: "ams", + group: "rel", + replace: "\u22af" + }, + "\\ntriangleright": { + font: "ams", + group: "rel", + replace: "\u22eb" + }, + "\\ntrianglerighteq": { + font: "ams", + group: "rel", + replace: "\u22ed" + }, + "\\nsupseteqq": { + font: "ams", + group: "rel", + replace: "\ue018" + }, + "\\supsetneq": { + font: "ams", + group: "rel", + replace: "\u228b" + }, + "\\varsupsetneq": { + font: "ams", + group: "rel", + replace: "\ue01b" + }, + "\\supsetneqq": { + font: "ams", + group: "rel", + replace: "\u2acc" + }, + "\\varsupsetneqq": { + font: "ams", + group: "rel", + replace: "\ue019" + }, + "\\nVdash": { + font: "ams", + group: "rel", + replace: "\u22ae" + }, + "\\precneqq": { + font: "ams", + group: "rel", + replace: "\u2ab5" + }, + "\\succneqq": { + font: "ams", + group: "rel", + replace: "\u2ab6" + }, + "\\nsubseteqq": { + font: "ams", + group: "rel", + replace: "\ue016" + }, + "\\unlhd": { + font: "ams", + group: "bin", + replace: "\u22b4" + }, + "\\unrhd": { + font: "ams", + group: "bin", + replace: "\u22b5" + }, + + // AMS Negated Arrows + "\\nleftarrow": { + font: "ams", + group: "rel", + replace: "\u219a" + }, + "\\nrightarrow": { + font: "ams", + group: "rel", + replace: "\u219b" + }, + "\\nLeftarrow": { + font: "ams", + group: "rel", + replace: "\u21cd" + }, + "\\nRightarrow": { + font: "ams", + group: "rel", + replace: "\u21cf" + }, + "\\nleftrightarrow": { + font: "ams", + group: "rel", + replace: "\u21ae" + }, + "\\nLeftrightarrow": { + font: "ams", + group: "rel", + replace: "\u21ce" + }, + + // AMS Misc + "\\vartriangle": { + font: "ams", + group: "rel", + replace: "\u25b3" + }, + "\\hslash": { + font: "ams", + group: "textord", + replace: "\u210f" + }, + "\\triangledown": { + font: "ams", + group: "textord", + replace: "\u25bd" + }, + "\\lozenge": { + font: "ams", + group: "textord", + replace: "\u25ca" + }, + "\\circledS": { + font: "ams", + group: "textord", + replace: "\u24c8" + }, + "\\circledR": { + font: "ams", + group: "textord", + replace: "\u00ae" + }, + "\\measuredangle": { + font: "ams", + group: "textord", + replace: "\u2221" + }, + "\\nexists": { + font: "ams", + group: "textord", + replace: "\u2204" + }, + "\\mho": { + font: "ams", + group: "textord", + replace: "\u2127" + }, + "\\Finv": { + font: "ams", + group: "textord", + replace: "\u2132" + }, + "\\Game": { + font: "ams", + group: "textord", + replace: "\u2141" + }, + "\\Bbbk": { + font: "ams", + group: "textord", + replace: "\u006b" + }, + "\\backprime": { + font: "ams", + group: "textord", + replace: "\u2035" + }, + "\\blacktriangle": { + font: "ams", + group: "textord", + replace: "\u25b2" + }, + "\\blacktriangledown": { + font: "ams", + group: "textord", + replace: "\u25bc" + }, + "\\blacksquare": { + font: "ams", + group: "textord", + replace: "\u25a0" + }, + "\\blacklozenge": { + font: "ams", + group: "textord", + replace: "\u29eb" + }, + "\\bigstar": { + font: "ams", + group: "textord", + replace: "\u2605" + }, + "\\sphericalangle": { + font: "ams", + group: "textord", + replace: "\u2222" + }, + "\\complement": { + font: "ams", + group: "textord", + replace: "\u2201" + }, + "\\eth": { + font: "ams", + group: "textord", + replace: "\u00f0" + }, + "\\diagup": { + font: "ams", + group: "textord", + replace: "\u2571" + }, + "\\diagdown": { + font: "ams", + group: "textord", + replace: "\u2572" + }, + "\\square": { + font: "ams", + group: "textord", + replace: "\u25a1" + }, + "\\Box": { + font: "ams", + group: "textord", + replace: "\u25a1" + }, + "\\Diamond": { + font: "ams", + group: "textord", + replace: "\u25ca" + }, + "\\yen": { + font: "ams", + group: "textord", + replace: "\u00a5" + }, + "\\checkmark": { + font: "ams", + group: "textord", + replace: "\u2713" + }, + + // AMS Hebrew + "\\beth": { + font: "ams", + group: "textord", + replace: "\u2136" + }, + "\\daleth": { + font: "ams", + group: "textord", + replace: "\u2138" + }, + "\\gimel": { + font: "ams", + group: "textord", + replace: "\u2137" + }, + + // AMS Greek + "\\digamma": { + font: "ams", + group: "textord", + replace: "\u03dd" + }, + "\\varkappa": { + font: "ams", + group: "textord", + replace: "\u03f0" + }, + + // AMS Delimiters + "\\ulcorner": { + font: "ams", + group: "open", + replace: "\u250c" + }, + "\\urcorner": { + font: "ams", + group: "close", + replace: "\u2510" + }, + "\\llcorner": { + font: "ams", + group: "open", + replace: "\u2514" + }, + "\\lrcorner": { + font: "ams", + group: "close", + replace: "\u2518" + }, + + // AMS Binary Relations + "\\leqq": { + font: "ams", + group: "rel", + replace: "\u2266" + }, + "\\leqslant": { + font: "ams", + group: "rel", + replace: "\u2a7d" + }, + "\\eqslantless": { + font: "ams", + group: "rel", + replace: "\u2a95" + }, + "\\lesssim": { + font: "ams", + group: "rel", + replace: "\u2272" + }, + "\\lessapprox": { + font: "ams", + group: "rel", + replace: "\u2a85" + }, + "\\approxeq": { + font: "ams", + group: "rel", + replace: "\u224a" + }, + "\\lessdot": { + font: "ams", + group: "bin", + replace: "\u22d6" + }, + "\\lll": { + font: "ams", + group: "rel", + replace: "\u22d8" + }, + "\\lessgtr": { + font: "ams", + group: "rel", + replace: "\u2276" + }, + "\\lesseqgtr": { + font: "ams", + group: "rel", + replace: "\u22da" + }, + "\\lesseqqgtr": { + font: "ams", + group: "rel", + replace: "\u2a8b" + }, + "\\doteqdot": { + font: "ams", + group: "rel", + replace: "\u2251" + }, + "\\risingdotseq": { + font: "ams", + group: "rel", + replace: "\u2253" + }, + "\\fallingdotseq": { + font: "ams", + group: "rel", + replace: "\u2252" + }, + "\\backsim": { + font: "ams", + group: "rel", + replace: "\u223d" + }, + "\\backsimeq": { + font: "ams", + group: "rel", + replace: "\u22cd" + }, + "\\subseteqq": { + font: "ams", + group: "rel", + replace: "\u2ac5" + }, + "\\Subset": { + font: "ams", + group: "rel", + replace: "\u22d0" + }, + "\\sqsubset": { + font: "ams", + group: "rel", + replace: "\u228f" + }, + "\\preccurlyeq": { + font: "ams", + group: "rel", + replace: "\u227c" + }, + "\\curlyeqprec": { + font: "ams", + group: "rel", + replace: "\u22de" + }, + "\\precsim": { + font: "ams", + group: "rel", + replace: "\u227e" + }, + "\\precapprox": { + font: "ams", + group: "rel", + replace: "\u2ab7" + }, + "\\vartriangleleft": { + font: "ams", + group: "rel", + replace: "\u22b2" + }, + "\\trianglelefteq": { + font: "ams", + group: "rel", + replace: "\u22b4" + }, + "\\vDash": { + font: "ams", + group: "rel", + replace: "\u22a8" + }, + "\\Vvdash": { + font: "ams", + group: "rel", + replace: "\u22aa" + }, + "\\smallsmile": { + font: "ams", + group: "rel", + replace: "\u2323" + }, + "\\smallfrown": { + font: "ams", + group: "rel", + replace: "\u2322" + }, + "\\bumpeq": { + font: "ams", + group: "rel", + replace: "\u224f" + }, + "\\Bumpeq": { + font: "ams", + group: "rel", + replace: "\u224e" + }, + "\\geqq": { + font: "ams", + group: "rel", + replace: "\u2267" + }, + "\\geqslant": { + font: "ams", + group: "rel", + replace: "\u2a7e" + }, + "\\eqslantgtr": { + font: "ams", + group: "rel", + replace: "\u2a96" + }, + "\\gtrsim": { + font: "ams", + group: "rel", + replace: "\u2273" + }, + "\\gtrapprox": { + font: "ams", + group: "rel", + replace: "\u2a86" + }, + "\\gtrdot": { + font: "ams", + group: "bin", + replace: "\u22d7" + }, + "\\ggg": { + font: "ams", + group: "rel", + replace: "\u22d9" + }, + "\\gtrless": { + font: "ams", + group: "rel", + replace: "\u2277" + }, + "\\gtreqless": { + font: "ams", + group: "rel", + replace: "\u22db" + }, + "\\gtreqqless": { + font: "ams", + group: "rel", + replace: "\u2a8c" + }, + "\\eqcirc": { + font: "ams", + group: "rel", + replace: "\u2256" + }, + "\\circeq": { + font: "ams", + group: "rel", + replace: "\u2257" + }, + "\\triangleq": { + font: "ams", + group: "rel", + replace: "\u225c" + }, + "\\thicksim": { + font: "ams", + group: "rel", + replace: "\u223c" + }, + "\\thickapprox": { + font: "ams", + group: "rel", + replace: "\u2248" + }, + "\\supseteqq": { + font: "ams", + group: "rel", + replace: "\u2ac6" + }, + "\\Supset": { + font: "ams", + group: "rel", + replace: "\u22d1" + }, + "\\sqsupset": { + font: "ams", + group: "rel", + replace: "\u2290" + }, + "\\succcurlyeq": { + font: "ams", + group: "rel", + replace: "\u227d" + }, + "\\curlyeqsucc": { + font: "ams", + group: "rel", + replace: "\u22df" + }, + "\\succsim": { + font: "ams", + group: "rel", + replace: "\u227f" + }, + "\\succapprox": { + font: "ams", + group: "rel", + replace: "\u2ab8" + }, + "\\vartriangleright": { + font: "ams", + group: "rel", + replace: "\u22b3" + }, + "\\trianglerighteq": { + font: "ams", + group: "rel", + replace: "\u22b5" + }, + "\\Vdash": { + font: "ams", + group: "rel", + replace: "\u22a9" + }, + "\\shortmid": { + font: "ams", + group: "rel", + replace: "\u2223" + }, + "\\shortparallel": { + font: "ams", + group: "rel", + replace: "\u2225" + }, + "\\between": { + font: "ams", + group: "rel", + replace: "\u226c" + }, + "\\pitchfork": { + font: "ams", + group: "rel", + replace: "\u22d4" + }, + "\\varpropto": { + font: "ams", + group: "rel", + replace: "\u221d" + }, + "\\blacktriangleleft": { + font: "ams", + group: "rel", + replace: "\u25c0" + }, + "\\therefore": { + font: "ams", + group: "rel", + replace: "\u2234" + }, + "\\backepsilon": { + font: "ams", + group: "rel", + replace: "\u220d" + }, + "\\blacktriangleright": { + font: "ams", + group: "rel", + replace: "\u25b6" + }, + "\\because": { + font: "ams", + group: "rel", + replace: "\u2235" + }, + "\\llless": { + font: "ams", + group: "rel", + replace: "\u22d8" + }, + "\\gggtr": { + font: "ams", + group: "rel", + replace: "\u22d9" + }, + "\\lhd": { + font: "ams", + group: "bin", + replace: "\u22b2" + }, + "\\rhd": { + font: "ams", + group: "bin", + replace: "\u22b3" + }, + "\\eqsim": { + font: "ams", + group: "rel", + replace: "\u2242" + }, + "\\Join": { + font: "main", + group: "rel", + replace: "\u22c8" + }, + "\\Doteq": { + font: "ams", + group: "rel", + replace: "\u2251" + }, + + // AMS Binary Operators + "\\dotplus": { + font: "ams", + group: "bin", + replace: "\u2214" + }, + "\\smallsetminus": { + font: "ams", + group: "bin", + replace: "\u2216" + }, + "\\Cap": { + font: "ams", + group: "bin", + replace: "\u22d2" + }, + "\\Cup": { + font: "ams", + group: "bin", + replace: "\u22d3" + }, + "\\doublebarwedge": { + font: "ams", + group: "bin", + replace: "\u2a5e" + }, + "\\boxminus": { + font: "ams", + group: "bin", + replace: "\u229f" + }, + "\\boxplus": { + font: "ams", + group: "bin", + replace: "\u229e" + }, + "\\divideontimes": { + font: "ams", + group: "bin", + replace: "\u22c7" + }, + "\\ltimes": { + font: "ams", + group: "bin", + replace: "\u22c9" + }, + "\\rtimes": { + font: "ams", + group: "bin", + replace: "\u22ca" + }, + "\\leftthreetimes": { + font: "ams", + group: "bin", + replace: "\u22cb" + }, + "\\rightthreetimes": { + font: "ams", + group: "bin", + replace: "\u22cc" + }, + "\\curlywedge": { + font: "ams", + group: "bin", + replace: "\u22cf" + }, + "\\curlyvee": { + font: "ams", + group: "bin", + replace: "\u22ce" + }, + "\\circleddash": { + font: "ams", + group: "bin", + replace: "\u229d" + }, + "\\circledast": { + font: "ams", + group: "bin", + replace: "\u229b" + }, + "\\centerdot": { + font: "ams", + group: "bin", + replace: "\u22c5" + }, + "\\intercal": { + font: "ams", + group: "bin", + replace: "\u22ba" + }, + "\\doublecap": { + font: "ams", + group: "bin", + replace: "\u22d2" + }, + "\\doublecup": { + font: "ams", + group: "bin", + replace: "\u22d3" + }, + "\\boxtimes": { + font: "ams", + group: "bin", + replace: "\u22a0" + }, + + // AMS Arrows + "\\dashrightarrow": { + font: "ams", + group: "rel", + replace: "\u21e2" + }, + "\\dashleftarrow": { + font: "ams", + group: "rel", + replace: "\u21e0" + }, + "\\leftleftarrows": { + font: "ams", + group: "rel", + replace: "\u21c7" + }, + "\\leftrightarrows": { + font: "ams", + group: "rel", + replace: "\u21c6" + }, + "\\Lleftarrow": { + font: "ams", + group: "rel", + replace: "\u21da" + }, + "\\twoheadleftarrow": { + font: "ams", + group: "rel", + replace: "\u219e" + }, + "\\leftarrowtail": { + font: "ams", + group: "rel", + replace: "\u21a2" + }, + "\\looparrowleft": { + font: "ams", + group: "rel", + replace: "\u21ab" + }, + "\\leftrightharpoons": { + font: "ams", + group: "rel", + replace: "\u21cb" + }, + "\\curvearrowleft": { + font: "ams", + group: "rel", + replace: "\u21b6" + }, + "\\circlearrowleft": { + font: "ams", + group: "rel", + replace: "\u21ba" + }, + "\\Lsh": { + font: "ams", + group: "rel", + replace: "\u21b0" + }, + "\\upuparrows": { + font: "ams", + group: "rel", + replace: "\u21c8" + }, + "\\upharpoonleft": { + font: "ams", + group: "rel", + replace: "\u21bf" + }, + "\\downharpoonleft": { + font: "ams", + group: "rel", + replace: "\u21c3" + }, + "\\multimap": { + font: "ams", + group: "rel", + replace: "\u22b8" + }, + "\\leftrightsquigarrow": { + font: "ams", + group: "rel", + replace: "\u21ad" + }, + "\\rightrightarrows": { + font: "ams", + group: "rel", + replace: "\u21c9" + }, + "\\rightleftarrows": { + font: "ams", + group: "rel", + replace: "\u21c4" + }, + "\\twoheadrightarrow": { + font: "ams", + group: "rel", + replace: "\u21a0" + }, + "\\rightarrowtail": { + font: "ams", + group: "rel", + replace: "\u21a3" + }, + "\\looparrowright": { + font: "ams", + group: "rel", + replace: "\u21ac" + }, + "\\curvearrowright": { + font: "ams", + group: "rel", + replace: "\u21b7" + }, + "\\circlearrowright": { + font: "ams", + group: "rel", + replace: "\u21bb" + }, + "\\Rsh": { + font: "ams", + group: "rel", + replace: "\u21b1" + }, + "\\downdownarrows": { + font: "ams", + group: "rel", + replace: "\u21ca" + }, + "\\upharpoonright": { + font: "ams", + group: "rel", + replace: "\u21be" + }, + "\\downharpoonright": { + font: "ams", + group: "rel", + replace: "\u21c2" + }, + "\\rightsquigarrow": { + font: "ams", + group: "rel", + replace: "\u21dd" + }, + "\\leadsto": { + font: "ams", + group: "rel", + replace: "\u21dd" + }, + "\\Rrightarrow": { + font: "ams", + group: "rel", + replace: "\u21db" + }, + "\\restriction": { + font: "ams", + group: "rel", + replace: "\u21be" + }, + + "`": { + font: "main", + group: "textord", + replace: "\u2018" + }, + "\\$": { + font: "main", + group: "textord", + replace: "$" + }, + "\\%": { + font: "main", + group: "textord", + replace: "%" + }, + "\\_": { + font: "main", + group: "textord", + replace: "_" + }, + "\\angle": { + font: "main", + group: "textord", + replace: "\u2220" + }, + "\\infty": { + font: "main", + group: "textord", + replace: "\u221e" + }, + "\\prime": { + font: "main", + group: "textord", + replace: "\u2032" + }, + "\\triangle": { + font: "main", + group: "textord", + replace: "\u25b3" + }, + "\\Gamma": { + font: "main", + group: "textord", + replace: "\u0393" + }, + "\\Delta": { + font: "main", + group: "textord", + replace: "\u0394" + }, + "\\Theta": { + font: "main", + group: "textord", + replace: "\u0398" + }, + "\\Lambda": { + font: "main", + group: "textord", + replace: "\u039b" + }, + "\\Xi": { + font: "main", + group: "textord", + replace: "\u039e" + }, + "\\Pi": { + font: "main", + group: "textord", + replace: "\u03a0" + }, + "\\Sigma": { + font: "main", + group: "textord", + replace: "\u03a3" + }, + "\\Upsilon": { + font: "main", + group: "textord", + replace: "\u03a5" + }, + "\\Phi": { + font: "main", + group: "textord", + replace: "\u03a6" + }, + "\\Psi": { + font: "main", + group: "textord", + replace: "\u03a8" + }, + "\\Omega": { + font: "main", + group: "textord", + replace: "\u03a9" + }, + "\\neg": { + font: "main", + group: "textord", + replace: "\u00ac" + }, + "\\lnot": { + font: "main", + group: "textord", + replace: "\u00ac" + }, + "\\top": { + font: "main", + group: "textord", + replace: "\u22a4" + }, + "\\bot": { + font: "main", + group: "textord", + replace: "\u22a5" + }, + "\\emptyset": { + font: "main", + group: "textord", + replace: "\u2205" + }, + "\\varnothing": { + font: "ams", + group: "textord", + replace: "\u2205" + }, + "\\alpha": { + font: "main", + group: "mathord", + replace: "\u03b1" + }, + "\\beta": { + font: "main", + group: "mathord", + replace: "\u03b2" + }, + "\\gamma": { + font: "main", + group: "mathord", + replace: "\u03b3" + }, + "\\delta": { + font: "main", + group: "mathord", + replace: "\u03b4" + }, + "\\epsilon": { + font: "main", + group: "mathord", + replace: "\u03f5" + }, + "\\zeta": { + font: "main", + group: "mathord", + replace: "\u03b6" + }, + "\\eta": { + font: "main", + group: "mathord", + replace: "\u03b7" + }, + "\\theta": { + font: "main", + group: "mathord", + replace: "\u03b8" + }, + "\\iota": { + font: "main", + group: "mathord", + replace: "\u03b9" + }, + "\\kappa": { + font: "main", + group: "mathord", + replace: "\u03ba" + }, + "\\lambda": { + font: "main", + group: "mathord", + replace: "\u03bb" + }, + "\\mu": { + font: "main", + group: "mathord", + replace: "\u03bc" + }, + "\\nu": { + font: "main", + group: "mathord", + replace: "\u03bd" + }, + "\\xi": { + font: "main", + group: "mathord", + replace: "\u03be" + }, + "\\omicron": { + font: "main", + group: "mathord", + replace: "o" + }, + "\\pi": { + font: "main", + group: "mathord", + replace: "\u03c0" + }, + "\\rho": { + font: "main", + group: "mathord", + replace: "\u03c1" + }, + "\\sigma": { + font: "main", + group: "mathord", + replace: "\u03c3" + }, + "\\tau": { + font: "main", + group: "mathord", + replace: "\u03c4" + }, + "\\upsilon": { + font: "main", + group: "mathord", + replace: "\u03c5" + }, + "\\phi": { + font: "main", + group: "mathord", + replace: "\u03d5" + }, + "\\chi": { + font: "main", + group: "mathord", + replace: "\u03c7" + }, + "\\psi": { + font: "main", + group: "mathord", + replace: "\u03c8" + }, + "\\omega": { + font: "main", + group: "mathord", + replace: "\u03c9" + }, + "\\varepsilon": { + font: "main", + group: "mathord", + replace: "\u03b5" + }, + "\\vartheta": { + font: "main", + group: "mathord", + replace: "\u03d1" + }, + "\\varpi": { + font: "main", + group: "mathord", + replace: "\u03d6" + }, + "\\varrho": { + font: "main", + group: "mathord", + replace: "\u03f1" + }, + "\\varsigma": { + font: "main", + group: "mathord", + replace: "\u03c2" + }, + "\\varphi": { + font: "main", + group: "mathord", + replace: "\u03c6" + }, + "*": { + font: "main", + group: "bin", + replace: "\u2217" + }, + "+": { + font: "main", + group: "bin" + }, + "-": { + font: "main", + group: "bin", + replace: "\u2212" + }, + "\\cdot": { + font: "main", + group: "bin", + replace: "\u22c5" + }, + "\\circ": { + font: "main", + group: "bin", + replace: "\u2218" + }, + "\\div": { + font: "main", + group: "bin", + replace: "\u00f7" + }, + "\\pm": { + font: "main", + group: "bin", + replace: "\u00b1" + }, + "\\times": { + font: "main", + group: "bin", + replace: "\u00d7" + }, + "\\cap": { + font: "main", + group: "bin", + replace: "\u2229" + }, + "\\cup": { + font: "main", + group: "bin", + replace: "\u222a" + }, + "\\setminus": { + font: "main", + group: "bin", + replace: "\u2216" + }, + "\\land": { + font: "main", + group: "bin", + replace: "\u2227" + }, + "\\lor": { + font: "main", + group: "bin", + replace: "\u2228" + }, + "\\wedge": { + font: "main", + group: "bin", + replace: "\u2227" + }, + "\\vee": { + font: "main", + group: "bin", + replace: "\u2228" + }, + "\\surd": { + font: "main", + group: "textord", + replace: "\u221a" + }, + "(": { + font: "main", + group: "open" + }, + "[": { + font: "main", + group: "open" + }, + "\\langle": { + font: "main", + group: "open", + replace: "\u27e8" + }, + "\\lvert": { + font: "main", + group: "open", + replace: "\u2223" + }, + "\\lVert": { + font: "main", + group: "open", + replace: "\u2225" + }, + ")": { + font: "main", + group: "close" + }, + "]": { + font: "main", + group: "close" + }, + "?": { + font: "main", + group: "close" + }, + "!": { + font: "main", + group: "close" + }, + "\\rangle": { + font: "main", + group: "close", + replace: "\u27e9" + }, + "\\rvert": { + font: "main", + group: "close", + replace: "\u2223" + }, + "\\rVert": { + font: "main", + group: "close", + replace: "\u2225" + }, + "=": { + font: "main", + group: "rel" + }, + "<": { + font: "main", + group: "rel" + }, + ">": { + font: "main", + group: "rel" + }, + ":": { + font: "main", + group: "rel" + }, + "\\approx": { + font: "main", + group: "rel", + replace: "\u2248" + }, + "\\cong": { + font: "main", + group: "rel", + replace: "\u2245" + }, + "\\ge": { + font: "main", + group: "rel", + replace: "\u2265" + }, + "\\geq": { + font: "main", + group: "rel", + replace: "\u2265" + }, + "\\gets": { + font: "main", + group: "rel", + replace: "\u2190" + }, + "\\in": { + font: "main", + group: "rel", + replace: "\u2208" + }, + "\\notin": { + font: "main", + group: "rel", + replace: "\u2209" + }, + "\\subset": { + font: "main", + group: "rel", + replace: "\u2282" + }, + "\\supset": { + font: "main", + group: "rel", + replace: "\u2283" + }, + "\\subseteq": { + font: "main", + group: "rel", + replace: "\u2286" + }, + "\\supseteq": { + font: "main", + group: "rel", + replace: "\u2287" + }, + "\\nsubseteq": { + font: "ams", + group: "rel", + replace: "\u2288" + }, + "\\nsupseteq": { + font: "ams", + group: "rel", + replace: "\u2289" + }, + "\\models": { + font: "main", + group: "rel", + replace: "\u22a8" + }, + "\\leftarrow": { + font: "main", + group: "rel", + replace: "\u2190" + }, + "\\le": { + font: "main", + group: "rel", + replace: "\u2264" + }, + "\\leq": { + font: "main", + group: "rel", + replace: "\u2264" + }, + "\\ne": { + font: "main", + group: "rel", + replace: "\u2260" + }, + "\\neq": { + font: "main", + group: "rel", + replace: "\u2260" + }, + "\\rightarrow": { + font: "main", + group: "rel", + replace: "\u2192" + }, + "\\to": { + font: "main", + group: "rel", + replace: "\u2192" + }, + "\\ngeq": { + font: "ams", + group: "rel", + replace: "\u2271" + }, + "\\nleq": { + font: "ams", + group: "rel", + replace: "\u2270" + }, + "\\!": { + font: "main", + group: "spacing" + }, + "\\ ": { + font: "main", + group: "spacing", + replace: "\u00a0" + }, + "~": { + font: "main", + group: "spacing", + replace: "\u00a0" + }, + "\\,": { + font: "main", + group: "spacing" + }, + "\\:": { + font: "main", + group: "spacing" + }, + "\\;": { + font: "main", + group: "spacing" + }, + "\\enspace": { + font: "main", + group: "spacing" + }, + "\\qquad": { + font: "main", + group: "spacing" + }, + "\\quad": { + font: "main", + group: "spacing" + }, + "\\space": { + font: "main", + group: "spacing", + replace: "\u00a0" + }, + ",": { + font: "main", + group: "punct" + }, + ";": { + font: "main", + group: "punct" + }, + "\\colon": { + font: "main", + group: "punct", + replace: ":" + }, + "\\barwedge": { + font: "ams", + group: "bin", + replace: "\u22bc" + }, + "\\veebar": { + font: "ams", + group: "bin", + replace: "\u22bb" + }, + "\\odot": { + font: "main", + group: "bin", + replace: "\u2299" + }, + "\\oplus": { + font: "main", + group: "bin", + replace: "\u2295" + }, + "\\otimes": { + font: "main", + group: "bin", + replace: "\u2297" + }, + "\\partial":{ + font: "main", + group: "textord", + replace: "\u2202" + }, + "\\oslash": { + font: "main", + group: "bin", + replace: "\u2298" + }, + "\\circledcirc": { + font: "ams", + group: "bin", + replace: "\u229a" + }, + "\\boxdot": { + font: "ams", + group: "bin", + replace: "\u22a1" + }, + "\\bigtriangleup": { + font: "main", + group: "bin", + replace: "\u25b3" + }, + "\\bigtriangledown": { + font: "main", + group: "bin", + replace: "\u25bd" + }, + "\\dagger": { + font: "main", + group: "bin", + replace: "\u2020" + }, + "\\diamond": { + font: "main", + group: "bin", + replace: "\u22c4" + }, + "\\star": { + font: "main", + group: "bin", + replace: "\u22c6" + }, + "\\triangleleft": { + font: "main", + group: "bin", + replace: "\u25c3" + }, + "\\triangleright": { + font: "main", + group: "bin", + replace: "\u25b9" + }, + "\\{": { + font: "main", + group: "open", + replace: "{" + }, + "\\}": { + font: "main", + group: "close", + replace: "}" + }, + "\\lbrace": { + font: "main", + group: "open", + replace: "{" + }, + "\\rbrace": { + font: "main", + group: "close", + replace: "}" + }, + "\\lbrack": { + font: "main", + group: "open", + replace: "[" + }, + "\\rbrack": { + font: "main", + group: "close", + replace: "]" + }, + "\\lfloor": { + font: "main", + group: "open", + replace: "\u230a" + }, + "\\rfloor": { + font: "main", + group: "close", + replace: "\u230b" + }, + "\\lceil": { + font: "main", + group: "open", + replace: "\u2308" + }, + "\\rceil": { + font: "main", + group: "close", + replace: "\u2309" + }, + "\\backslash": { + font: "main", + group: "textord", + replace: "\\" + }, + "|": { + font: "main", + group: "textord", + replace: "\u2223" + }, + "\\vert": { + font: "main", + group: "textord", + replace: "\u2223" + }, + "\\|": { + font: "main", + group: "textord", + replace: "\u2225" + }, + "\\Vert": { + font: "main", + group: "textord", + replace: "\u2225" + }, + "\\uparrow": { + font: "main", + group: "rel", + replace: "\u2191" + }, + "\\Uparrow": { + font: "main", + group: "rel", + replace: "\u21d1" + }, + "\\downarrow": { + font: "main", + group: "rel", + replace: "\u2193" + }, + "\\Downarrow": { + font: "main", + group: "rel", + replace: "\u21d3" + }, + "\\updownarrow": { + font: "main", + group: "rel", + replace: "\u2195" + }, + "\\Updownarrow": { + font: "main", + group: "rel", + replace: "\u21d5" + }, + "\\coprod": { + font: "math", + group: "op", + replace: "\u2210" + }, + "\\bigvee": { + font: "math", + group: "op", + replace: "\u22c1" + }, + "\\bigwedge": { + font: "math", + group: "op", + replace: "\u22c0" + }, + "\\biguplus": { + font: "math", + group: "op", + replace: "\u2a04" + }, + "\\bigcap": { + font: "math", + group: "op", + replace: "\u22c2" + }, + "\\bigcup": { + font: "math", + group: "op", + replace: "\u22c3" + }, + "\\int": { + font: "math", + group: "op", + replace: "\u222b" + }, + "\\intop": { + font: "math", + group: "op", + replace: "\u222b" + }, + "\\iint": { + font: "math", + group: "op", + replace: "\u222c" + }, + "\\iiint": { + font: "math", + group: "op", + replace: "\u222d" + }, + "\\prod": { + font: "math", + group: "op", + replace: "\u220f" + }, + "\\sum": { + font: "math", + group: "op", + replace: "\u2211" + }, + "\\bigotimes": { + font: "math", + group: "op", + replace: "\u2a02" + }, + "\\bigoplus": { + font: "math", + group: "op", + replace: "\u2a01" + }, + "\\bigodot": { + font: "math", + group: "op", + replace: "\u2a00" + }, + "\\oint": { + font: "math", + group: "op", + replace: "\u222e" + }, + "\\bigsqcup": { + font: "math", + group: "op", + replace: "\u2a06" + }, + "\\smallint": { + font: "math", + group: "op", + replace: "\u222b" + }, + "\\ldots": { + font: "main", + group: "inner", + replace: "\u2026" + }, + "\\cdots": { + font: "main", + group: "inner", + replace: "\u22ef" + }, + "\\ddots": { + font: "main", + group: "inner", + replace: "\u22f1" + }, + "\\vdots": { + font: "main", + group: "textord", + replace: "\u22ee" + }, + "\\acute": { + font: "main", + group: "accent", + replace: "\u00b4" + }, + "\\grave": { + font: "main", + group: "accent", + replace: "\u0060" + }, + "\\ddot": { + font: "main", + group: "accent", + replace: "\u00a8" + }, + "\\tilde": { + font: "main", + group: "accent", + replace: "\u007e" + }, + "\\bar": { + font: "main", + group: "accent", + replace: "\u00af" + }, + "\\breve": { + font: "main", + group: "accent", + replace: "\u02d8" + }, + "\\check": { + font: "main", + group: "accent", + replace: "\u02c7" + }, + "\\hat": { + font: "main", + group: "accent", + replace: "\u005e" + }, + "\\vec": { + font: "main", + group: "accent", + replace: "\u20d7" + }, + "\\dot": { + font: "main", + group: "accent", + replace: "\u02d9" + }, + + "\\imath": { + font: "main", + group: "mathord", + replace: "\u0131" + }, + "\\jmath": { + font: "main", + group: "mathord", + replace: "\u0237" + } + }, + "text": { + "\\ ": { + font: "main", + group: "spacing", + replace: "\u00a0" + }, + " ": { + font: "main", + group: "spacing", + replace: "\u00a0" + }, + "~": { + font: "main", + group: "spacing", + replace: "\u00a0" + } + } +}; + +// There are lots of symbols which are the same, so we add them in afterwards. + +// All of these are textords in math mode +var mathTextSymbols = "0123456789/@.\""; +for (var i = 0; i < mathTextSymbols.length; i++) { + var ch = mathTextSymbols.charAt(i); + symbols.math[ch] = { + font: "main", + group: "textord" + }; +} + +// All of these are textords in text mode +var textSymbols = "0123456789`!@*()-=+[]'\";:?/.,"; +for (var i = 0; i < textSymbols.length; i++) { + var ch = textSymbols.charAt(i); + symbols.text[ch] = { + font: "main", + group: "textord" + }; +} + +// All of these are textords in text mode, and mathords in math mode +var letters = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"; +for (var i = 0; i < letters.length; i++) { + var ch = letters.charAt(i); + symbols.math[ch] = { + font: "main", + group: "mathord" + }; + symbols.text[ch] = { + font: "main", + group: "textord" + }; +} + +module.exports = symbols; + +},{}],25:[function(require,module,exports){ +/** + * This file contains a list of utility functions which are useful in other + * files. + */ + +/** + * Provide an `indexOf` function which works in IE8, but defers to native if + * possible. + */ +var nativeIndexOf = Array.prototype.indexOf; +var indexOf = function(list, elem) { + if (list == null) { + return -1; + } + if (nativeIndexOf && list.indexOf === nativeIndexOf) { + return list.indexOf(elem); + } + var i = 0, l = list.length; + for (; i < l; i++) { + if (list[i] === elem) { + return i; + } + } + return -1; +}; + +/** + * Return whether an element is contained in a list + */ +var contains = function(list, elem) { + return indexOf(list, elem) !== -1; +}; + +/** + * Provide a default value if a setting is undefined + */ +var deflt = function(setting, defaultIfUndefined) { + return setting === undefined ? defaultIfUndefined : setting; +}; + +// hyphenate and escape adapted from Facebook's React under Apache 2 license + +var uppercase = /([A-Z])/g; +var hyphenate = function(str) { + return str.replace(uppercase, "-$1").toLowerCase(); +}; + +var ESCAPE_LOOKUP = { + "&": "&", + ">": ">", + "<": "<", + "\"": """, + "'": "'" +}; + +var ESCAPE_REGEX = /[&><"']/g; + +function escaper(match) { + return ESCAPE_LOOKUP[match]; +} + +/** + * Escapes text to prevent scripting attacks. + * + * @param {*} text Text value to escape. + * @return {string} An escaped string. + */ +function escape(text) { + return ("" + text).replace(ESCAPE_REGEX, escaper); +} + +/** + * A function to set the text content of a DOM element in all supported + * browsers. Note that we don't define this if there is no document. + */ +var setTextContent; +if (typeof document !== "undefined") { + var testNode = document.createElement("span"); + if ("textContent" in testNode) { + setTextContent = function(node, text) { + node.textContent = text; + }; + } else { + setTextContent = function(node, text) { + node.innerText = text; + }; + } +} + +/** + * A function to clear a node. + */ +function clearNode(node) { + setTextContent(node, ""); +} + +module.exports = { + contains: contains, + deflt: deflt, + escape: escape, + hyphenate: hyphenate, + indexOf: indexOf, + setTextContent: setTextContent, + clearNode: clearNode +}; + +},{}],26:[function(require,module,exports){ +'use strict'; + + +//////////////////////////////////////////////////////////////////////////////// +// Helpers + +// Merge objects +// +function assign(obj /*from1, from2, from3, ...*/) { + var sources = Array.prototype.slice.call(arguments, 1); + + sources.forEach(function (source) { + if (!source) { return; } + + Object.keys(source).forEach(function (key) { + obj[key] = source[key]; + }); + }); + + return obj; +} + +function _class(obj) { return Object.prototype.toString.call(obj); } +function isString(obj) { return _class(obj) === '[object String]'; } +function isObject(obj) { return _class(obj) === '[object Object]'; } +function isRegExp(obj) { return _class(obj) === '[object RegExp]'; } +function isFunction(obj) { return _class(obj) === '[object Function]'; } + + +function escapeRE (str) { return str.replace(/[.?*+^$[\]\\(){}|-]/g, '\\$&'); } + +//////////////////////////////////////////////////////////////////////////////// + + +var defaultOptions = { + fuzzyLink: true, + fuzzyEmail: true, + fuzzyIP: false +}; + + +function isOptionsObj(obj) { + return Object.keys(obj || {}).reduce(function (acc, k) { + return acc || defaultOptions.hasOwnProperty(k); + }, false); +} + + +var defaultSchemas = { + 'http:': { + validate: function (text, pos, self) { + var tail = text.slice(pos); + + if (!self.re.http) { + // compile lazily, because "host"-containing variables can change on tlds update. + self.re.http = new RegExp( + '^\\/\\/' + self.re.src_auth + self.re.src_host_port_strict + self.re.src_path, 'i' + ); + } + if (self.re.http.test(tail)) { + return tail.match(self.re.http)[0].length; + } + return 0; + } + }, + 'https:': 'http:', + 'ftp:': 'http:', + '//': { + validate: function (text, pos, self) { + var tail = text.slice(pos); + + if (!self.re.no_http) { + // compile lazily, becayse "host"-containing variables can change on tlds update. + self.re.no_http = new RegExp( + '^' + self.re.src_auth + self.re.src_host_port_strict + self.re.src_path, 'i' + ); + } + + if (self.re.no_http.test(tail)) { + // should not be `://`, that protects from errors in protocol name + if (pos >= 3 && text[pos - 3] === ':') { return 0; } + return tail.match(self.re.no_http)[0].length; + } + return 0; + } + }, + 'mailto:': { + validate: function (text, pos, self) { + var tail = text.slice(pos); + + if (!self.re.mailto) { + self.re.mailto = new RegExp( + '^' + self.re.src_email_name + '@' + self.re.src_host_strict, 'i' + ); + } + if (self.re.mailto.test(tail)) { + return tail.match(self.re.mailto)[0].length; + } + return 0; + } + } +}; + +/*eslint-disable max-len*/ + +// RE pattern for 2-character tlds (autogenerated by ./support/tlds_2char_gen.js) +var tlds_2ch_src_re = 'a[cdefgilmnoqrstuwxz]|b[abdefghijmnorstvwyz]|c[acdfghiklmnoruvwxyz]|d[ejkmoz]|e[cegrstu]|f[ijkmor]|g[abdefghilmnpqrstuwy]|h[kmnrtu]|i[delmnoqrst]|j[emop]|k[eghimnprwyz]|l[abcikrstuvy]|m[acdeghklmnopqrstuvwxyz]|n[acefgilopruz]|om|p[aefghklmnrstwy]|qa|r[eosuw]|s[abcdeghijklmnortuvxyz]|t[cdfghjklmnortvwz]|u[agksyz]|v[aceginu]|w[fs]|y[et]|z[amw]'; + +// DON'T try to make PRs with changes. Extend TLDs with LinkifyIt.tlds() instead +var tlds_default = 'biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф'.split('|'); + +/*eslint-enable max-len*/ + +//////////////////////////////////////////////////////////////////////////////// + +function resetScanCache(self) { + self.__index__ = -1; + self.__text_cache__ = ''; +} + +function createValidator(re) { + return function (text, pos) { + var tail = text.slice(pos); + + if (re.test(tail)) { + return tail.match(re)[0].length; + } + return 0; + }; +} + +function createNormalizer() { + return function (match, self) { + self.normalize(match); + }; +} + +// Schemas compiler. Build regexps. +// +function compile(self) { + + // Load & clone RE patterns. + var re = self.re = assign({}, require('./lib/re')); + + // Define dynamic patterns + var tlds = self.__tlds__.slice(); + + if (!self.__tlds_replaced__) { + tlds.push(tlds_2ch_src_re); + } + tlds.push(re.src_xn); + + re.src_tlds = tlds.join('|'); + + function untpl(tpl) { return tpl.replace('%TLDS%', re.src_tlds); } + + re.email_fuzzy = RegExp(untpl(re.tpl_email_fuzzy), 'i'); + re.link_fuzzy = RegExp(untpl(re.tpl_link_fuzzy), 'i'); + re.link_no_ip_fuzzy = RegExp(untpl(re.tpl_link_no_ip_fuzzy), 'i'); + re.host_fuzzy_test = RegExp(untpl(re.tpl_host_fuzzy_test), 'i'); + + // + // Compile each schema + // + + var aliases = []; + + self.__compiled__ = {}; // Reset compiled data + + function schemaError(name, val) { + throw new Error('(LinkifyIt) Invalid schema "' + name + '": ' + val); + } + + Object.keys(self.__schemas__).forEach(function (name) { + var val = self.__schemas__[name]; + + // skip disabled methods + if (val === null) { return; } + + var compiled = { validate: null, link: null }; + + self.__compiled__[name] = compiled; + + if (isObject(val)) { + if (isRegExp(val.validate)) { + compiled.validate = createValidator(val.validate); + } else if (isFunction(val.validate)) { + compiled.validate = val.validate; + } else { + schemaError(name, val); + } + + if (isFunction(val.normalize)) { + compiled.normalize = val.normalize; + } else if (!val.normalize) { + compiled.normalize = createNormalizer(); + } else { + schemaError(name, val); + } + + return; + } + + if (isString(val)) { + aliases.push(name); + return; + } + + schemaError(name, val); + }); + + // + // Compile postponed aliases + // + + aliases.forEach(function (alias) { + if (!self.__compiled__[self.__schemas__[alias]]) { + // Silently fail on missed schemas to avoid errons on disable. + // schemaError(alias, self.__schemas__[alias]); + return; + } + + self.__compiled__[alias].validate = + self.__compiled__[self.__schemas__[alias]].validate; + self.__compiled__[alias].normalize = + self.__compiled__[self.__schemas__[alias]].normalize; + }); + + // + // Fake record for guessed links + // + self.__compiled__[''] = { validate: null, normalize: createNormalizer() }; + + // + // Build schema condition + // + var slist = Object.keys(self.__compiled__) + .filter(function(name) { + // Filter disabled & fake schemas + return name.length > 0 && self.__compiled__[name]; + }) + .map(escapeRE) + .join('|'); + // (?!_) cause 1.5x slowdown + self.re.schema_test = RegExp('(^|(?!_)(?:>|' + re.src_ZPCc + '))(' + slist + ')', 'i'); + self.re.schema_search = RegExp('(^|(?!_)(?:>|' + re.src_ZPCc + '))(' + slist + ')', 'ig'); + + self.re.pretest = RegExp( + '(' + self.re.schema_test.source + ')|' + + '(' + self.re.host_fuzzy_test.source + ')|' + + '@', + 'i'); + + // + // Cleanup + // + + resetScanCache(self); +} + +/** + * class Match + * + * Match result. Single element of array, returned by [[LinkifyIt#match]] + **/ +function Match(self, shift) { + var start = self.__index__, + end = self.__last_index__, + text = self.__text_cache__.slice(start, end); + + /** + * Match#schema -> String + * + * Prefix (protocol) for matched string. + **/ + this.schema = self.__schema__.toLowerCase(); + /** + * Match#index -> Number + * + * First position of matched string. + **/ + this.index = start + shift; + /** + * Match#lastIndex -> Number + * + * Next position after matched string. + **/ + this.lastIndex = end + shift; + /** + * Match#raw -> String + * + * Matched string. + **/ + this.raw = text; + /** + * Match#text -> String + * + * Notmalized text of matched string. + **/ + this.text = text; + /** + * Match#url -> String + * + * Normalized url of matched string. + **/ + this.url = text; +} + +function createMatch(self, shift) { + var match = new Match(self, shift); + + self.__compiled__[match.schema].normalize(match, self); + + return match; +} + + +/** + * class LinkifyIt + **/ + +/** + * new LinkifyIt(schemas, options) + * - schemas (Object): Optional. Additional schemas to validate (prefix/validator) + * - options (Object): { fuzzyLink|fuzzyEmail|fuzzyIP: true|false } + * + * Creates new linkifier instance with optional additional schemas. + * Can be called without `new` keyword for convenience. + * + * By default understands: + * + * - `http(s)://...` , `ftp://...`, `mailto:...` & `//...` links + * - "fuzzy" links and emails (example.com, foo@bar.com). + * + * `schemas` is an object, where each key/value describes protocol/rule: + * + * - __key__ - link prefix (usually, protocol name with `:` at the end, `skype:` + * for example). `linkify-it` makes shure that prefix is not preceeded with + * alphanumeric char and symbols. Only whitespaces and punctuation allowed. + * - __value__ - rule to check tail after link prefix + * - _String_ - just alias to existing rule + * - _Object_ + * - _validate_ - validator function (should return matched length on success), + * or `RegExp`. + * - _normalize_ - optional function to normalize text & url of matched result + * (for example, for @twitter mentions). + * + * `options`: + * + * - __fuzzyLink__ - recognige URL-s without `http(s):` prefix. Default `true`. + * - __fuzzyIP__ - allow IPs in fuzzy links above. Can conflict with some texts + * like version numbers. Default `false`. + * - __fuzzyEmail__ - recognize emails without `mailto:` prefix. + * + **/ +function LinkifyIt(schemas, options) { + if (!(this instanceof LinkifyIt)) { + return new LinkifyIt(schemas, options); + } + + if (!options) { + if (isOptionsObj(schemas)) { + options = schemas; + schemas = {}; + } + } + + this.__opts__ = assign({}, defaultOptions, options); + + // Cache last tested result. Used to skip repeating steps on next `match` call. + this.__index__ = -1; + this.__last_index__ = -1; // Next scan position + this.__schema__ = ''; + this.__text_cache__ = ''; + + this.__schemas__ = assign({}, defaultSchemas, schemas); + this.__compiled__ = {}; + + this.__tlds__ = tlds_default; + this.__tlds_replaced__ = false; + + this.re = {}; + + compile(this); +} + + +/** chainable + * LinkifyIt#add(schema, definition) + * - schema (String): rule name (fixed pattern prefix) + * - definition (String|RegExp|Object): schema definition + * + * Add new rule definition. See constructor description for details. + **/ +LinkifyIt.prototype.add = function add(schema, definition) { + this.__schemas__[schema] = definition; + compile(this); + return this; +}; + + +/** chainable + * LinkifyIt#set(options) + * - options (Object): { fuzzyLink|fuzzyEmail|fuzzyIP: true|false } + * + * Set recognition options for links without schema. + **/ +LinkifyIt.prototype.set = function set(options) { + this.__opts__ = assign(this.__opts__, options); + return this; +}; + + +/** + * LinkifyIt#test(text) -> Boolean + * + * Searches linkifiable pattern and returns `true` on success or `false` on fail. + **/ +LinkifyIt.prototype.test = function test(text) { + // Reset scan cache + this.__text_cache__ = text; + this.__index__ = -1; + + if (!text.length) { return false; } + + var m, ml, me, len, shift, next, re, tld_pos, at_pos; + + // try to scan for link with schema - that's the most simple rule + if (this.re.schema_test.test(text)) { + re = this.re.schema_search; + re.lastIndex = 0; + while ((m = re.exec(text)) !== null) { + len = this.testSchemaAt(text, m[2], re.lastIndex); + if (len) { + this.__schema__ = m[2]; + this.__index__ = m.index + m[1].length; + this.__last_index__ = m.index + m[0].length + len; + break; + } + } + } + + if (this.__opts__.fuzzyLink && this.__compiled__['http:']) { + // guess schemaless links + tld_pos = text.search(this.re.host_fuzzy_test); + if (tld_pos >= 0) { + // if tld is located after found link - no need to check fuzzy pattern + if (this.__index__ < 0 || tld_pos < this.__index__) { + if ((ml = text.match(this.__opts__.fuzzyIP ? this.re.link_fuzzy : this.re.link_no_ip_fuzzy)) !== null) { + + shift = ml.index + ml[1].length; + + if (this.__index__ < 0 || shift < this.__index__) { + this.__schema__ = ''; + this.__index__ = shift; + this.__last_index__ = ml.index + ml[0].length; + } + } + } + } + } + + if (this.__opts__.fuzzyEmail && this.__compiled__['mailto:']) { + // guess schemaless emails + at_pos = text.indexOf('@'); + if (at_pos >= 0) { + // We can't skip this check, because this cases are possible: + // 192.168.1.1@gmail.com, my.in@example.com + if ((me = text.match(this.re.email_fuzzy)) !== null) { + + shift = me.index + me[1].length; + next = me.index + me[0].length; + + if (this.__index__ < 0 || shift < this.__index__ || + (shift === this.__index__ && next > this.__last_index__)) { + this.__schema__ = 'mailto:'; + this.__index__ = shift; + this.__last_index__ = next; + } + } + } + } + + return this.__index__ >= 0; +}; + + +/** + * LinkifyIt#pretest(text) -> Boolean + * + * Very quick check, that can give false positives. Returns true if link MAY BE + * can exists. Can be used for speed optimization, when you need to check that + * link NOT exists. + **/ +LinkifyIt.prototype.pretest = function pretest(text) { + return this.re.pretest.test(text); +}; + + +/** + * LinkifyIt#testSchemaAt(text, name, position) -> Number + * - text (String): text to scan + * - name (String): rule (schema) name + * - position (Number): text offset to check from + * + * Similar to [[LinkifyIt#test]] but checks only specific protocol tail exactly + * at given position. Returns length of found pattern (0 on fail). + **/ +LinkifyIt.prototype.testSchemaAt = function testSchemaAt(text, schema, pos) { + // If not supported schema check requested - terminate + if (!this.__compiled__[schema.toLowerCase()]) { + return 0; + } + return this.__compiled__[schema.toLowerCase()].validate(text, pos, this); +}; + + +/** + * LinkifyIt#match(text) -> Array|null + * + * Returns array of found link descriptions or `null` on fail. We strongly + * to use [[LinkifyIt#test]] first, for best speed. + * + * ##### Result match description + * + * - __schema__ - link schema, can be empty for fuzzy links, or `//` for + * protocol-neutral links. + * - __index__ - offset of matched text + * - __lastIndex__ - index of next char after mathch end + * - __raw__ - matched text + * - __text__ - normalized text + * - __url__ - link, generated from matched text + **/ +LinkifyIt.prototype.match = function match(text) { + var shift = 0, result = []; + + // Try to take previous element from cache, if .test() called before + if (this.__index__ >= 0 && this.__text_cache__ === text) { + result.push(createMatch(this, shift)); + shift = this.__last_index__; + } + + // Cut head if cache was used + var tail = shift ? text.slice(shift) : text; + + // Scan string until end reached + while (this.test(tail)) { + result.push(createMatch(this, shift)); + + tail = tail.slice(this.__last_index__); + shift += this.__last_index__; + } + + if (result.length) { + return result; + } + + return null; +}; + + +/** chainable + * LinkifyIt#tlds(list [, keepOld]) -> this + * - list (Array): list of tlds + * - keepOld (Boolean): merge with current list if `true` (`false` by default) + * + * Load (or merge) new tlds list. Those are user for fuzzy links (without prefix) + * to avoid false positives. By default this algorythm used: + * + * - hostname with any 2-letter root zones are ok. + * - biz|com|edu|gov|net|org|pro|web|xxx|aero|asia|coop|info|museum|name|shop|рф + * are ok. + * - encoded (`xn--...`) root zones are ok. + * + * If list is replaced, then exact match for 2-chars root zones will be checked. + **/ +LinkifyIt.prototype.tlds = function tlds(list, keepOld) { + list = Array.isArray(list) ? list : [ list ]; + + if (!keepOld) { + this.__tlds__ = list.slice(); + this.__tlds_replaced__ = true; + compile(this); + return this; + } + + this.__tlds__ = this.__tlds__.concat(list) + .sort() + .filter(function(el, idx, arr) { + return el !== arr[idx - 1]; + }) + .reverse(); + + compile(this); + return this; +}; + +/** + * LinkifyIt#normalize(match) + * + * Default normalizer (if schema does not define it's own). + **/ +LinkifyIt.prototype.normalize = function normalize(match) { + + // Do minimal possible changes by default. Need to collect feedback prior + // to move forward https://github.com/markdown-it/linkify-it/issues/1 + + if (!match.schema) { match.url = 'http://' + match.url; } + + if (match.schema === 'mailto:' && !/^mailto:/i.test(match.url)) { + match.url = 'mailto:' + match.url; + } +}; + + +module.exports = LinkifyIt; + +},{"./lib/re":27}],27:[function(require,module,exports){ +'use strict'; + +// Use direct extract instead of `regenerate` to reduse browserified size +var src_Any = exports.src_Any = require('uc.micro/properties/Any/regex').source; +var src_Cc = exports.src_Cc = require('uc.micro/categories/Cc/regex').source; +var src_Z = exports.src_Z = require('uc.micro/categories/Z/regex').source; +var src_P = exports.src_P = require('uc.micro/categories/P/regex').source; + +// \p{\Z\P\Cc\CF} (white spaces + control + format + punctuation) +var src_ZPCc = exports.src_ZPCc = [ src_Z, src_P, src_Cc ].join('|'); + +// \p{\Z\Cc} (white spaces + control) +var src_ZCc = exports.src_ZCc = [ src_Z, src_Cc ].join('|'); + +// All possible word characters (everything without punctuation, spaces & controls) +// Defined via punctuation & spaces to save space +// Should be something like \p{\L\N\S\M} (\w but without `_`) +var src_pseudo_letter = '(?:(?!' + src_ZPCc + ')' + src_Any + ')'; +// The same as abothe but without [0-9] +var src_pseudo_letter_non_d = '(?:(?![0-9]|' + src_ZPCc + ')' + src_Any + ')'; + +//////////////////////////////////////////////////////////////////////////////// + +var src_ip4 = exports.src_ip4 = + + '(?:(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)'; + +exports.src_auth = '(?:(?:(?!' + src_ZCc + ').)+@)?'; + +var src_port = exports.src_port = + + '(?::(?:6(?:[0-4]\\d{3}|5(?:[0-4]\\d{2}|5(?:[0-2]\\d|3[0-5])))|[1-5]?\\d{1,4}))?'; + +var src_host_terminator = exports.src_host_terminator = + + '(?=$|' + src_ZPCc + ')(?!-|_|:\\d|\\.-|\\.(?!$|' + src_ZPCc + '))'; + +var src_path = exports.src_path = + + '(?:' + + '[/?#]' + + '(?:' + + '(?!' + src_ZCc + '|[()[\\]{}.,"\'?!\\-]).|' + + '\\[(?:(?!' + src_ZCc + '|\\]).)*\\]|' + + '\\((?:(?!' + src_ZCc + '|[)]).)*\\)|' + + '\\{(?:(?!' + src_ZCc + '|[}]).)*\\}|' + + '\\"(?:(?!' + src_ZCc + '|["]).)+\\"|' + + "\\'(?:(?!" + src_ZCc + "|[']).)+\\'|" + + "\\'(?=" + src_pseudo_letter + ').|' + // allow `I'm_king` if no pair found + '\\.{2,3}[a-zA-Z0-9%/]|' + // github has ... in commit range links. Restrict to + // - english + // - percent-encoded + // - parts of file path + // until more examples found. + '\\.(?!' + src_ZCc + '|[.]).|' + + '\\-(?!--(?:[^-]|$))(?:-*)|' + // `---` => long dash, terminate + '\\,(?!' + src_ZCc + ').|' + // allow `,,,` in paths + '\\!(?!' + src_ZCc + '|[!]).|' + + '\\?(?!' + src_ZCc + '|[?]).' + + ')+' + + '|\\/' + + ')?'; + +var src_email_name = exports.src_email_name = + + '[\\-;:&=\\+\\$,\\"\\.a-zA-Z0-9_]+'; + +var src_xn = exports.src_xn = + + 'xn--[a-z0-9\\-]{1,59}'; + +// More to read about domain names +// http://serverfault.com/questions/638260/ + +var src_domain_root = exports.src_domain_root = + + // Can't have digits and dashes + '(?:' + + src_xn + + '|' + + src_pseudo_letter_non_d + '{1,63}' + + ')'; + +var src_domain = exports.src_domain = + + '(?:' + + src_xn + + '|' + + '(?:' + src_pseudo_letter + ')' + + '|' + + // don't allow `--` in domain names, because: + // - that can conflict with markdown — / – + // - nobody use those anyway + '(?:' + src_pseudo_letter + '(?:-(?!-)|' + src_pseudo_letter + '){0,61}' + src_pseudo_letter + ')' + + ')'; + +var src_host = exports.src_host = + + '(?:' + + src_ip4 + + '|' + + '(?:(?:(?:' + src_domain + ')\\.)*' + src_domain_root + ')' + + ')'; + +var tpl_host_fuzzy = exports.tpl_host_fuzzy = + + '(?:' + + src_ip4 + + '|' + + '(?:(?:(?:' + src_domain + ')\\.)+(?:%TLDS%))' + + ')'; + +var tpl_host_no_ip_fuzzy = exports.tpl_host_no_ip_fuzzy = + + '(?:(?:(?:' + src_domain + ')\\.)+(?:%TLDS%))'; + +exports.src_host_strict = + + src_host + src_host_terminator; + +var tpl_host_fuzzy_strict = exports.tpl_host_fuzzy_strict = + + tpl_host_fuzzy + src_host_terminator; + +exports.src_host_port_strict = + + src_host + src_port + src_host_terminator; + +var tpl_host_port_fuzzy_strict = exports.tpl_host_port_fuzzy_strict = + + tpl_host_fuzzy + src_port + src_host_terminator; + +var tpl_host_port_no_ip_fuzzy_strict = exports.tpl_host_port_no_ip_fuzzy_strict = + + tpl_host_no_ip_fuzzy + src_port + src_host_terminator; + + +//////////////////////////////////////////////////////////////////////////////// +// Main rules + +// Rude test fuzzy links by host, for quick deny +exports.tpl_host_fuzzy_test = + + 'localhost|\\.\\d{1,3}\\.|(?:\\.(?:%TLDS%)(?:' + src_ZPCc + '|$))'; + +exports.tpl_email_fuzzy = + + '(^|>|' + src_ZCc + ')(' + src_email_name + '@' + tpl_host_fuzzy_strict + ')'; + +exports.tpl_link_fuzzy = + // Fuzzy link can't be prepended with .:/\- and non punctuation. + // but can start with > (markdown blockquote) + '(^|(?![.:/\\-_@])(?:[$+<=>^`|]|' + src_ZPCc + '))' + + '((?![$+<=>^`|])' + tpl_host_port_fuzzy_strict + src_path + ')'; + +exports.tpl_link_no_ip_fuzzy = + // Fuzzy link can't be prepended with .:/\- and non punctuation. + // but can start with > (markdown blockquote) + '(^|(?![.:/\\-_@])(?:[$+<=>^`|]|' + src_ZPCc + '))' + + '((?![$+<=>^`|])' + tpl_host_port_no_ip_fuzzy_strict + src_path + ')'; + +},{"uc.micro/categories/Cc/regex":86,"uc.micro/categories/P/regex":88,"uc.micro/categories/Z/regex":89,"uc.micro/properties/Any/regex":91}],28:[function(require,module,exports){ +'use strict'; + + +module.exports = require('./lib/'); + +},{"./lib/":37}],29:[function(require,module,exports){ +// HTML5 entities map: { name -> utf16string } +// +'use strict'; + +/*eslint quotes:0*/ +module.exports = require('entities/maps/entities.json'); + +},{"entities/maps/entities.json":3}],30:[function(require,module,exports){ +// List of valid html blocks names, accorting to commonmark spec +// http://jgm.github.io/CommonMark/spec.html#html-blocks + +'use strict'; + + +module.exports = [ + 'address', + 'article', + 'aside', + 'base', + 'basefont', + 'blockquote', + 'body', + 'caption', + 'center', + 'col', + 'colgroup', + 'dd', + 'details', + 'dialog', + 'dir', + 'div', + 'dl', + 'dt', + 'fieldset', + 'figcaption', + 'figure', + 'footer', + 'form', + 'frame', + 'frameset', + 'h1', + 'head', + 'header', + 'hr', + 'html', + 'iframe', + 'legend', + 'li', + 'link', + 'main', + 'menu', + 'menuitem', + 'meta', + 'nav', + 'noframes', + 'ol', + 'optgroup', + 'option', + 'p', + 'param', + 'pre', + 'section', + 'source', + 'title', + 'summary', + 'table', + 'tbody', + 'td', + 'tfoot', + 'th', + 'thead', + 'title', + 'tr', + 'track', + 'ul' +]; + +},{}],31:[function(require,module,exports){ +// Regexps to match html elements + +'use strict'; + +var attr_name = '[a-zA-Z_:][a-zA-Z0-9:._-]*'; + +var unquoted = '[^"\'=<>`\\x00-\\x20]+'; +var single_quoted = "'[^']*'"; +var double_quoted = '"[^"]*"'; + +var attr_value = '(?:' + unquoted + '|' + single_quoted + '|' + double_quoted + ')'; + +var attribute = '(?:\\s+' + attr_name + '(?:\\s*=\\s*' + attr_value + ')?)'; + +var open_tag = '<[A-Za-z][A-Za-z0-9\\-]*' + attribute + '*\\s*\\/?>'; + +var close_tag = '<\\/[A-Za-z][A-Za-z0-9\\-]*\\s*>'; +var comment = '|'; +var processing = '<[?].*?[?]>'; +var declaration = ']*>'; +var cdata = ''; + +var HTML_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + '|' + comment + + '|' + processing + '|' + declaration + '|' + cdata + ')'); +var HTML_OPEN_CLOSE_TAG_RE = new RegExp('^(?:' + open_tag + '|' + close_tag + ')'); + +module.exports.HTML_TAG_RE = HTML_TAG_RE; +module.exports.HTML_OPEN_CLOSE_TAG_RE = HTML_OPEN_CLOSE_TAG_RE; + +},{}],32:[function(require,module,exports){ +// Utilities +// +'use strict'; + + +function _class(obj) { return Object.prototype.toString.call(obj); } + +function isString(obj) { return _class(obj) === '[object String]'; } + +var _hasOwnProperty = Object.prototype.hasOwnProperty; + +function has(object, key) { + return _hasOwnProperty.call(object, key); +} + +// Merge objects +// +function assign(obj /*from1, from2, from3, ...*/) { + var sources = Array.prototype.slice.call(arguments, 1); + + sources.forEach(function (source) { + if (!source) { return; } + + if (typeof source !== 'object') { + throw new TypeError(source + 'must be object'); + } + + Object.keys(source).forEach(function (key) { + obj[key] = source[key]; + }); + }); + + return obj; +} + +// Remove element from array and put another array at those position. +// Useful for some operations with tokens +function arrayReplaceAt(src, pos, newElements) { + return [].concat(src.slice(0, pos), newElements, src.slice(pos + 1)); +} + +//////////////////////////////////////////////////////////////////////////////// + +function isValidEntityCode(c) { + /*eslint no-bitwise:0*/ + // broken sequence + if (c >= 0xD800 && c <= 0xDFFF) { return false; } + // never used + if (c >= 0xFDD0 && c <= 0xFDEF) { return false; } + if ((c & 0xFFFF) === 0xFFFF || (c & 0xFFFF) === 0xFFFE) { return false; } + // control codes + if (c >= 0x00 && c <= 0x08) { return false; } + if (c === 0x0B) { return false; } + if (c >= 0x0E && c <= 0x1F) { return false; } + if (c >= 0x7F && c <= 0x9F) { return false; } + // out of range + if (c > 0x10FFFF) { return false; } + return true; +} + +function fromCodePoint(c) { + /*eslint no-bitwise:0*/ + if (c > 0xffff) { + c -= 0x10000; + var surrogate1 = 0xd800 + (c >> 10), + surrogate2 = 0xdc00 + (c & 0x3ff); + + return String.fromCharCode(surrogate1, surrogate2); + } + return String.fromCharCode(c); +} + + +var UNESCAPE_MD_RE = /\\([!"#$%&'()*+,\-.\/:;<=>?@[\\\]^_`{|}~])/g; +var ENTITY_RE = /&([a-z#][a-z0-9]{1,31});/gi; +var UNESCAPE_ALL_RE = new RegExp(UNESCAPE_MD_RE.source + '|' + ENTITY_RE.source, 'gi'); + +var DIGITAL_ENTITY_TEST_RE = /^#((?:x[a-f0-9]{1,8}|[0-9]{1,8}))/i; + +var entities = require('./entities'); + +function replaceEntityPattern(match, name) { + var code = 0; + + if (has(entities, name)) { + return entities[name]; + } + + if (name.charCodeAt(0) === 0x23/* # */ && DIGITAL_ENTITY_TEST_RE.test(name)) { + code = name[1].toLowerCase() === 'x' ? + parseInt(name.slice(2), 16) + : + parseInt(name.slice(1), 10); + if (isValidEntityCode(code)) { + return fromCodePoint(code); + } + } + + return match; +} + +/*function replaceEntities(str) { + if (str.indexOf('&') < 0) { return str; } + + return str.replace(ENTITY_RE, replaceEntityPattern); +}*/ + +function unescapeMd(str) { + if (str.indexOf('\\') < 0) { return str; } + return str.replace(UNESCAPE_MD_RE, '$1'); +} + +function unescapeAll(str) { + if (str.indexOf('\\') < 0 && str.indexOf('&') < 0) { return str; } + + return str.replace(UNESCAPE_ALL_RE, function(match, escaped, entity) { + if (escaped) { return escaped; } + return replaceEntityPattern(match, entity); + }); +} + +//////////////////////////////////////////////////////////////////////////////// + +var HTML_ESCAPE_TEST_RE = /[&<>"]/; +var HTML_ESCAPE_REPLACE_RE = /[&<>"]/g; +var HTML_REPLACEMENTS = { + '&': '&', + '<': '<', + '>': '>', + '"': '"' +}; + +function replaceUnsafeChar(ch) { + return HTML_REPLACEMENTS[ch]; +} + +function escapeHtml(str) { + if (HTML_ESCAPE_TEST_RE.test(str)) { + return str.replace(HTML_ESCAPE_REPLACE_RE, replaceUnsafeChar); + } + return str; +} + +//////////////////////////////////////////////////////////////////////////////// + +var REGEXP_ESCAPE_RE = /[.?*+^$[\]\\(){}|-]/g; + +function escapeRE (str) { + return str.replace(REGEXP_ESCAPE_RE, '\\$&'); +} + +//////////////////////////////////////////////////////////////////////////////// + +function isSpace(code) { + switch (code) { + case 0x09: + case 0x20: + return true; + } + return false; +} + +// Zs (unicode class) || [\t\f\v\r\n] +function isWhiteSpace(code) { + if (code >= 0x2000 && code <= 0x200A) { return true; } + switch (code) { + case 0x09: // \t + case 0x0A: // \n + case 0x0B: // \v + case 0x0C: // \f + case 0x0D: // \r + case 0x20: + case 0xA0: + case 0x1680: + case 0x202F: + case 0x205F: + case 0x3000: + return true; + } + return false; +} + +//////////////////////////////////////////////////////////////////////////////// + +/*eslint-disable max-len*/ +var UNICODE_PUNCT_RE = require('uc.micro/categories/P/regex'); + +// Currently without astral characters support. +function isPunctChar(ch) { + return UNICODE_PUNCT_RE.test(ch); +} + + +// Markdown ASCII punctuation characters. +// +// !, ", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \, ], ^, _, `, {, |, }, or ~ +// http://spec.commonmark.org/0.15/#ascii-punctuation-character +// +// Don't confuse with unicode punctuation !!! It lacks some chars in ascii range. +// +function isMdAsciiPunct(ch) { + switch (ch) { + case 0x21/* ! */: + case 0x22/* " */: + case 0x23/* # */: + case 0x24/* $ */: + case 0x25/* % */: + case 0x26/* & */: + case 0x27/* ' */: + case 0x28/* ( */: + case 0x29/* ) */: + case 0x2A/* * */: + case 0x2B/* + */: + case 0x2C/* , */: + case 0x2D/* - */: + case 0x2E/* . */: + case 0x2F/* / */: + case 0x3A/* : */: + case 0x3B/* ; */: + case 0x3C/* < */: + case 0x3D/* = */: + case 0x3E/* > */: + case 0x3F/* ? */: + case 0x40/* @ */: + case 0x5B/* [ */: + case 0x5C/* \ */: + case 0x5D/* ] */: + case 0x5E/* ^ */: + case 0x5F/* _ */: + case 0x60/* ` */: + case 0x7B/* { */: + case 0x7C/* | */: + case 0x7D/* } */: + case 0x7E/* ~ */: + return true; + default: + return false; + } +} + +// Hepler to unify [reference labels]. +// +function normalizeReference(str) { + // use .toUpperCase() instead of .toLowerCase() + // here to avoid a conflict with Object.prototype + // members (most notably, `__proto__`) + return str.trim().replace(/\s+/g, ' ').toUpperCase(); +} + +//////////////////////////////////////////////////////////////////////////////// + +// Re-export libraries commonly used in both markdown-it and its plugins, +// so plugins won't have to depend on them explicitly, which reduces their +// bundled size (e.g. a browser build). +// +exports.lib = {}; +exports.lib.mdurl = require('mdurl'); +exports.lib.ucmicro = require('uc.micro'); + +exports.assign = assign; +exports.isString = isString; +exports.has = has; +exports.unescapeMd = unescapeMd; +exports.unescapeAll = unescapeAll; +exports.isValidEntityCode = isValidEntityCode; +exports.fromCodePoint = fromCodePoint; +// exports.replaceEntities = replaceEntities; +exports.escapeHtml = escapeHtml; +exports.arrayReplaceAt = arrayReplaceAt; +exports.isSpace = isSpace; +exports.isWhiteSpace = isWhiteSpace; +exports.isMdAsciiPunct = isMdAsciiPunct; +exports.isPunctChar = isPunctChar; +exports.escapeRE = escapeRE; +exports.normalizeReference = normalizeReference; + +},{"./entities":29,"mdurl":84,"uc.micro":90,"uc.micro/categories/P/regex":88}],33:[function(require,module,exports){ +// Just a shortcut for bulk export +'use strict'; + + +exports.parseLinkLabel = require('./parse_link_label'); +exports.parseLinkDestination = require('./parse_link_destination'); +exports.parseLinkTitle = require('./parse_link_title'); + +},{"./parse_link_destination":34,"./parse_link_label":35,"./parse_link_title":36}],34:[function(require,module,exports){ +// Parse link destination +// +'use strict'; + + +var isSpace = require('../common/utils').isSpace; +var unescapeAll = require('../common/utils').unescapeAll; + + +module.exports = function parseLinkDestination(str, pos, max) { + var code, level, + lines = 0, + start = pos, + result = { + ok: false, + pos: 0, + lines: 0, + str: '' + }; + + if (str.charCodeAt(pos) === 0x3C /* < */) { + pos++; + while (pos < max) { + code = str.charCodeAt(pos); + if (code === 0x0A /* \n */ || isSpace(code)) { return result; } + if (code === 0x3E /* > */) { + result.pos = pos + 1; + result.str = unescapeAll(str.slice(start + 1, pos)); + result.ok = true; + return result; + } + if (code === 0x5C /* \ */ && pos + 1 < max) { + pos += 2; + continue; + } + + pos++; + } + + // no closing '>' + return result; + } + + // this should be ... } else { ... branch + + level = 0; + while (pos < max) { + code = str.charCodeAt(pos); + + if (code === 0x20) { break; } + + // ascii control characters + if (code < 0x20 || code === 0x7F) { break; } + + if (code === 0x5C /* \ */ && pos + 1 < max) { + pos += 2; + continue; + } + + if (code === 0x28 /* ( */) { + level++; + if (level > 1) { break; } + } + + if (code === 0x29 /* ) */) { + level--; + if (level < 0) { break; } + } + + pos++; + } + + if (start === pos) { return result; } + + result.str = unescapeAll(str.slice(start, pos)); + result.lines = lines; + result.pos = pos; + result.ok = true; + return result; +}; + +},{"../common/utils":32}],35:[function(require,module,exports){ +// Parse link label +// +// this function assumes that first character ("[") already matches; +// returns the end of the label +// +'use strict'; + +module.exports = function parseLinkLabel(state, start, disableNested) { + var level, found, marker, prevPos, + labelEnd = -1, + max = state.posMax, + oldPos = state.pos; + + state.pos = start + 1; + level = 1; + + while (state.pos < max) { + marker = state.src.charCodeAt(state.pos); + if (marker === 0x5D /* ] */) { + level--; + if (level === 0) { + found = true; + break; + } + } + + prevPos = state.pos; + state.md.inline.skipToken(state); + if (marker === 0x5B /* [ */) { + if (prevPos === state.pos - 1) { + // increase level if we find text `[`, which is not a part of any token + level++; + } else if (disableNested) { + state.pos = oldPos; + return -1; + } + } + } + + if (found) { + labelEnd = state.pos; + } + + // restore old state + state.pos = oldPos; + + return labelEnd; +}; + +},{}],36:[function(require,module,exports){ +// Parse link title +// +'use strict'; + + +var unescapeAll = require('../common/utils').unescapeAll; + + +module.exports = function parseLinkTitle(str, pos, max) { + var code, + marker, + lines = 0, + start = pos, + result = { + ok: false, + pos: 0, + lines: 0, + str: '' + }; + + if (pos >= max) { return result; } + + marker = str.charCodeAt(pos); + + if (marker !== 0x22 /* " */ && marker !== 0x27 /* ' */ && marker !== 0x28 /* ( */) { return result; } + + pos++; + + // if opening marker is "(", switch it to closing marker ")" + if (marker === 0x28) { marker = 0x29; } + + while (pos < max) { + code = str.charCodeAt(pos); + if (code === marker) { + result.pos = pos + 1; + result.lines = lines; + result.str = unescapeAll(str.slice(start + 1, pos)); + result.ok = true; + return result; + } else if (code === 0x0A) { + lines++; + } else if (code === 0x5C /* \ */ && pos + 1 < max) { + pos++; + if (str.charCodeAt(pos) === 0x0A) { + lines++; + } + } + + pos++; + } + + return result; +}; + +},{"../common/utils":32}],37:[function(require,module,exports){ +// Main perser class + +'use strict'; + + +var utils = require('./common/utils'); +var helpers = require('./helpers'); +var Renderer = require('./renderer'); +var ParserCore = require('./parser_core'); +var ParserBlock = require('./parser_block'); +var ParserInline = require('./parser_inline'); +var LinkifyIt = require('linkify-it'); +var mdurl = require('mdurl'); +var punycode = require('punycode'); + + +var config = { + 'default': require('./presets/default'), + zero: require('./presets/zero'), + commonmark: require('./presets/commonmark') +}; + +//////////////////////////////////////////////////////////////////////////////// +// +// This validator can prohibit more than really needed to prevent XSS. It's a +// tradeoff to keep code simple and to be secure by default. +// +// If you need different setup - override validator method as you wish. Or +// replace it with dummy function and use external sanitizer. +// + +var BAD_PROTO_RE = /^(vbscript|javascript|file|data):/; +var GOOD_DATA_RE = /^data:image\/(gif|png|jpeg|webp);/; + +function validateLink(url) { + // url should be normalized at this point, and existing entities are decoded + var str = url.trim().toLowerCase(); + + return BAD_PROTO_RE.test(str) ? (GOOD_DATA_RE.test(str) ? true : false) : true; +} + +//////////////////////////////////////////////////////////////////////////////// + + +var RECODE_HOSTNAME_FOR = [ 'http:', 'https:', 'mailto:' ]; + +function normalizeLink(url) { + var parsed = mdurl.parse(url, true); + + if (parsed.hostname) { + // Encode hostnames in urls like: + // `http://host/`, `https://host/`, `mailto:user@host`, `//host/` + // + // We don't encode unknown schemas, because it's likely that we encode + // something we shouldn't (e.g. `skype:name` treated as `skype:host`) + // + if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) { + try { + parsed.hostname = punycode.toASCII(parsed.hostname); + } catch (er) { /**/ } + } + } + + return mdurl.encode(mdurl.format(parsed)); +} + +function normalizeLinkText(url) { + var parsed = mdurl.parse(url, true); + + if (parsed.hostname) { + // Encode hostnames in urls like: + // `http://host/`, `https://host/`, `mailto:user@host`, `//host/` + // + // We don't encode unknown schemas, because it's likely that we encode + // something we shouldn't (e.g. `skype:name` treated as `skype:host`) + // + if (!parsed.protocol || RECODE_HOSTNAME_FOR.indexOf(parsed.protocol) >= 0) { + try { + parsed.hostname = punycode.toUnicode(parsed.hostname); + } catch (er) { /**/ } + } + } + + return mdurl.decode(mdurl.format(parsed)); +} + + +/** + * class MarkdownIt + * + * Main parser/renderer class. + * + * ##### Usage + * + * ```javascript + * // node.js, "classic" way: + * var MarkdownIt = require('markdown-it'), + * md = new MarkdownIt(); + * var result = md.render('# markdown-it rulezz!'); + * + * // node.js, the same, but with sugar: + * var md = require('markdown-it')(); + * var result = md.render('# markdown-it rulezz!'); + * + * // browser without AMD, added to "window" on script load + * // Note, there are no dash. + * var md = window.markdownit(); + * var result = md.render('# markdown-it rulezz!'); + * ``` + * + * Single line rendering, without paragraph wrap: + * + * ```javascript + * var md = require('markdown-it')(); + * var result = md.renderInline('__markdown-it__ rulezz!'); + * ``` + **/ + +/** + * new MarkdownIt([presetName, options]) + * - presetName (String): optional, `commonmark` / `zero` + * - options (Object) + * + * Creates parser instanse with given config. Can be called without `new`. + * + * ##### presetName + * + * MarkdownIt provides named presets as a convenience to quickly + * enable/disable active syntax rules and options for common use cases. + * + * - ["commonmark"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/commonmark.js) - + * configures parser to strict [CommonMark](http://commonmark.org/) mode. + * - [default](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/default.js) - + * similar to GFM, used when no preset name given. Enables all available rules, + * but still without html, typographer & autolinker. + * - ["zero"](https://github.com/markdown-it/markdown-it/blob/master/lib/presets/zero.js) - + * all rules disabled. Useful to quickly setup your config via `.enable()`. + * For example, when you need only `bold` and `italic` markup and nothing else. + * + * ##### options: + * + * - __html__ - `false`. Set `true` to enable HTML tags in source. Be careful! + * That's not safe! You may need external sanitizer to protect output from XSS. + * It's better to extend features via plugins, instead of enabling HTML. + * - __xhtmlOut__ - `false`. Set `true` to add '/' when closing single tags + * (`
`). This is needed only for full CommonMark compatibility. In real + * world you will need HTML output. + * - __breaks__ - `false`. Set `true` to convert `\n` in paragraphs into `
`. + * - __langPrefix__ - `language-`. CSS language class prefix for fenced blocks. + * Can be useful for external highlighters. + * - __linkify__ - `false`. Set `true` to autoconvert URL-like text to links. + * - __typographer__ - `false`. Set `true` to enable [some language-neutral + * replacement](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/replacements.js) + + * quotes beautification (smartquotes). + * - __quotes__ - `“”‘’`, String or Array. Double + single quotes replacement + * pairs, when typographer enabled and smartquotes on. For example, you can + * use `'«»„“'` for Russian, `'„“‚‘'` for German, and + * `['«\xA0', '\xA0»', '‹\xA0', '\xA0›']` for French (including nbsp). + * - __highlight__ - `null`. Highlighter function for fenced code blocks. + * Highlighter `function (str, lang)` should return escaped HTML. It can also + * return empty string if the source was not changed and should be escaped + * externaly. If result starts with `): + * + * ```javascript + * var hljs = require('highlight.js') // https://highlightjs.org/ + * + * // Actual default values + * var md = require('markdown-it')({ + * highlight: function (str, lang) { + * if (lang && hljs.getLanguage(lang)) { + * try { + * return '
' +
+ *                hljs.highlight(lang, str, true).value +
+ *                '
'; + * } catch (__) {} + * } + * + * return '
' + md.utils.escapeHtml(str) + '
'; + * } + * }); + * ``` + * + **/ +function MarkdownIt(presetName, options) { + if (!(this instanceof MarkdownIt)) { + return new MarkdownIt(presetName, options); + } + + if (!options) { + if (!utils.isString(presetName)) { + options = presetName || {}; + presetName = 'default'; + } + } + + /** + * MarkdownIt#inline -> ParserInline + * + * Instance of [[ParserInline]]. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.inline = new ParserInline(); + + /** + * MarkdownIt#block -> ParserBlock + * + * Instance of [[ParserBlock]]. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.block = new ParserBlock(); + + /** + * MarkdownIt#core -> Core + * + * Instance of [[Core]] chain executor. You may need it to add new rules when + * writing plugins. For simple rules control use [[MarkdownIt.disable]] and + * [[MarkdownIt.enable]]. + **/ + this.core = new ParserCore(); + + /** + * MarkdownIt#renderer -> Renderer + * + * Instance of [[Renderer]]. Use it to modify output look. Or to add rendering + * rules for new token types, generated by plugins. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * function myToken(tokens, idx, options, env, self) { + * //... + * return result; + * }; + * + * md.renderer.rules['my_token'] = myToken + * ``` + * + * See [[Renderer]] docs and [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.js). + **/ + this.renderer = new Renderer(); + + /** + * MarkdownIt#linkify -> LinkifyIt + * + * [linkify-it](https://github.com/markdown-it/linkify-it) instance. + * Used by [linkify](https://github.com/markdown-it/markdown-it/blob/master/lib/rules_core/linkify.js) + * rule. + **/ + this.linkify = new LinkifyIt(); + + /** + * MarkdownIt#validateLink(url) -> Boolean + * + * Link validation function. CommonMark allows too much in links. By default + * we disable `javascript:`, `vbscript:`, `file:` schemas, and almost all `data:...` schemas + * except some embedded image types. + * + * You can change this behaviour: + * + * ```javascript + * var md = require('markdown-it')(); + * // enable everything + * md.validateLink = function () { return true; } + * ``` + **/ + this.validateLink = validateLink; + + /** + * MarkdownIt#normalizeLink(url) -> String + * + * Function used to encode link url to a machine-readable format, + * which includes url-encoding, punycode, etc. + **/ + this.normalizeLink = normalizeLink; + + /** + * MarkdownIt#normalizeLinkText(url) -> String + * + * Function used to decode link url to a human-readable format` + **/ + this.normalizeLinkText = normalizeLinkText; + + + // Expose utils & helpers for easy acces from plugins + + /** + * MarkdownIt#utils -> utils + * + * Assorted utility functions, useful to write plugins. See details + * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/common/utils.js). + **/ + this.utils = utils; + + /** + * MarkdownIt#helpers -> helpers + * + * Link components parser functions, useful to write plugins. See details + * [here](https://github.com/markdown-it/markdown-it/blob/master/lib/helpers). + **/ + this.helpers = helpers; + + + this.options = {}; + this.configure(presetName); + + if (options) { this.set(options); } +} + + +/** chainable + * MarkdownIt.set(options) + * + * Set parser options (in the same format as in constructor). Probably, you + * will never need it, but you can change options after constructor call. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')() + * .set({ html: true, breaks: true }) + * .set({ typographer, true }); + * ``` + * + * __Note:__ To achieve the best possible performance, don't modify a + * `markdown-it` instance options on the fly. If you need multiple configurations + * it's best to create multiple instances and initialize each with separate + * config. + **/ +MarkdownIt.prototype.set = function (options) { + utils.assign(this.options, options); + return this; +}; + + +/** chainable, internal + * MarkdownIt.configure(presets) + * + * Batch load of all options and compenent settings. This is internal method, + * and you probably will not need it. But if you with - see available presets + * and data structure [here](https://github.com/markdown-it/markdown-it/tree/master/lib/presets) + * + * We strongly recommend to use presets instead of direct config loads. That + * will give better compatibility with next versions. + **/ +MarkdownIt.prototype.configure = function (presets) { + var self = this, presetName; + + if (utils.isString(presets)) { + presetName = presets; + presets = config[presetName]; + if (!presets) { throw new Error('Wrong `markdown-it` preset "' + presetName + '", check name'); } + } + + if (!presets) { throw new Error('Wrong `markdown-it` preset, can\'t be empty'); } + + if (presets.options) { self.set(presets.options); } + + if (presets.components) { + Object.keys(presets.components).forEach(function (name) { + if (presets.components[name].rules) { + self[name].ruler.enableOnly(presets.components[name].rules); + } + if (presets.components[name].rules2) { + self[name].ruler2.enableOnly(presets.components[name].rules2); + } + }); + } + return this; +}; + + +/** chainable + * MarkdownIt.enable(list, ignoreInvalid) + * - list (String|Array): rule name or list of rule names to enable + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable list or rules. It will automatically find appropriate components, + * containing rules with given names. If rule not found, and `ignoreInvalid` + * not set - throws exception. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')() + * .enable(['sub', 'sup']) + * .disable('smartquotes'); + * ``` + **/ +MarkdownIt.prototype.enable = function (list, ignoreInvalid) { + var result = []; + + if (!Array.isArray(list)) { list = [ list ]; } + + [ 'core', 'block', 'inline' ].forEach(function (chain) { + result = result.concat(this[chain].ruler.enable(list, true)); + }, this); + + result = result.concat(this.inline.ruler2.enable(list, true)); + + var missed = list.filter(function (name) { return result.indexOf(name) < 0; }); + + if (missed.length && !ignoreInvalid) { + throw new Error('MarkdownIt. Failed to enable unknown rule(s): ' + missed); + } + + return this; +}; + + +/** chainable + * MarkdownIt.disable(list, ignoreInvalid) + * - list (String|Array): rule name or list of rule names to disable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * The same as [[MarkdownIt.enable]], but turn specified rules off. + **/ +MarkdownIt.prototype.disable = function (list, ignoreInvalid) { + var result = []; + + if (!Array.isArray(list)) { list = [ list ]; } + + [ 'core', 'block', 'inline' ].forEach(function (chain) { + result = result.concat(this[chain].ruler.disable(list, true)); + }, this); + + result = result.concat(this.inline.ruler2.disable(list, true)); + + var missed = list.filter(function (name) { return result.indexOf(name) < 0; }); + + if (missed.length && !ignoreInvalid) { + throw new Error('MarkdownIt. Failed to disable unknown rule(s): ' + missed); + } + return this; +}; + + +/** chainable + * MarkdownIt.use(plugin, params) + * + * Load specified plugin with given params into current parser instance. + * It's just a sugar to call `plugin(md, params)` with curring. + * + * ##### Example + * + * ```javascript + * var iterator = require('markdown-it-for-inline'); + * var md = require('markdown-it')() + * .use(iterator, 'foo_replace', 'text', function (tokens, idx) { + * tokens[idx].content = tokens[idx].content.replace(/foo/g, 'bar'); + * }); + * ``` + **/ +MarkdownIt.prototype.use = function (plugin /*, params, ... */) { + var args = [ this ].concat(Array.prototype.slice.call(arguments, 1)); + plugin.apply(plugin, args); + return this; +}; + + +/** internal + * MarkdownIt.parse(src, env) -> Array + * - src (String): source string + * - env (Object): environment sandbox + * + * Parse input string and returns list of block tokens (special token type + * "inline" will contain list of inline tokens). You should not call this + * method directly, until you write custom renderer (for example, to produce + * AST). + * + * `env` is used to pass data between "distributed" rules and return additional + * metadata like reference info, needed for the renderer. It also can be used to + * inject data in specific cases. Usually, you will be ok to pass `{}`, + * and then pass updated object to renderer. + **/ +MarkdownIt.prototype.parse = function (src, env) { + var state = new this.core.State(src, this, env); + + this.core.process(state); + + return state.tokens; +}; + + +/** + * MarkdownIt.render(src [, env]) -> String + * - src (String): source string + * - env (Object): environment sandbox + * + * Render markdown string into html. It does all magic for you :). + * + * `env` can be used to inject additional metadata (`{}` by default). + * But you will not need it with high probability. See also comment + * in [[MarkdownIt.parse]]. + **/ +MarkdownIt.prototype.render = function (src, env) { + env = env || {}; + + return this.renderer.render(this.parse(src, env), this.options, env); +}; + + +/** internal + * MarkdownIt.parseInline(src, env) -> Array + * - src (String): source string + * - env (Object): environment sandbox + * + * The same as [[MarkdownIt.parse]] but skip all block rules. It returns the + * block tokens list with the single `inline` element, containing parsed inline + * tokens in `children` property. Also updates `env` object. + **/ +MarkdownIt.prototype.parseInline = function (src, env) { + var state = new this.core.State(src, this, env); + + state.inlineMode = true; + this.core.process(state); + + return state.tokens; +}; + + +/** + * MarkdownIt.renderInline(src [, env]) -> String + * - src (String): source string + * - env (Object): environment sandbox + * + * Similar to [[MarkdownIt.render]] but for single paragraph content. Result + * will NOT be wrapped into `

` tags. + **/ +MarkdownIt.prototype.renderInline = function (src, env) { + env = env || {}; + + return this.renderer.render(this.parseInline(src, env), this.options, env); +}; + + +module.exports = MarkdownIt; + +},{"./common/utils":32,"./helpers":33,"./parser_block":38,"./parser_core":39,"./parser_inline":40,"./presets/commonmark":41,"./presets/default":42,"./presets/zero":43,"./renderer":44,"linkify-it":26,"mdurl":84,"punycode":92}],38:[function(require,module,exports){ +/** internal + * class ParserBlock + * + * Block-level tokenizer. + **/ +'use strict'; + + +var Ruler = require('./ruler'); + + +var _rules = [ + // First 2 params - rule name & source. Secondary array - list of rules, + // which can be terminated by this one. + [ 'table', require('./rules_block/table'), [ 'paragraph', 'reference' ] ], + [ 'code', require('./rules_block/code') ], + [ 'fence', require('./rules_block/fence'), [ 'paragraph', 'reference', 'blockquote', 'list' ] ], + [ 'blockquote', require('./rules_block/blockquote'), [ 'paragraph', 'reference', 'list' ] ], + [ 'hr', require('./rules_block/hr'), [ 'paragraph', 'reference', 'blockquote', 'list' ] ], + [ 'list', require('./rules_block/list'), [ 'paragraph', 'reference', 'blockquote' ] ], + [ 'reference', require('./rules_block/reference') ], + [ 'heading', require('./rules_block/heading'), [ 'paragraph', 'reference', 'blockquote' ] ], + [ 'lheading', require('./rules_block/lheading') ], + [ 'html_block', require('./rules_block/html_block'), [ 'paragraph', 'reference', 'blockquote' ] ], + [ 'paragraph', require('./rules_block/paragraph') ] +]; + + +/** + * new ParserBlock() + **/ +function ParserBlock() { + /** + * ParserBlock#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of block rules. + **/ + this.ruler = new Ruler(); + + for (var i = 0; i < _rules.length; i++) { + this.ruler.push(_rules[i][0], _rules[i][1], { alt: (_rules[i][2] || []).slice() }); + } +} + + +// Generate tokens for input range +// +ParserBlock.prototype.tokenize = function (state, startLine, endLine) { + var ok, i, + rules = this.ruler.getRules(''), + len = rules.length, + line = startLine, + hasEmptyLines = false, + maxNesting = state.md.options.maxNesting; + + while (line < endLine) { + state.line = line = state.skipEmptyLines(line); + if (line >= endLine) { break; } + + // Termination condition for nested calls. + // Nested calls currently used for blockquotes & lists + if (state.sCount[line] < state.blkIndent) { break; } + + // If nesting level exceeded - skip tail to the end. That's not ordinary + // situation and we should not care about content. + if (state.level >= maxNesting) { + state.line = endLine; + break; + } + + // Try all possible rules. + // On success, rule should: + // + // - update `state.line` + // - update `state.tokens` + // - return true + + for (i = 0; i < len; i++) { + ok = rules[i](state, line, endLine, false); + if (ok) { break; } + } + + // set state.tight iff we had an empty line before current tag + // i.e. latest empty line should not count + state.tight = !hasEmptyLines; + + // paragraph might "eat" one newline after it in nested lists + if (state.isEmpty(state.line - 1)) { + hasEmptyLines = true; + } + + line = state.line; + + if (line < endLine && state.isEmpty(line)) { + hasEmptyLines = true; + line++; + + // two empty lines should stop the parser in list mode + if (line < endLine && state.parentType === 'list' && state.isEmpty(line)) { break; } + state.line = line; + } + } +}; + + +/** + * ParserBlock.parse(str, md, env, outTokens) + * + * Process input string and push block tokens into `outTokens` + **/ +ParserBlock.prototype.parse = function (src, md, env, outTokens) { + var state; + + if (!src) { return []; } + + state = new this.State(src, md, env, outTokens); + + this.tokenize(state, state.line, state.lineMax); +}; + + +ParserBlock.prototype.State = require('./rules_block/state_block'); + + +module.exports = ParserBlock; + +},{"./ruler":45,"./rules_block/blockquote":46,"./rules_block/code":47,"./rules_block/fence":48,"./rules_block/heading":49,"./rules_block/hr":50,"./rules_block/html_block":51,"./rules_block/lheading":52,"./rules_block/list":53,"./rules_block/paragraph":54,"./rules_block/reference":55,"./rules_block/state_block":56,"./rules_block/table":57}],39:[function(require,module,exports){ +/** internal + * class Core + * + * Top-level rules executor. Glues block/inline parsers and does intermediate + * transformations. + **/ +'use strict'; + + +var Ruler = require('./ruler'); + + +var _rules = [ + [ 'normalize', require('./rules_core/normalize') ], + [ 'block', require('./rules_core/block') ], + [ 'inline', require('./rules_core/inline') ], + [ 'linkify', require('./rules_core/linkify') ], + [ 'replacements', require('./rules_core/replacements') ], + [ 'smartquotes', require('./rules_core/smartquotes') ] +]; + + +/** + * new Core() + **/ +function Core() { + /** + * Core#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of core rules. + **/ + this.ruler = new Ruler(); + + for (var i = 0; i < _rules.length; i++) { + this.ruler.push(_rules[i][0], _rules[i][1]); + } +} + + +/** + * Core.process(state) + * + * Executes core chain rules. + **/ +Core.prototype.process = function (state) { + var i, l, rules; + + rules = this.ruler.getRules(''); + + for (i = 0, l = rules.length; i < l; i++) { + rules[i](state); + } +}; + +Core.prototype.State = require('./rules_core/state_core'); + + +module.exports = Core; + +},{"./ruler":45,"./rules_core/block":58,"./rules_core/inline":59,"./rules_core/linkify":60,"./rules_core/normalize":61,"./rules_core/replacements":62,"./rules_core/smartquotes":63,"./rules_core/state_core":64}],40:[function(require,module,exports){ +/** internal + * class ParserInline + * + * Tokenizes paragraph content. + **/ +'use strict'; + + +var Ruler = require('./ruler'); + + +//////////////////////////////////////////////////////////////////////////////// +// Parser rules + +var _rules = [ + [ 'text', require('./rules_inline/text') ], + [ 'newline', require('./rules_inline/newline') ], + [ 'escape', require('./rules_inline/escape') ], + [ 'backticks', require('./rules_inline/backticks') ], + [ 'strikethrough', require('./rules_inline/strikethrough').tokenize ], + [ 'emphasis', require('./rules_inline/emphasis').tokenize ], + [ 'link', require('./rules_inline/link') ], + [ 'image', require('./rules_inline/image') ], + [ 'autolink', require('./rules_inline/autolink') ], + [ 'html_inline', require('./rules_inline/html_inline') ], + [ 'entity', require('./rules_inline/entity') ] +]; + +var _rules2 = [ + [ 'balance_pairs', require('./rules_inline/balance_pairs') ], + [ 'strikethrough', require('./rules_inline/strikethrough').postProcess ], + [ 'emphasis', require('./rules_inline/emphasis').postProcess ], + [ 'text_collapse', require('./rules_inline/text_collapse') ] +]; + + +/** + * new ParserInline() + **/ +function ParserInline() { + var i; + + /** + * ParserInline#ruler -> Ruler + * + * [[Ruler]] instance. Keep configuration of inline rules. + **/ + this.ruler = new Ruler(); + + for (i = 0; i < _rules.length; i++) { + this.ruler.push(_rules[i][0], _rules[i][1]); + } + + /** + * ParserInline#ruler2 -> Ruler + * + * [[Ruler]] instance. Second ruler used for post-processing + * (e.g. in emphasis-like rules). + **/ + this.ruler2 = new Ruler(); + + for (i = 0; i < _rules2.length; i++) { + this.ruler2.push(_rules2[i][0], _rules2[i][1]); + } +} + + +// Skip single token by running all rules in validation mode; +// returns `true` if any rule reported success +// +ParserInline.prototype.skipToken = function (state) { + var ok, i, pos = state.pos, + rules = this.ruler.getRules(''), + len = rules.length, + maxNesting = state.md.options.maxNesting, + cache = state.cache; + + + if (typeof cache[pos] !== 'undefined') { + state.pos = cache[pos]; + return; + } + + if (state.level < maxNesting) { + for (i = 0; i < len; i++) { + // Increment state.level and decrement it later to limit recursion. + // It's harmless to do here, because no tokens are created. But ideally, + // we'd need a separate private state variable for this purpose. + // + state.level++; + ok = rules[i](state, true); + state.level--; + + if (ok) { break; } + } + } else { + // Too much nesting, just skip until the end of the paragraph. + // + // NOTE: this will cause links to behave incorrectly in the following case, + // when an amount of `[` is exactly equal to `maxNesting + 1`: + // + // [[[[[[[[[[[[[[[[[[[[[foo]() + // + // TODO: remove this workaround when CM standard will allow nested links + // (we can replace it by preventing links from being parsed in + // validation mode) + // + state.pos = state.posMax; + } + + if (!ok) { state.pos++; } + cache[pos] = state.pos; +}; + + +// Generate tokens for input range +// +ParserInline.prototype.tokenize = function (state) { + var ok, i, + rules = this.ruler.getRules(''), + len = rules.length, + end = state.posMax, + maxNesting = state.md.options.maxNesting; + + while (state.pos < end) { + // Try all possible rules. + // On success, rule should: + // + // - update `state.pos` + // - update `state.tokens` + // - return true + + if (state.level < maxNesting) { + for (i = 0; i < len; i++) { + ok = rules[i](state, false); + if (ok) { break; } + } + } + + if (ok) { + if (state.pos >= end) { break; } + continue; + } + + state.pending += state.src[state.pos++]; + } + + if (state.pending) { + state.pushPending(); + } +}; + + +/** + * ParserInline.parse(str, md, env, outTokens) + * + * Process input string and push inline tokens into `outTokens` + **/ +ParserInline.prototype.parse = function (str, md, env, outTokens) { + var i, rules, len; + var state = new this.State(str, md, env, outTokens); + + this.tokenize(state); + + rules = this.ruler2.getRules(''); + len = rules.length; + + for (i = 0; i < len; i++) { + rules[i](state); + } +}; + + +ParserInline.prototype.State = require('./rules_inline/state_inline'); + + +module.exports = ParserInline; + +},{"./ruler":45,"./rules_inline/autolink":65,"./rules_inline/backticks":66,"./rules_inline/balance_pairs":67,"./rules_inline/emphasis":68,"./rules_inline/entity":69,"./rules_inline/escape":70,"./rules_inline/html_inline":71,"./rules_inline/image":72,"./rules_inline/link":73,"./rules_inline/newline":74,"./rules_inline/state_inline":75,"./rules_inline/strikethrough":76,"./rules_inline/text":77,"./rules_inline/text_collapse":78}],41:[function(require,module,exports){ +// Commonmark default options + +'use strict'; + + +module.exports = { + options: { + html: true, // Enable HTML tags in source + xhtmlOut: true, // Use '/' to close single tags (
) + breaks: false, // Convert '\n' in paragraphs into
+ langPrefix: 'language-', // CSS language prefix for fenced blocks + linkify: false, // autoconvert URL-like texts to links + + // Enable some language-neutral replacements + quotes beautification + typographer: false, + + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ) + breaks: false, // Convert '\n' in paragraphs into
+ langPrefix: 'language-', // CSS language prefix for fenced blocks + linkify: false, // autoconvert URL-like texts to links + + // Enable some language-neutral replacements + quotes beautification + typographer: false, + + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ) + breaks: false, // Convert '\n' in paragraphs into
+ langPrefix: 'language-', // CSS language prefix for fenced blocks + linkify: false, // autoconvert URL-like texts to links + + // Enable some language-neutral replacements + quotes beautification + typographer: false, + + // Double + single quotes replacement pairs, when typographer enabled, + // and smartquotes on. Could be either a String or an Array. + // + // For example, you can use '«»„“' for Russian, '„“‚‘' for German, + // and ['«\xA0', '\xA0»', '‹\xA0', '\xA0›'] for French (including nbsp). + quotes: '\u201c\u201d\u2018\u2019', /* “”‘’ */ + + // Highlighter function. Should return escaped HTML, + // or '' if the source string is not changed and should be escaped externaly. + // If result starts with ' + escapeHtml(tokens[idx].content) + ''; +}; + + +default_rules.code_block = function (tokens, idx /*, options, env */) { + return '

' + escapeHtml(tokens[idx].content) + '
\n'; +}; + + +default_rules.fence = function (tokens, idx, options, env, slf) { + var token = tokens[idx], + info = token.info ? unescapeAll(token.info).trim() : '', + langName = '', + highlighted; + + if (info) { + langName = info.split(/\s+/g)[0]; + token.attrJoin('class', options.langPrefix + langName); + } + + if (options.highlight) { + highlighted = options.highlight(token.content, langName) || escapeHtml(token.content); + } else { + highlighted = escapeHtml(token.content); + } + + if (highlighted.indexOf('' + + highlighted + + '\n'; +}; + + +default_rules.image = function (tokens, idx, options, env, slf) { + var token = tokens[idx]; + + // "alt" attr MUST be set, even if empty. Because it's mandatory and + // should be placed on proper position for tests. + // + // Replace content with actual value + + token.attrs[token.attrIndex('alt')][1] = + slf.renderInlineAsText(token.children, options, env); + + return slf.renderToken(tokens, idx, options); +}; + + +default_rules.hardbreak = function (tokens, idx, options /*, env */) { + return options.xhtmlOut ? '
\n' : '
\n'; +}; +default_rules.softbreak = function (tokens, idx, options /*, env */) { + return options.breaks ? (options.xhtmlOut ? '
\n' : '
\n') : '\n'; +}; + + +default_rules.text = function (tokens, idx /*, options, env */) { + return escapeHtml(tokens[idx].content); +}; + + +default_rules.html_block = function (tokens, idx /*, options, env */) { + return tokens[idx].content; +}; +default_rules.html_inline = function (tokens, idx /*, options, env */) { + return tokens[idx].content; +}; + + +/** + * new Renderer() + * + * Creates new [[Renderer]] instance and fill [[Renderer#rules]] with defaults. + **/ +function Renderer() { + + /** + * Renderer#rules -> Object + * + * Contains render rules for tokens. Can be updated and extended. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.renderer.rules.strong_open = function () { return ''; }; + * md.renderer.rules.strong_close = function () { return ''; }; + * + * var result = md.renderInline(...); + * ``` + * + * Each rule is called as independed static function with fixed signature: + * + * ```javascript + * function my_token_render(tokens, idx, options, env, renderer) { + * // ... + * return renderedHTML; + * } + * ``` + * + * See [source code](https://github.com/markdown-it/markdown-it/blob/master/lib/renderer.js) + * for more details and examples. + **/ + this.rules = assign({}, default_rules); +} + + +/** + * Renderer.renderAttrs(token) -> String + * + * Render token attributes to string. + **/ +Renderer.prototype.renderAttrs = function renderAttrs(token) { + var i, l, result; + + if (!token.attrs) { return ''; } + + result = ''; + + for (i = 0, l = token.attrs.length; i < l; i++) { + result += ' ' + escapeHtml(token.attrs[i][0]) + '="' + escapeHtml(token.attrs[i][1]) + '"'; + } + + return result; +}; + + +/** + * Renderer.renderToken(tokens, idx, options) -> String + * - tokens (Array): list of tokens + * - idx (Numbed): token index to render + * - options (Object): params of parser instance + * + * Default token renderer. Can be overriden by custom function + * in [[Renderer#rules]]. + **/ +Renderer.prototype.renderToken = function renderToken(tokens, idx, options) { + var nextToken, + result = '', + needLf = false, + token = tokens[idx]; + + // Tight list paragraphs + if (token.hidden) { + return ''; + } + + // Insert a newline between hidden paragraph and subsequent opening + // block-level tag. + // + // For example, here we should insert a newline before blockquote: + // - a + // > + // + if (token.block && token.nesting !== -1 && idx && tokens[idx - 1].hidden) { + result += '\n'; + } + + // Add token name, e.g. ``. + // + needLf = false; + } + } + } + } + + result += needLf ? '>\n' : '>'; + + return result; +}; + + +/** + * Renderer.renderInline(tokens, options, env) -> String + * - tokens (Array): list on block tokens to renter + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * The same as [[Renderer.render]], but for single token of `inline` type. + **/ +Renderer.prototype.renderInline = function (tokens, options, env) { + var type, + result = '', + rules = this.rules; + + for (var i = 0, len = tokens.length; i < len; i++) { + type = tokens[i].type; + + if (typeof rules[type] !== 'undefined') { + result += rules[type](tokens, i, options, env, this); + } else { + result += this.renderToken(tokens, i, options); + } + } + + return result; +}; + + +/** internal + * Renderer.renderInlineAsText(tokens, options, env) -> String + * - tokens (Array): list on block tokens to renter + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * Special kludge for image `alt` attributes to conform CommonMark spec. + * Don't try to use it! Spec requires to show `alt` content with stripped markup, + * instead of simple escaping. + **/ +Renderer.prototype.renderInlineAsText = function (tokens, options, env) { + var result = '', + rules = this.rules; + + for (var i = 0, len = tokens.length; i < len; i++) { + if (tokens[i].type === 'text') { + result += rules.text(tokens, i, options, env, this); + } else if (tokens[i].type === 'image') { + result += this.renderInlineAsText(tokens[i].children, options, env); + } + } + + return result; +}; + + +/** + * Renderer.render(tokens, options, env) -> String + * - tokens (Array): list on block tokens to renter + * - options (Object): params of parser instance + * - env (Object): additional data from parsed input (references, for example) + * + * Takes token stream and generates HTML. Probably, you will never need to call + * this method directly. + **/ +Renderer.prototype.render = function (tokens, options, env) { + var i, len, type, + result = '', + rules = this.rules; + + for (i = 0, len = tokens.length; i < len; i++) { + type = tokens[i].type; + + if (type === 'inline') { + result += this.renderInline(tokens[i].children, options, env); + } else if (typeof rules[type] !== 'undefined') { + result += rules[tokens[i].type](tokens, i, options, env, this); + } else { + result += this.renderToken(tokens, i, options, env); + } + } + + return result; +}; + +module.exports = Renderer; + +},{"./common/utils":32}],45:[function(require,module,exports){ +/** + * class Ruler + * + * Helper class, used by [[MarkdownIt#core]], [[MarkdownIt#block]] and + * [[MarkdownIt#inline]] to manage sequences of functions (rules): + * + * - keep rules in defined order + * - assign the name to each rule + * - enable/disable rules + * - add/replace rules + * - allow assign rules to additional named chains (in the same) + * - cacheing lists of active rules + * + * You will not need use this class directly until write plugins. For simple + * rules control use [[MarkdownIt.disable]], [[MarkdownIt.enable]] and + * [[MarkdownIt.use]]. + **/ +'use strict'; + + +/** + * new Ruler() + **/ +function Ruler() { + // List of added rules. Each element is: + // + // { + // name: XXX, + // enabled: Boolean, + // fn: Function(), + // alt: [ name2, name3 ] + // } + // + this.__rules__ = []; + + // Cached rule chains. + // + // First level - chain name, '' for default. + // Second level - diginal anchor for fast filtering by charcodes. + // + this.__cache__ = null; +} + +//////////////////////////////////////////////////////////////////////////////// +// Helper methods, should not be used directly + + +// Find rule index by name +// +Ruler.prototype.__find__ = function (name) { + for (var i = 0; i < this.__rules__.length; i++) { + if (this.__rules__[i].name === name) { + return i; + } + } + return -1; +}; + + +// Build rules lookup cache +// +Ruler.prototype.__compile__ = function () { + var self = this; + var chains = [ '' ]; + + // collect unique names + self.__rules__.forEach(function (rule) { + if (!rule.enabled) { return; } + + rule.alt.forEach(function (altName) { + if (chains.indexOf(altName) < 0) { + chains.push(altName); + } + }); + }); + + self.__cache__ = {}; + + chains.forEach(function (chain) { + self.__cache__[chain] = []; + self.__rules__.forEach(function (rule) { + if (!rule.enabled) { return; } + + if (chain && rule.alt.indexOf(chain) < 0) { return; } + + self.__cache__[chain].push(rule.fn); + }); + }); +}; + + +/** + * Ruler.at(name, fn [, options]) + * - name (String): rule name to replace. + * - fn (Function): new rule function. + * - options (Object): new rule options (not mandatory). + * + * Replace rule by name with new function & options. Throws error if name not + * found. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * Replace existing typorgapher replacement rule with new one: + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.core.ruler.at('replacements', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.at = function (name, fn, options) { + var index = this.__find__(name); + var opt = options || {}; + + if (index === -1) { throw new Error('Parser rule not found: ' + name); } + + this.__rules__[index].fn = fn; + this.__rules__[index].alt = opt.alt || []; + this.__cache__ = null; +}; + + +/** + * Ruler.before(beforeName, ruleName, fn [, options]) + * - beforeName (String): new rule will be added before this one. + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Add new rule to chain before one with given name. See also + * [[Ruler.after]], [[Ruler.push]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.block.ruler.before('paragraph', 'my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.before = function (beforeName, ruleName, fn, options) { + var index = this.__find__(beforeName); + var opt = options || {}; + + if (index === -1) { throw new Error('Parser rule not found: ' + beforeName); } + + this.__rules__.splice(index, 0, { + name: ruleName, + enabled: true, + fn: fn, + alt: opt.alt || [] + }); + + this.__cache__ = null; +}; + + +/** + * Ruler.after(afterName, ruleName, fn [, options]) + * - afterName (String): new rule will be added after this one. + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Add new rule to chain after one with given name. See also + * [[Ruler.before]], [[Ruler.push]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.inline.ruler.after('text', 'my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.after = function (afterName, ruleName, fn, options) { + var index = this.__find__(afterName); + var opt = options || {}; + + if (index === -1) { throw new Error('Parser rule not found: ' + afterName); } + + this.__rules__.splice(index + 1, 0, { + name: ruleName, + enabled: true, + fn: fn, + alt: opt.alt || [] + }); + + this.__cache__ = null; +}; + +/** + * Ruler.push(ruleName, fn [, options]) + * - ruleName (String): name of added rule. + * - fn (Function): rule function. + * - options (Object): rule options (not mandatory). + * + * Push new rule to the end of chain. See also + * [[Ruler.before]], [[Ruler.after]]. + * + * ##### Options: + * + * - __alt__ - array with names of "alternate" chains. + * + * ##### Example + * + * ```javascript + * var md = require('markdown-it')(); + * + * md.core.ruler.push('my_rule', function replace(state) { + * //... + * }); + * ``` + **/ +Ruler.prototype.push = function (ruleName, fn, options) { + var opt = options || {}; + + this.__rules__.push({ + name: ruleName, + enabled: true, + fn: fn, + alt: opt.alt || [] + }); + + this.__cache__ = null; +}; + + +/** + * Ruler.enable(list [, ignoreInvalid]) -> Array + * - list (String|Array): list of rule names to enable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable rules with given names. If any rule name not found - throw Error. + * Errors can be disabled by second param. + * + * Returns list of found rule names (if no exception happened). + * + * See also [[Ruler.disable]], [[Ruler.enableOnly]]. + **/ +Ruler.prototype.enable = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { list = [ list ]; } + + var result = []; + + // Search by name and enable + list.forEach(function (name) { + var idx = this.__find__(name); + + if (idx < 0) { + if (ignoreInvalid) { return; } + throw new Error('Rules manager: invalid rule name ' + name); + } + this.__rules__[idx].enabled = true; + result.push(name); + }, this); + + this.__cache__ = null; + return result; +}; + + +/** + * Ruler.enableOnly(list [, ignoreInvalid]) + * - list (String|Array): list of rule names to enable (whitelist). + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Enable rules with given names, and disable everything else. If any rule name + * not found - throw Error. Errors can be disabled by second param. + * + * See also [[Ruler.disable]], [[Ruler.enable]]. + **/ +Ruler.prototype.enableOnly = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { list = [ list ]; } + + this.__rules__.forEach(function (rule) { rule.enabled = false; }); + + this.enable(list, ignoreInvalid); +}; + + +/** + * Ruler.disable(list [, ignoreInvalid]) -> Array + * - list (String|Array): list of rule names to disable. + * - ignoreInvalid (Boolean): set `true` to ignore errors when rule not found. + * + * Disable rules with given names. If any rule name not found - throw Error. + * Errors can be disabled by second param. + * + * Returns list of found rule names (if no exception happened). + * + * See also [[Ruler.enable]], [[Ruler.enableOnly]]. + **/ +Ruler.prototype.disable = function (list, ignoreInvalid) { + if (!Array.isArray(list)) { list = [ list ]; } + + var result = []; + + // Search by name and disable + list.forEach(function (name) { + var idx = this.__find__(name); + + if (idx < 0) { + if (ignoreInvalid) { return; } + throw new Error('Rules manager: invalid rule name ' + name); + } + this.__rules__[idx].enabled = false; + result.push(name); + }, this); + + this.__cache__ = null; + return result; +}; + + +/** + * Ruler.getRules(chainName) -> Array + * + * Return array of active functions (rules) for given chain name. It analyzes + * rules configuration, compiles caches if not exists and returns result. + * + * Default chain name is `''` (empty string). It can't be skipped. That's + * done intentionally, to keep signature monomorphic for high speed. + **/ +Ruler.prototype.getRules = function (chainName) { + if (this.__cache__ === null) { + this.__compile__(); + } + + // Chain can be empty, if rules disabled. But we still have to return Array. + return this.__cache__[chainName] || []; +}; + +module.exports = Ruler; + +},{}],46:[function(require,module,exports){ +// Block quotes + +'use strict'; + +var isSpace = require('../common/utils').isSpace; + + +module.exports = function blockquote(state, startLine, endLine, silent) { + var nextLine, lastLineEmpty, oldTShift, oldSCount, oldBMarks, oldIndent, oldParentType, lines, initial, offset, ch, + terminatorRules, token, + i, l, terminate, + pos = state.bMarks[startLine] + state.tShift[startLine], + max = state.eMarks[startLine]; + + // check the block quote marker + if (state.src.charCodeAt(pos++) !== 0x3E/* > */) { return false; } + + // we know that it's going to be a valid blockquote, + // so no point trying to find the end of it in silent mode + if (silent) { return true; } + + // skip one optional space (but not tab, check cmark impl) after '>' + if (state.src.charCodeAt(pos) === 0x20) { pos++; } + + oldIndent = state.blkIndent; + state.blkIndent = 0; + + // skip spaces after ">" and re-calculate offset + initial = offset = state.sCount[startLine] + pos - (state.bMarks[startLine] + state.tShift[startLine]); + + oldBMarks = [ state.bMarks[startLine] ]; + state.bMarks[startLine] = pos; + + while (pos < max) { + ch = state.src.charCodeAt(pos); + + if (isSpace(ch)) { + if (ch === 0x09) { + offset += 4 - offset % 4; + } else { + offset++; + } + } else { + break; + } + + pos++; + } + + lastLineEmpty = pos >= max; + + oldSCount = [ state.sCount[startLine] ]; + state.sCount[startLine] = offset - initial; + + oldTShift = [ state.tShift[startLine] ]; + state.tShift[startLine] = pos - state.bMarks[startLine]; + + terminatorRules = state.md.block.ruler.getRules('blockquote'); + + // Search the end of the block + // + // Block ends with either: + // 1. an empty line outside: + // ``` + // > test + // + // ``` + // 2. an empty line inside: + // ``` + // > + // test + // ``` + // 3. another tag + // ``` + // > test + // - - - + // ``` + for (nextLine = startLine + 1; nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < oldIndent) { break; } + + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + + if (pos >= max) { + // Case 1: line is not inside the blockquote, and this line is empty. + break; + } + + if (state.src.charCodeAt(pos++) === 0x3E/* > */) { + // This line is inside the blockquote. + + // skip one optional space (but not tab, check cmark impl) after '>' + if (state.src.charCodeAt(pos) === 0x20) { pos++; } + + // skip spaces after ">" and re-calculate offset + initial = offset = state.sCount[nextLine] + pos - (state.bMarks[nextLine] + state.tShift[nextLine]); + + oldBMarks.push(state.bMarks[nextLine]); + state.bMarks[nextLine] = pos; + + while (pos < max) { + ch = state.src.charCodeAt(pos); + + if (isSpace(ch)) { + if (ch === 0x09) { + offset += 4 - offset % 4; + } else { + offset++; + } + } else { + break; + } + + pos++; + } + + lastLineEmpty = pos >= max; + + oldSCount.push(state.sCount[nextLine]); + state.sCount[nextLine] = offset - initial; + + oldTShift.push(state.tShift[nextLine]); + state.tShift[nextLine] = pos - state.bMarks[nextLine]; + continue; + } + + // Case 2: line is not inside the blockquote, and the last line was empty. + if (lastLineEmpty) { break; } + + // Case 3: another tag found. + terminate = false; + for (i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { break; } + + oldBMarks.push(state.bMarks[nextLine]); + oldTShift.push(state.tShift[nextLine]); + oldSCount.push(state.sCount[nextLine]); + + // A negative indentation means that this is a paragraph continuation + // + state.sCount[nextLine] = -1; + } + + oldParentType = state.parentType; + state.parentType = 'blockquote'; + + token = state.push('blockquote_open', 'blockquote', 1); + token.markup = '>'; + token.map = lines = [ startLine, 0 ]; + + state.md.block.tokenize(state, startLine, nextLine); + + token = state.push('blockquote_close', 'blockquote', -1); + token.markup = '>'; + + state.parentType = oldParentType; + lines[1] = state.line; + + // Restore original tShift; this might not be necessary since the parser + // has already been here, but just to make sure we can do that. + for (i = 0; i < oldTShift.length; i++) { + state.bMarks[i + startLine] = oldBMarks[i]; + state.tShift[i + startLine] = oldTShift[i]; + state.sCount[i + startLine] = oldSCount[i]; + } + state.blkIndent = oldIndent; + + return true; +}; + +},{"../common/utils":32}],47:[function(require,module,exports){ +// Code block (4 spaces padded) + +'use strict'; + + +module.exports = function code(state, startLine, endLine/*, silent*/) { + var nextLine, last, token, emptyLines = 0; + + if (state.sCount[startLine] - state.blkIndent < 4) { return false; } + + last = nextLine = startLine + 1; + + while (nextLine < endLine) { + if (state.isEmpty(nextLine)) { + emptyLines++; + + // workaround for lists: 2 blank lines should terminate indented + // code block, but not fenced code block + if (emptyLines >= 2 && state.parentType === 'list') { + break; + } + + nextLine++; + continue; + } + + emptyLines = 0; + + if (state.sCount[nextLine] - state.blkIndent >= 4) { + nextLine++; + last = nextLine; + continue; + } + break; + } + + state.line = last; + + token = state.push('code_block', 'code', 0); + token.content = state.getLines(startLine, last, 4 + state.blkIndent, true); + token.map = [ startLine, state.line ]; + + return true; +}; + +},{}],48:[function(require,module,exports){ +// fences (``` lang, ~~~ lang) + +'use strict'; + + +module.exports = function fence(state, startLine, endLine, silent) { + var marker, len, params, nextLine, mem, token, markup, + haveEndMarker = false, + pos = state.bMarks[startLine] + state.tShift[startLine], + max = state.eMarks[startLine]; + + if (pos + 3 > max) { return false; } + + marker = state.src.charCodeAt(pos); + + if (marker !== 0x7E/* ~ */ && marker !== 0x60 /* ` */) { + return false; + } + + // scan marker length + mem = pos; + pos = state.skipChars(pos, marker); + + len = pos - mem; + + if (len < 3) { return false; } + + markup = state.src.slice(mem, pos); + params = state.src.slice(pos, max); + + if (params.indexOf('`') >= 0) { return false; } + + // Since start is found, we can report success here in validation mode + if (silent) { return true; } + + // search end of block + nextLine = startLine; + + for (;;) { + nextLine++; + if (nextLine >= endLine) { + // unclosed block should be autoclosed by end of document. + // also block seems to be autoclosed by end of parent + break; + } + + pos = mem = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + + if (pos < max && state.sCount[nextLine] < state.blkIndent) { + // non-empty line with negative indent should stop the list: + // - ``` + // test + break; + } + + if (state.src.charCodeAt(pos) !== marker) { continue; } + + if (state.sCount[nextLine] - state.blkIndent >= 4) { + // closing fence should be indented less than 4 spaces + continue; + } + + pos = state.skipChars(pos, marker); + + // closing code fence must be at least as long as the opening one + if (pos - mem < len) { continue; } + + // make sure tail has spaces only + pos = state.skipSpaces(pos); + + if (pos < max) { continue; } + + haveEndMarker = true; + // found! + break; + } + + // If a fence has heading spaces, they should be removed from its inner block + len = state.sCount[startLine]; + + state.line = nextLine + (haveEndMarker ? 1 : 0); + + token = state.push('fence', 'code', 0); + token.info = params; + token.content = state.getLines(startLine + 1, nextLine, len, true); + token.markup = markup; + token.map = [ startLine, state.line ]; + + return true; +}; + +},{}],49:[function(require,module,exports){ +// heading (#, ##, ...) + +'use strict'; + +var isSpace = require('../common/utils').isSpace; + + +module.exports = function heading(state, startLine, endLine, silent) { + var ch, level, tmp, token, + pos = state.bMarks[startLine] + state.tShift[startLine], + max = state.eMarks[startLine]; + + ch = state.src.charCodeAt(pos); + + if (ch !== 0x23/* # */ || pos >= max) { return false; } + + // count heading level + level = 1; + ch = state.src.charCodeAt(++pos); + while (ch === 0x23/* # */ && pos < max && level <= 6) { + level++; + ch = state.src.charCodeAt(++pos); + } + + if (level > 6 || (pos < max && ch !== 0x20/* space */)) { return false; } + + if (silent) { return true; } + + // Let's cut tails like ' ### ' from the end of string + + max = state.skipSpacesBack(max, pos); + tmp = state.skipCharsBack(max, 0x23, pos); // # + if (tmp > pos && isSpace(state.src.charCodeAt(tmp - 1))) { + max = tmp; + } + + state.line = startLine + 1; + + token = state.push('heading_open', 'h' + String(level), 1); + token.markup = '########'.slice(0, level); + token.map = [ startLine, state.line ]; + + token = state.push('inline', '', 0); + token.content = state.src.slice(pos, max).trim(); + token.map = [ startLine, state.line ]; + token.children = []; + + token = state.push('heading_close', 'h' + String(level), -1); + token.markup = '########'.slice(0, level); + + return true; +}; + +},{"../common/utils":32}],50:[function(require,module,exports){ +// Horizontal rule + +'use strict'; + +var isSpace = require('../common/utils').isSpace; + + +module.exports = function hr(state, startLine, endLine, silent) { + var marker, cnt, ch, token, + pos = state.bMarks[startLine] + state.tShift[startLine], + max = state.eMarks[startLine]; + + marker = state.src.charCodeAt(pos++); + + // Check hr marker + if (marker !== 0x2A/* * */ && + marker !== 0x2D/* - */ && + marker !== 0x5F/* _ */) { + return false; + } + + // markers can be mixed with spaces, but there should be at least 3 of them + + cnt = 1; + while (pos < max) { + ch = state.src.charCodeAt(pos++); + if (ch !== marker && !isSpace(ch)) { return false; } + if (ch === marker) { cnt++; } + } + + if (cnt < 3) { return false; } + + if (silent) { return true; } + + state.line = startLine + 1; + + token = state.push('hr', 'hr', 0); + token.map = [ startLine, state.line ]; + token.markup = Array(cnt + 1).join(String.fromCharCode(marker)); + + return true; +}; + +},{"../common/utils":32}],51:[function(require,module,exports){ +// HTML block + +'use strict'; + + +var block_names = require('../common/html_blocks'); +var HTML_OPEN_CLOSE_TAG_RE = require('../common/html_re').HTML_OPEN_CLOSE_TAG_RE; + +// An array of opening and corresponding closing sequences for html tags, +// last argument defines whether it can terminate a paragraph or not +// +var HTML_SEQUENCES = [ + [ /^<(script|pre|style)(?=(\s|>|$))/i, /<\/(script|pre|style)>/i, true ], + [ /^/, true ], + [ /^<\?/, /\?>/, true ], + [ /^/, true ], + [ /^/, true ], + [ new RegExp('^|$))', 'i'), /^$/, true ], + [ new RegExp(HTML_OPEN_CLOSE_TAG_RE.source + '\\s*$'), /^$/, false ] +]; + + +module.exports = function html_block(state, startLine, endLine, silent) { + var i, nextLine, token, lineText, + pos = state.bMarks[startLine] + state.tShift[startLine], + max = state.eMarks[startLine]; + + if (!state.md.options.html) { return false; } + + if (state.src.charCodeAt(pos) !== 0x3C/* < */) { return false; } + + lineText = state.src.slice(pos, max); + + for (i = 0; i < HTML_SEQUENCES.length; i++) { + if (HTML_SEQUENCES[i][0].test(lineText)) { break; } + } + + if (i === HTML_SEQUENCES.length) { return false; } + + if (silent) { + // true if this sequence can be a terminator, false otherwise + return HTML_SEQUENCES[i][2]; + } + + nextLine = startLine + 1; + + // If we are here - we detected HTML block. + // Let's roll down till block end. + if (!HTML_SEQUENCES[i][1].test(lineText)) { + for (; nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < state.blkIndent) { break; } + + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + lineText = state.src.slice(pos, max); + + if (HTML_SEQUENCES[i][1].test(lineText)) { + if (lineText.length !== 0) { nextLine++; } + break; + } + } + } + + state.line = nextLine; + + token = state.push('html_block', '', 0); + token.map = [ startLine, nextLine ]; + token.content = state.getLines(startLine, nextLine, state.blkIndent, true); + + return true; +}; + +},{"../common/html_blocks":30,"../common/html_re":31}],52:[function(require,module,exports){ +// lheading (---, ===) + +'use strict'; + + +module.exports = function lheading(state, startLine, endLine/*, silent*/) { + var content, terminate, i, l, token, pos, max, level, marker, + nextLine = startLine + 1, + terminatorRules = state.md.block.ruler.getRules('paragraph'); + + // jump line-by-line until empty one or EOF + for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { continue; } + + // + // Check for underline in setext header + // + if (state.sCount[nextLine] >= state.blkIndent) { + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + max = state.eMarks[nextLine]; + + if (pos < max) { + marker = state.src.charCodeAt(pos); + + if (marker === 0x2D/* - */ || marker === 0x3D/* = */) { + pos = state.skipChars(pos, marker); + pos = state.skipSpaces(pos); + + if (pos >= max) { + level = (marker === 0x3D/* = */ ? 1 : 2); + break; + } + } + } + } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { continue; } + + // Some tags can terminate paragraph without empty line. + terminate = false; + for (i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { break; } + } + + if (!level) { + // Didn't find valid underline + return false; + } + + content = state.getLines(startLine, nextLine, state.blkIndent, false).trim(); + + state.line = nextLine + 1; + + token = state.push('heading_open', 'h' + String(level), 1); + token.markup = String.fromCharCode(marker); + token.map = [ startLine, state.line ]; + + token = state.push('inline', '', 0); + token.content = content; + token.map = [ startLine, state.line - 1 ]; + token.children = []; + + token = state.push('heading_close', 'h' + String(level), -1); + token.markup = String.fromCharCode(marker); + + return true; +}; + +},{}],53:[function(require,module,exports){ +// Lists + +'use strict'; + +var isSpace = require('../common/utils').isSpace; + + +// Search `[-+*][\n ]`, returns next pos arter marker on success +// or -1 on fail. +function skipBulletListMarker(state, startLine) { + var marker, pos, max, ch; + + pos = state.bMarks[startLine] + state.tShift[startLine]; + max = state.eMarks[startLine]; + + marker = state.src.charCodeAt(pos++); + // Check bullet + if (marker !== 0x2A/* * */ && + marker !== 0x2D/* - */ && + marker !== 0x2B/* + */) { + return -1; + } + + if (pos < max) { + ch = state.src.charCodeAt(pos); + + if (!isSpace(ch)) { + // " -test " - is not a list item + return -1; + } + } + + return pos; +} + +// Search `\d+[.)][\n ]`, returns next pos arter marker on success +// or -1 on fail. +function skipOrderedListMarker(state, startLine) { + var ch, + start = state.bMarks[startLine] + state.tShift[startLine], + pos = start, + max = state.eMarks[startLine]; + + // List marker should have at least 2 chars (digit + dot) + if (pos + 1 >= max) { return -1; } + + ch = state.src.charCodeAt(pos++); + + if (ch < 0x30/* 0 */ || ch > 0x39/* 9 */) { return -1; } + + for (;;) { + // EOL -> fail + if (pos >= max) { return -1; } + + ch = state.src.charCodeAt(pos++); + + if (ch >= 0x30/* 0 */ && ch <= 0x39/* 9 */) { + + // List marker should have no more than 9 digits + // (prevents integer overflow in browsers) + if (pos - start >= 10) { return -1; } + + continue; + } + + // found valid marker + if (ch === 0x29/* ) */ || ch === 0x2e/* . */) { + break; + } + + return -1; + } + + + if (pos < max) { + ch = state.src.charCodeAt(pos); + + if (!isSpace(ch)) { + // " 1.test " - is not a list item + return -1; + } + } + return pos; +} + +function markTightParagraphs(state, idx) { + var i, l, + level = state.level + 2; + + for (i = idx + 2, l = state.tokens.length - 2; i < l; i++) { + if (state.tokens[i].level === level && state.tokens[i].type === 'paragraph_open') { + state.tokens[i + 2].hidden = true; + state.tokens[i].hidden = true; + i += 2; + } + } +} + + +module.exports = function list(state, startLine, endLine, silent) { + var nextLine, + initial, + offset, + indent, + oldTShift, + oldIndent, + oldLIndent, + oldTight, + oldParentType, + start, + posAfterMarker, + ch, + pos, + max, + indentAfterMarker, + markerValue, + markerCharCode, + isOrdered, + contentStart, + listTokIdx, + prevEmptyEnd, + listLines, + itemLines, + tight = true, + terminatorRules, + token, + i, l, terminate; + + // Detect list type and position after marker + if ((posAfterMarker = skipOrderedListMarker(state, startLine)) >= 0) { + isOrdered = true; + } else if ((posAfterMarker = skipBulletListMarker(state, startLine)) >= 0) { + isOrdered = false; + } else { + return false; + } + + // We should terminate list on style change. Remember first one to compare. + markerCharCode = state.src.charCodeAt(posAfterMarker - 1); + + // For validation mode we can terminate immediately + if (silent) { return true; } + + // Start list + listTokIdx = state.tokens.length; + + if (isOrdered) { + start = state.bMarks[startLine] + state.tShift[startLine]; + markerValue = Number(state.src.substr(start, posAfterMarker - start - 1)); + + token = state.push('ordered_list_open', 'ol', 1); + if (markerValue !== 1) { + token.attrs = [ [ 'start', markerValue ] ]; + } + + } else { + token = state.push('bullet_list_open', 'ul', 1); + } + + token.map = listLines = [ startLine, 0 ]; + token.markup = String.fromCharCode(markerCharCode); + + // + // Iterate list items + // + + nextLine = startLine; + prevEmptyEnd = false; + terminatorRules = state.md.block.ruler.getRules('list'); + + while (nextLine < endLine) { + pos = posAfterMarker; + max = state.eMarks[nextLine]; + + initial = offset = state.sCount[nextLine] + posAfterMarker - (state.bMarks[startLine] + state.tShift[startLine]); + + while (pos < max) { + ch = state.src.charCodeAt(pos); + + if (isSpace(ch)) { + if (ch === 0x09) { + offset += 4 - offset % 4; + } else { + offset++; + } + } else { + break; + } + + pos++; + } + + contentStart = pos; + + if (contentStart >= max) { + // trimming space in "- \n 3" case, indent is 1 here + indentAfterMarker = 1; + } else { + indentAfterMarker = offset - initial; + } + + // If we have more than 4 spaces, the indent is 1 + // (the rest is just indented code block) + if (indentAfterMarker > 4) { indentAfterMarker = 1; } + + // " - test" + // ^^^^^ - calculating total length of this thing + indent = initial + indentAfterMarker; + + // Run subparser & write tokens + token = state.push('list_item_open', 'li', 1); + token.markup = String.fromCharCode(markerCharCode); + token.map = itemLines = [ startLine, 0 ]; + + oldIndent = state.blkIndent; + oldTight = state.tight; + oldTShift = state.tShift[startLine]; + oldLIndent = state.sCount[startLine]; + oldParentType = state.parentType; + state.blkIndent = indent; + state.tight = true; + state.parentType = 'list'; + state.tShift[startLine] = contentStart - state.bMarks[startLine]; + state.sCount[startLine] = offset; + + if (contentStart >= max && state.isEmpty(startLine + 1)) { + // workaround for this case + // (list item is empty, list terminates before "foo"): + // ~~~~~~~~ + // - + // + // foo + // ~~~~~~~~ + state.line = Math.min(state.line + 2, endLine); + } else { + state.md.block.tokenize(state, startLine, endLine, true); + } + + // If any of list item is tight, mark list as tight + if (!state.tight || prevEmptyEnd) { + tight = false; + } + // Item become loose if finish with empty line, + // but we should filter last element, because it means list finish + prevEmptyEnd = (state.line - startLine) > 1 && state.isEmpty(state.line - 1); + + state.blkIndent = oldIndent; + state.tShift[startLine] = oldTShift; + state.sCount[startLine] = oldLIndent; + state.tight = oldTight; + state.parentType = oldParentType; + + token = state.push('list_item_close', 'li', -1); + token.markup = String.fromCharCode(markerCharCode); + + nextLine = startLine = state.line; + itemLines[1] = nextLine; + contentStart = state.bMarks[startLine]; + + if (nextLine >= endLine) { break; } + + if (state.isEmpty(nextLine)) { + break; + } + + // + // Try to check if list is terminated or continued. + // + if (state.sCount[nextLine] < state.blkIndent) { break; } + + // fail if terminating block found + terminate = false; + for (i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { break; } + + // fail if list has another type + if (isOrdered) { + posAfterMarker = skipOrderedListMarker(state, nextLine); + if (posAfterMarker < 0) { break; } + } else { + posAfterMarker = skipBulletListMarker(state, nextLine); + if (posAfterMarker < 0) { break; } + } + + if (markerCharCode !== state.src.charCodeAt(posAfterMarker - 1)) { break; } + } + + // Finilize list + if (isOrdered) { + token = state.push('ordered_list_close', 'ol', -1); + } else { + token = state.push('bullet_list_close', 'ul', -1); + } + token.markup = String.fromCharCode(markerCharCode); + + listLines[1] = nextLine; + state.line = nextLine; + + // mark paragraphs tight if needed + if (tight) { + markTightParagraphs(state, listTokIdx); + } + + return true; +}; + +},{"../common/utils":32}],54:[function(require,module,exports){ +// Paragraph + +'use strict'; + + +module.exports = function paragraph(state, startLine/*, endLine*/) { + var content, terminate, i, l, token, + nextLine = startLine + 1, + terminatorRules = state.md.block.ruler.getRules('paragraph'), + endLine = state.lineMax; + + // jump line-by-line until empty one or EOF + for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { continue; } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { continue; } + + // Some tags can terminate paragraph without empty line. + terminate = false; + for (i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { break; } + } + + content = state.getLines(startLine, nextLine, state.blkIndent, false).trim(); + + state.line = nextLine; + + token = state.push('paragraph_open', 'p', 1); + token.map = [ startLine, state.line ]; + + token = state.push('inline', '', 0); + token.content = content; + token.map = [ startLine, state.line ]; + token.children = []; + + token = state.push('paragraph_close', 'p', -1); + + return true; +}; + +},{}],55:[function(require,module,exports){ +'use strict'; + + +var parseLinkDestination = require('../helpers/parse_link_destination'); +var parseLinkTitle = require('../helpers/parse_link_title'); +var normalizeReference = require('../common/utils').normalizeReference; +var isSpace = require('../common/utils').isSpace; + + +module.exports = function reference(state, startLine, _endLine, silent) { + var ch, + destEndPos, + destEndLineNo, + endLine, + href, + i, + l, + label, + labelEnd, + res, + start, + str, + terminate, + terminatorRules, + title, + lines = 0, + pos = state.bMarks[startLine] + state.tShift[startLine], + max = state.eMarks[startLine], + nextLine = startLine + 1; + + if (state.src.charCodeAt(pos) !== 0x5B/* [ */) { return false; } + + // Simple check to quickly interrupt scan on [link](url) at the start of line. + // Can be useful on practice: https://github.com/markdown-it/markdown-it/issues/54 + while (++pos < max) { + if (state.src.charCodeAt(pos) === 0x5D /* ] */ && + state.src.charCodeAt(pos - 1) !== 0x5C/* \ */) { + if (pos + 1 === max) { return false; } + if (state.src.charCodeAt(pos + 1) !== 0x3A/* : */) { return false; } + break; + } + } + + endLine = state.lineMax; + + // jump line-by-line until empty one or EOF + terminatorRules = state.md.block.ruler.getRules('reference'); + + for (; nextLine < endLine && !state.isEmpty(nextLine); nextLine++) { + // this would be a code block normally, but after paragraph + // it's considered a lazy continuation regardless of what's there + if (state.sCount[nextLine] - state.blkIndent > 3) { continue; } + + // quirk for blockquotes, this line should already be checked by that rule + if (state.sCount[nextLine] < 0) { continue; } + + // Some tags can terminate paragraph without empty line. + terminate = false; + for (i = 0, l = terminatorRules.length; i < l; i++) { + if (terminatorRules[i](state, nextLine, endLine, true)) { + terminate = true; + break; + } + } + if (terminate) { break; } + } + + str = state.getLines(startLine, nextLine, state.blkIndent, false).trim(); + max = str.length; + + for (pos = 1; pos < max; pos++) { + ch = str.charCodeAt(pos); + if (ch === 0x5B /* [ */) { + return false; + } else if (ch === 0x5D /* ] */) { + labelEnd = pos; + break; + } else if (ch === 0x0A /* \n */) { + lines++; + } else if (ch === 0x5C /* \ */) { + pos++; + if (pos < max && str.charCodeAt(pos) === 0x0A) { + lines++; + } + } + } + + if (labelEnd < 0 || str.charCodeAt(labelEnd + 1) !== 0x3A/* : */) { return false; } + + // [label]: destination 'title' + // ^^^ skip optional whitespace here + for (pos = labelEnd + 2; pos < max; pos++) { + ch = str.charCodeAt(pos); + if (ch === 0x0A) { + lines++; + } else if (isSpace(ch)) { + /*eslint no-empty:0*/ + } else { + break; + } + } + + // [label]: destination 'title' + // ^^^^^^^^^^^ parse this + res = parseLinkDestination(str, pos, max); + if (!res.ok) { return false; } + + href = state.md.normalizeLink(res.str); + if (!state.md.validateLink(href)) { return false; } + + pos = res.pos; + lines += res.lines; + + // save cursor state, we could require to rollback later + destEndPos = pos; + destEndLineNo = lines; + + // [label]: destination 'title' + // ^^^ skipping those spaces + start = pos; + for (; pos < max; pos++) { + ch = str.charCodeAt(pos); + if (ch === 0x0A) { + lines++; + } else if (isSpace(ch)) { + /*eslint no-empty:0*/ + } else { + break; + } + } + + // [label]: destination 'title' + // ^^^^^^^ parse this + res = parseLinkTitle(str, pos, max); + if (pos < max && start !== pos && res.ok) { + title = res.str; + pos = res.pos; + lines += res.lines; + } else { + title = ''; + pos = destEndPos; + lines = destEndLineNo; + } + + // skip trailing spaces until the rest of the line + while (pos < max) { + ch = str.charCodeAt(pos); + if (!isSpace(ch)) { break; } + pos++; + } + + if (pos < max && str.charCodeAt(pos) !== 0x0A) { + if (title) { + // garbage at the end of the line after title, + // but it could still be a valid reference if we roll back + title = ''; + pos = destEndPos; + lines = destEndLineNo; + while (pos < max) { + ch = str.charCodeAt(pos); + if (!isSpace(ch)) { break; } + pos++; + } + } + } + + if (pos < max && str.charCodeAt(pos) !== 0x0A) { + // garbage at the end of the line + return false; + } + + label = normalizeReference(str.slice(1, labelEnd)); + if (!label) { + // CommonMark 0.20 disallows empty labels + return false; + } + + // Reference can not terminate anything. This check is for safety only. + /*istanbul ignore if*/ + if (silent) { return true; } + + if (typeof state.env.references === 'undefined') { + state.env.references = {}; + } + if (typeof state.env.references[label] === 'undefined') { + state.env.references[label] = { title: title, href: href }; + } + + state.line = startLine + lines + 1; + return true; +}; + +},{"../common/utils":32,"../helpers/parse_link_destination":34,"../helpers/parse_link_title":36}],56:[function(require,module,exports){ +// Parser state class + +'use strict'; + +var Token = require('../token'); +var isSpace = require('../common/utils').isSpace; + + +function StateBlock(src, md, env, tokens) { + var ch, s, start, pos, len, indent, offset, indent_found; + + this.src = src; + + // link to parser instance + this.md = md; + + this.env = env; + + // + // Internal state vartiables + // + + this.tokens = tokens; + + this.bMarks = []; // line begin offsets for fast jumps + this.eMarks = []; // line end offsets for fast jumps + this.tShift = []; // offsets of the first non-space characters (tabs not expanded) + this.sCount = []; // indents for each line (tabs expanded) + + // block parser variables + this.blkIndent = 0; // required block content indent + // (for example, if we are in list) + this.line = 0; // line index in src + this.lineMax = 0; // lines count + this.tight = false; // loose/tight mode for lists + this.parentType = 'root'; // if `list`, block parser stops on two newlines + this.ddIndent = -1; // indent of the current dd block (-1 if there isn't any) + + this.level = 0; + + // renderer + this.result = ''; + + // Create caches + // Generate markers. + s = this.src; + indent_found = false; + + for (start = pos = indent = offset = 0, len = s.length; pos < len; pos++) { + ch = s.charCodeAt(pos); + + if (!indent_found) { + if (isSpace(ch)) { + indent++; + + if (ch === 0x09) { + offset += 4 - offset % 4; + } else { + offset++; + } + continue; + } else { + indent_found = true; + } + } + + if (ch === 0x0A || pos === len - 1) { + if (ch !== 0x0A) { pos++; } + this.bMarks.push(start); + this.eMarks.push(pos); + this.tShift.push(indent); + this.sCount.push(offset); + + indent_found = false; + indent = 0; + offset = 0; + start = pos + 1; + } + } + + // Push fake entry to simplify cache bounds checks + this.bMarks.push(s.length); + this.eMarks.push(s.length); + this.tShift.push(0); + this.sCount.push(0); + + this.lineMax = this.bMarks.length - 1; // don't count last fake line +} + +// Push new token to "stream". +// +StateBlock.prototype.push = function (type, tag, nesting) { + var token = new Token(type, tag, nesting); + token.block = true; + + if (nesting < 0) { this.level--; } + token.level = this.level; + if (nesting > 0) { this.level++; } + + this.tokens.push(token); + return token; +}; + +StateBlock.prototype.isEmpty = function isEmpty(line) { + return this.bMarks[line] + this.tShift[line] >= this.eMarks[line]; +}; + +StateBlock.prototype.skipEmptyLines = function skipEmptyLines(from) { + for (var max = this.lineMax; from < max; from++) { + if (this.bMarks[from] + this.tShift[from] < this.eMarks[from]) { + break; + } + } + return from; +}; + +// Skip spaces from given position. +StateBlock.prototype.skipSpaces = function skipSpaces(pos) { + var ch; + + for (var max = this.src.length; pos < max; pos++) { + ch = this.src.charCodeAt(pos); + if (!isSpace(ch)) { break; } + } + return pos; +}; + +// Skip spaces from given position in reverse. +StateBlock.prototype.skipSpacesBack = function skipSpacesBack(pos, min) { + if (pos <= min) { return pos; } + + while (pos > min) { + if (!isSpace(this.src.charCodeAt(--pos))) { return pos + 1; } + } + return pos; +}; + +// Skip char codes from given position +StateBlock.prototype.skipChars = function skipChars(pos, code) { + for (var max = this.src.length; pos < max; pos++) { + if (this.src.charCodeAt(pos) !== code) { break; } + } + return pos; +}; + +// Skip char codes reverse from given position - 1 +StateBlock.prototype.skipCharsBack = function skipCharsBack(pos, code, min) { + if (pos <= min) { return pos; } + + while (pos > min) { + if (code !== this.src.charCodeAt(--pos)) { return pos + 1; } + } + return pos; +}; + +// cut lines range from source. +StateBlock.prototype.getLines = function getLines(begin, end, indent, keepLastLF) { + var i, lineIndent, ch, first, last, queue, lineStart, + line = begin; + + if (begin >= end) { + return ''; + } + + queue = new Array(end - begin); + + for (i = 0; line < end; line++, i++) { + lineIndent = 0; + lineStart = first = this.bMarks[line]; + + if (line + 1 < end || keepLastLF) { + // No need for bounds check because we have fake entry on tail. + last = this.eMarks[line] + 1; + } else { + last = this.eMarks[line]; + } + + while (first < last && lineIndent < indent) { + ch = this.src.charCodeAt(first); + + if (isSpace(ch)) { + if (ch === 0x09) { + lineIndent += 4 - lineIndent % 4; + } else { + lineIndent++; + } + } else if (first - lineStart < this.tShift[line]) { + // patched tShift masked characters to look like spaces (blockquotes, list markers) + lineIndent++; + } else { + break; + } + + first++; + } + + queue[i] = this.src.slice(first, last); + } + + return queue.join(''); +}; + +// re-export Token class to use in block rules +StateBlock.prototype.Token = Token; + + +module.exports = StateBlock; + +},{"../common/utils":32,"../token":79}],57:[function(require,module,exports){ +// GFM table, non-standard + +'use strict'; + + +function getLine(state, line) { + var pos = state.bMarks[line] + state.blkIndent, + max = state.eMarks[line]; + + return state.src.substr(pos, max - pos); +} + +function escapedSplit(str) { + var result = [], + pos = 0, + max = str.length, + ch, + escapes = 0, + lastPos = 0, + backTicked = false, + lastBackTick = 0; + + ch = str.charCodeAt(pos); + + while (pos < max) { + if (ch === 0x60/* ` */ && (escapes % 2 === 0)) { + backTicked = !backTicked; + lastBackTick = pos; + } else if (ch === 0x7c/* | */ && (escapes % 2 === 0) && !backTicked) { + result.push(str.substring(lastPos, pos)); + lastPos = pos + 1; + } else if (ch === 0x5c/* \ */) { + escapes++; + } else { + escapes = 0; + } + + pos++; + + // If there was an un-closed backtick, go back to just after + // the last backtick, but as if it was a normal character + if (pos === max && backTicked) { + backTicked = false; + pos = lastBackTick + 1; + } + + ch = str.charCodeAt(pos); + } + + result.push(str.substring(lastPos)); + + return result; +} + + +module.exports = function table(state, startLine, endLine, silent) { + var ch, lineText, pos, i, nextLine, columns, columnCount, token, + aligns, t, tableLines, tbodyLines; + + // should have at least three lines + if (startLine + 2 > endLine) { return false; } + + nextLine = startLine + 1; + + if (state.sCount[nextLine] < state.blkIndent) { return false; } + + // first character of the second line should be '|' or '-' + + pos = state.bMarks[nextLine] + state.tShift[nextLine]; + if (pos >= state.eMarks[nextLine]) { return false; } + + ch = state.src.charCodeAt(pos); + if (ch !== 0x7C/* | */ && ch !== 0x2D/* - */ && ch !== 0x3A/* : */) { return false; } + + lineText = getLine(state, startLine + 1); + if (!/^[-:| ]+$/.test(lineText)) { return false; } + + columns = lineText.split('|'); + aligns = []; + for (i = 0; i < columns.length; i++) { + t = columns[i].trim(); + if (!t) { + // allow empty columns before and after table, but not in between columns; + // e.g. allow ` |---| `, disallow ` ---||--- ` + if (i === 0 || i === columns.length - 1) { + continue; + } else { + return false; + } + } + + if (!/^:?-+:?$/.test(t)) { return false; } + if (t.charCodeAt(t.length - 1) === 0x3A/* : */) { + aligns.push(t.charCodeAt(0) === 0x3A/* : */ ? 'center' : 'right'); + } else if (t.charCodeAt(0) === 0x3A/* : */) { + aligns.push('left'); + } else { + aligns.push(''); + } + } + + lineText = getLine(state, startLine).trim(); + if (lineText.indexOf('|') === -1) { return false; } + columns = escapedSplit(lineText.replace(/^\||\|$/g, '')); + + // header row will define an amount of columns in the entire table, + // and align row shouldn't be smaller than that (the rest of the rows can) + columnCount = columns.length; + if (columnCount > aligns.length) { return false; } + + if (silent) { return true; } + + token = state.push('table_open', 'table', 1); + token.map = tableLines = [ startLine, 0 ]; + + token = state.push('thead_open', 'thead', 1); + token.map = [ startLine, startLine + 1 ]; + + token = state.push('tr_open', 'tr', 1); + token.map = [ startLine, startLine + 1 ]; + + for (i = 0; i < columns.length; i++) { + token = state.push('th_open', 'th', 1); + token.map = [ startLine, startLine + 1 ]; + if (aligns[i]) { + token.attrs = [ [ 'style', 'text-align:' + aligns[i] ] ]; + } + + token = state.push('inline', '', 0); + token.content = columns[i].trim(); + token.map = [ startLine, startLine + 1 ]; + token.children = []; + + token = state.push('th_close', 'th', -1); + } + + token = state.push('tr_close', 'tr', -1); + token = state.push('thead_close', 'thead', -1); + + token = state.push('tbody_open', 'tbody', 1); + token.map = tbodyLines = [ startLine + 2, 0 ]; + + for (nextLine = startLine + 2; nextLine < endLine; nextLine++) { + if (state.sCount[nextLine] < state.blkIndent) { break; } + + lineText = getLine(state, nextLine).trim(); + if (lineText.indexOf('|') === -1) { break; } + columns = escapedSplit(lineText.replace(/^\||\|$/g, '')); + + token = state.push('tr_open', 'tr', 1); + for (i = 0; i < columnCount; i++) { + token = state.push('td_open', 'td', 1); + if (aligns[i]) { + token.attrs = [ [ 'style', 'text-align:' + aligns[i] ] ]; + } + + token = state.push('inline', '', 0); + token.content = columns[i] ? columns[i].trim() : ''; + token.children = []; + + token = state.push('td_close', 'td', -1); + } + token = state.push('tr_close', 'tr', -1); + } + token = state.push('tbody_close', 'tbody', -1); + token = state.push('table_close', 'table', -1); + + tableLines[1] = tbodyLines[1] = nextLine; + state.line = nextLine; + return true; +}; + +},{}],58:[function(require,module,exports){ +'use strict'; + + +module.exports = function block(state) { + var token; + + if (state.inlineMode) { + token = new state.Token('inline', '', 0); + token.content = state.src; + token.map = [ 0, 1 ]; + token.children = []; + state.tokens.push(token); + } else { + state.md.block.parse(state.src, state.md, state.env, state.tokens); + } +}; + +},{}],59:[function(require,module,exports){ +'use strict'; + +module.exports = function inline(state) { + var tokens = state.tokens, tok, i, l; + + // Parse inlines + for (i = 0, l = tokens.length; i < l; i++) { + tok = tokens[i]; + if (tok.type === 'inline') { + state.md.inline.parse(tok.content, state.md, state.env, tok.children); + } + } +}; + +},{}],60:[function(require,module,exports){ +// Replace link-like texts with link nodes. +// +// Currently restricted by `md.validateLink()` to http/https/ftp +// +'use strict'; + + +var arrayReplaceAt = require('../common/utils').arrayReplaceAt; + + +function isLinkOpen(str) { + return /^\s]/i.test(str); +} +function isLinkClose(str) { + return /^<\/a\s*>/i.test(str); +} + + +module.exports = function linkify(state) { + var i, j, l, tokens, token, currentToken, nodes, ln, text, pos, lastPos, + level, htmlLinkLevel, url, fullUrl, urlText, + blockTokens = state.tokens, + links; + + if (!state.md.options.linkify) { return; } + + for (j = 0, l = blockTokens.length; j < l; j++) { + if (blockTokens[j].type !== 'inline' || + !state.md.linkify.pretest(blockTokens[j].content)) { + continue; + } + + tokens = blockTokens[j].children; + + htmlLinkLevel = 0; + + // We scan from the end, to keep position when new tags added. + // Use reversed logic in links start/end match + for (i = tokens.length - 1; i >= 0; i--) { + currentToken = tokens[i]; + + // Skip content of markdown links + if (currentToken.type === 'link_close') { + i--; + while (tokens[i].level !== currentToken.level && tokens[i].type !== 'link_open') { + i--; + } + continue; + } + + // Skip content of html tag links + if (currentToken.type === 'html_inline') { + if (isLinkOpen(currentToken.content) && htmlLinkLevel > 0) { + htmlLinkLevel--; + } + if (isLinkClose(currentToken.content)) { + htmlLinkLevel++; + } + } + if (htmlLinkLevel > 0) { continue; } + + if (currentToken.type === 'text' && state.md.linkify.test(currentToken.content)) { + + text = currentToken.content; + links = state.md.linkify.match(text); + + // Now split string to nodes + nodes = []; + level = currentToken.level; + lastPos = 0; + + for (ln = 0; ln < links.length; ln++) { + + url = links[ln].url; + fullUrl = state.md.normalizeLink(url); + if (!state.md.validateLink(fullUrl)) { continue; } + + urlText = links[ln].text; + + // Linkifier might send raw hostnames like "example.com", where url + // starts with domain name. So we prepend http:// in those cases, + // and remove it afterwards. + // + if (!links[ln].schema) { + urlText = state.md.normalizeLinkText('http://' + urlText).replace(/^http:\/\//, ''); + } else if (links[ln].schema === 'mailto:' && !/^mailto:/i.test(urlText)) { + urlText = state.md.normalizeLinkText('mailto:' + urlText).replace(/^mailto:/, ''); + } else { + urlText = state.md.normalizeLinkText(urlText); + } + + pos = links[ln].index; + + if (pos > lastPos) { + token = new state.Token('text', '', 0); + token.content = text.slice(lastPos, pos); + token.level = level; + nodes.push(token); + } + + token = new state.Token('link_open', 'a', 1); + token.attrs = [ [ 'href', fullUrl ] ]; + token.level = level++; + token.markup = 'linkify'; + token.info = 'auto'; + nodes.push(token); + + token = new state.Token('text', '', 0); + token.content = urlText; + token.level = level; + nodes.push(token); + + token = new state.Token('link_close', 'a', -1); + token.level = --level; + token.markup = 'linkify'; + token.info = 'auto'; + nodes.push(token); + + lastPos = links[ln].lastIndex; + } + if (lastPos < text.length) { + token = new state.Token('text', '', 0); + token.content = text.slice(lastPos); + token.level = level; + nodes.push(token); + } + + // replace current node + blockTokens[j].children = tokens = arrayReplaceAt(tokens, i, nodes); + } + } + } +}; + +},{"../common/utils":32}],61:[function(require,module,exports){ +// Normalize input string + +'use strict'; + + +var NEWLINES_RE = /\r[\n\u0085]|[\u2424\u2028\u0085]/g; +var NULL_RE = /\u0000/g; + + +module.exports = function inline(state) { + var str; + + // Normalize newlines + str = state.src.replace(NEWLINES_RE, '\n'); + + // Replace NULL characters + str = str.replace(NULL_RE, '\uFFFD'); + + state.src = str; +}; + +},{}],62:[function(require,module,exports){ +// Simple typographyc replacements +// +// (c) (C) → © +// (tm) (TM) → ™ +// (r) (R) → ® +// +- → ± +// (p) (P) -> § +// ... → … (also ?.... → ?.., !.... → !..) +// ???????? → ???, !!!!! → !!!, `,,` → `,` +// -- → –, --- → — +// +'use strict'; + +// TODO: +// - fractionals 1/2, 1/4, 3/4 -> ½, ¼, ¾ +// - miltiplication 2 x 4 -> 2 × 4 + +var RARE_RE = /\+-|\.\.|\?\?\?\?|!!!!|,,|--/; + +// Workaround for phantomjs - need regex without /g flag, +// or root check will fail every second time +var SCOPED_ABBR_TEST_RE = /\((c|tm|r|p)\)/i; + +var SCOPED_ABBR_RE = /\((c|tm|r|p)\)/ig; +var SCOPED_ABBR = { + 'c': '©', + 'r': '®', + 'p': '§', + 'tm': '™' +}; + +function replaceFn(match, name) { + return SCOPED_ABBR[name.toLowerCase()]; +} + +function replace_scoped(inlineTokens) { + var i, token; + + for (i = inlineTokens.length - 1; i >= 0; i--) { + token = inlineTokens[i]; + if (token.type === 'text') { + token.content = token.content.replace(SCOPED_ABBR_RE, replaceFn); + } + } +} + +function replace_rare(inlineTokens) { + var i, token; + + for (i = inlineTokens.length - 1; i >= 0; i--) { + token = inlineTokens[i]; + if (token.type === 'text') { + if (RARE_RE.test(token.content)) { + token.content = token.content + .replace(/\+-/g, '±') + // .., ..., ....... -> … + // but ?..... & !..... -> ?.. & !.. + .replace(/\.{2,}/g, '…').replace(/([?!])…/g, '$1..') + .replace(/([?!]){4,}/g, '$1$1$1').replace(/,{2,}/g, ',') + // em-dash + .replace(/(^|[^-])---([^-]|$)/mg, '$1\u2014$2') + // en-dash + .replace(/(^|\s)--(\s|$)/mg, '$1\u2013$2') + .replace(/(^|[^-\s])--([^-\s]|$)/mg, '$1\u2013$2'); + } + } + } +} + + +module.exports = function replace(state) { + var blkIdx; + + if (!state.md.options.typographer) { return; } + + for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) { + + if (state.tokens[blkIdx].type !== 'inline') { continue; } + + if (SCOPED_ABBR_TEST_RE.test(state.tokens[blkIdx].content)) { + replace_scoped(state.tokens[blkIdx].children); + } + + if (RARE_RE.test(state.tokens[blkIdx].content)) { + replace_rare(state.tokens[blkIdx].children); + } + + } +}; + +},{}],63:[function(require,module,exports){ +// Convert straight quotation marks to typographic ones +// +'use strict'; + + +var isWhiteSpace = require('../common/utils').isWhiteSpace; +var isPunctChar = require('../common/utils').isPunctChar; +var isMdAsciiPunct = require('../common/utils').isMdAsciiPunct; + +var QUOTE_TEST_RE = /['"]/; +var QUOTE_RE = /['"]/g; +var APOSTROPHE = '\u2019'; /* ’ */ + + +function replaceAt(str, index, ch) { + return str.substr(0, index) + ch + str.substr(index + 1); +} + +function process_inlines(tokens, state) { + var i, token, text, t, pos, max, thisLevel, item, lastChar, nextChar, + isLastPunctChar, isNextPunctChar, isLastWhiteSpace, isNextWhiteSpace, + canOpen, canClose, j, isSingle, stack, openQuote, closeQuote; + + stack = []; + + for (i = 0; i < tokens.length; i++) { + token = tokens[i]; + + thisLevel = tokens[i].level; + + for (j = stack.length - 1; j >= 0; j--) { + if (stack[j].level <= thisLevel) { break; } + } + stack.length = j + 1; + + if (token.type !== 'text') { continue; } + + text = token.content; + pos = 0; + max = text.length; + + /*eslint no-labels:0,block-scoped-var:0*/ + OUTER: + while (pos < max) { + QUOTE_RE.lastIndex = pos; + t = QUOTE_RE.exec(text); + if (!t) { break; } + + canOpen = canClose = true; + pos = t.index + 1; + isSingle = (t[0] === "'"); + + // Find previous character, + // default to space if it's the beginning of the line + // + lastChar = 0x20; + + if (t.index - 1 >= 0) { + lastChar = text.charCodeAt(t.index - 1); + } else { + for (j = i - 1; j >= 0; j--) { + if (tokens[j].type !== 'text') { continue; } + + lastChar = tokens[j].content.charCodeAt(tokens[j].content.length - 1); + break; + } + } + + // Find next character, + // default to space if it's the end of the line + // + nextChar = 0x20; + + if (pos < max) { + nextChar = text.charCodeAt(pos); + } else { + for (j = i + 1; j < tokens.length; j++) { + if (tokens[j].type !== 'text') { continue; } + + nextChar = tokens[j].content.charCodeAt(0); + break; + } + } + + isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)); + isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)); + + isLastWhiteSpace = isWhiteSpace(lastChar); + isNextWhiteSpace = isWhiteSpace(nextChar); + + if (isNextWhiteSpace) { + canOpen = false; + } else if (isNextPunctChar) { + if (!(isLastWhiteSpace || isLastPunctChar)) { + canOpen = false; + } + } + + if (isLastWhiteSpace) { + canClose = false; + } else if (isLastPunctChar) { + if (!(isNextWhiteSpace || isNextPunctChar)) { + canClose = false; + } + } + + if (nextChar === 0x22 /* " */ && t[0] === '"') { + if (lastChar >= 0x30 /* 0 */ && lastChar <= 0x39 /* 9 */) { + // special case: 1"" - count first quote as an inch + canClose = canOpen = false; + } + } + + if (canOpen && canClose) { + // treat this as the middle of the word + canOpen = false; + canClose = isNextPunctChar; + } + + if (!canOpen && !canClose) { + // middle of word + if (isSingle) { + token.content = replaceAt(token.content, t.index, APOSTROPHE); + } + continue; + } + + if (canClose) { + // this could be a closing quote, rewind the stack to get a match + for (j = stack.length - 1; j >= 0; j--) { + item = stack[j]; + if (stack[j].level < thisLevel) { break; } + if (item.single === isSingle && stack[j].level === thisLevel) { + item = stack[j]; + + if (isSingle) { + openQuote = state.md.options.quotes[2]; + closeQuote = state.md.options.quotes[3]; + } else { + openQuote = state.md.options.quotes[0]; + closeQuote = state.md.options.quotes[1]; + } + + // replace token.content *before* tokens[item.token].content, + // because, if they are pointing at the same token, replaceAt + // could mess up indices when quote length != 1 + token.content = replaceAt(token.content, t.index, closeQuote); + tokens[item.token].content = replaceAt( + tokens[item.token].content, item.pos, openQuote); + + pos += closeQuote.length - 1; + if (item.token === i) { pos += openQuote.length - 1; } + + text = token.content; + max = text.length; + + stack.length = j; + continue OUTER; + } + } + } + + if (canOpen) { + stack.push({ + token: i, + pos: t.index, + single: isSingle, + level: thisLevel + }); + } else if (canClose && isSingle) { + token.content = replaceAt(token.content, t.index, APOSTROPHE); + } + } + } +} + + +module.exports = function smartquotes(state) { + /*eslint max-depth:0*/ + var blkIdx; + + if (!state.md.options.typographer) { return; } + + for (blkIdx = state.tokens.length - 1; blkIdx >= 0; blkIdx--) { + + if (state.tokens[blkIdx].type !== 'inline' || + !QUOTE_TEST_RE.test(state.tokens[blkIdx].content)) { + continue; + } + + process_inlines(state.tokens[blkIdx].children, state); + } +}; + +},{"../common/utils":32}],64:[function(require,module,exports){ +// Core state object +// +'use strict'; + +var Token = require('../token'); + + +function StateCore(src, md, env) { + this.src = src; + this.env = env; + this.tokens = []; + this.inlineMode = false; + this.md = md; // link to parser instance +} + +// re-export Token class to use in core rules +StateCore.prototype.Token = Token; + + +module.exports = StateCore; + +},{"../token":79}],65:[function(require,module,exports){ +// Process autolinks '' + +'use strict'; + + +/*eslint max-len:0*/ +var EMAIL_RE = /^<([a-zA-Z0-9.!#$%&'*+\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*)>/; +var AUTOLINK_RE = /^<([a-zA-Z][a-zA-Z0-9+.\-]{1,31}):([^<>\x00-\x20]*)>/; + + +module.exports = function autolink(state, silent) { + var tail, linkMatch, emailMatch, url, fullUrl, token, + pos = state.pos; + + if (state.src.charCodeAt(pos) !== 0x3C/* < */) { return false; } + + tail = state.src.slice(pos); + + if (tail.indexOf('>') < 0) { return false; } + + if (AUTOLINK_RE.test(tail)) { + linkMatch = tail.match(AUTOLINK_RE); + + url = linkMatch[0].slice(1, -1); + fullUrl = state.md.normalizeLink(url); + if (!state.md.validateLink(fullUrl)) { return false; } + + if (!silent) { + token = state.push('link_open', 'a', 1); + token.attrs = [ [ 'href', fullUrl ] ]; + token.markup = 'autolink'; + token.info = 'auto'; + + token = state.push('text', '', 0); + token.content = state.md.normalizeLinkText(url); + + token = state.push('link_close', 'a', -1); + token.markup = 'autolink'; + token.info = 'auto'; + } + + state.pos += linkMatch[0].length; + return true; + } + + if (EMAIL_RE.test(tail)) { + emailMatch = tail.match(EMAIL_RE); + + url = emailMatch[0].slice(1, -1); + fullUrl = state.md.normalizeLink('mailto:' + url); + if (!state.md.validateLink(fullUrl)) { return false; } + + if (!silent) { + token = state.push('link_open', 'a', 1); + token.attrs = [ [ 'href', fullUrl ] ]; + token.markup = 'autolink'; + token.info = 'auto'; + + token = state.push('text', '', 0); + token.content = state.md.normalizeLinkText(url); + + token = state.push('link_close', 'a', -1); + token.markup = 'autolink'; + token.info = 'auto'; + } + + state.pos += emailMatch[0].length; + return true; + } + + return false; +}; + +},{}],66:[function(require,module,exports){ +// Parse backticks + +'use strict'; + +module.exports = function backtick(state, silent) { + var start, max, marker, matchStart, matchEnd, token, + pos = state.pos, + ch = state.src.charCodeAt(pos); + + if (ch !== 0x60/* ` */) { return false; } + + start = pos; + pos++; + max = state.posMax; + + while (pos < max && state.src.charCodeAt(pos) === 0x60/* ` */) { pos++; } + + marker = state.src.slice(start, pos); + + matchStart = matchEnd = pos; + + while ((matchStart = state.src.indexOf('`', matchEnd)) !== -1) { + matchEnd = matchStart + 1; + + while (matchEnd < max && state.src.charCodeAt(matchEnd) === 0x60/* ` */) { matchEnd++; } + + if (matchEnd - matchStart === marker.length) { + if (!silent) { + token = state.push('code_inline', 'code', 0); + token.markup = marker; + token.content = state.src.slice(pos, matchStart) + .replace(/[ \n]+/g, ' ') + .trim(); + } + state.pos = matchEnd; + return true; + } + } + + if (!silent) { state.pending += marker; } + state.pos += marker.length; + return true; +}; + +},{}],67:[function(require,module,exports){ +// For each opening emphasis-like marker find a matching closing one +// +'use strict'; + + +module.exports = function link_pairs(state) { + var i, j, lastDelim, currDelim, + delimiters = state.delimiters, + max = state.delimiters.length; + + for (i = 0; i < max; i++) { + lastDelim = delimiters[i]; + + if (!lastDelim.close) { continue; } + + j = i - lastDelim.jump - 1; + + while (j >= 0) { + currDelim = delimiters[j]; + + if (currDelim.open && + currDelim.marker === lastDelim.marker && + currDelim.end < 0 && + currDelim.level === lastDelim.level) { + + lastDelim.jump = i - j; + lastDelim.open = false; + currDelim.end = i; + currDelim.jump = 0; + break; + } + + j -= currDelim.jump + 1; + } + } +}; + +},{}],68:[function(require,module,exports){ +// Process *this* and _that_ +// +'use strict'; + + +// Insert each marker as a separate text token, and add it to delimiter list +// +module.exports.tokenize = function emphasis(state, silent) { + var i, scanned, token, + start = state.pos, + marker = state.src.charCodeAt(start); + + if (silent) { return false; } + + if (marker !== 0x5F /* _ */ && marker !== 0x2A /* * */) { return false; } + + scanned = state.scanDelims(state.pos, marker === 0x2A); + + for (i = 0; i < scanned.length; i++) { + token = state.push('text', '', 0); + token.content = String.fromCharCode(marker); + + state.delimiters.push({ + // Char code of the starting marker (number). + // + marker: marker, + + // An amount of characters before this one that's equivalent to + // current one. In plain English: if this delimiter does not open + // an emphasis, neither do previous `jump` characters. + // + // Used to skip sequences like "*****" in one step, for 1st asterisk + // value will be 0, for 2nd it's 1 and so on. + // + jump: i, + + // A position of the token this delimiter corresponds to. + // + token: state.tokens.length - 1, + + // Token level. + // + level: state.level, + + // If this delimiter is matched as a valid opener, `end` will be + // equal to its position, otherwise it's `-1`. + // + end: -1, + + // Boolean flags that determine if this delimiter could open or close + // an emphasis. + // + open: scanned.can_open, + close: scanned.can_close + }); + } + + state.pos += scanned.length; + + return true; +}; + + +// Walk through delimiter list and replace text tokens with tags +// +module.exports.postProcess = function emphasis(state) { + var i, + startDelim, + endDelim, + token, + ch, + isStrong, + delimiters = state.delimiters, + max = state.delimiters.length; + + for (i = 0; i < max; i++) { + startDelim = delimiters[i]; + + if (startDelim.marker !== 0x5F/* _ */ && startDelim.marker !== 0x2A/* * */) { + continue; + } + + // Process only opening markers + if (startDelim.end === -1) { + continue; + } + + endDelim = delimiters[startDelim.end]; + + // If the next delimiter has the same marker and is adjacent to this one, + // merge those into one strong delimiter. + // + // `whatever` -> `whatever` + // + isStrong = i + 1 < max && + delimiters[i + 1].end === startDelim.end - 1 && + delimiters[i + 1].token === startDelim.token + 1 && + delimiters[startDelim.end - 1].token === endDelim.token - 1 && + delimiters[i + 1].marker === startDelim.marker; + + ch = String.fromCharCode(startDelim.marker); + + token = state.tokens[startDelim.token]; + token.type = isStrong ? 'strong_open' : 'em_open'; + token.tag = isStrong ? 'strong' : 'em'; + token.nesting = 1; + token.markup = isStrong ? ch + ch : ch; + token.content = ''; + + token = state.tokens[endDelim.token]; + token.type = isStrong ? 'strong_close' : 'em_close'; + token.tag = isStrong ? 'strong' : 'em'; + token.nesting = -1; + token.markup = isStrong ? ch + ch : ch; + token.content = ''; + + if (isStrong) { + state.tokens[delimiters[i + 1].token].content = ''; + state.tokens[delimiters[startDelim.end - 1].token].content = ''; + i++; + } + } +}; + +},{}],69:[function(require,module,exports){ +// Process html entity - {, ¯, ", ... + +'use strict'; + +var entities = require('../common/entities'); +var has = require('../common/utils').has; +var isValidEntityCode = require('../common/utils').isValidEntityCode; +var fromCodePoint = require('../common/utils').fromCodePoint; + + +var DIGITAL_RE = /^&#((?:x[a-f0-9]{1,8}|[0-9]{1,8}));/i; +var NAMED_RE = /^&([a-z][a-z0-9]{1,31});/i; + + +module.exports = function entity(state, silent) { + var ch, code, match, pos = state.pos, max = state.posMax; + + if (state.src.charCodeAt(pos) !== 0x26/* & */) { return false; } + + if (pos + 1 < max) { + ch = state.src.charCodeAt(pos + 1); + + if (ch === 0x23 /* # */) { + match = state.src.slice(pos).match(DIGITAL_RE); + if (match) { + if (!silent) { + code = match[1][0].toLowerCase() === 'x' ? parseInt(match[1].slice(1), 16) : parseInt(match[1], 10); + state.pending += isValidEntityCode(code) ? fromCodePoint(code) : fromCodePoint(0xFFFD); + } + state.pos += match[0].length; + return true; + } + } else { + match = state.src.slice(pos).match(NAMED_RE); + if (match) { + if (has(entities, match[1])) { + if (!silent) { state.pending += entities[match[1]]; } + state.pos += match[0].length; + return true; + } + } + } + } + + if (!silent) { state.pending += '&'; } + state.pos++; + return true; +}; + +},{"../common/entities":29,"../common/utils":32}],70:[function(require,module,exports){ +// Proceess escaped chars and hardbreaks + +'use strict'; + +var isSpace = require('../common/utils').isSpace; + +var ESCAPED = []; + +for (var i = 0; i < 256; i++) { ESCAPED.push(0); } + +'\\!"#$%&\'()*+,./:;<=>?@[]^_`{|}~-' + .split('').forEach(function(ch) { ESCAPED[ch.charCodeAt(0)] = 1; }); + + +module.exports = function escape(state, silent) { + var ch, pos = state.pos, max = state.posMax; + + if (state.src.charCodeAt(pos) !== 0x5C/* \ */) { return false; } + + pos++; + + if (pos < max) { + ch = state.src.charCodeAt(pos); + + if (ch < 256 && ESCAPED[ch] !== 0) { + if (!silent) { state.pending += state.src[pos]; } + state.pos += 2; + return true; + } + + if (ch === 0x0A) { + if (!silent) { + state.push('hardbreak', 'br', 0); + } + + pos++; + // skip leading whitespaces from next line + while (pos < max) { + ch = state.src.charCodeAt(pos); + if (!isSpace(ch)) { break; } + pos++; + } + + state.pos = pos; + return true; + } + } + + if (!silent) { state.pending += '\\'; } + state.pos++; + return true; +}; + +},{"../common/utils":32}],71:[function(require,module,exports){ +// Process html tags + +'use strict'; + + +var HTML_TAG_RE = require('../common/html_re').HTML_TAG_RE; + + +function isLetter(ch) { + /*eslint no-bitwise:0*/ + var lc = ch | 0x20; // to lower case + return (lc >= 0x61/* a */) && (lc <= 0x7a/* z */); +} + + +module.exports = function html_inline(state, silent) { + var ch, match, max, token, + pos = state.pos; + + if (!state.md.options.html) { return false; } + + // Check start + max = state.posMax; + if (state.src.charCodeAt(pos) !== 0x3C/* < */ || + pos + 2 >= max) { + return false; + } + + // Quick fail on second char + ch = state.src.charCodeAt(pos + 1); + if (ch !== 0x21/* ! */ && + ch !== 0x3F/* ? */ && + ch !== 0x2F/* / */ && + !isLetter(ch)) { + return false; + } + + match = state.src.slice(pos).match(HTML_TAG_RE); + if (!match) { return false; } + + if (!silent) { + token = state.push('html_inline', '', 0); + token.content = state.src.slice(pos, pos + match[0].length); + } + state.pos += match[0].length; + return true; +}; + +},{"../common/html_re":31}],72:[function(require,module,exports){ +// Process ![image]( "title") + +'use strict'; + +var parseLinkLabel = require('../helpers/parse_link_label'); +var parseLinkDestination = require('../helpers/parse_link_destination'); +var parseLinkTitle = require('../helpers/parse_link_title'); +var normalizeReference = require('../common/utils').normalizeReference; +var isSpace = require('../common/utils').isSpace; + + +module.exports = function image(state, silent) { + var attrs, + code, + content, + label, + labelEnd, + labelStart, + pos, + ref, + res, + title, + token, + tokens, + start, + href = '', + oldPos = state.pos, + max = state.posMax; + + if (state.src.charCodeAt(state.pos) !== 0x21/* ! */) { return false; } + if (state.src.charCodeAt(state.pos + 1) !== 0x5B/* [ */) { return false; } + + labelStart = state.pos + 2; + labelEnd = parseLinkLabel(state, state.pos + 1, false); + + // parser failed to find ']', so it's not a valid link + if (labelEnd < 0) { return false; } + + pos = labelEnd + 1; + if (pos < max && state.src.charCodeAt(pos) === 0x28/* ( */) { + // + // Inline link + // + + // [link]( "title" ) + // ^^ skipping these spaces + pos++; + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { break; } + } + if (pos >= max) { return false; } + + // [link]( "title" ) + // ^^^^^^ parsing link destination + start = pos; + res = parseLinkDestination(state.src, pos, state.posMax); + if (res.ok) { + href = state.md.normalizeLink(res.str); + if (state.md.validateLink(href)) { + pos = res.pos; + } else { + href = ''; + } + } + + // [link]( "title" ) + // ^^ skipping these spaces + start = pos; + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { break; } + } + + // [link]( "title" ) + // ^^^^^^^ parsing link title + res = parseLinkTitle(state.src, pos, state.posMax); + if (pos < max && start !== pos && res.ok) { + title = res.str; + pos = res.pos; + + // [link]( "title" ) + // ^^ skipping these spaces + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { break; } + } + } else { + title = ''; + } + + if (pos >= max || state.src.charCodeAt(pos) !== 0x29/* ) */) { + state.pos = oldPos; + return false; + } + pos++; + } else { + // + // Link reference + // + if (typeof state.env.references === 'undefined') { return false; } + + if (pos < max && state.src.charCodeAt(pos) === 0x5B/* [ */) { + start = pos + 1; + pos = parseLinkLabel(state, pos); + if (pos >= 0) { + label = state.src.slice(start, pos++); + } else { + pos = labelEnd + 1; + } + } else { + pos = labelEnd + 1; + } + + // covers label === '' and label === undefined + // (collapsed reference link and shortcut reference link respectively) + if (!label) { label = state.src.slice(labelStart, labelEnd); } + + ref = state.env.references[normalizeReference(label)]; + if (!ref) { + state.pos = oldPos; + return false; + } + href = ref.href; + title = ref.title; + } + + // + // We found the end of the link, and know for a fact it's a valid link; + // so all that's left to do is to call tokenizer. + // + if (!silent) { + content = state.src.slice(labelStart, labelEnd); + + state.md.inline.parse( + content, + state.md, + state.env, + tokens = [] + ); + + token = state.push('image', 'img', 0); + token.attrs = attrs = [ [ 'src', href ], [ 'alt', '' ] ]; + token.children = tokens; + token.content = content; + + if (title) { + attrs.push([ 'title', title ]); + } + } + + state.pos = pos; + state.posMax = max; + return true; +}; + +},{"../common/utils":32,"../helpers/parse_link_destination":34,"../helpers/parse_link_label":35,"../helpers/parse_link_title":36}],73:[function(require,module,exports){ +// Process [link]( "stuff") + +'use strict'; + +var parseLinkLabel = require('../helpers/parse_link_label'); +var parseLinkDestination = require('../helpers/parse_link_destination'); +var parseLinkTitle = require('../helpers/parse_link_title'); +var normalizeReference = require('../common/utils').normalizeReference; +var isSpace = require('../common/utils').isSpace; + + +module.exports = function link(state, silent) { + var attrs, + code, + label, + labelEnd, + labelStart, + pos, + res, + ref, + title, + token, + href = '', + oldPos = state.pos, + max = state.posMax, + start = state.pos; + + if (state.src.charCodeAt(state.pos) !== 0x5B/* [ */) { return false; } + + labelStart = state.pos + 1; + labelEnd = parseLinkLabel(state, state.pos, true); + + // parser failed to find ']', so it's not a valid link + if (labelEnd < 0) { return false; } + + pos = labelEnd + 1; + if (pos < max && state.src.charCodeAt(pos) === 0x28/* ( */) { + // + // Inline link + // + + // [link]( "title" ) + // ^^ skipping these spaces + pos++; + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { break; } + } + if (pos >= max) { return false; } + + // [link]( "title" ) + // ^^^^^^ parsing link destination + start = pos; + res = parseLinkDestination(state.src, pos, state.posMax); + if (res.ok) { + href = state.md.normalizeLink(res.str); + if (state.md.validateLink(href)) { + pos = res.pos; + } else { + href = ''; + } + } + + // [link]( "title" ) + // ^^ skipping these spaces + start = pos; + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { break; } + } + + // [link]( "title" ) + // ^^^^^^^ parsing link title + res = parseLinkTitle(state.src, pos, state.posMax); + if (pos < max && start !== pos && res.ok) { + title = res.str; + pos = res.pos; + + // [link]( "title" ) + // ^^ skipping these spaces + for (; pos < max; pos++) { + code = state.src.charCodeAt(pos); + if (!isSpace(code) && code !== 0x0A) { break; } + } + } else { + title = ''; + } + + if (pos >= max || state.src.charCodeAt(pos) !== 0x29/* ) */) { + state.pos = oldPos; + return false; + } + pos++; + } else { + // + // Link reference + // + if (typeof state.env.references === 'undefined') { return false; } + + if (pos < max && state.src.charCodeAt(pos) === 0x5B/* [ */) { + start = pos + 1; + pos = parseLinkLabel(state, pos); + if (pos >= 0) { + label = state.src.slice(start, pos++); + } else { + pos = labelEnd + 1; + } + } else { + pos = labelEnd + 1; + } + + // covers label === '' and label === undefined + // (collapsed reference link and shortcut reference link respectively) + if (!label) { label = state.src.slice(labelStart, labelEnd); } + + ref = state.env.references[normalizeReference(label)]; + if (!ref) { + state.pos = oldPos; + return false; + } + href = ref.href; + title = ref.title; + } + + // + // We found the end of the link, and know for a fact it's a valid link; + // so all that's left to do is to call tokenizer. + // + if (!silent) { + state.pos = labelStart; + state.posMax = labelEnd; + + token = state.push('link_open', 'a', 1); + token.attrs = attrs = [ [ 'href', href ] ]; + if (title) { + attrs.push([ 'title', title ]); + } + + state.md.inline.tokenize(state); + + token = state.push('link_close', 'a', -1); + } + + state.pos = pos; + state.posMax = max; + return true; +}; + +},{"../common/utils":32,"../helpers/parse_link_destination":34,"../helpers/parse_link_label":35,"../helpers/parse_link_title":36}],74:[function(require,module,exports){ +// Proceess '\n' + +'use strict'; + +module.exports = function newline(state, silent) { + var pmax, max, pos = state.pos; + + if (state.src.charCodeAt(pos) !== 0x0A/* \n */) { return false; } + + pmax = state.pending.length - 1; + max = state.posMax; + + // ' \n' -> hardbreak + // Lookup in pending chars is bad practice! Don't copy to other rules! + // Pending string is stored in concat mode, indexed lookups will cause + // convertion to flat mode. + if (!silent) { + if (pmax >= 0 && state.pending.charCodeAt(pmax) === 0x20) { + if (pmax >= 1 && state.pending.charCodeAt(pmax - 1) === 0x20) { + state.pending = state.pending.replace(/ +$/, ''); + state.push('hardbreak', 'br', 0); + } else { + state.pending = state.pending.slice(0, -1); + state.push('softbreak', 'br', 0); + } + + } else { + state.push('softbreak', 'br', 0); + } + } + + pos++; + + // skip heading spaces for next line + while (pos < max && state.src.charCodeAt(pos) === 0x20) { pos++; } + + state.pos = pos; + return true; +}; + +},{}],75:[function(require,module,exports){ +// Inline parser state + +'use strict'; + + +var Token = require('../token'); +var isWhiteSpace = require('../common/utils').isWhiteSpace; +var isPunctChar = require('../common/utils').isPunctChar; +var isMdAsciiPunct = require('../common/utils').isMdAsciiPunct; + + +function StateInline(src, md, env, outTokens) { + this.src = src; + this.env = env; + this.md = md; + this.tokens = outTokens; + + this.pos = 0; + this.posMax = this.src.length; + this.level = 0; + this.pending = ''; + this.pendingLevel = 0; + + this.cache = {}; // Stores { start: end } pairs. Useful for backtrack + // optimization of pairs parse (emphasis, strikes). + + this.delimiters = []; // Emphasis-like delimiters +} + + +// Flush pending text +// +StateInline.prototype.pushPending = function () { + var token = new Token('text', '', 0); + token.content = this.pending; + token.level = this.pendingLevel; + this.tokens.push(token); + this.pending = ''; + return token; +}; + + +// Push new token to "stream". +// If pending text exists - flush it as text token +// +StateInline.prototype.push = function (type, tag, nesting) { + if (this.pending) { + this.pushPending(); + } + + var token = new Token(type, tag, nesting); + + if (nesting < 0) { this.level--; } + token.level = this.level; + if (nesting > 0) { this.level++; } + + this.pendingLevel = this.level; + this.tokens.push(token); + return token; +}; + + +// Scan a sequence of emphasis-like markers, and determine whether +// it can start an emphasis sequence or end an emphasis sequence. +// +// - start - position to scan from (it should point at a valid marker); +// - canSplitWord - determine if these markers can be found inside a word +// +StateInline.prototype.scanDelims = function (start, canSplitWord) { + var pos = start, lastChar, nextChar, count, can_open, can_close, + isLastWhiteSpace, isLastPunctChar, + isNextWhiteSpace, isNextPunctChar, + left_flanking = true, + right_flanking = true, + max = this.posMax, + marker = this.src.charCodeAt(start); + + // treat beginning of the line as a whitespace + lastChar = start > 0 ? this.src.charCodeAt(start - 1) : 0x20; + + while (pos < max && this.src.charCodeAt(pos) === marker) { pos++; } + + count = pos - start; + + // treat end of the line as a whitespace + nextChar = pos < max ? this.src.charCodeAt(pos) : 0x20; + + isLastPunctChar = isMdAsciiPunct(lastChar) || isPunctChar(String.fromCharCode(lastChar)); + isNextPunctChar = isMdAsciiPunct(nextChar) || isPunctChar(String.fromCharCode(nextChar)); + + isLastWhiteSpace = isWhiteSpace(lastChar); + isNextWhiteSpace = isWhiteSpace(nextChar); + + if (isNextWhiteSpace) { + left_flanking = false; + } else if (isNextPunctChar) { + if (!(isLastWhiteSpace || isLastPunctChar)) { + left_flanking = false; + } + } + + if (isLastWhiteSpace) { + right_flanking = false; + } else if (isLastPunctChar) { + if (!(isNextWhiteSpace || isNextPunctChar)) { + right_flanking = false; + } + } + + if (!canSplitWord) { + can_open = left_flanking && (!right_flanking || isLastPunctChar); + can_close = right_flanking && (!left_flanking || isNextPunctChar); + } else { + can_open = left_flanking; + can_close = right_flanking; + } + + return { + can_open: can_open, + can_close: can_close, + length: count + }; +}; + + +// re-export Token class to use in block rules +StateInline.prototype.Token = Token; + + +module.exports = StateInline; + +},{"../common/utils":32,"../token":79}],76:[function(require,module,exports){ +// ~~strike through~~ +// +'use strict'; + + +// Insert each marker as a separate text token, and add it to delimiter list +// +module.exports.tokenize = function strikethrough(state, silent) { + var i, scanned, token, len, ch, + start = state.pos, + marker = state.src.charCodeAt(start); + + if (silent) { return false; } + + if (marker !== 0x7E/* ~ */) { return false; } + + scanned = state.scanDelims(state.pos, true); + len = scanned.length; + ch = String.fromCharCode(marker); + + if (len < 2) { return false; } + + if (len % 2) { + token = state.push('text', '', 0); + token.content = ch; + len--; + } + + for (i = 0; i < len; i += 2) { + token = state.push('text', '', 0); + token.content = ch + ch; + + state.delimiters.push({ + marker: marker, + jump: i, + token: state.tokens.length - 1, + level: state.level, + end: -1, + open: scanned.can_open, + close: scanned.can_close + }); + } + + state.pos += scanned.length; + + return true; +}; + + +// Walk through delimiter list and replace text tokens with tags +// +module.exports.postProcess = function strikethrough(state) { + var i, j, + startDelim, + endDelim, + token, + loneMarkers = [], + delimiters = state.delimiters, + max = state.delimiters.length; + + for (i = 0; i < max; i++) { + startDelim = delimiters[i]; + + if (startDelim.marker !== 0x7E/* ~ */) { + continue; + } + + if (startDelim.end === -1) { + continue; + } + + endDelim = delimiters[startDelim.end]; + + token = state.tokens[startDelim.token]; + token.type = 's_open'; + token.tag = 's'; + token.nesting = 1; + token.markup = '~~'; + token.content = ''; + + token = state.tokens[endDelim.token]; + token.type = 's_close'; + token.tag = 's'; + token.nesting = -1; + token.markup = '~~'; + token.content = ''; + + if (state.tokens[endDelim.token - 1].type === 'text' && + state.tokens[endDelim.token - 1].content === '~') { + + loneMarkers.push(endDelim.token - 1); + } + } + + // If a marker sequence has an odd number of characters, it's splitted + // like this: `~~~~~` -> `~` + `~~` + `~~`, leaving one marker at the + // start of the sequence. + // + // So, we have to move all those markers after subsequent s_close tags. + // + while (loneMarkers.length) { + i = loneMarkers.pop(); + j = i + 1; + + while (j < state.tokens.length && state.tokens[j].type === 's_close') { + j++; + } + + j--; + + if (i !== j) { + token = state.tokens[j]; + state.tokens[j] = state.tokens[i]; + state.tokens[i] = token; + } + } +}; + +},{}],77:[function(require,module,exports){ +// Skip text characters for text token, place those to pending buffer +// and increment current pos + +'use strict'; + + +// Rule to skip pure text +// '{}$%@~+=:' reserved for extentions + +// !, ", #, $, %, &, ', (, ), *, +, ,, -, ., /, :, ;, <, =, >, ?, @, [, \, ], ^, _, `, {, |, }, or ~ + +// !!!! Don't confuse with "Markdown ASCII Punctuation" chars +// http://spec.commonmark.org/0.15/#ascii-punctuation-character +function isTerminatorChar(ch) { + switch (ch) { + case 0x0A/* \n */: + case 0x21/* ! */: + case 0x23/* # */: + case 0x24/* $ */: + case 0x25/* % */: + case 0x26/* & */: + case 0x2A/* * */: + case 0x2B/* + */: + case 0x2D/* - */: + case 0x3A/* : */: + case 0x3C/* < */: + case 0x3D/* = */: + case 0x3E/* > */: + case 0x40/* @ */: + case 0x5B/* [ */: + case 0x5C/* \ */: + case 0x5D/* ] */: + case 0x5E/* ^ */: + case 0x5F/* _ */: + case 0x60/* ` */: + case 0x7B/* { */: + case 0x7D/* } */: + case 0x7E/* ~ */: + return true; + default: + return false; + } +} + +module.exports = function text(state, silent) { + var pos = state.pos; + + while (pos < state.posMax && !isTerminatorChar(state.src.charCodeAt(pos))) { + pos++; + } + + if (pos === state.pos) { return false; } + + if (!silent) { state.pending += state.src.slice(state.pos, pos); } + + state.pos = pos; + + return true; +}; + +// Alternative implementation, for memory. +// +// It costs 10% of performance, but allows extend terminators list, if place it +// to `ParcerInline` property. Probably, will switch to it sometime, such +// flexibility required. + +/* +var TERMINATOR_RE = /[\n!#$%&*+\-:<=>@[\\\]^_`{}~]/; + +module.exports = function text(state, silent) { + var pos = state.pos, + idx = state.src.slice(pos).search(TERMINATOR_RE); + + // first char is terminator -> empty text + if (idx === 0) { return false; } + + // no terminator -> text till end of string + if (idx < 0) { + if (!silent) { state.pending += state.src.slice(pos); } + state.pos = state.src.length; + return true; + } + + if (!silent) { state.pending += state.src.slice(pos, pos + idx); } + + state.pos += idx; + + return true; +};*/ + +},{}],78:[function(require,module,exports){ +// Merge adjacent text nodes into one, and re-calculate all token levels +// +'use strict'; + + +module.exports = function text_collapse(state) { + var curr, last, + level = 0, + tokens = state.tokens, + max = state.tokens.length; + + for (curr = last = 0; curr < max; curr++) { + // re-calculate levels + level += tokens[curr].nesting; + tokens[curr].level = level; + + if (tokens[curr].type === 'text' && + curr + 1 < max && + tokens[curr + 1].type === 'text') { + + // collapse two adjacent text nodes + tokens[curr + 1].content = tokens[curr].content + tokens[curr + 1].content; + } else { + if (curr !== last) { tokens[last] = tokens[curr]; } + + last++; + } + } + + if (curr !== last) { + tokens.length = last; + } +}; + +},{}],79:[function(require,module,exports){ +// Token class + +'use strict'; + + +/** + * class Token + **/ + +/** + * new Token(type, tag, nesting) + * + * Create new token and fill passed properties. + **/ +function Token(type, tag, nesting) { + /** + * Token#type -> String + * + * Type of the token (string, e.g. "paragraph_open") + **/ + this.type = type; + + /** + * Token#tag -> String + * + * html tag name, e.g. "p" + **/ + this.tag = tag; + + /** + * Token#attrs -> Array + * + * Html attributes. Format: `[ [ name1, value1 ], [ name2, value2 ] ]` + **/ + this.attrs = null; + + /** + * Token#map -> Array + * + * Source map info. Format: `[ line_begin, line_end ]` + **/ + this.map = null; + + /** + * Token#nesting -> Number + * + * Level change (number in {-1, 0, 1} set), where: + * + * - `1` means the tag is opening + * - `0` means the tag is self-closing + * - `-1` means the tag is closing + **/ + this.nesting = nesting; + + /** + * Token#level -> Number + * + * nesting level, the same as `state.level` + **/ + this.level = 0; + + /** + * Token#children -> Array + * + * An array of child nodes (inline and img tokens) + **/ + this.children = null; + + /** + * Token#content -> String + * + * In a case of self-closing tag (code, html, fence, etc.), + * it has contents of this tag. + **/ + this.content = ''; + + /** + * Token#markup -> String + * + * '*' or '_' for emphasis, fence string for fence, etc. + **/ + this.markup = ''; + + /** + * Token#info -> String + * + * fence infostring + **/ + this.info = ''; + + /** + * Token#meta -> Object + * + * A place for plugins to store an arbitrary data + **/ + this.meta = null; + + /** + * Token#block -> Boolean + * + * True for block-level tokens, false for inline tokens. + * Used in renderer to calculate line breaks + **/ + this.block = false; + + /** + * Token#hidden -> Boolean + * + * If it's true, ignore this element when rendering. Used for tight lists + * to hide paragraphs. + **/ + this.hidden = false; +} + + +/** + * Token.attrIndex(name) -> Number + * + * Search attribute index by name. + **/ +Token.prototype.attrIndex = function attrIndex(name) { + var attrs, i, len; + + if (!this.attrs) { return -1; } + + attrs = this.attrs; + + for (i = 0, len = attrs.length; i < len; i++) { + if (attrs[i][0] === name) { return i; } + } + return -1; +}; + + +/** + * Token.attrPush(attrData) + * + * Add `[ name, value ]` attribute to list. Init attrs if necessary + **/ +Token.prototype.attrPush = function attrPush(attrData) { + if (this.attrs) { + this.attrs.push(attrData); + } else { + this.attrs = [ attrData ]; + } +}; + + +/** + * Token.attrSet(name, value) + * + * Set `name` attribute to `value`. Override old value if exists. + **/ +Token.prototype.attrSet = function attrSet(name, value) { + var idx = this.attrIndex(name), + attrData = [ name, value ]; + + if (idx < 0) { + this.attrPush(attrData); + } else { + this.attrs[idx] = attrData; + } +}; + + +/** + * Token.attrJoin(name, value) + * + * Join value to existing attribute via space. Or create new attribute if not + * exists. Useful to operate with token classes. + **/ +Token.prototype.attrJoin = function attrJoin(name, value) { + var idx = this.attrIndex(name); + + if (idx < 0) { + this.attrPush([ name, value ]); + } else { + this.attrs[idx][1] = this.attrs[idx][1] + ' ' + value; + } +}; + + +module.exports = Token; + +},{}],80:[function(require,module,exports){ +/** @flow */ + +"use strict"; + +function getRelocatable(re) { + // In the future, this could use a WeakMap instead of an expando. + if (!re.__matchAtRelocatable) { + // Disjunctions are the lowest-precedence operator, so we can make any + // pattern match the empty string by appending `|()` to it: + // https://people.mozilla.org/~jorendorff/es6-draft.html#sec-patterns + var source = re.source + "|()"; + + // We always make the new regex global. + var flags = "g" + (re.ignoreCase ? "i" : "") + (re.multiline ? "m" : "") + (re.unicode ? "u" : "") + // sticky (/.../y) doesn't make sense in conjunction with our relocation + // logic, so we ignore it here. + ; + + re.__matchAtRelocatable = new RegExp(source, flags); + } + return re.__matchAtRelocatable; +} + +function matchAt(re, str, pos) { + if (re.global || re.sticky) { + throw new Error("matchAt(...): Only non-global regexes are supported"); + } + var reloc = getRelocatable(re); + reloc.lastIndex = pos; + var match = reloc.exec(str); + // Last capturing group is our sentinel that indicates whether the regex + // matched at the given location. + if (match[match.length - 1] == null) { + // Original regex matched. + match.length = match.length - 1; + return match; + } else { + return null; + } +} + +module.exports = matchAt; +},{}],81:[function(require,module,exports){ + +'use strict'; + + +/* eslint-disable no-bitwise */ + +var decodeCache = {}; + +function getDecodeCache(exclude) { + var i, ch, cache = decodeCache[exclude]; + if (cache) { return cache; } + + cache = decodeCache[exclude] = []; + + for (i = 0; i < 128; i++) { + ch = String.fromCharCode(i); + cache.push(ch); + } + + for (i = 0; i < exclude.length; i++) { + ch = exclude.charCodeAt(i); + cache[ch] = '%' + ('0' + ch.toString(16).toUpperCase()).slice(-2); + } + + return cache; +} + + +// Decode percent-encoded string. +// +function decode(string, exclude) { + var cache; + + if (typeof exclude !== 'string') { + exclude = decode.defaultChars; + } + + cache = getDecodeCache(exclude); + + return string.replace(/(%[a-f0-9]{2})+/gi, function(seq) { + var i, l, b1, b2, b3, b4, chr, + result = ''; + + for (i = 0, l = seq.length; i < l; i += 3) { + b1 = parseInt(seq.slice(i + 1, i + 3), 16); + + if (b1 < 0x80) { + result += cache[b1]; + continue; + } + + if ((b1 & 0xE0) === 0xC0 && (i + 3 < l)) { + // 110xxxxx 10xxxxxx + b2 = parseInt(seq.slice(i + 4, i + 6), 16); + + if ((b2 & 0xC0) === 0x80) { + chr = ((b1 << 6) & 0x7C0) | (b2 & 0x3F); + + if (chr < 0x80) { + result += '\ufffd\ufffd'; + } else { + result += String.fromCharCode(chr); + } + + i += 3; + continue; + } + } + + if ((b1 & 0xF0) === 0xE0 && (i + 6 < l)) { + // 1110xxxx 10xxxxxx 10xxxxxx + b2 = parseInt(seq.slice(i + 4, i + 6), 16); + b3 = parseInt(seq.slice(i + 7, i + 9), 16); + + if ((b2 & 0xC0) === 0x80 && (b3 & 0xC0) === 0x80) { + chr = ((b1 << 12) & 0xF000) | ((b2 << 6) & 0xFC0) | (b3 & 0x3F); + + if (chr < 0x800 || (chr >= 0xD800 && chr <= 0xDFFF)) { + result += '\ufffd\ufffd\ufffd'; + } else { + result += String.fromCharCode(chr); + } + + i += 6; + continue; + } + } + + if ((b1 & 0xF8) === 0xF0 && (i + 9 < l)) { + // 111110xx 10xxxxxx 10xxxxxx 10xxxxxx + b2 = parseInt(seq.slice(i + 4, i + 6), 16); + b3 = parseInt(seq.slice(i + 7, i + 9), 16); + b4 = parseInt(seq.slice(i + 10, i + 12), 16); + + if ((b2 & 0xC0) === 0x80 && (b3 & 0xC0) === 0x80 && (b4 & 0xC0) === 0x80) { + chr = ((b1 << 18) & 0x1C0000) | ((b2 << 12) & 0x3F000) | ((b3 << 6) & 0xFC0) | (b4 & 0x3F); + + if (chr < 0x10000 || chr > 0x10FFFF) { + result += '\ufffd\ufffd\ufffd\ufffd'; + } else { + chr -= 0x10000; + result += String.fromCharCode(0xD800 + (chr >> 10), 0xDC00 + (chr & 0x3FF)); + } + + i += 9; + continue; + } + } + + result += '\ufffd'; + } + + return result; + }); +} + + +decode.defaultChars = ';/?:@&=+$,#'; +decode.componentChars = ''; + + +module.exports = decode; + +},{}],82:[function(require,module,exports){ + +'use strict'; + + +var encodeCache = {}; + + +// Create a lookup array where anything but characters in `chars` string +// and alphanumeric chars is percent-encoded. +// +function getEncodeCache(exclude) { + var i, ch, cache = encodeCache[exclude]; + if (cache) { return cache; } + + cache = encodeCache[exclude] = []; + + for (i = 0; i < 128; i++) { + ch = String.fromCharCode(i); + + if (/^[0-9a-z]$/i.test(ch)) { + // always allow unencoded alphanumeric characters + cache.push(ch); + } else { + cache.push('%' + ('0' + i.toString(16).toUpperCase()).slice(-2)); + } + } + + for (i = 0; i < exclude.length; i++) { + cache[exclude.charCodeAt(i)] = exclude[i]; + } + + return cache; +} + + +// Encode unsafe characters with percent-encoding, skipping already +// encoded sequences. +// +// - string - string to encode +// - exclude - list of characters to ignore (in addition to a-zA-Z0-9) +// - keepEscaped - don't encode '%' in a correct escape sequence (default: true) +// +function encode(string, exclude, keepEscaped) { + var i, l, code, nextCode, cache, + result = ''; + + if (typeof exclude !== 'string') { + // encode(string, keepEscaped) + keepEscaped = exclude; + exclude = encode.defaultChars; + } + + if (typeof keepEscaped === 'undefined') { + keepEscaped = true; + } + + cache = getEncodeCache(exclude); + + for (i = 0, l = string.length; i < l; i++) { + code = string.charCodeAt(i); + + if (keepEscaped && code === 0x25 /* % */ && i + 2 < l) { + if (/^[0-9a-f]{2}$/i.test(string.slice(i + 1, i + 3))) { + result += string.slice(i, i + 3); + i += 2; + continue; + } + } + + if (code < 128) { + result += cache[code]; + continue; + } + + if (code >= 0xD800 && code <= 0xDFFF) { + if (code >= 0xD800 && code <= 0xDBFF && i + 1 < l) { + nextCode = string.charCodeAt(i + 1); + if (nextCode >= 0xDC00 && nextCode <= 0xDFFF) { + result += encodeURIComponent(string[i] + string[i + 1]); + i++; + continue; + } + } + result += '%EF%BF%BD'; + continue; + } + + result += encodeURIComponent(string[i]); + } + + return result; +} + +encode.defaultChars = ";/?:@&=+$,-_.!~*'()#"; +encode.componentChars = "-_.!~*'()"; + + +module.exports = encode; + +},{}],83:[function(require,module,exports){ + +'use strict'; + + +module.exports = function format(url) { + var result = ''; + + result += url.protocol || ''; + result += url.slashes ? '//' : ''; + result += url.auth ? url.auth + '@' : ''; + + if (url.hostname && url.hostname.indexOf(':') !== -1) { + // ipv6 address + result += '[' + url.hostname + ']'; + } else { + result += url.hostname || ''; + } + + result += url.port ? ':' + url.port : ''; + result += url.pathname || ''; + result += url.search || ''; + result += url.hash || ''; + + return result; +}; + +},{}],84:[function(require,module,exports){ +'use strict'; + + +module.exports.encode = require('./encode'); +module.exports.decode = require('./decode'); +module.exports.format = require('./format'); +module.exports.parse = require('./parse'); + +},{"./decode":81,"./encode":82,"./format":83,"./parse":85}],85:[function(require,module,exports){ +// Copyright Joyent, Inc. and other Node contributors. +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the +// "Software"), to deal in the Software without restriction, including +// without limitation the rights to use, copy, modify, merge, publish, +// distribute, sublicense, and/or sell copies of the Software, and to permit +// persons to whom the Software is furnished to do so, subject to the +// following conditions: +// +// The above copyright notice and this permission notice shall be included +// in all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS +// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN +// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, +// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR +// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE +// USE OR OTHER DEALINGS IN THE SOFTWARE. + +'use strict'; + +// +// Changes from joyent/node: +// +// 1. No leading slash in paths, +// e.g. in `url.parse('http://foo?bar')` pathname is ``, not `/` +// +// 2. Backslashes are not replaced with slashes, +// so `http:\\example.org\` is treated like a relative path +// +// 3. Trailing colon is treated like a part of the path, +// i.e. in `http://example.org:foo` pathname is `:foo` +// +// 4. Nothing is URL-encoded in the resulting object, +// (in joyent/node some chars in auth and paths are encoded) +// +// 5. `url.parse()` does not have `parseQueryString` argument +// +// 6. Removed extraneous result properties: `host`, `path`, `query`, etc., +// which can be constructed using other parts of the url. +// + + +function Url() { + this.protocol = null; + this.slashes = null; + this.auth = null; + this.port = null; + this.hostname = null; + this.hash = null; + this.search = null; + this.pathname = null; +} + +// Reference: RFC 3986, RFC 1808, RFC 2396 + +// define these here so at least they only have to be +// compiled once on the first module load. +var protocolPattern = /^([a-z0-9.+-]+:)/i, + portPattern = /:[0-9]*$/, + + // Special case for a simple path URL + simplePathPattern = /^(\/\/?(?!\/)[^\?\s]*)(\?[^\s]*)?$/, + + // RFC 2396: characters reserved for delimiting URLs. + // We actually just auto-escape these. + delims = [ '<', '>', '"', '`', ' ', '\r', '\n', '\t' ], + + // RFC 2396: characters not allowed for various reasons. + unwise = [ '{', '}', '|', '\\', '^', '`' ].concat(delims), + + // Allowed by RFCs, but cause of XSS attacks. Always escape these. + autoEscape = [ '\'' ].concat(unwise), + // Characters that are never ever allowed in a hostname. + // Note that any invalid chars are also handled, but these + // are the ones that are *expected* to be seen, so we fast-path + // them. + nonHostChars = [ '%', '/', '?', ';', '#' ].concat(autoEscape), + hostEndingChars = [ '/', '?', '#' ], + hostnameMaxLen = 255, + hostnamePartPattern = /^[+a-z0-9A-Z_-]{0,63}$/, + hostnamePartStart = /^([+a-z0-9A-Z_-]{0,63})(.*)$/, + // protocols that can allow "unsafe" and "unwise" chars. + /* eslint-disable no-script-url */ + // protocols that never have a hostname. + hostlessProtocol = { + 'javascript': true, + 'javascript:': true + }, + // protocols that always contain a // bit. + slashedProtocol = { + 'http': true, + 'https': true, + 'ftp': true, + 'gopher': true, + 'file': true, + 'http:': true, + 'https:': true, + 'ftp:': true, + 'gopher:': true, + 'file:': true + }; + /* eslint-enable no-script-url */ + +function urlParse(url, slashesDenoteHost) { + if (url && url instanceof Url) { return url; } + + var u = new Url(); + u.parse(url, slashesDenoteHost); + return u; +} + +Url.prototype.parse = function(url, slashesDenoteHost) { + var i, l, lowerProto, hec, slashes, + rest = url; + + // trim before proceeding. + // This is to support parse stuff like " http://foo.com \n" + rest = rest.trim(); + + if (!slashesDenoteHost && url.split('#').length === 1) { + // Try fast path regexp + var simplePath = simplePathPattern.exec(rest); + if (simplePath) { + this.pathname = simplePath[1]; + if (simplePath[2]) { + this.search = simplePath[2]; + } + return this; + } + } + + var proto = protocolPattern.exec(rest); + if (proto) { + proto = proto[0]; + lowerProto = proto.toLowerCase(); + this.protocol = proto; + rest = rest.substr(proto.length); + } + + // figure out if it's got a host + // user@server is *always* interpreted as a hostname, and url + // resolution will treat //foo/bar as host=foo,path=bar because that's + // how the browser resolves relative URLs. + if (slashesDenoteHost || proto || rest.match(/^\/\/[^@\/]+@[^@\/]+/)) { + slashes = rest.substr(0, 2) === '//'; + if (slashes && !(proto && hostlessProtocol[proto])) { + rest = rest.substr(2); + this.slashes = true; + } + } + + if (!hostlessProtocol[proto] && + (slashes || (proto && !slashedProtocol[proto]))) { + + // there's a hostname. + // the first instance of /, ?, ;, or # ends the host. + // + // If there is an @ in the hostname, then non-host chars *are* allowed + // to the left of the last @ sign, unless some host-ending character + // comes *before* the @-sign. + // URLs are obnoxious. + // + // ex: + // http://a@b@c/ => user:a@b host:c + // http://a@b?@c => user:a host:c path:/?@c + + // v0.12 TODO(isaacs): This is not quite how Chrome does things. + // Review our test case against browsers more comprehensively. + + // find the first instance of any hostEndingChars + var hostEnd = -1; + for (i = 0; i < hostEndingChars.length; i++) { + hec = rest.indexOf(hostEndingChars[i]); + if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) { + hostEnd = hec; + } + } + + // at this point, either we have an explicit point where the + // auth portion cannot go past, or the last @ char is the decider. + var auth, atSign; + if (hostEnd === -1) { + // atSign can be anywhere. + atSign = rest.lastIndexOf('@'); + } else { + // atSign must be in auth portion. + // http://a@b/c@d => host:b auth:a path:/c@d + atSign = rest.lastIndexOf('@', hostEnd); + } + + // Now we have a portion which is definitely the auth. + // Pull that off. + if (atSign !== -1) { + auth = rest.slice(0, atSign); + rest = rest.slice(atSign + 1); + this.auth = auth; + } + + // the host is the remaining to the left of the first non-host char + hostEnd = -1; + for (i = 0; i < nonHostChars.length; i++) { + hec = rest.indexOf(nonHostChars[i]); + if (hec !== -1 && (hostEnd === -1 || hec < hostEnd)) { + hostEnd = hec; + } + } + // if we still have not hit it, then the entire thing is a host. + if (hostEnd === -1) { + hostEnd = rest.length; + } + + if (rest[hostEnd - 1] === ':') { hostEnd--; } + var host = rest.slice(0, hostEnd); + rest = rest.slice(hostEnd); + + // pull out port. + this.parseHost(host); + + // we've indicated that there is a hostname, + // so even if it's empty, it has to be present. + this.hostname = this.hostname || ''; + + // if hostname begins with [ and ends with ] + // assume that it's an IPv6 address. + var ipv6Hostname = this.hostname[0] === '[' && + this.hostname[this.hostname.length - 1] === ']'; + + // validate a little. + if (!ipv6Hostname) { + var hostparts = this.hostname.split(/\./); + for (i = 0, l = hostparts.length; i < l; i++) { + var part = hostparts[i]; + if (!part) { continue; } + if (!part.match(hostnamePartPattern)) { + var newpart = ''; + for (var j = 0, k = part.length; j < k; j++) { + if (part.charCodeAt(j) > 127) { + // we replace non-ASCII char with a temporary placeholder + // we need this to make sure size of hostname is not + // broken by replacing non-ASCII by nothing + newpart += 'x'; + } else { + newpart += part[j]; + } + } + // we test again with ASCII char only + if (!newpart.match(hostnamePartPattern)) { + var validParts = hostparts.slice(0, i); + var notHost = hostparts.slice(i + 1); + var bit = part.match(hostnamePartStart); + if (bit) { + validParts.push(bit[1]); + notHost.unshift(bit[2]); + } + if (notHost.length) { + rest = notHost.join('.') + rest; + } + this.hostname = validParts.join('.'); + break; + } + } + } + } + + if (this.hostname.length > hostnameMaxLen) { + this.hostname = ''; + } + + // strip [ and ] from the hostname + // the host field still retains them, though + if (ipv6Hostname) { + this.hostname = this.hostname.substr(1, this.hostname.length - 2); + } + } + + // chop off from the tail first. + var hash = rest.indexOf('#'); + if (hash !== -1) { + // got a fragment string. + this.hash = rest.substr(hash); + rest = rest.slice(0, hash); + } + var qm = rest.indexOf('?'); + if (qm !== -1) { + this.search = rest.substr(qm); + rest = rest.slice(0, qm); + } + if (rest) { this.pathname = rest; } + if (slashedProtocol[lowerProto] && + this.hostname && !this.pathname) { + this.pathname = ''; + } + + return this; +}; + +Url.prototype.parseHost = function(host) { + var port = portPattern.exec(host); + if (port) { + port = port[0]; + if (port !== ':') { + this.port = port.substr(1); + } + host = host.substr(0, host.length - port.length); + } + if (host) { this.hostname = host; } +}; + +module.exports = urlParse; + +},{}],86:[function(require,module,exports){ +module.exports=/[\0-\x1F\x7F-\x9F]/ +},{}],87:[function(require,module,exports){ +module.exports=/[\xAD\u0600-\u0605\u061C\u06DD\u070F\u180E\u200B-\u200F\u202A-\u202E\u2060-\u2064\u2066-\u206F\uFEFF\uFFF9-\uFFFB]|\uD804\uDCBD|\uD82F[\uDCA0-\uDCA3]|\uD834[\uDD73-\uDD7A]|\uDB40[\uDC01\uDC20-\uDC7F]/ +},{}],88:[function(require,module,exports){ +module.exports=/[!-#%-\*,-/:;\?@\[-\]_\{\}\xA1\xA7\xAB\xB6\xB7\xBB\xBF\u037E\u0387\u055A-\u055F\u0589\u058A\u05BE\u05C0\u05C3\u05C6\u05F3\u05F4\u0609\u060A\u060C\u060D\u061B\u061E\u061F\u066A-\u066D\u06D4\u0700-\u070D\u07F7-\u07F9\u0830-\u083E\u085E\u0964\u0965\u0970\u0AF0\u0DF4\u0E4F\u0E5A\u0E5B\u0F04-\u0F12\u0F14\u0F3A-\u0F3D\u0F85\u0FD0-\u0FD4\u0FD9\u0FDA\u104A-\u104F\u10FB\u1360-\u1368\u1400\u166D\u166E\u169B\u169C\u16EB-\u16ED\u1735\u1736\u17D4-\u17D6\u17D8-\u17DA\u1800-\u180A\u1944\u1945\u1A1E\u1A1F\u1AA0-\u1AA6\u1AA8-\u1AAD\u1B5A-\u1B60\u1BFC-\u1BFF\u1C3B-\u1C3F\u1C7E\u1C7F\u1CC0-\u1CC7\u1CD3\u2010-\u2027\u2030-\u2043\u2045-\u2051\u2053-\u205E\u207D\u207E\u208D\u208E\u2308-\u230B\u2329\u232A\u2768-\u2775\u27C5\u27C6\u27E6-\u27EF\u2983-\u2998\u29D8-\u29DB\u29FC\u29FD\u2CF9-\u2CFC\u2CFE\u2CFF\u2D70\u2E00-\u2E2E\u2E30-\u2E42\u3001-\u3003\u3008-\u3011\u3014-\u301F\u3030\u303D\u30A0\u30FB\uA4FE\uA4FF\uA60D-\uA60F\uA673\uA67E\uA6F2-\uA6F7\uA874-\uA877\uA8CE\uA8CF\uA8F8-\uA8FA\uA92E\uA92F\uA95F\uA9C1-\uA9CD\uA9DE\uA9DF\uAA5C-\uAA5F\uAADE\uAADF\uAAF0\uAAF1\uABEB\uFD3E\uFD3F\uFE10-\uFE19\uFE30-\uFE52\uFE54-\uFE61\uFE63\uFE68\uFE6A\uFE6B\uFF01-\uFF03\uFF05-\uFF0A\uFF0C-\uFF0F\uFF1A\uFF1B\uFF1F\uFF20\uFF3B-\uFF3D\uFF3F\uFF5B\uFF5D\uFF5F-\uFF65]|\uD800[\uDD00-\uDD02\uDF9F\uDFD0]|\uD801\uDD6F|\uD802[\uDC57\uDD1F\uDD3F\uDE50-\uDE58\uDE7F\uDEF0-\uDEF6\uDF39-\uDF3F\uDF99-\uDF9C]|\uD804[\uDC47-\uDC4D\uDCBB\uDCBC\uDCBE-\uDCC1\uDD40-\uDD43\uDD74\uDD75\uDDC5-\uDDC8\uDDCD\uDE38-\uDE3D]|\uD805[\uDCC6\uDDC1-\uDDC9\uDE41-\uDE43]|\uD809[\uDC70-\uDC74]|\uD81A[\uDE6E\uDE6F\uDEF5\uDF37-\uDF3B\uDF44]|\uD82F\uDC9F/ +},{}],89:[function(require,module,exports){ +module.exports=/[ \xA0\u1680\u2000-\u200A\u2028\u2029\u202F\u205F\u3000]/ +},{}],90:[function(require,module,exports){ + +module.exports.Any = require('./properties/Any/regex'); +module.exports.Cc = require('./categories/Cc/regex'); +module.exports.Cf = require('./categories/Cf/regex'); +module.exports.P = require('./categories/P/regex'); +module.exports.Z = require('./categories/Z/regex'); + +},{"./categories/Cc/regex":86,"./categories/Cf/regex":87,"./categories/P/regex":88,"./categories/Z/regex":89,"./properties/Any/regex":91}],91:[function(require,module,exports){ +module.exports=/[\0-\uD7FF\uDC00-\uFFFF]|[\uD800-\uDBFF][\uDC00-\uDFFF]|[\uD800-\uDBFF]/ +},{}],92:[function(require,module,exports){ +(function (global){ +/*! https://mths.be/punycode v1.4.0 by @mathias */ +;(function(root) { + + /** Detect free variables */ + var freeExports = typeof exports == 'object' && exports && + !exports.nodeType && exports; + var freeModule = typeof module == 'object' && module && + !module.nodeType && module; + var freeGlobal = typeof global == 'object' && global; + if ( + freeGlobal.global === freeGlobal || + freeGlobal.window === freeGlobal || + freeGlobal.self === freeGlobal + ) { + root = freeGlobal; + } + + /** + * The `punycode` object. + * @name punycode + * @type Object + */ + var punycode, + + /** Highest positive signed 32-bit float value */ + maxInt = 2147483647, // aka. 0x7FFFFFFF or 2^31-1 + + /** Bootstring parameters */ + base = 36, + tMin = 1, + tMax = 26, + skew = 38, + damp = 700, + initialBias = 72, + initialN = 128, // 0x80 + delimiter = '-', // '\x2D' + + /** Regular expressions */ + regexPunycode = /^xn--/, + regexNonASCII = /[^\x20-\x7E]/, // unprintable ASCII chars + non-ASCII chars + regexSeparators = /[\x2E\u3002\uFF0E\uFF61]/g, // RFC 3490 separators + + /** Error messages */ + errors = { + 'overflow': 'Overflow: input needs wider integers to process', + 'not-basic': 'Illegal input >= 0x80 (not a basic code point)', + 'invalid-input': 'Invalid input' + }, + + /** Convenience shortcuts */ + baseMinusTMin = base - tMin, + floor = Math.floor, + stringFromCharCode = String.fromCharCode, + + /** Temporary variable */ + key; + + /*--------------------------------------------------------------------------*/ + + /** + * A generic error utility function. + * @private + * @param {String} type The error type. + * @returns {Error} Throws a `RangeError` with the applicable error message. + */ + function error(type) { + throw new RangeError(errors[type]); + } + + /** + * A generic `Array#map` utility function. + * @private + * @param {Array} array The array to iterate over. + * @param {Function} callback The function that gets called for every array + * item. + * @returns {Array} A new array of values returned by the callback function. + */ + function map(array, fn) { + var length = array.length; + var result = []; + while (length--) { + result[length] = fn(array[length]); + } + return result; + } + + /** + * A simple `Array#map`-like wrapper to work with domain name strings or email + * addresses. + * @private + * @param {String} domain The domain name or email address. + * @param {Function} callback The function that gets called for every + * character. + * @returns {Array} A new string of characters returned by the callback + * function. + */ + function mapDomain(string, fn) { + var parts = string.split('@'); + var result = ''; + if (parts.length > 1) { + // In email addresses, only the domain name should be punycoded. Leave + // the local part (i.e. everything up to `@`) intact. + result = parts[0] + '@'; + string = parts[1]; + } + // Avoid `split(regex)` for IE8 compatibility. See #17. + string = string.replace(regexSeparators, '\x2E'); + var labels = string.split('.'); + var encoded = map(labels, fn).join('.'); + return result + encoded; + } + + /** + * Creates an array containing the numeric code points of each Unicode + * character in the string. While JavaScript uses UCS-2 internally, + * this function will convert a pair of surrogate halves (each of which + * UCS-2 exposes as separate characters) into a single code point, + * matching UTF-16. + * @see `punycode.ucs2.encode` + * @see + * @memberOf punycode.ucs2 + * @name decode + * @param {String} string The Unicode input string (UCS-2). + * @returns {Array} The new array of code points. + */ + function ucs2decode(string) { + var output = [], + counter = 0, + length = string.length, + value, + extra; + while (counter < length) { + value = string.charCodeAt(counter++); + if (value >= 0xD800 && value <= 0xDBFF && counter < length) { + // high surrogate, and there is a next character + extra = string.charCodeAt(counter++); + if ((extra & 0xFC00) == 0xDC00) { // low surrogate + output.push(((value & 0x3FF) << 10) + (extra & 0x3FF) + 0x10000); + } else { + // unmatched surrogate; only append this code unit, in case the next + // code unit is the high surrogate of a surrogate pair + output.push(value); + counter--; + } + } else { + output.push(value); + } + } + return output; + } + + /** + * Creates a string based on an array of numeric code points. + * @see `punycode.ucs2.decode` + * @memberOf punycode.ucs2 + * @name encode + * @param {Array} codePoints The array of numeric code points. + * @returns {String} The new Unicode string (UCS-2). + */ + function ucs2encode(array) { + return map(array, function(value) { + var output = ''; + if (value > 0xFFFF) { + value -= 0x10000; + output += stringFromCharCode(value >>> 10 & 0x3FF | 0xD800); + value = 0xDC00 | value & 0x3FF; + } + output += stringFromCharCode(value); + return output; + }).join(''); + } + + /** + * Converts a basic code point into a digit/integer. + * @see `digitToBasic()` + * @private + * @param {Number} codePoint The basic numeric code point value. + * @returns {Number} The numeric value of a basic code point (for use in + * representing integers) in the range `0` to `base - 1`, or `base` if + * the code point does not represent a value. + */ + function basicToDigit(codePoint) { + if (codePoint - 48 < 10) { + return codePoint - 22; + } + if (codePoint - 65 < 26) { + return codePoint - 65; + } + if (codePoint - 97 < 26) { + return codePoint - 97; + } + return base; + } + + /** + * Converts a digit/integer into a basic code point. + * @see `basicToDigit()` + * @private + * @param {Number} digit The numeric value of a basic code point. + * @returns {Number} The basic code point whose value (when used for + * representing integers) is `digit`, which needs to be in the range + * `0` to `base - 1`. If `flag` is non-zero, the uppercase form is + * used; else, the lowercase form is used. The behavior is undefined + * if `flag` is non-zero and `digit` has no uppercase form. + */ + function digitToBasic(digit, flag) { + // 0..25 map to ASCII a..z or A..Z + // 26..35 map to ASCII 0..9 + return digit + 22 + 75 * (digit < 26) - ((flag != 0) << 5); + } + + /** + * Bias adaptation function as per section 3.4 of RFC 3492. + * https://tools.ietf.org/html/rfc3492#section-3.4 + * @private + */ + function adapt(delta, numPoints, firstTime) { + var k = 0; + delta = firstTime ? floor(delta / damp) : delta >> 1; + delta += floor(delta / numPoints); + for (/* no initialization */; delta > baseMinusTMin * tMax >> 1; k += base) { + delta = floor(delta / baseMinusTMin); + } + return floor(k + (baseMinusTMin + 1) * delta / (delta + skew)); + } + + /** + * Converts a Punycode string of ASCII-only symbols to a string of Unicode + * symbols. + * @memberOf punycode + * @param {String} input The Punycode string of ASCII-only symbols. + * @returns {String} The resulting string of Unicode symbols. + */ + function decode(input) { + // Don't use UCS-2 + var output = [], + inputLength = input.length, + out, + i = 0, + n = initialN, + bias = initialBias, + basic, + j, + index, + oldi, + w, + k, + digit, + t, + /** Cached calculation results */ + baseMinusT; + + // Handle the basic code points: let `basic` be the number of input code + // points before the last delimiter, or `0` if there is none, then copy + // the first basic code points to the output. + + basic = input.lastIndexOf(delimiter); + if (basic < 0) { + basic = 0; + } + + for (j = 0; j < basic; ++j) { + // if it's not a basic code point + if (input.charCodeAt(j) >= 0x80) { + error('not-basic'); + } + output.push(input.charCodeAt(j)); + } + + // Main decoding loop: start just after the last delimiter if any basic code + // points were copied; start at the beginning otherwise. + + for (index = basic > 0 ? basic + 1 : 0; index < inputLength; /* no final expression */) { + + // `index` is the index of the next character to be consumed. + // Decode a generalized variable-length integer into `delta`, + // which gets added to `i`. The overflow checking is easier + // if we increase `i` as we go, then subtract off its starting + // value at the end to obtain `delta`. + for (oldi = i, w = 1, k = base; /* no condition */; k += base) { + + if (index >= inputLength) { + error('invalid-input'); + } + + digit = basicToDigit(input.charCodeAt(index++)); + + if (digit >= base || digit > floor((maxInt - i) / w)) { + error('overflow'); + } + + i += digit * w; + t = k <= bias ? tMin : (k >= bias + tMax ? tMax : k - bias); + + if (digit < t) { + break; + } + + baseMinusT = base - t; + if (w > floor(maxInt / baseMinusT)) { + error('overflow'); + } + + w *= baseMinusT; + + } + + out = output.length + 1; + bias = adapt(i - oldi, out, oldi == 0); + + // `i` was supposed to wrap around from `out` to `0`, + // incrementing `n` each time, so we'll fix that now: + if (floor(i / out) > maxInt - n) { + error('overflow'); + } + + n += floor(i / out); + i %= out; + + // Insert `n` at position `i` of the output + output.splice(i++, 0, n); + + } + + return ucs2encode(output); + } + + /** + * Converts a string of Unicode symbols (e.g. a domain name label) to a + * Punycode string of ASCII-only symbols. + * @memberOf punycode + * @param {String} input The string of Unicode symbols. + * @returns {String} The resulting Punycode string of ASCII-only symbols. + */ + function encode(input) { + var n, + delta, + handledCPCount, + basicLength, + bias, + j, + m, + q, + k, + t, + currentValue, + output = [], + /** `inputLength` will hold the number of code points in `input`. */ + inputLength, + /** Cached calculation results */ + handledCPCountPlusOne, + baseMinusT, + qMinusT; + + // Convert the input in UCS-2 to Unicode + input = ucs2decode(input); + + // Cache the length + inputLength = input.length; + + // Initialize the state + n = initialN; + delta = 0; + bias = initialBias; + + // Handle the basic code points + for (j = 0; j < inputLength; ++j) { + currentValue = input[j]; + if (currentValue < 0x80) { + output.push(stringFromCharCode(currentValue)); + } + } + + handledCPCount = basicLength = output.length; + + // `handledCPCount` is the number of code points that have been handled; + // `basicLength` is the number of basic code points. + + // Finish the basic string - if it is not empty - with a delimiter + if (basicLength) { + output.push(delimiter); + } + + // Main encoding loop: + while (handledCPCount < inputLength) { + + // All non-basic code points < n have been handled already. Find the next + // larger one: + for (m = maxInt, j = 0; j < inputLength; ++j) { + currentValue = input[j]; + if (currentValue >= n && currentValue < m) { + m = currentValue; + } + } + + // Increase `delta` enough to advance the decoder's state to , + // but guard against overflow + handledCPCountPlusOne = handledCPCount + 1; + if (m - n > floor((maxInt - delta) / handledCPCountPlusOne)) { + error('overflow'); + } + + delta += (m - n) * handledCPCountPlusOne; + n = m; + + for (j = 0; j < inputLength; ++j) { + currentValue = input[j]; + + if (currentValue < n && ++delta > maxInt) { + error('overflow'); + } + + if (currentValue == n) { + // Represent delta as a generalized variable-length integer + for (q = delta, k = base; /* no condition */; k += base) { + t = k <= bias ? tMin : (k >= bias + tMax ? tMax : k - bias); + if (q < t) { + break; + } + qMinusT = q - t; + baseMinusT = base - t; + output.push( + stringFromCharCode(digitToBasic(t + qMinusT % baseMinusT, 0)) + ); + q = floor(qMinusT / baseMinusT); + } + + output.push(stringFromCharCode(digitToBasic(q, 0))); + bias = adapt(delta, handledCPCountPlusOne, handledCPCount == basicLength); + delta = 0; + ++handledCPCount; + } + } + + ++delta; + ++n; + + } + return output.join(''); + } + + /** + * Converts a Punycode string representing a domain name or an email address + * to Unicode. Only the Punycoded parts of the input will be converted, i.e. + * it doesn't matter if you call it on a string that has already been + * converted to Unicode. + * @memberOf punycode + * @param {String} input The Punycoded domain name or email address to + * convert to Unicode. + * @returns {String} The Unicode representation of the given Punycode + * string. + */ + function toUnicode(input) { + return mapDomain(input, function(string) { + return regexPunycode.test(string) + ? decode(string.slice(4).toLowerCase()) + : string; + }); + } + + /** + * Converts a Unicode string representing a domain name or an email address to + * Punycode. Only the non-ASCII parts of the domain name will be converted, + * i.e. it doesn't matter if you call it with a domain that's already in + * ASCII. + * @memberOf punycode + * @param {String} input The domain name or email address to convert, as a + * Unicode string. + * @returns {String} The Punycode representation of the given domain name or + * email address. + */ + function toASCII(input) { + return mapDomain(input, function(string) { + return regexNonASCII.test(string) + ? 'xn--' + encode(string) + : string; + }); + } + + /*--------------------------------------------------------------------------*/ + + /** Define the public API */ + punycode = { + /** + * A string representing the current Punycode.js version number. + * @memberOf punycode + * @type String + */ + 'version': '1.3.2', + /** + * An object of methods to convert from JavaScript's internal character + * representation (UCS-2) to Unicode code points, and back. + * @see + * @memberOf punycode + * @type Object + */ + 'ucs2': { + 'decode': ucs2decode, + 'encode': ucs2encode + }, + 'decode': decode, + 'encode': encode, + 'toASCII': toASCII, + 'toUnicode': toUnicode + }; + + /** Expose `punycode` */ + // Some AMD build optimizers, like r.js, check for specific condition patterns + // like the following: + if ( + typeof define == 'function' && + typeof define.amd == 'object' && + define.amd + ) { + define('punycode', function() { + return punycode; + }); + } else if (freeExports && freeModule) { + if (module.exports == freeExports) { + // in Node.js, io.js, or RingoJS v0.8.0+ + freeModule.exports = punycode; + } else { + // in Narwhal or RingoJS v0.7.0- + for (key in punycode) { + punycode.hasOwnProperty(key) && (freeExports[key] = punycode[key]); + } + } + } else { + // in Rhino or a web browser + root.punycode = punycode; + } + +}(this)); + +}).call(this,typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {}) +},{}]},{},[1]);