MediaWiki REL1_28
Html.php
Go to the documentation of this file.
1<?php
48class Html {
49 // List of void elements from HTML5, section 8.1.2 as of 2016-09-19
50 private static $voidElements = [
51 'area',
52 'base',
53 'br',
54 'col',
55 'embed',
56 'hr',
57 'img',
58 'input',
59 'keygen',
60 'link',
61 'meta',
62 'param',
63 'source',
64 'track',
65 'wbr',
66 ];
67
68 // Boolean attributes, which may have the value omitted entirely. Manually
69 // collected from the HTML5 spec as of 2011-08-12.
70 private static $boolAttribs = [
71 'async',
72 'autofocus',
73 'autoplay',
74 'checked',
75 'controls',
76 'default',
77 'defer',
78 'disabled',
79 'formnovalidate',
80 'hidden',
81 'ismap',
82 'itemscope',
83 'loop',
84 'multiple',
85 'muted',
86 'novalidate',
87 'open',
88 'pubdate',
89 'readonly',
90 'required',
91 'reversed',
92 'scoped',
93 'seamless',
94 'selected',
95 'truespeed',
96 'typemustmatch',
97 // HTML5 Microdata
98 'itemscope',
99 ];
100
109 public static function buttonAttributes( array $attrs, array $modifiers = [] ) {
112 if ( isset( $attrs['class'] ) ) {
113 if ( is_array( $attrs['class'] ) ) {
114 $attrs['class'][] = 'mw-ui-button';
115 $attrs['class'] = array_merge( $attrs['class'], $modifiers );
116 // ensure compatibility with Xml
117 $attrs['class'] = implode( ' ', $attrs['class'] );
118 } else {
119 $attrs['class'] .= ' mw-ui-button ' . implode( ' ', $modifiers );
120 }
121 } else {
122 // ensure compatibility with Xml
123 $attrs['class'] = 'mw-ui-button ' . implode( ' ', $modifiers );
124 }
125 }
126 return $attrs;
127 }
128
136 public static function getTextInputAttributes( array $attrs ) {
139 if ( isset( $attrs['class'] ) ) {
140 if ( is_array( $attrs['class'] ) ) {
141 $attrs['class'][] = 'mw-ui-input';
142 } else {
143 $attrs['class'] .= ' mw-ui-input';
144 }
145 } else {
146 $attrs['class'] = 'mw-ui-input';
147 }
148 }
149 return $attrs;
150 }
151
165 public static function linkButton( $contents, array $attrs, array $modifiers = [] ) {
166 return self::element( 'a',
167 self::buttonAttributes( $attrs, $modifiers ),
168 $contents
169 );
170 }
171
185 public static function submitButton( $contents, array $attrs, array $modifiers = [] ) {
186 $attrs['type'] = 'submit';
187 $attrs['value'] = $contents;
188 return self::element( 'input', self::buttonAttributes( $attrs, $modifiers ) );
189 }
190
209 public static function rawElement( $element, $attribs = [], $contents = '' ) {
210 $start = self::openElement( $element, $attribs );
211 if ( in_array( $element, self::$voidElements ) ) {
212 // Silly XML.
213 return substr( $start, 0, -1 ) . '/>';
214 } else {
215 return "$start$contents" . self::closeElement( $element );
216 }
217 }
218
229 public static function element( $element, $attribs = [], $contents = '' ) {
230 return self::rawElement( $element, $attribs, strtr( $contents, [
231 // There's no point in escaping quotes, >, etc. in the contents of
232 // elements.
233 '&' => '&amp;',
234 '<' => '&lt;'
235 ] ) );
236 }
237
247 public static function openElement( $element, $attribs = [] ) {
249 // This is not required in HTML5, but let's do it anyway, for
250 // consistency and better compression.
251 $element = strtolower( $element );
252
253 // Remove invalid input types
254 if ( $element == 'input' ) {
255 $validTypes = [
256 'hidden',
257 'text',
258 'password',
259 'checkbox',
260 'radio',
261 'file',
262 'submit',
263 'image',
264 'reset',
265 'button',
266
267 // HTML input types
268 'datetime',
269 'datetime-local',
270 'date',
271 'month',
272 'time',
273 'week',
274 'number',
275 'range',
276 'email',
277 'url',
278 'search',
279 'tel',
280 'color',
281 ];
282 if ( isset( $attribs['type'] ) && !in_array( $attribs['type'], $validTypes ) ) {
283 unset( $attribs['type'] );
284 }
285 }
286
287 // According to standard the default type for <button> elements is "submit".
288 // Depending on compatibility mode IE might use "button", instead.
289 // We enforce the standard "submit".
290 if ( $element == 'button' && !isset( $attribs['type'] ) ) {
291 $attribs['type'] = 'submit';
292 }
293
294 return "<$element" . self::expandAttributes(
295 self::dropDefaults( $element, $attribs ) ) . '>';
296 }
297
305 public static function closeElement( $element ) {
306 $element = strtolower( $element );
307
308 return "</$element>";
309 }
310
328 private static function dropDefaults( $element, array $attribs ) {
329 // Whenever altering this array, please provide a covering test case
330 // in HtmlTest::provideElementsWithAttributesHavingDefaultValues
331 static $attribDefaults = [
332 'area' => [ 'shape' => 'rect' ],
333 'button' => [
334 'formaction' => 'GET',
335 'formenctype' => 'application/x-www-form-urlencoded',
336 ],
337 'canvas' => [
338 'height' => '150',
339 'width' => '300',
340 ],
341 'form' => [
342 'action' => 'GET',
343 'autocomplete' => 'on',
344 'enctype' => 'application/x-www-form-urlencoded',
345 ],
346 'input' => [
347 'formaction' => 'GET',
348 'type' => 'text',
349 ],
350 'keygen' => [ 'keytype' => 'rsa' ],
351 'link' => [ 'media' => 'all' ],
352 'menu' => [ 'type' => 'list' ],
353 'script' => [ 'type' => 'text/javascript' ],
354 'style' => [
355 'media' => 'all',
356 'type' => 'text/css',
357 ],
358 'textarea' => [ 'wrap' => 'soft' ],
359 ];
360
361 $element = strtolower( $element );
362
363 foreach ( $attribs as $attrib => $value ) {
364 $lcattrib = strtolower( $attrib );
365 if ( is_array( $value ) ) {
366 $value = implode( ' ', $value );
367 } else {
368 $value = strval( $value );
369 }
370
371 // Simple checks using $attribDefaults
372 if ( isset( $attribDefaults[$element][$lcattrib] )
373 && $attribDefaults[$element][$lcattrib] == $value
374 ) {
375 unset( $attribs[$attrib] );
376 }
377
378 if ( $lcattrib == 'class' && $value == '' ) {
379 unset( $attribs[$attrib] );
380 }
381 }
382
383 // More subtle checks
384 if ( $element === 'link'
385 && isset( $attribs['type'] ) && strval( $attribs['type'] ) == 'text/css'
386 ) {
387 unset( $attribs['type'] );
388 }
389 if ( $element === 'input' ) {
390 $type = isset( $attribs['type'] ) ? $attribs['type'] : null;
391 $value = isset( $attribs['value'] ) ? $attribs['value'] : null;
392 if ( $type === 'checkbox' || $type === 'radio' ) {
393 // The default value for checkboxes and radio buttons is 'on'
394 // not ''. By stripping value="" we break radio boxes that
395 // actually wants empty values.
396 if ( $value === 'on' ) {
397 unset( $attribs['value'] );
398 }
399 } elseif ( $type === 'submit' ) {
400 // The default value for submit appears to be "Submit" but
401 // let's not bother stripping out localized text that matches
402 // that.
403 } else {
404 // The default value for nearly every other field type is ''
405 // The 'range' and 'color' types use different defaults but
406 // stripping a value="" does not hurt them.
407 if ( $value === '' ) {
408 unset( $attribs['value'] );
409 }
410 }
411 }
412 if ( $element === 'select' && isset( $attribs['size'] ) ) {
413 if ( in_array( 'multiple', $attribs )
414 || ( isset( $attribs['multiple'] ) && $attribs['multiple'] !== false )
415 ) {
416 // A multi-select
417 if ( strval( $attribs['size'] ) == '4' ) {
418 unset( $attribs['size'] );
419 }
420 } else {
421 // Single select
422 if ( strval( $attribs['size'] ) == '1' ) {
423 unset( $attribs['size'] );
424 }
425 }
426 }
427
428 return $attribs;
429 }
430
470 public static function expandAttributes( array $attribs ) {
471 $ret = '';
472 foreach ( $attribs as $key => $value ) {
473 // Support intuitive [ 'checked' => true/false ] form
474 if ( $value === false || is_null( $value ) ) {
475 continue;
476 }
477
478 // For boolean attributes, support [ 'foo' ] instead of
479 // requiring [ 'foo' => 'meaningless' ].
480 if ( is_int( $key ) && in_array( strtolower( $value ), self::$boolAttribs ) ) {
481 $key = $value;
482 }
483
484 // Not technically required in HTML5 but we'd like consistency
485 // and better compression anyway.
486 $key = strtolower( $key );
487
488 // Bug 23769: Blacklist all form validation attributes for now. Current
489 // (June 2010) WebKit has no UI, so the form just refuses to submit
490 // without telling the user why, which is much worse than failing
491 // server-side validation. Opera is the only other implementation at
492 // this time, and has ugly UI, so just kill the feature entirely until
493 // we have at least one good implementation.
494
495 // As the default value of "1" for "step" rejects decimal
496 // numbers to be entered in 'type="number"' fields, allow
497 // the special case 'step="any"'.
498
499 if ( in_array( $key, [ 'max', 'min', 'pattern', 'required' ] )
500 || $key === 'step' && $value !== 'any' ) {
501 continue;
502 }
503
504 // http://www.w3.org/TR/html401/index/attributes.html ("space-separated")
505 // http://www.w3.org/TR/html5/index.html#attributes-1 ("space-separated")
506 $spaceSeparatedListAttributes = [
507 'class', // html4, html5
508 'accesskey', // as of html5, multiple space-separated values allowed
509 // html4-spec doesn't document rel= as space-separated
510 // but has been used like that and is now documented as such
511 // in the html5-spec.
512 'rel',
513 ];
514
515 // Specific features for attributes that allow a list of space-separated values
516 if ( in_array( $key, $spaceSeparatedListAttributes ) ) {
517 // Apply some normalization and remove duplicates
518
519 // Convert into correct array. Array can contain space-separated
520 // values. Implode/explode to get those into the main array as well.
521 if ( is_array( $value ) ) {
522 // If input wasn't an array, we can skip this step
523 $newValue = [];
524 foreach ( $value as $k => $v ) {
525 if ( is_string( $v ) ) {
526 // String values should be normal `array( 'foo' )`
527 // Just append them
528 if ( !isset( $value[$v] ) ) {
529 // As a special case don't set 'foo' if a
530 // separate 'foo' => true/false exists in the array
531 // keys should be authoritative
532 $newValue[] = $v;
533 }
534 } elseif ( $v ) {
535 // If the value is truthy but not a string this is likely
536 // an [ 'foo' => true ], falsy values don't add strings
537 $newValue[] = $k;
538 }
539 }
540 $value = implode( ' ', $newValue );
541 }
542 $value = explode( ' ', $value );
543
544 // Normalize spacing by fixing up cases where people used
545 // more than 1 space and/or a trailing/leading space
546 $value = array_diff( $value, [ '', ' ' ] );
547
548 // Remove duplicates and create the string
549 $value = implode( ' ', array_unique( $value ) );
550 } elseif ( is_array( $value ) ) {
551 throw new MWException( "HTML attribute $key can not contain a list of values" );
552 }
553
554 $quote = '"';
555
556 if ( in_array( $key, self::$boolAttribs ) ) {
557 $ret .= " $key=\"\"";
558 } else {
559 // Apparently we need to entity-encode \n, \r, \t, although the
560 // spec doesn't mention that. Since we're doing strtr() anyway,
561 // we may as well not call htmlspecialchars().
562 // @todo FIXME: Verify that we actually need to
563 // escape \n\r\t here, and explain why, exactly.
564 // We could call Sanitizer::encodeAttribute() for this, but we
565 // don't because we're stubborn and like our marginal savings on
566 // byte size from not having to encode unnecessary quotes.
567 // The only difference between this transform and the one by
568 // Sanitizer::encodeAttribute() is ' is not encoded.
569 $map = [
570 '&' => '&amp;',
571 '"' => '&quot;',
572 '>' => '&gt;',
573 // '<' allegedly allowed per spec
574 // but breaks some tools if not escaped.
575 "<" => '&lt;',
576 "\n" => '&#10;',
577 "\r" => '&#13;',
578 "\t" => '&#9;'
579 ];
580 $ret .= " $key=$quote" . strtr( $value, $map ) . $quote;
581 }
582 }
583 return $ret;
584 }
585
595 public static function inlineScript( $contents ) {
596 $attrs = [];
597
598 if ( preg_match( '/[<&]/', $contents ) ) {
599 $contents = "/*<![CDATA[*/$contents/*]]>*/";
600 }
601
602 return self::rawElement( 'script', $attrs, $contents );
603 }
604
612 public static function linkedScript( $url ) {
613 $attrs = [ 'src' => $url ];
614
615 return self::element( 'script', $attrs );
616 }
617
627 public static function inlineStyle( $contents, $media = 'all' ) {
628 // Don't escape '>' since that is used
629 // as direct child selector.
630 // Remember, in css, there is no "x" for hexadecimal escapes, and
631 // the space immediately after an escape sequence is swallowed.
632 $contents = strtr( $contents, [
633 '<' => '\3C ',
634 // CDATA end tag for good measure, but the main security
635 // is from escaping the '<'.
636 ']]>' => '\5D\5D\3E '
637 ] );
638
639 if ( preg_match( '/[<&]/', $contents ) ) {
640 $contents = "/*<![CDATA[*/$contents/*]]>*/";
641 }
642
643 return self::rawElement( 'style', [
644 'media' => $media,
645 ], $contents );
646 }
647
656 public static function linkedStyle( $url, $media = 'all' ) {
657 return self::element( 'link', [
658 'rel' => 'stylesheet',
659 'href' => $url,
660 'media' => $media,
661 ] );
662 }
663
675 public static function input( $name, $value = '', $type = 'text', array $attribs = [] ) {
676 $attribs['type'] = $type;
677 $attribs['value'] = $value;
678 $attribs['name'] = $name;
679 if ( in_array( $type, [ 'text', 'search', 'email', 'password', 'number' ] ) ) {
680 $attribs = self::getTextInputAttributes( $attribs );
681 }
682 if ( in_array( $type, [ 'button', 'reset', 'submit' ] ) ) {
683 $attribs = self::buttonAttributes( $attribs );
684 }
685 return self::element( 'input', $attribs );
686 }
687
696 public static function check( $name, $checked = false, array $attribs = [] ) {
697 if ( isset( $attribs['value'] ) ) {
698 $value = $attribs['value'];
699 unset( $attribs['value'] );
700 } else {
701 $value = 1;
702 }
703
704 if ( $checked ) {
705 $attribs[] = 'checked';
706 }
707
708 return self::input( $name, $value, 'checkbox', $attribs );
709 }
710
719 public static function radio( $name, $checked = false, array $attribs = [] ) {
720 if ( isset( $attribs['value'] ) ) {
721 $value = $attribs['value'];
722 unset( $attribs['value'] );
723 } else {
724 $value = 1;
725 }
726
727 if ( $checked ) {
728 $attribs[] = 'checked';
729 }
730
731 return self::input( $name, $value, 'radio', $attribs );
732 }
733
742 public static function label( $label, $id, array $attribs = [] ) {
743 $attribs += [
744 'for' => $id
745 ];
746 return self::element( 'label', $attribs, $label );
747 }
748
758 public static function hidden( $name, $value, array $attribs = [] ) {
759 return self::input( $name, $value, 'hidden', $attribs );
760 }
761
774 public static function textarea( $name, $value = '', array $attribs = [] ) {
775 $attribs['name'] = $name;
776
777 if ( substr( $value, 0, 1 ) == "\n" ) {
778 // Workaround for bug 12130: browsers eat the initial newline
779 // assuming that it's just for show, but they do keep the later
780 // newlines, which we may want to preserve during editing.
781 // Prepending a single newline
782 $spacedValue = "\n" . $value;
783 } else {
784 $spacedValue = $value;
785 }
786 return self::element( 'textarea', self::getTextInputAttributes( $attribs ), $spacedValue );
787 }
788
794 public static function namespaceSelectorOptions( array $params = [] ) {
796
797 $options = [];
798
799 if ( !isset( $params['exclude'] ) || !is_array( $params['exclude'] ) ) {
800 $params['exclude'] = [];
801 }
802
803 if ( isset( $params['all'] ) ) {
804 // add an option that would let the user select all namespaces.
805 // Value is provided by user, the name shown is localized for the user.
806 $options[$params['all']] = wfMessage( 'namespacesall' )->text();
807 }
808 // Add all namespaces as options (in the content language)
809 $options += $wgContLang->getFormattedNamespaces();
810
811 $optionsOut = [];
812 // Filter out namespaces below 0 and massage labels
813 foreach ( $options as $nsId => $nsName ) {
814 if ( $nsId < NS_MAIN || in_array( $nsId, $params['exclude'] ) ) {
815 continue;
816 }
817 if ( $nsId === NS_MAIN ) {
818 // For other namespaces use the namespace prefix as label, but for
819 // main we don't use "" but the user message describing it (e.g. "(Main)" or "(Article)")
820 $nsName = wfMessage( 'blanknamespace' )->text();
821 } elseif ( is_int( $nsId ) ) {
822 $nsName = $wgContLang->convertNamespace( $nsId );
823 }
824 $optionsOut[$nsId] = $nsName;
825 }
826
827 return $optionsOut;
828 }
829
846 public static function namespaceSelector( array $params = [],
847 array $selectAttribs = []
848 ) {
849 ksort( $selectAttribs );
850
851 // Is a namespace selected?
852 if ( isset( $params['selected'] ) ) {
853 // If string only contains digits, convert to clean int. Selected could also
854 // be "all" or "" etc. which needs to be left untouched.
855 // PHP is_numeric() has issues with large strings, PHP ctype_digit has other issues
856 // and returns false for already clean ints. Use regex instead..
857 if ( preg_match( '/^\d+$/', $params['selected'] ) ) {
858 $params['selected'] = intval( $params['selected'] );
859 }
860 // else: leaves it untouched for later processing
861 } else {
862 $params['selected'] = '';
863 }
864
865 if ( !isset( $params['disable'] ) || !is_array( $params['disable'] ) ) {
866 $params['disable'] = [];
867 }
868
869 // Associative array between option-values and option-labels
870 $options = self::namespaceSelectorOptions( $params );
871
872 // Convert $options to HTML
873 $optionsHtml = [];
874 foreach ( $options as $nsId => $nsName ) {
875 $optionsHtml[] = self::element(
876 'option', [
877 'disabled' => in_array( $nsId, $params['disable'] ),
878 'value' => $nsId,
879 'selected' => $nsId === $params['selected'],
880 ], $nsName
881 );
882 }
883
884 if ( !array_key_exists( 'id', $selectAttribs ) ) {
885 $selectAttribs['id'] = 'namespace';
886 }
887
888 if ( !array_key_exists( 'name', $selectAttribs ) ) {
889 $selectAttribs['name'] = 'namespace';
890 }
891
892 $ret = '';
893 if ( isset( $params['label'] ) ) {
894 $ret .= self::element(
895 'label', [
896 'for' => isset( $selectAttribs['id'] ) ? $selectAttribs['id'] : null,
897 ], $params['label']
898 ) . '&#160;';
899 }
900
901 // Wrap options in a <select>
902 $ret .= self::openElement( 'select', $selectAttribs )
903 . "\n"
904 . implode( "\n", $optionsHtml )
905 . "\n"
906 . self::closeElement( 'select' );
907
908 return $ret;
909 }
910
919 public static function htmlHeader( array $attribs = [] ) {
920 $ret = '';
921
923
924 $isXHTML = self::isXmlMimeType( $wgMimeType );
925
926 if ( $isXHTML ) { // XHTML5
927 // XML MIME-typed markup should have an xml header.
928 // However a DOCTYPE is not needed.
929 $ret .= "<?xml version=\"1.0\" encoding=\"UTF-8\" ?" . ">\n";
930
931 // Add the standard xmlns
932 $attribs['xmlns'] = 'http://www.w3.org/1999/xhtml';
933
934 // And support custom namespaces
935 foreach ( $wgXhtmlNamespaces as $tag => $ns ) {
936 $attribs["xmlns:$tag"] = $ns;
937 }
938 } else { // HTML5
939 // DOCTYPE
940 $ret .= "<!DOCTYPE html>\n";
941 }
942
943 if ( $wgHtml5Version ) {
944 $attribs['version'] = $wgHtml5Version;
945 }
946
947 $ret .= self::openElement( 'html', $attribs );
948
949 return $ret;
950 }
951
958 public static function isXmlMimeType( $mimetype ) {
959 # http://www.whatwg.org/html/infrastructure.html#xml-mime-type
960 # * text/xml
961 # * application/xml
962 # * Any MIME type with a subtype ending in +xml (this implicitly includes application/xhtml+xml)
963 return (bool)preg_match( '!^(text|application)/xml$|^.+/.+\+xml$!', $mimetype );
964 }
965
976 static function infoBox( $text, $icon, $alt, $class = '' ) {
977 $s = self::openElement( 'div', [ 'class' => "mw-infobox $class" ] );
978
979 $s .= self::openElement( 'div', [ 'class' => 'mw-infobox-left' ] ) .
980 self::element( 'img',
981 [
982 'src' => $icon,
983 'alt' => $alt,
984 ]
985 ) .
986 self::closeElement( 'div' );
987
988 $s .= self::openElement( 'div', [ 'class' => 'mw-infobox-right' ] ) .
989 $text .
990 self::closeElement( 'div' );
991 $s .= self::element( 'div', [ 'style' => 'clear: left;' ], ' ' );
992
993 $s .= self::closeElement( 'div' );
994
995 $s .= self::element( 'div', [ 'style' => 'clear: left;' ], ' ' );
996
997 return $s;
998 }
999
1023 static function srcSet( array $urls ) {
1024 $candidates = [];
1025 foreach ( $urls as $density => $url ) {
1026 // Cast density to float to strip 'x', then back to string to serve
1027 // as array index.
1028 $density = (string)(float)$density;
1029 $candidates[$density] = $url;
1030 }
1031
1032 // Remove duplicates that are the same as a smaller value
1033 ksort( $candidates, SORT_NUMERIC );
1034 $candidates = array_unique( $candidates );
1035
1036 // Append density info to the url
1037 foreach ( $candidates as $density => $url ) {
1038 $candidates[$density] = $url . ' ' . $density . 'x';
1039 }
1040
1041 return implode( ", ", $candidates );
1042 }
1043}
$wgMimeType
The default Content-Type header.
$wgUseMediaWikiUIEverywhere
Temporary variable that applies MediaWiki UI wherever it can be supported.
$wgHtml5Version
Defines the value of the version attribute in the <html> tag, if any.
$wgXhtmlNamespaces
Permit other namespaces in addition to the w3.org default.
This class is a collection of static functions that serve two purposes:
Definition Html.php:48
static label( $label, $id, array $attribs=[])
Convenience function for generating a label for inputs.
Definition Html.php:742
static textarea( $name, $value='', array $attribs=[])
Convenience function to produce a <textarea> element.
Definition Html.php:774
static infoBox( $text, $icon, $alt, $class='')
Get HTML for an info box with an icon.
Definition Html.php:976
static namespaceSelectorOptions(array $params=[])
Helper for Html::namespaceSelector().
Definition Html.php:794
static linkedScript( $url)
Output a "<script>" tag linking to the given URL, e.g., "<script src=foo.js></script>".
Definition Html.php:612
static buttonAttributes(array $attrs, array $modifiers=[])
Modifies a set of attributes meant for button elements and apply a set of default attributes when $wg...
Definition Html.php:109
static linkedStyle( $url, $media='all')
Output a "<link rel=stylesheet>" linking to the given URL for the given media type (if any).
Definition Html.php:656
static element( $element, $attribs=[], $contents='')
Identical to rawElement(), but HTML-escapes $contents (like Xml::element()).
Definition Html.php:229
static isXmlMimeType( $mimetype)
Determines if the given MIME type is xml.
Definition Html.php:958
static linkButton( $contents, array $attrs, array $modifiers=[])
Returns an HTML link element in a string styled as a button (when $wgUseMediaWikiUIEverywhere is enab...
Definition Html.php:165
static htmlHeader(array $attribs=[])
Constructs the opening html-tag with necessary doctypes depending on global variables.
Definition Html.php:919
static input( $name, $value='', $type='text', array $attribs=[])
Convenience function to produce an "<input>" element.
Definition Html.php:675
static dropDefaults( $element, array $attribs)
Given an element name and an associative array of element attributes, return an array that is functio...
Definition Html.php:328
static $boolAttribs
Definition Html.php:70
static submitButton( $contents, array $attrs, array $modifiers=[])
Returns an HTML link element in a string styled as a button (when $wgUseMediaWikiUIEverywhere is enab...
Definition Html.php:185
static getTextInputAttributes(array $attrs)
Modifies a set of attributes meant for text input elements and apply a set of default attributes.
Definition Html.php:136
static radio( $name, $checked=false, array $attribs=[])
Convenience function to produce a radio button (input element with type=radio)
Definition Html.php:719
static expandAttributes(array $attribs)
Given an associative array of element attributes, generate a string to stick after the element name i...
Definition Html.php:470
static rawElement( $element, $attribs=[], $contents='')
Returns an HTML element in a string.
Definition Html.php:209
static namespaceSelector(array $params=[], array $selectAttribs=[])
Build a drop-down box for selecting a namespace.
Definition Html.php:846
static openElement( $element, $attribs=[])
Identical to rawElement(), but has no third parameter and omits the end tag (and the self-closing '/'...
Definition Html.php:247
static inlineScript( $contents)
Output a "<script>" tag with the given contents.
Definition Html.php:595
static check( $name, $checked=false, array $attribs=[])
Convenience function to produce a checkbox (input element with type=checkbox)
Definition Html.php:696
static srcSet(array $urls)
Generate a srcset attribute value.
Definition Html.php:1023
static inlineStyle( $contents, $media='all')
Output a "<style>" tag with the given contents for the given media type (if any).
Definition Html.php:627
static closeElement( $element)
Returns "</$element>".
Definition Html.php:305
static $voidElements
Definition Html.php:50
static hidden( $name, $value, array $attribs=[])
Convenience function to produce an input element with type=hidden.
Definition Html.php:758
MediaWiki exception.
this class mediates it Skin Encapsulates a look and feel for the wiki All of the functions that render HTML and make choices about how to render it are here and are called from various other places when and is meant to be subclassed with other skins that may override some of its functions The User object contains a reference to a and so rather than having a global skin object we just rely on the global User and get the skin with $wgUser and also has some character encoding functions and other locale stuff The current user interface language is instantiated as and the local content language as $wgContLang
Definition design.txt:57
when a variable name is used in a it is silently declared as a new local masking the global
Definition design.txt:95
This document is intended to provide useful advice for parties seeking to redistribute MediaWiki to end users It s targeted particularly at maintainers for Linux since it s been observed that distribution packages of MediaWiki often break We ve consistently had to recommend that users seeking support use official tarballs instead of their distribution s and this often solves whatever problem the user is having It would be nice if this could such as
const NS_MAIN
Definition Defines.php:56
the array() calling protocol came about after MediaWiki 1.4rc1.
namespace are movable Hooks may change this value to override the return value of MWNamespace::isMovable(). 'NewDifferenceEngine' do that in ParserLimitReportFormat instead use this to modify the parameters of the image and a DIV can begin in one section and end in another Make sure your code can handle that case gracefully See the EditSectionClearerLink extension for an example zero but section is usually empty its values are the globals values before the output is cached one of or reset my talk my contributions etc etc otherwise the built in rate limiting checks are if enabled allows for interception of redirect as a string mapping parameter names to values & $type
Definition hooks.txt:2568
This code would result in ircNotify being run twice when an article is and once for brion Hooks can return three possible true was required This is the default since MediaWiki *some string
Definition hooks.txt:183
this hook is for auditing only RecentChangesLinked and Watchlist RecentChangesLinked and Watchlist e g Watchlist removed from all revisions and log entries to which it was applied This gives extensions a chance to take it off their books as the deletion has already been partly carried out by this point or something similar the user will be unable to create the tag set and then return false from the hook function Ensure you consume the ChangeTagAfterDelete hook to carry out custom deletion actions as context called by AbstractContent::getParserOutput May be used to override the normal model specific rendering of page content as context as context $options
Definition hooks.txt:1096
either a unescaped string or a HtmlArmor object after in associative array form externallinks including delete and has completed for all link tables whether this was an auto creation default is conds Array Extra conditions for the No matching items in log is displayed if loglist is empty msgKey Array If you want a nice box with a set this to the key of the message First element is the message additional optional elements are parameters for the key that are processed with wfMessage() -> params() ->parseAsBlock() - offset Set to overwrite offset parameter in $wgRequest set to '' to unset offset - wrap String Wrap the message in html(usually something like "&lt;div ...>$1&lt;/div>"). - flags Integer display flags(NO_ACTION_LINK, NO_EXTRA_USER_LINKS) 'LogException':Called before an exception(or PHP error) is logged. This is meant for integration with external error aggregation services
null means default in associative array with keys and values unescaped Should be merged with default with a value of false meaning to suppress the attribute in associative array with keys and values unescaped noclasses & $ret
Definition hooks.txt:1949
this hook is for auditing only RecentChangesLinked and Watchlist RecentChangesLinked and Watchlist e g Watchlist removed from all revisions and log entries to which it was applied This gives extensions a chance to take it off their books $tag
Definition hooks.txt:1033
null means default in associative array with keys and values unescaped Should be merged with default with a value of false meaning to suppress the attribute in associative array with keys and values unescaped noclasses just before the function returns a value If you return an< a > element with HTML attributes $attribs and contents $html will be returned If you return $ret will be returned and may include noclasses after processing & $attribs
Definition hooks.txt:1958
Allows to change the fields on the form that will be generated $name
Definition hooks.txt:304
injection txt This is an overview of how MediaWiki makes use of dependency injection The design described here grew from the discussion of RFC T384 The term dependency this means that anything an object needs to operate should be injected from the the object itself should only know narrow no concrete implementation of the logic it relies on The requirement to inject everything typically results in an architecture that based on two main types of and essentially stateless service objects that use other service objects to operate on the value objects As of the beginning MediaWiki is only starting to use the DI approach Much of the code still relies on global state or direct resulting in a highly cyclical dependency which acts as the top level factory for services in MediaWiki which can be used to gain access to default instances of various services MediaWikiServices however also allows new services to be defined and default services to be redefined Services are defined or redefined by providing a callback the instantiator that will return a new instance of the service When it will create an instance of MediaWikiServices and populate it with the services defined in the files listed by thereby bootstrapping the DI framework Per $wgServiceWiringFiles lists includes ServiceWiring php
Definition injection.txt:37
$params