PluginProbe
Easy Invoice – Invoice Generator, PDF Quotes & Payments / 2.4.0
Easy Invoice – Invoice Generator, PDF Quotes & Payments v2.4.0
2.4.0 2.4.1 2.3.8 2.3.7 2.3.6 2.3.5 2.3.4 2.3.3 2.3.2 2.3.1 2.2.0 2.1.21 2.1.20 2.1.19 2.1.18 2.1.0 2.1.1 2.1.10 2.1.11 2.1.12 2.1.13 2.1.14 2.1.15 2.1.16 2.1.2 All 57 releases
easy-invoice / vendor / masterminds / html5 / src / HTML5 / Elements.php

Elements.php in Easy Invoice – Invoice Generator, PDF Quotes & Payments 2.4.0, at vendor/masterminds/html5/src/HTML5/Elements.php

640 lines 20.1 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Provide general element functions.
4 */
5
6 namespace Masterminds\HTML5;
7
8 /**
9 * This class provides general information about HTML5 elements,
10 * including syntactic and semantic issues.
11 * Parsers and serializers can
12 * use this class as a reference point for information about the rules
13 * of various HTML5 elements.
14 *
15 * @todo consider using a bitmask table lookup. There is enough overlap in
16 * naming that this could significantly shrink the size and maybe make it
17 * faster. See the Go teams implementation at https://code.google.com/p/go/source/browse/html/atom.
18 */
19 class Elements
20 {
21 /**
22 * Indicates an element is described in the specification.
23 */
24 const KNOWN_ELEMENT = 1;
25
26 // From section 8.1.2: "script", "style"
27 // From 8.2.5.4.7 ("in body" insertion mode): "noembed"
28 // From 8.4 "style", "xmp", "iframe", "noembed", "noframes"
29 /**
30 * Indicates the contained text should be processed as raw text.
31 */
32 const TEXT_RAW = 2;
33
34 // From section 8.1.2: "textarea", "title"
35 /**
36 * Indicates the contained text should be processed as RCDATA.
37 */
38 const TEXT_RCDATA = 4;
39
40 /**
41 * Indicates the tag cannot have content.
42 */
43 const VOID_TAG = 8;
44
45 // "address", "article", "aside", "blockquote", "center", "details", "dialog", "dir", "div", "dl",
46 // "fieldset", "figcaption", "figure", "footer", "header", "hgroup", "menu",
47 // "nav", "ol", "p", "section", "summary", "ul"
48 // "h1", "h2", "h3", "h4", "h5", "h6"
49 // "pre", "listing"
50 // "form"
51 // "plaintext"
52 /**
53 * Indicates that if a previous event is for a P tag, that element
54 * should be considered closed.
55 */
56 const AUTOCLOSE_P = 16;
57
58 /**
59 * Indicates that the text inside is plaintext (pre).
60 */
61 const TEXT_PLAINTEXT = 32;
62
63 // See https://developer.mozilla.org/en-US/docs/HTML/Block-level_elements
64 /**
65 * Indicates that the tag is a block.
66 */
67 const BLOCK_TAG = 64;
68
69 /**
70 * Indicates that the tag allows only inline elements as child nodes.
71 */
72 const BLOCK_ONLY_INLINE = 128;
73
74 /**
75 * Elements with optional end tags that cause auto-closing of previous and parent tags,
76 * as example most of the table related tags, see https://www.w3.org/TR/html401/struct/tables.html
77 * Structure is as follows:
78 * TAG-NAME => [PARENT-TAG-NAME-TO-CLOSE1, PARENT-TAG-NAME-TO-CLOSE2, ...].
79 *
80 * Order is important, after auto-closing one parent with might have to close also their parent.
81 *
82 * @var array<string, string[]>
83 */
84 public static $optionalEndElementsParentsToClose = array(
85 'tr' => array('td', 'tr'),
86 'td' => array('td', 'th'),
87 'th' => array('td', 'th'),
88 'tfoot' => array('td', 'th', 'tr', 'tbody', 'thead'),
89 'tbody' => array('td', 'th', 'tr', 'thead'),
90 );
91
92 /**
93 * The HTML5 elements as defined in http://dev.w3.org/html5/markup/elements.html.
94 *
95 * @var array
96 */
97 public static $html5 = array(
98 'a' => 1,
99 'abbr' => 1,
100 'address' => 65, // NORMAL | BLOCK_TAG
101 'area' => 9, // NORMAL | VOID_TAG
102 'article' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
103 'aside' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
104 'audio' => 1, // NORMAL
105 'b' => 1,
106 'base' => 9, // NORMAL | VOID_TAG
107 'bdi' => 1,
108 'bdo' => 1,
109 'blockquote' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
110 'body' => 1,
111 'br' => 9, // NORMAL | VOID_TAG
112 'button' => 1,
113 'canvas' => 65, // NORMAL | BLOCK_TAG
114 'caption' => 1,
115 'cite' => 1,
116 'code' => 1,
117 'col' => 9, // NORMAL | VOID_TAG
118 'colgroup' => 1,
119 'command' => 9, // NORMAL | VOID_TAG
120 // "data" => 1, // This is highly experimental and only part of the whatwg spec (not w3c). See https://developer.mozilla.org/en-US/docs/HTML/Element/data
121 'datalist' => 1,
122 'dd' => 65, // NORMAL | BLOCK_TAG
123 'del' => 1,
124 'details' => 17, // NORMAL | AUTOCLOSE_P,
125 'dfn' => 1,
126 'dialog' => 17, // NORMAL | AUTOCLOSE_P,
127 'div' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
128 'dl' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
129 'dt' => 1,
130 'em' => 1,
131 'embed' => 9, // NORMAL | VOID_TAG
132 'fieldset' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
133 'figcaption' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
134 'figure' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
135 'footer' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
136 'form' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
137 'h1' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
138 'h2' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
139 'h3' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
140 'h4' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
141 'h5' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
142 'h6' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
143 'head' => 1,
144 'header' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
145 'hgroup' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
146 'hr' => 73, // NORMAL | VOID_TAG
147 'html' => 1,
148 'i' => 1,
149 'iframe' => 3, // NORMAL | TEXT_RAW
150 'img' => 9, // NORMAL | VOID_TAG
151 'input' => 9, // NORMAL | VOID_TAG
152 'kbd' => 1,
153 'ins' => 1,
154 'keygen' => 9, // NORMAL | VOID_TAG
155 'label' => 1,
156 'legend' => 1,
157 'li' => 1,
158 'link' => 9, // NORMAL | VOID_TAG
159 'map' => 1,
160 'mark' => 1,
161 'menu' => 17, // NORMAL | AUTOCLOSE_P,
162 'meta' => 9, // NORMAL | VOID_TAG
163 'meter' => 1,
164 'nav' => 17, // NORMAL | AUTOCLOSE_P,
165 'noscript' => 65, // NORMAL | BLOCK_TAG
166 'object' => 1,
167 'ol' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
168 'optgroup' => 1,
169 'option' => 1,
170 'output' => 65, // NORMAL | BLOCK_TAG
171 'p' => 209, // NORMAL | AUTOCLOSE_P | BLOCK_TAG | BLOCK_ONLY_INLINE
172 'param' => 9, // NORMAL | VOID_TAG
173 'pre' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
174 'progress' => 1,
175 'q' => 1,
176 'rp' => 1,
177 'rt' => 1,
178 'ruby' => 1,
179 's' => 1,
180 'samp' => 1,
181 'script' => 3, // NORMAL | TEXT_RAW
182 'section' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
183 'select' => 1,
184 'small' => 1,
185 'source' => 9, // NORMAL | VOID_TAG
186 'span' => 1,
187 'strong' => 1,
188 'style' => 3, // NORMAL | TEXT_RAW
189 'sub' => 1,
190 'summary' => 17, // NORMAL | AUTOCLOSE_P,
191 'sup' => 1,
192 'table' => 65, // NORMAL | BLOCK_TAG
193 'tbody' => 1,
194 'td' => 1,
195 'textarea' => 5, // NORMAL | TEXT_RCDATA
196 'tfoot' => 65, // NORMAL | BLOCK_TAG
197 'th' => 1,
198 'thead' => 1,
199 'time' => 1,
200 'title' => 5, // NORMAL | TEXT_RCDATA
201 'tr' => 1,
202 'track' => 9, // NORMAL | VOID_TAG
203 'u' => 1,
204 'ul' => 81, // NORMAL | AUTOCLOSE_P | BLOCK_TAG
205 'var' => 1,
206 'video' => 1,
207 'wbr' => 9, // NORMAL | VOID_TAG
208
209 // Legacy?
210 'basefont' => 8, // VOID_TAG
211 'bgsound' => 8, // VOID_TAG
212 'noframes' => 2, // RAW_TEXT
213 'frame' => 9, // NORMAL | VOID_TAG
214 'frameset' => 1,
215 'center' => 16,
216 'dir' => 16,
217 'listing' => 16, // AUTOCLOSE_P
218 'plaintext' => 48, // AUTOCLOSE_P | TEXT_PLAINTEXT
219 'applet' => 0,
220 'marquee' => 0,
221 'isindex' => 8, // VOID_TAG
222 'xmp' => 20, // AUTOCLOSE_P | VOID_TAG | RAW_TEXT
223 'noembed' => 2, // RAW_TEXT
224 );
225
226 /**
227 * The MathML elements.
228 * See http://www.w3.org/wiki/MathML/Elements.
229 *
230 * In our case we are only concerned with presentation MathML and not content
231 * MathML. There is a nice list of this subset at https://developer.mozilla.org/en-US/docs/MathML/Element.
232 *
233 * @var array
234 */
235 public static $mathml = array(
236 'maction' => 1,
237 'maligngroup' => 1,
238 'malignmark' => 1,
239 'math' => 1,
240 'menclose' => 1,
241 'merror' => 1,
242 'mfenced' => 1,
243 'mfrac' => 1,
244 'mglyph' => 1,
245 'mi' => 1,
246 'mlabeledtr' => 1,
247 'mlongdiv' => 1,
248 'mmultiscripts' => 1,
249 'mn' => 1,
250 'mo' => 1,
251 'mover' => 1,
252 'mpadded' => 1,
253 'mphantom' => 1,
254 'mroot' => 1,
255 'mrow' => 1,
256 'ms' => 1,
257 'mscarries' => 1,
258 'mscarry' => 1,
259 'msgroup' => 1,
260 'msline' => 1,
261 'mspace' => 1,
262 'msqrt' => 1,
263 'msrow' => 1,
264 'mstack' => 1,
265 'mstyle' => 1,
266 'msub' => 1,
267 'msup' => 1,
268 'msubsup' => 1,
269 'mtable' => 1,
270 'mtd' => 1,
271 'mtext' => 1,
272 'mtr' => 1,
273 'munder' => 1,
274 'munderover' => 1,
275 );
276
277 /**
278 * The svg elements.
279 *
280 * The Mozilla documentation has a good list at https://developer.mozilla.org/en-US/docs/SVG/Element.
281 * The w3c list appears to be lacking in some areas like filter effect elements.
282 * That list can be found at http://www.w3.org/wiki/SVG/Elements.
283 *
284 * Note, FireFox appears to do a better job rendering filter effects than chrome.
285 * While they are in the spec I'm not sure how widely implemented they are.
286 *
287 * @var array
288 */
289 public static $svg = array(
290 'a' => 1,
291 'altGlyph' => 1,
292 'altGlyphDef' => 1,
293 'altGlyphItem' => 1,
294 'animate' => 1,
295 'animateColor' => 1,
296 'animateMotion' => 1,
297 'animateTransform' => 1,
298 'circle' => 1,
299 'clipPath' => 1,
300 'color-profile' => 1,
301 'cursor' => 1,
302 'defs' => 1,
303 'desc' => 1,
304 'ellipse' => 1,
305 'feBlend' => 1,
306 'feColorMatrix' => 1,
307 'feComponentTransfer' => 1,
308 'feComposite' => 1,
309 'feConvolveMatrix' => 1,
310 'feDiffuseLighting' => 1,
311 'feDisplacementMap' => 1,
312 'feDistantLight' => 1,
313 'feDropShadow' => 1,
314 'feFlood' => 1,
315 'feFuncA' => 1,
316 'feFuncB' => 1,
317 'feFuncG' => 1,
318 'feFuncR' => 1,
319 'feGaussianBlur' => 1,
320 'feImage' => 1,
321 'feMerge' => 1,
322 'feMergeNode' => 1,
323 'feMorphology' => 1,
324 'feOffset' => 1,
325 'fePointLight' => 1,
326 'feSpecularLighting' => 1,
327 'feSpotLight' => 1,
328 'feTile' => 1,
329 'feTurbulence' => 1,
330 'filter' => 1,
331 'font' => 1,
332 'font-face' => 1,
333 'font-face-format' => 1,
334 'font-face-name' => 1,
335 'font-face-src' => 1,
336 'font-face-uri' => 1,
337 'foreignObject' => 1,
338 'g' => 1,
339 'glyph' => 1,
340 'glyphRef' => 1,
341 'hkern' => 1,
342 'image' => 1,
343 'line' => 1,
344 'linearGradient' => 1,
345 'marker' => 1,
346 'mask' => 1,
347 'metadata' => 1,
348 'missing-glyph' => 1,
349 'mpath' => 1,
350 'path' => 1,
351 'pattern' => 1,
352 'polygon' => 1,
353 'polyline' => 1,
354 'radialGradient' => 1,
355 'rect' => 1,
356 'script' => 3, // NORMAL | RAW_TEXT
357 'set' => 1,
358 'stop' => 1,
359 'style' => 3, // NORMAL | RAW_TEXT
360 'svg' => 1,
361 'switch' => 1,
362 'symbol' => 1,
363 'text' => 1,
364 'textPath' => 1,
365 'title' => 1,
366 'tref' => 1,
367 'tspan' => 1,
368 'use' => 1,
369 'view' => 1,
370 'vkern' => 1,
371 );
372
373 /**
374 * Some attributes in SVG are case sensitive.
375 *
376 * This map contains key/value pairs with the key as the lowercase attribute
377 * name and the value with the correct casing.
378 */
379 public static $svgCaseSensitiveAttributeMap = array(
380 'attributename' => 'attributeName',
381 'attributetype' => 'attributeType',
382 'basefrequency' => 'baseFrequency',
383 'baseprofile' => 'baseProfile',
384 'calcmode' => 'calcMode',
385 'clippathunits' => 'clipPathUnits',
386 'contentscripttype' => 'contentScriptType',
387 'contentstyletype' => 'contentStyleType',
388 'diffuseconstant' => 'diffuseConstant',
389 'edgemode' => 'edgeMode',
390 'externalresourcesrequired' => 'externalResourcesRequired',
391 'filterres' => 'filterRes',
392 'filterunits' => 'filterUnits',
393 'glyphref' => 'glyphRef',
394 'gradienttransform' => 'gradientTransform',
395 'gradientunits' => 'gradientUnits',
396 'kernelmatrix' => 'kernelMatrix',
397 'kernelunitlength' => 'kernelUnitLength',
398 'keypoints' => 'keyPoints',
399 'keysplines' => 'keySplines',
400 'keytimes' => 'keyTimes',
401 'lengthadjust' => 'lengthAdjust',
402 'limitingconeangle' => 'limitingConeAngle',
403 'markerheight' => 'markerHeight',
404 'markerunits' => 'markerUnits',
405 'markerwidth' => 'markerWidth',
406 'maskcontentunits' => 'maskContentUnits',
407 'maskunits' => 'maskUnits',
408 'numoctaves' => 'numOctaves',
409 'pathlength' => 'pathLength',
410 'patterncontentunits' => 'patternContentUnits',
411 'patterntransform' => 'patternTransform',
412 'patternunits' => 'patternUnits',
413 'pointsatx' => 'pointsAtX',
414 'pointsaty' => 'pointsAtY',
415 'pointsatz' => 'pointsAtZ',
416 'preservealpha' => 'preserveAlpha',
417 'preserveaspectratio' => 'preserveAspectRatio',
418 'primitiveunits' => 'primitiveUnits',
419 'refx' => 'refX',
420 'refy' => 'refY',
421 'repeatcount' => 'repeatCount',
422 'repeatdur' => 'repeatDur',
423 'requiredextensions' => 'requiredExtensions',
424 'requiredfeatures' => 'requiredFeatures',
425 'specularconstant' => 'specularConstant',
426 'specularexponent' => 'specularExponent',
427 'spreadmethod' => 'spreadMethod',
428 'startoffset' => 'startOffset',
429 'stddeviation' => 'stdDeviation',
430 'stitchtiles' => 'stitchTiles',
431 'surfacescale' => 'surfaceScale',
432 'systemlanguage' => 'systemLanguage',
433 'tablevalues' => 'tableValues',
434 'targetx' => 'targetX',
435 'targety' => 'targetY',
436 'textlength' => 'textLength',
437 'viewbox' => 'viewBox',
438 'viewtarget' => 'viewTarget',
439 'xchannelselector' => 'xChannelSelector',
440 'ychannelselector' => 'yChannelSelector',
441 'zoomandpan' => 'zoomAndPan',
442 );
443
444 /**
445 * Some SVG elements are case sensitive.
446 * This map contains these.
447 *
448 * The map contains key/value store of the name is lowercase as the keys and
449 * the correct casing as the value.
450 */
451 public static $svgCaseSensitiveElementMap = array(
452 'altglyph' => 'altGlyph',
453 'altglyphdef' => 'altGlyphDef',
454 'altglyphitem' => 'altGlyphItem',
455 'animatecolor' => 'animateColor',
456 'animatemotion' => 'animateMotion',
457 'animatetransform' => 'animateTransform',
458 'clippath' => 'clipPath',
459 'feblend' => 'feBlend',
460 'fecolormatrix' => 'feColorMatrix',
461 'fecomponenttransfer' => 'feComponentTransfer',
462 'fecomposite' => 'feComposite',
463 'feconvolvematrix' => 'feConvolveMatrix',
464 'fediffuselighting' => 'feDiffuseLighting',
465 'fedisplacementmap' => 'feDisplacementMap',
466 'fedistantlight' => 'feDistantLight',
467 'fedropshadow' => 'feDropShadow',
468 'feflood' => 'feFlood',
469 'fefunca' => 'feFuncA',
470 'fefuncb' => 'feFuncB',
471 'fefuncg' => 'feFuncG',
472 'fefuncr' => 'feFuncR',
473 'fegaussianblur' => 'feGaussianBlur',
474 'feimage' => 'feImage',
475 'femerge' => 'feMerge',
476 'femergenode' => 'feMergeNode',
477 'femorphology' => 'feMorphology',
478 'feoffset' => 'feOffset',
479 'fepointlight' => 'fePointLight',
480 'fespecularlighting' => 'feSpecularLighting',
481 'fespotlight' => 'feSpotLight',
482 'fetile' => 'feTile',
483 'feturbulence' => 'feTurbulence',
484 'foreignobject' => 'foreignObject',
485 'glyphref' => 'glyphRef',
486 'lineargradient' => 'linearGradient',
487 'radialgradient' => 'radialGradient',
488 'textpath' => 'textPath',
489 );
490
491 /**
492 * Check whether the given element meets the given criterion.
493 *
494 * Example:
495 *
496 * Elements::isA('script', Elements::TEXT_RAW); // Returns true.
497 *
498 * Elements::isA('script', Elements::TEXT_RCDATA); // Returns false.
499 *
500 * @param string $name The element name.
501 * @param int $mask One of the constants on this class.
502 *
503 * @return bool true if the element matches the mask, false otherwise.
504 */
505 public static function isA($name, $mask)
506 {
507 return (static::element($name) & $mask) === $mask;
508 }
509
510 /**
511 * Test if an element is a valid html5 element.
512 *
513 * @param string $name The name of the element.
514 *
515 * @return bool true if a html5 element and false otherwise.
516 */
517 public static function isHtml5Element($name)
518 {
519 // html5 element names are case insensitive. Forcing lowercase for the check.
520 // Do we need this check or will all data passed here already be lowercase?
521 return isset(static::$html5[strtolower($name)]);
522 }
523
524 /**
525 * Test if an element name is a valid MathML presentation element.
526 *
527 * @param string $name The name of the element.
528 *
529 * @return bool true if a MathML name and false otherwise.
530 */
531 public static function isMathMLElement($name)
532 {
533 // MathML is case-sensitive unlike html5 elements.
534 return isset(static::$mathml[$name]);
535 }
536
537 /**
538 * Test if an element is a valid SVG element.
539 *
540 * @param string $name The name of the element.
541 *
542 * @return bool true if a SVG element and false otherise.
543 */
544 public static function isSvgElement($name)
545 {
546 // SVG is case-sensitive unlike html5 elements.
547 return isset(static::$svg[$name]);
548 }
549
550 /**
551 * Is an element name valid in an html5 document.
552 * This includes html5 elements along with other allowed embedded content
553 * such as svg and mathml.
554 *
555 * @param string $name The name of the element.
556 *
557 * @return bool true if valid and false otherwise.
558 */
559 public static function isElement($name)
560 {
561 return static::isHtml5Element($name) || static::isMathMLElement($name) || static::isSvgElement($name);
562 }
563
564 /**
565 * Get the element mask for the given element name.
566 *
567 * @param string $name The name of the element.
568 *
569 * @return int the element mask.
570 */
571 public static function element($name)
572 {
573 if (isset(static::$html5[$name])) {
574 return static::$html5[$name];
575 }
576 if (isset(static::$svg[$name])) {
577 return static::$svg[$name];
578 }
579 if (isset(static::$mathml[$name])) {
580 return static::$mathml[$name];
581 }
582
583 return 0;
584 }
585
586 /**
587 * Normalize a SVG element name to its proper case and form.
588 *
589 * @param string $name The name of the element.
590 *
591 * @return string the normalized form of the element name.
592 */
593 public static function normalizeSvgElement($name)
594 {
595 $name = strtolower($name);
596 if (isset(static::$svgCaseSensitiveElementMap[$name])) {
597 $name = static::$svgCaseSensitiveElementMap[$name];
598 }
599
600 return $name;
601 }
602
603 /**
604 * Normalize a SVG attribute name to its proper case and form.
605 *
606 * @param string $name The name of the attribute.
607 *
608 * @return string The normalized form of the attribute name.
609 */
610 public static function normalizeSvgAttribute($name)
611 {
612 $name = strtolower($name);
613 if (isset(static::$svgCaseSensitiveAttributeMap[$name])) {
614 $name = static::$svgCaseSensitiveAttributeMap[$name];
615 }
616
617 return $name;
618 }
619
620 /**
621 * Normalize a MathML attribute name to its proper case and form.
622 * Note, all MathML element names are lowercase.
623 *
624 * @param string $name The name of the attribute.
625 *
626 * @return string The normalized form of the attribute name.
627 */
628 public static function normalizeMathMlAttribute($name)
629 {
630 $name = strtolower($name);
631
632 // Only one attribute has a mixed case form for MathML.
633 if ('definitionurl' === $name) {
634 $name = 'definitionURL';
635 }
636
637 return $name;
638 }
639 }
640