| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 /** | 5 /** |
| 6 * @fileoverview DOM utility functions to aid in math expressions navigation. | 6 * @fileoverview DOM utility functions to aid in math expressions navigation. |
| 7 */ | 7 */ |
| 8 | 8 |
| 9 goog.provide('cvox.MathUtil'); | 9 goog.provide('cvox.MathUtil'); |
| 10 | 10 |
| (...skipping 16 matching lines...) Expand all Loading... |
| 27 /** | 27 /** |
| 28 * Checks if a node is in a given class of MathJax nodes. | 28 * Checks if a node is in a given class of MathJax nodes. |
| 29 * @private | 29 * @private |
| 30 * @param {!Node} node The node to test. | 30 * @param {!Node} node The node to test. |
| 31 * @param {Array<string>} tags List of tag names. | 31 * @param {Array<string>} tags List of tag names. |
| 32 * @return {boolean} True if node has a tag name included in tags. | 32 * @return {boolean} True if node has a tag name included in tags. |
| 33 */ | 33 */ |
| 34 cvox.MathUtil.isMathjaxNodeOfClass_ = function(node, tags) { | 34 cvox.MathUtil.isMathjaxNodeOfClass_ = function(node, tags) { |
| 35 if (node.tagName == 'SPAN') { | 35 if (node.tagName == 'SPAN') { |
| 36 var classes = node.className.split(' '); | 36 var classes = node.className.split(' '); |
| 37 return classes.some(function(x) | 37 return classes.some(function(x) { |
| 38 {return tags.indexOf(x.toUpperCase()) != -1;}); | 38 return tags.indexOf(x.toUpperCase()) != -1; |
| 39 }); |
| 39 } | 40 } |
| 40 return false; | 41 return false; |
| 41 }; | 42 }; |
| 42 | 43 |
| 43 | 44 |
| 44 /** | 45 /** |
| 45 * Checks if a node is an element node that belongs to a given class | 46 * Checks if a node is an element node that belongs to a given class |
| 46 * of MathML or MathJax nodes. | 47 * of MathML or MathJax nodes. |
| 47 * @private | 48 * @private |
| 48 * @param {!Node} node The node to test. | 49 * @param {!Node} node The node to test. |
| 49 * @param {Array<string>} tags List of tag names. | 50 * @param {Array<string>} tags List of tag names. |
| 50 * @return {boolean} True if node has a tag name included in tags. | 51 * @return {boolean} True if node has a tag name included in tags. |
| 51 */ | 52 */ |
| 52 cvox.MathUtil.isMathNodeOfClass_ = function(node, tags) { | 53 cvox.MathUtil.isMathNodeOfClass_ = function(node, tags) { |
| 53 return (node.nodeType == Node.ELEMENT_NODE && | 54 return ( |
| 54 (cvox.MathUtil.isMathmlNodeOfClass_(node, tags) || | 55 node.nodeType == Node.ELEMENT_NODE && |
| 55 cvox.MathUtil.isMathjaxNodeOfClass_(node, tags))); | 56 (cvox.MathUtil.isMathmlNodeOfClass_(node, tags) || |
| 57 cvox.MathUtil.isMathjaxNodeOfClass_(node, tags))); |
| 56 }; | 58 }; |
| 57 | 59 |
| 58 | 60 |
| 59 /** | 61 /** |
| 60 * Array of MathML Token Elements. | 62 * Array of MathML Token Elements. |
| 61 * @type {!Array<string>} | 63 * @type {!Array<string>} |
| 62 */ | 64 */ |
| 63 cvox.MathUtil.TOKEN_LIST = ['MI', 'MN', 'MO', 'MTEXT', 'MSPACE', 'MS']; | 65 cvox.MathUtil.TOKEN_LIST = ['MI', 'MN', 'MO', 'MTEXT', 'MSPACE', 'MS']; |
| 64 | 66 |
| 65 | 67 |
| (...skipping 11 matching lines...) Expand all Loading... |
| 77 */ | 79 */ |
| 78 cvox.MathUtil.isToken = function(element) { | 80 cvox.MathUtil.isToken = function(element) { |
| 79 return cvox.MathUtil.isMathNodeOfClass_(element, cvox.MathUtil.TOKEN_LIST); | 81 return cvox.MathUtil.isMathNodeOfClass_(element, cvox.MathUtil.TOKEN_LIST); |
| 80 }; | 82 }; |
| 81 | 83 |
| 82 | 84 |
| 83 /** | 85 /** |
| 84 * Array of MathML Layout Schemata. | 86 * Array of MathML Layout Schemata. |
| 85 * @type {!Array<string>} | 87 * @type {!Array<string>} |
| 86 */ | 88 */ |
| 87 cvox.MathUtil.LAYOUT_LIST = ['MROW', 'MFRAC', 'MSQRT', 'MROOT', 'MSTYLE', | 89 cvox.MathUtil.LAYOUT_LIST = [ |
| 88 'MERROR', 'MPADDED', 'MPHANTOM', 'MFENCED', | 90 'MROW', 'MFRAC', 'MSQRT', 'MROOT', 'MSTYLE', 'MERROR', 'MPADDED', 'MPHANTOM', |
| 89 'MENCLOSE']; | 91 'MFENCED', 'MENCLOSE' |
| 92 ]; |
| 90 | 93 |
| 91 | 94 |
| 92 /** | 95 /** |
| 93 * Checks if an element of a math expression is a Layout Schema. | 96 * Checks if an element of a math expression is a Layout Schema. |
| 94 * Layout elements are the following: | 97 * Layout elements are the following: |
| 95 * <mrow> group any number of sub-expressions horizontally | 98 * <mrow> group any number of sub-expressions horizontally |
| 96 * <mfrac> form a fraction from two sub-expressions | 99 * <mfrac> form a fraction from two sub-expressions |
| 97 * <msqrt> form a square root (radical without an index) | 100 * <msqrt> form a square root (radical without an index) |
| 98 * <mroot> form a radical with specified index | 101 * <mroot> form a radical with specified index |
| 99 * <mstyle> style change | 102 * <mstyle> style change |
| 100 * <merror> enclose a syntax error message from a preprocessor | 103 * <merror> enclose a syntax error message from a preprocessor |
| 101 * <mpadded> adjust space around content | 104 * <mpadded> adjust space around content |
| 102 * <mphantom> make content invisible but preserve its size | 105 * <mphantom> make content invisible but preserve its size |
| 103 * <mfenced> surround content with a pair of fences | 106 * <mfenced> surround content with a pair of fences |
| 104 * <menclose> enclose content with a stretching symbol such as a long | 107 * <menclose> enclose content with a stretching symbol such as a long |
| 105 * division sign. | 108 * division sign. |
| 106 * @param {!Node} element The element of the math expression. | 109 * @param {!Node} element The element of the math expression. |
| 107 * @return {boolean} True if element is a layout schema. | 110 * @return {boolean} True if element is a layout schema. |
| 108 */ | 111 */ |
| 109 cvox.MathUtil.isLayout = function(element) { | 112 cvox.MathUtil.isLayout = function(element) { |
| 110 return cvox.MathUtil.isMathNodeOfClass_(element, cvox.MathUtil.LAYOUT_LIST); | 113 return cvox.MathUtil.isMathNodeOfClass_(element, cvox.MathUtil.LAYOUT_LIST); |
| 111 }; | 114 }; |
| 112 | 115 |
| 113 | 116 |
| 114 /** | 117 /** |
| 115 * Array of MathML Script Schemata. | 118 * Array of MathML Script Schemata. |
| 116 * @type {!Array<string>} | 119 * @type {!Array<string>} |
| 117 */ | 120 */ |
| 118 cvox.MathUtil.SCRIPT_LIST = ['MSUB', 'MSUP', 'MSUBSUP', 'MUNDER', 'MOVER', | 121 cvox.MathUtil.SCRIPT_LIST = [ |
| 119 'MUNDEROVER', 'MMULTISCRIPTS', 'MPRESCRIPTS']; | 122 'MSUB', 'MSUP', 'MSUBSUP', 'MUNDER', 'MOVER', 'MUNDEROVER', 'MMULTISCRIPTS', |
| 123 'MPRESCRIPTS' |
| 124 ]; |
| 120 | 125 |
| 121 | 126 |
| 122 /** | 127 /** |
| 123 * Checks if an element of a math expression is a Script Schema. | 128 * Checks if an element of a math expression is a Script Schema. |
| 124 * Script elements are the following: | 129 * Script elements are the following: |
| 125 * <msub> attach a subscript to a base. | 130 * <msub> attach a subscript to a base. |
| 126 * <msup> attach a superscript to a base. | 131 * <msup> attach a superscript to a base. |
| 127 * <msubsup> attach a subscript-superscript pair to a base. | 132 * <msubsup> attach a subscript-superscript pair to a base. |
| 128 * <munder> attach an underscript to a base. | 133 * <munder> attach an underscript to a base. |
| 129 * <mover> attach an overscript to a base. | 134 * <mover> attach an overscript to a base. |
| 130 * <munderover> attach an underscript-overscript pair to a base. | 135 * <munderover> attach an underscript-overscript pair to a base. |
| 131 * <mmultiscripts> attach prescripts and tensor indices to a base. | 136 * <mmultiscripts> attach prescripts and tensor indices to a base. |
| 132 * Prescripts are optional. | 137 * Prescripts are optional. |
| 133 * <mprescripts> two elements prescripts of mmultiscripts. Only makes sense | 138 * <mprescripts> two elements prescripts of mmultiscripts. Only makes sense |
| 134 * in that environment (although not illegal outside)! Two | 139 * in that environment (although not illegal outside)! Two |
| 135 * arguments mandatory (can be <none/>). | 140 * arguments mandatory (can be <none/>). |
| 136 * @param {!Node} element The element of the math expression. | 141 * @param {!Node} element The element of the math expression. |
| 137 * @return {boolean} True if element is a script schema. | 142 * @return {boolean} True if element is a script schema. |
| 138 */ | 143 */ |
| 139 cvox.MathUtil.isScript = function(element) { | 144 cvox.MathUtil.isScript = function(element) { |
| 140 return cvox.MathUtil.isMathNodeOfClass_(element, cvox.MathUtil.SCRIPT_LIST); | 145 return cvox.MathUtil.isMathNodeOfClass_(element, cvox.MathUtil.SCRIPT_LIST); |
| 141 }; | 146 }; |
| 142 | 147 |
| 143 | 148 |
| 144 /** | 149 /** |
| 145 * Array of MathML Table and Matrix tokens. | 150 * Array of MathML Table and Matrix tokens. |
| 146 * @type {!Array<string>} | 151 * @type {!Array<string>} |
| 147 */ | 152 */ |
| 148 cvox.MathUtil.TABLES_LIST = ['MTABLE', 'MLABELEDTR', 'MTR', 'MTD', | 153 cvox.MathUtil.TABLES_LIST = |
| 149 'MALIGNGROUP', 'MALIGNMARK']; | 154 ['MTABLE', 'MLABELEDTR', 'MTR', 'MTD', 'MALIGNGROUP', 'MALIGNMARK']; |
| 150 | 155 |
| 151 | 156 |
| 152 /** | 157 /** |
| 153 * Checks if an element of a math expression is a Tables Schema. | 158 * Checks if an element of a math expression is a Tables Schema. |
| 154 * Tables elements are the following: | 159 * Tables elements are the following: |
| 155 * <mtable> table or matrix. | 160 * <mtable> table or matrix. |
| 156 * <mlabeledtr> row in a table or matrix with a label or equation number. | 161 * <mlabeledtr> row in a table or matrix with a label or equation number. |
| 157 * <mtr> row in a table or matrix. | 162 * <mtr> row in a table or matrix. |
| 158 * <mtd> one entry in a table or matrix. | 163 * <mtd> one entry in a table or matrix. |
| 159 * <maligngroup> and | 164 * <maligngroup> and |
| 160 * <malignmark> alignment markers. | 165 * <malignmark> alignment markers. |
| 161 * @param {!Node} element The element of the math expression. | 166 * @param {!Node} element The element of the math expression. |
| 162 * @return {boolean} True if element is a tables schema. | 167 * @return {boolean} True if element is a tables schema. |
| 163 */ | 168 */ |
| 164 cvox.MathUtil.isTables = function(element) { | 169 cvox.MathUtil.isTables = function(element) { |
| 165 return cvox.MathUtil.isMathNodeOfClass_(element, cvox.MathUtil.TABLES_LIST); | 170 return cvox.MathUtil.isMathNodeOfClass_(element, cvox.MathUtil.TABLES_LIST); |
| 166 }; | 171 }; |
| 167 | 172 |
| 168 | 173 |
| 169 /** | 174 /** |
| 170 * Array of MathML Elementary Layout Schemata. | 175 * Array of MathML Elementary Layout Schemata. |
| 171 * @type {!Array<string>} | 176 * @type {!Array<string>} |
| 172 */ | 177 */ |
| 173 cvox.MathUtil.ELEMENTARY_LIST = ['MSTACK', 'MLONGDIV', 'MSGROUP', 'MSROW', | 178 cvox.MathUtil.ELEMENTARY_LIST = [ |
| 174 'MSCARRIES', 'MSCARRY', 'MSLINE']; | 179 'MSTACK', 'MLONGDIV', 'MSGROUP', 'MSROW', 'MSCARRIES', 'MSCARRY', 'MSLINE' |
| 180 ]; |
| 175 | 181 |
| 176 | 182 |
| 177 /** | 183 /** |
| 178 * Checks if an element of a math expression is a Elementary Schema. | 184 * Checks if an element of a math expression is a Elementary Schema. |
| 179 * Elementary elements are the following: | 185 * Elementary elements are the following: |
| 180 * <mstack> columns of aligned characters. | 186 * <mstack> columns of aligned characters. |
| 181 * <mlongdiv> similar to msgroup, with the addition of a divisor and result. | 187 * <mlongdiv> similar to msgroup, with the addition of a divisor and result. |
| 182 * <msgroup> a group of rows in an mstack that are shifted by similar amounts. | 188 * <msgroup> a group of rows in an mstack that are shifted by similar amounts. |
| 183 * <msrow> a row in an mstack. | 189 * <msrow> a row in an mstack. |
| 184 * <mscarries> row in an mstack that whose contents represent carries | 190 * <mscarries> row in an mstack that whose contents represent carries |
| 185 * or borrows. | 191 * or borrows. |
| 186 * <mscarry> one entry in an mscarries. | 192 * <mscarry> one entry in an mscarries. |
| 187 * <msline> horizontal line inside of mstack. | 193 * <msline> horizontal line inside of mstack. |
| 188 * @param {!Node} element The element of the math expression. | 194 * @param {!Node} element The element of the math expression. |
| 189 * @return {boolean} True if element is a elementary schema. | 195 * @return {boolean} True if element is a elementary schema. |
| 190 */ | 196 */ |
| 191 cvox.MathUtil.isElementary = function(element) { | 197 cvox.MathUtil.isElementary = function(element) { |
| 192 return cvox.MathUtil.isMathNodeOfClass_(element, | 198 return cvox.MathUtil.isMathNodeOfClass_( |
| 193 cvox.MathUtil.ELEMENTARY_LIST); | 199 element, cvox.MathUtil.ELEMENTARY_LIST); |
| 194 }; | 200 }; |
| 195 | 201 |
| 196 | 202 |
| 197 /** | 203 /** |
| 198 * Array of all valid tags in a MathML expression. | 204 * Array of all valid tags in a MathML expression. |
| 199 * This is a union of all other token lists. | 205 * This is a union of all other token lists. |
| 200 * @type {!Array<string>} | 206 * @type {!Array<string>} |
| 201 */ | 207 */ |
| 202 cvox.MathUtil.MATHML_TAG_LIST = [cvox.MathUtil.TOKEN_LIST, | 208 cvox.MathUtil.MATHML_TAG_LIST = [ |
| 203 cvox.MathUtil.LAYOUT_LIST, | 209 cvox.MathUtil.TOKEN_LIST, cvox.MathUtil.LAYOUT_LIST, |
| 204 cvox.MathUtil.SCRIPT_LIST, | 210 cvox.MathUtil.SCRIPT_LIST, cvox.MathUtil.TABLES_LIST, |
| 205 cvox.MathUtil.TABLES_LIST, | 211 cvox.MathUtil.ELEMENTARY_LIST |
| 206 cvox.MathUtil.ELEMENTARY_LIST].reduce( | 212 ].reduce(function(x, y) { |
| 207 function(x, y) { return x.concat(y); }); | 213 return x.concat(y); |
| 214 }); |
| 208 | 215 |
| 209 | 216 |
| 210 /** | 217 /** |
| 211 * Checks if a node is valid element of a MathML expression. | 218 * Checks if a node is valid element of a MathML expression. |
| 212 * @param {!Node} element The element of the math expression. | 219 * @param {!Node} element The element of the math expression. |
| 213 * @return {boolean} True if element has a valid MathML tag. | 220 * @return {boolean} True if element has a valid MathML tag. |
| 214 */ | 221 */ |
| 215 cvox.MathUtil.isMathmlTag = function(element) { | 222 cvox.MathUtil.isMathmlTag = function(element) { |
| 216 return cvox.MathUtil.isMathNodeOfClass_(element, | 223 return cvox.MathUtil.isMathNodeOfClass_( |
| 217 cvox.MathUtil.MATHML_TAG_LIST); | 224 element, cvox.MathUtil.MATHML_TAG_LIST); |
| 218 }; | 225 }; |
| 219 | 226 |
| 220 | 227 |
| 221 /** | 228 /** |
| 222 * Array of MathML Whitespace and Alignment tokens. | 229 * Array of MathML Whitespace and Alignment tokens. |
| 223 * These are elements that can occur in the other token lists. | 230 * These are elements that can occur in the other token lists. |
| 224 * @type {!Array<string>} | 231 * @type {!Array<string>} |
| 225 */ | 232 */ |
| 226 cvox.MathUtil.WHITESPACE_LIST = ['MSROW', 'MROW', 'MSPACE', | 233 cvox.MathUtil.WHITESPACE_LIST = |
| 227 'MPHANTOM', 'MPADDED']; | 234 ['MSROW', 'MROW', 'MSPACE', 'MPHANTOM', 'MPADDED']; |
| 228 | 235 |
| 229 | 236 |
| 230 /** | 237 /** |
| 231 * Checks if an element of a math expression is whitespace or an | 238 * Checks if an element of a math expression is whitespace or an |
| 232 * alignment marker. | 239 * alignment marker. |
| 233 * @param {!Node} element The element of the math expression. | 240 * @param {!Node} element The element of the math expression. |
| 234 * @return {boolean} True if element is a whitespace node. | 241 * @return {boolean} True if element is a whitespace node. |
| 235 */ | 242 */ |
| 236 cvox.MathUtil.isWhitespace = function(element) { | 243 cvox.MathUtil.isWhitespace = function(element) { |
| 237 return cvox.MathUtil.isMathNodeOfClass_(element, | 244 return cvox.MathUtil.isMathNodeOfClass_( |
| 238 cvox.MathUtil.WHITESPACE_LIST); | 245 element, cvox.MathUtil.WHITESPACE_LIST); |
| 239 }; | 246 }; |
| 240 | 247 |
| 241 | 248 |
| 242 /** | 249 /** |
| 243 * Checks if an element of a math expression is a legal mathml markup element | 250 * Checks if an element of a math expression is a legal mathml markup element |
| 244 * but not a whitespace or an alignment marker. | 251 * but not a whitespace or an alignment marker. |
| 245 * @param {!Node} element The element of the math expression. | 252 * @param {!Node} element The element of the math expression. |
| 246 * @return {boolean} True if element is a non-whitespace node. | 253 * @return {boolean} True if element is a non-whitespace node. |
| 247 */ | 254 */ |
| 248 cvox.MathUtil.isNotWhitespace = function(element) { | 255 cvox.MathUtil.isNotWhitespace = function(element) { |
| 249 return (cvox.MathUtil.isMathmlTag(element) && | 256 return ( |
| 250 !cvox.MathUtil.isWhitespace(element)); | 257 cvox.MathUtil.isMathmlTag(element) && |
| 258 !cvox.MathUtil.isWhitespace(element)); |
| 251 }; | 259 }; |
| 252 | 260 |
| 253 | 261 |
| 254 /** | 262 /** |
| 255 * Computes the union of two arrays (not in a strictly set theoretical sense | 263 * Computes the union of two arrays (not in a strictly set theoretical sense |
| 256 * as all duplicate elements in either array still remain as duplicates!). | 264 * as all duplicate elements in either array still remain as duplicates!). |
| 257 * @param {Array} a An array. | 265 * @param {Array} a An array. |
| 258 * @param {Array} b Another array. | 266 * @param {Array} b Another array. |
| 259 * @return {Array} Union of a and b. | 267 * @return {Array} Union of a and b. |
| 260 */ | 268 */ |
| 261 cvox.MathUtil.union = function(a, b) { | 269 cvox.MathUtil.union = function(a, b) { |
| 262 return a.concat(b.filter(function(x) {return a.indexOf(x) < 0;})); | 270 return a.concat(b.filter(function(x) { |
| 271 return a.indexOf(x) < 0; |
| 272 })); |
| 263 }; | 273 }; |
| OLD | NEW |