Merge "Split DateInputWidget & CalendarWidget into a separate ResourceLoader module"
[lhc/web/wiklou.git] / resources / src / mediawiki / mediawiki.js
index 5ba9781..9ec70b5 100644 (file)
                                // List of modules to be loaded
                                queue = [],
 
-                               // List of callback functions waiting for modules to be ready to be called
+                               /**
+                                * List of callback jobs waiting for modules to be ready.
+                                *
+                                * Jobs are created by #request() and run by #handlePending().
+                                *
+                                * Typically when a job is created for a module, the job's dependencies contain
+                                * both the module being requested and all its recursive dependencies.
+                                *
+                                * Format:
+                                *
+                                *     {
+                                *         'dependencies': [ module names ],
+                                *         'ready': Function callback
+                                *         'error': Function callback
+                                *     }
+                                *
+                                * @property {Object[]} jobs
+                                * @private
+                                */
                                jobs = [],
 
                                // Selector cache for the marker element. Use getMarker() to get/use the marker!
                                        // Verify that the element before the marker actually is a
                                        // <style> tag and one that came from ResourceLoader
                                        // (not some other style tag or even a `<meta>` or `<script>`).
-                                       if ( $style.data( 'ResourceLoaderDynamicStyleTag' ) === true ) {
+                                       if ( $style.data( 'ResourceLoaderDynamicStyleTag' ) ) {
                                                // There's already a dynamic <style> tag present and
                                                // we are able to append more to it.
                                                styleEl = $style.get( 0 );
                                                // Support: IE6-10
                                                if ( styleEl.styleSheet ) {
                                                        try {
-                                                               styleEl.styleSheet.cssText += cssText;
+                                                               // Support: IE9
+                                                               // We can't do styleSheet.cssText += cssText, since IE9 mangles this property on
+                                                               // write, dropping @media queries from the CSS text. If we read it and used its
+                                                               // value, we would accidentally apply @media-specific styles to all media. (T108727)
+                                                               if ( document.documentMode === 9 ) {
+                                                                       styleEl.styleSheet.cssText = $style.data( 'ResourceLoaderDynamicStyleTag' ) + cssText;
+                                                               } else {
+                                                                       styleEl.styleSheet.cssText += cssText;
+                                                               }
                                                        } catch ( e ) {
                                                                mw.track( 'resourceloader.exception', { exception: e, source: 'stylesheet' } );
                                                        }
                                        }
                                }
 
-                               $( newStyleTag( cssText, getMarker() ) ).data( 'ResourceLoaderDynamicStyleTag', true );
+                               $style = $( newStyleTag( cssText, getMarker() ) );
+
+                               if ( document.documentMode === 9 ) {
+                                       // Support: IE9
+                                       // Preserve original CSS text because IE9 mangles it on write
+                                       $style.data( 'ResourceLoaderDynamicStyleTag', cssText );
+                               } else {
+                                       $style.data( 'ResourceLoaderDynamicStyleTag', true );
+                               }
 
                                fireCallbacks();
                        }
 
                                // Add ready and error callbacks if they were given
                                if ( ready !== undefined || error !== undefined ) {
-                                       jobs[ jobs.length ] = {
+                                       jobs.push( {
+                                               // Narrow down the list to modules that are worth waiting for
                                                dependencies: $.grep( dependencies, function ( module ) {
                                                        var state = mw.loader.getState( module );
-                                                       return state === 'registered' || state === 'loaded' || state === 'loading';
+                                                       return state === 'registered' || state === 'loaded' || state === 'loading' || state === 'executing';
                                                } ),
                                                ready: ready,
                                                error: error
-                                       };
+                                       } );
                                }
 
                                $.each( dependencies, function ( idx, module ) {
                                        if ( typeof modules !== 'object' && typeof modules !== 'string' ) {
                                                throw new Error( 'modules must be a string or an array, not a ' + typeof modules );
                                        }
-                                       // Allow calling with an external url or single dependency as a string
+                                       // Allow calling with a url or single dependency as a string
                                        if ( typeof modules === 'string' ) {
-                                               if ( /^(https?:)?\/\//.test( modules ) ) {
+                                               // "https://example.org/x.js", "http://example.org/x.js", "//example.org/x.js", "/x.js"
+                                               if ( /^(https?:)?\/?\//.test( modules ) ) {
                                                        if ( type === 'text/css' ) {
                                                                // Support: IE 7-8
                                                                // Use properties instead of attributes as IE throws security
                        tokens: new Map()
                },
 
+               // OOUI widgets specific to MediaWiki
+               widgets: {},
+
                /**
                 * Registry and firing of events.
                 *
                        } );
                } );
                $.when.apply( $, loading ).then( function () {
-                       performance.mark( 'mwLoadEnd' );
+                       mwPerformance.mark( 'mwLoadEnd' );
                        mw.hook( 'resourceloader.loadEnd' ).fire();
                } );
        } );