[extensions-web] Update bundled require.js
- From: Jasper St. Pierre <jstpierre src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [extensions-web] Update bundled require.js
- Date: Mon, 28 Nov 2011 01:33:21 +0000 (UTC)
commit 847afe9c6c952d1f6177e72e6f2204f1a0728119
Author: Jasper St. Pierre <jstpierre mecheye net>
Date: Thu Nov 24 18:52:45 2011 -0500
Update bundled require.js
sweettooth/static/js/require.js | 1008 +++++++++++++++++++--------------------
1 files changed, 481 insertions(+), 527 deletions(-)
---
diff --git a/sweettooth/static/js/require.js b/sweettooth/static/js/require.js
index 279a320..5d6b299 100644
--- a/sweettooth/static/js/require.js
+++ b/sweettooth/static/js/require.js
@@ -1,9 +1,9 @@
/** vim: et:ts=4:sw=4:sts=4
- * @license RequireJS 0.25.0 Copyright (c) 2010-2011, The Dojo Foundation All Rights Reserved.
+ * @license RequireJS 1.0.2 Copyright (c) 2010-2011, The Dojo Foundation All Rights Reserved.
* Available via the MIT or new BSD license.
* see: http://github.com/jrburke/requirejs for details
*/
-/*jslint strict: false, plusplus: false */
+/*jslint strict: false, plusplus: false, sub: true */
/*global window: false, navigator: false, document: false, importScripts: false,
jQuery: false, clearInterval: false, setInterval: false, self: false,
setTimeout: false, opera: false */
@@ -11,9 +11,9 @@
var requirejs, require, define;
(function () {
//Change this version number for each release.
- var version = "0.25.0",
- commentRegExp = /(\/\*([\s\S]*?)\*\/|\/\/(.*)$)/mg,
- cjsRequireRegExp = /require\(["']([^'"\s]+)["']\)/g,
+ var version = "1.0.2",
+ commentRegExp = /(\/\*([\s\S]*?)\*\/|([^:]|^)\/\/(.*)$)/mg,
+ cjsRequireRegExp = /require\(\s*["']([^'"\s]+)["']\s*\)/g,
currDirRegExp = /^\.\//,
jsSuffixRegExp = /\.js$/,
ostring = Object.prototype.toString,
@@ -31,17 +31,14 @@ var requirejs, require, define;
defContextName = "_",
//Oh the tragedy, detecting opera. See the usage of isOpera for reason.
isOpera = typeof opera !== "undefined" && opera.toString() === "[object Opera]",
- reqWaitIdPrefix = "_r@@",
empty = {},
contexts = {},
globalDefQueue = [],
interactiveScript = null,
- isDone = false,
checkLoadedDepth = 0,
useInteractive = false,
req, cfg = {}, currentlyAddingScript, s, head, baseElement, scripts, script,
- src, subPath, mainScript, dataMain, i, scrollIntervalId, setReadyState, ctx,
- jQueryCheck, checkLoadedTimeoutId;
+ src, subPath, mainScript, dataMain, i, ctx, jQueryCheck, checkLoadedTimeoutId;
function isFunction(it) {
return ostring.call(it) === "[object Function]";
@@ -172,9 +169,10 @@ var requirejs, require, define;
var context, resume,
config = {
waitSeconds: 7,
- baseUrl: s.baseUrl || "./",
+ baseUrl: "./",
paths: {},
- pkgs: {}
+ pkgs: {},
+ catchError: {}
},
defQueue = [],
specified = {
@@ -187,12 +185,15 @@ var requirejs, require, define;
loaded = {},
waiting = {},
waitAry = [],
- waitIdCounter = 0,
+ urlFetched = {},
+ managerCounter = 0,
managerCallbacks = {},
plugins = {},
- pluginsQueue = {},
- resumeDepth = 0,
- normalizedWaiting = {};
+ //Used to indicate which modules in a build scenario
+ //need to be full executed.
+ needFullExec = {},
+ fullExec = {},
+ resumeDepth = 0;
/**
* Trims the . and .. from an array of path segments.
@@ -238,7 +239,7 @@ var requirejs, require, define;
var pkgName, pkgConfig;
//Adjust any relative paths.
- if (name.charAt(0) === ".") {
+ if (name && name.charAt(0) === ".") {
//If have a base name, try to normalize against it,
//otherwise, assume it is a top-level require that will
//be relative to baseUrl in the end.
@@ -267,6 +268,10 @@ var requirejs, require, define;
if (pkgConfig && name === pkgName + '/' + pkgConfig.main) {
name = pkgName;
}
+ } else if (name.indexOf("./") === 0) {
+ // No baseName, so this is ID is resolved relative
+ // to baseUrl, pull off the leading dot.
+ name = name.substring(2);
}
}
return name;
@@ -303,41 +308,26 @@ var requirejs, require, define;
if (name) {
if (prefix) {
pluginModule = defined[prefix];
- if (pluginModule) {
- //Plugin is loaded, use its normalize method, otherwise,
- //normalize name as usual.
- if (pluginModule.normalize) {
- normalizedName = pluginModule.normalize(name, function (name) {
- return normalize(name, parentName);
- });
- } else {
- normalizedName = normalize(name, parentName);
- }
+ if (pluginModule && pluginModule.normalize) {
+ //Plugin is loaded, use its normalize method.
+ normalizedName = pluginModule.normalize(name, function (name) {
+ return normalize(name, parentName);
+ });
} else {
- //Plugin is not loaded yet, so do not normalize
- //the name, wait for plugin to load to see if
- //it has a normalize method. To avoid possible
- //ambiguity with relative names loaded from another
- //plugin, use the parent's name as part of this name.
- normalizedName = '__$p' + parentName + '@' + name;
+ normalizedName = normalize(name, parentName);
}
} else {
+ //A regular module.
normalizedName = normalize(name, parentName);
- }
- url = urlMap[normalizedName];
- if (!url) {
- //Calculate url for the module, if it has a name.
- if (req.toModuleUrl) {
- //Special logic required for a particular engine,
- //like Node.
- url = req.toModuleUrl(context, normalizedName, parentModuleMap);
- } else {
+ url = urlMap[normalizedName];
+ if (!url) {
+ //Calculate url for the module, if it has a name.
url = context.nameToUrl(normalizedName, null, parentModuleMap);
- }
- //Store the URL mapping for later.
- urlMap[normalizedName] = url;
+ //Store the URL mapping for later.
+ urlMap[normalizedName] = url;
+ }
}
}
@@ -347,7 +337,7 @@ var requirejs, require, define;
parentMap: parentModuleMap,
url: url,
originalName: originalName,
- fullName: prefix ? prefix + "!" + normalizedName : normalizedName
+ fullName: prefix ? prefix + "!" + (normalizedName || '') : normalizedName
};
}
@@ -372,23 +362,12 @@ var requirejs, require, define;
return priorityDone;
}
- /**
- * Helper function that creates a setExports function for a "module"
- * CommonJS dependency. Do this here to avoid creating a closure that
- * is part of a loop.
- */
- function makeSetExports(moduleObj) {
- return function (exports) {
- moduleObj.exports = exports;
- };
- }
-
function makeContextModuleFunc(func, relModuleMap, enableBuildCallback) {
return function () {
//A version of a require function that passes a moduleName
//value for items that may need to
//look up paths relative to the moduleName
- var args = [].concat(aps.call(arguments, 0)), lastArg;
+ var args = aps.call(arguments, 0), lastArg;
if (enableBuildCallback &&
isFunction((lastArg = args[args.length - 1]))) {
lastArg.__requireJsBuild = true;
@@ -412,147 +391,50 @@ var requirejs, require, define;
toUrl: makeContextModuleFunc(context.toUrl, relModuleMap),
defined: makeContextModuleFunc(context.requireDefined, relModuleMap),
specified: makeContextModuleFunc(context.requireSpecified, relModuleMap),
- ready: req.ready,
isBrowser: req.isBrowser
});
- //Something used by node.
- if (req.paths) {
- modRequire.paths = req.paths;
- }
return modRequire;
}
- /**
- * Used to update the normalized name for plugin-based dependencies
- * after a plugin loads, since it can have its own normalization structure.
- * @param {String} pluginName the normalized plugin module name.
- */
- function updateNormalizedNames(pluginName) {
-
- var oldFullName, oldModuleMap, moduleMap, fullName, callbacks,
- i, j, k, depArray, existingCallbacks,
- maps = normalizedWaiting[pluginName];
-
- if (maps) {
- for (i = 0; (oldModuleMap = maps[i]); i++) {
- oldFullName = oldModuleMap.fullName;
- moduleMap = makeModuleMap(oldModuleMap.originalName, oldModuleMap.parentMap);
- fullName = moduleMap.fullName;
- //Callbacks could be undefined if the same plugin!name was
- //required twice in a row, so use empty array in that case.
- callbacks = managerCallbacks[oldFullName] || [];
- existingCallbacks = managerCallbacks[fullName];
-
- if (fullName !== oldFullName) {
- //Update the specified object, but only if it is already
- //in there. In sync environments, it may not be yet.
- if (oldFullName in specified) {
- delete specified[oldFullName];
- specified[fullName] = true;
- }
-
- //Update managerCallbacks to use the correct normalized name.
- //If there are already callbacks for the normalized name,
- //just add to them.
- if (existingCallbacks) {
- managerCallbacks[fullName] = existingCallbacks.concat(callbacks);
- } else {
- managerCallbacks[fullName] = callbacks;
- }
- delete managerCallbacks[oldFullName];
-
- //In each manager callback, update the normalized name in the depArray.
- for (j = 0; j < callbacks.length; j++) {
- depArray = callbacks[j].depArray;
- for (k = 0; k < depArray.length; k++) {
- if (depArray[k] === oldFullName) {
- depArray[k] = fullName;
- }
- }
- }
- }
- }
- }
-
- delete normalizedWaiting[pluginName];
- }
-
/*
* Queues a dependency for checking after the loader is out of a
* "paused" state, for example while a script file is being loaded
* in the browser, where it may have many modules defined in it.
- *
- * depName will be fully qualified, no relative . or .. path.
*/
- function queueDependency(dep) {
- //Make sure to load any plugin and associate the dependency
- //with that plugin.
- var prefix = dep.prefix,
- fullName = dep.fullName;
-
- //Do not bother if the depName is already in transit
- if (specified[fullName] || fullName in defined) {
- return;
- }
-
- if (prefix && !plugins[prefix]) {
- //Queue up loading of the dependency, track it
- //via context.plugins. Mark it as a plugin so
- //that the build system will know to treat it
- //special.
- plugins[prefix] = undefined;
-
- //Remember this dep that needs to have normaliztion done
- //after the plugin loads.
- (normalizedWaiting[prefix] || (normalizedWaiting[prefix] = []))
- .push(dep);
-
- //Register an action to do once the plugin loads, to update
- //all managerCallbacks to use a properly normalized module
- //name.
- (managerCallbacks[prefix] ||
- (managerCallbacks[prefix] = [])).push({
- onDep: function (name, value) {
- if (name === prefix) {
- updateNormalizedNames(prefix);
- }
- }
- });
-
- queueDependency(makeModuleMap(prefix));
- }
-
- context.paused.push(dep);
+ function queueDependency(manager) {
+ context.paused.push(manager);
}
function execManager(manager) {
- var i, ret, waitingCallbacks, err,
+ var i, ret, err, errFile, errModuleTree,
cb = manager.callback,
- fullName = manager.fullName,
- args = [],
- ary = manager.depArray;
+ map = manager.map,
+ fullName = map.fullName,
+ args = manager.deps,
+ listeners = manager.listeners,
+ cjsModule;
//Call the callback to define the module, if necessary.
if (cb && isFunction(cb)) {
- //Pull out the defined dependencies and pass the ordered
- //values to the callback.
- if (ary) {
- for (i = 0; i < ary.length; i++) {
- args.push(manager.deps[ary[i]]);
+ if (config.catchError.define) {
+ try {
+ ret = req.execCb(fullName, manager.callback, args, defined[fullName]);
+ } catch (e) {
+ err = e;
}
- }
-
- try {
+ } else {
ret = req.execCb(fullName, manager.callback, args, defined[fullName]);
- } catch (e) {
- err = e;
}
if (fullName) {
//If setting exports via "module" is in play,
//favor that over return value and exports. After that,
//favor a non-undefined return value over exports use.
- if (manager.cjsModule && manager.cjsModule.exports !== undefined) {
+ cjsModule = manager.cjsModule;
+ if (cjsModule &&
+ cjsModule.exports !== undefined &&
+ //Make sure it is not already the exports value
+ cjsModule.exports !== defined[fullName]) {
ret = defined[fullName] = manager.cjsModule.exports;
} else if (ret === undefined && manager.usingExports) {
//exports already set the defined value.
@@ -560,21 +442,32 @@ var requirejs, require, define;
} else {
//Use the return value from the function.
defined[fullName] = ret;
+ //If this module needed full execution in a build
+ //environment, mark that now.
+ if (needFullExec[fullName]) {
+ fullExec[fullName] = true;
+ }
}
}
} else if (fullName) {
//May just be an object definition for the module. Only
//worry about defining if have a module name.
ret = defined[fullName] = cb;
+
+ //If this module needed full execution in a build
+ //environment, mark that now.
+ if (needFullExec[fullName]) {
+ fullExec[fullName] = true;
+ }
}
//Clean up waiting. Do this before error calls, and before
- //calling back waitingCallbacks, so that bookkeeping is correct
+ //calling back listeners, so that bookkeeping is correct
//in the event of an error and error is reported in correct order,
- //since the waitingCallbacks will likely have errors if the
+ //since the listeners will likely have errors if the
//onError function does not throw.
- if (waiting[manager.waitId]) {
- delete waiting[manager.waitId];
+ if (waiting[manager.id]) {
+ delete waiting[manager.id];
manager.isDone = true;
context.waitCount -= 1;
if (context.waitCount === 0) {
@@ -583,66 +476,241 @@ var requirejs, require, define;
}
}
+ //Do not need to track manager callback now that it is defined.
+ delete managerCallbacks[fullName];
+
+ //Allow instrumentation like the optimizer to know the order
+ //of modules executed and their dependencies.
+ if (req.onResourceLoad && !manager.placeholder) {
+ req.onResourceLoad(context, map, manager.depArray);
+ }
+
if (err) {
+ errFile = (fullName ? makeModuleMap(fullName).url : '') ||
+ err.fileName || err.sourceURL;
+ errModuleTree = err.moduleTree;
err = makeError('defineerror', 'Error evaluating ' +
'module "' + fullName + '" at location "' +
- (fullName ? makeModuleMap(fullName).url : '') + '":\n' +
- err + '\nfileName:' + (err.fileName || err.sourceURL) +
+ errFile + '":\n' +
+ err + '\nfileName:' + errFile +
'\nlineNumber: ' + (err.lineNumber || err.line), err);
err.moduleName = fullName;
+ err.moduleTree = errModuleTree;
return req.onError(err);
}
- if (fullName) {
- //If anything was waiting for this module to be defined,
- //notify them now.
- waitingCallbacks = managerCallbacks[fullName];
- if (waitingCallbacks) {
- for (i = 0; i < waitingCallbacks.length; i++) {
- waitingCallbacks[i].onDep(fullName, ret);
+ //Let listeners know of this manager's value.
+ for (i = 0; (cb = listeners[i]); i++) {
+ cb(ret);
+ }
+
+ return undefined;
+ }
+
+ /**
+ * Helper that creates a callack function that is called when a dependency
+ * is ready, and sets the i-th dependency for the manager as the
+ * value passed to the callback generated by this function.
+ */
+ function makeArgCallback(manager, i) {
+ return function (value) {
+ //Only do the work if it has not been done
+ //already for a dependency. Cycle breaking
+ //logic in forceExec could mean this function
+ //is called more than once for a given dependency.
+ if (!manager.depDone[i]) {
+ manager.depDone[i] = true;
+ manager.deps[i] = value;
+ manager.depCount -= 1;
+ if (!manager.depCount) {
+ //All done, execute!
+ execManager(manager);
}
- delete managerCallbacks[fullName];
}
+ };
+ }
+
+ function callPlugin(pluginName, depManager) {
+ var map = depManager.map,
+ fullName = map.fullName,
+ name = map.name,
+ plugin = plugins[pluginName] ||
+ (plugins[pluginName] = defined[pluginName]),
+ load;
+
+ //No need to continue if the manager is already
+ //in the process of loading.
+ if (depManager.loading) {
+ return;
}
+ depManager.loading = true;
- return undefined;
+ load = function (ret) {
+ depManager.callback = function () {
+ return ret;
+ };
+ execManager(depManager);
+
+ loaded[depManager.id] = true;
+
+ //The loading of this plugin
+ //might have placed other things
+ //in the paused queue. In particular,
+ //a loader plugin that depends on
+ //a different plugin loaded resource.
+ resume();
+ };
+
+ //Allow plugins to load other code without having to know the
+ //context or how to "complete" the load.
+ load.fromText = function (moduleName, text) {
+ /*jslint evil: true */
+ var hasInteractive = useInteractive;
+
+ //Indicate a the module is in process of loading.
+ loaded[moduleName] = false;
+ context.scriptCount += 1;
+
+ //Indicate this is not a "real" module, so do not track it
+ //for builds, it does not map to a real file.
+ context.fake[moduleName] = true;
+
+ //Turn off interactive script matching for IE for any define
+ //calls in the text, then turn it back on at the end.
+ if (hasInteractive) {
+ useInteractive = false;
+ }
+
+ req.exec(text);
+
+ if (hasInteractive) {
+ useInteractive = true;
+ }
+
+ //Support anonymous modules.
+ context.completeLoad(moduleName);
+ };
+
+ //No need to continue if the plugin value has already been
+ //defined by a build.
+ if (fullName in defined) {
+ load(defined[fullName]);
+ } else {
+ //Use parentName here since the plugin's name is not reliable,
+ //could be some weird string with no path that actually wants to
+ //reference the parentName's path.
+ plugin.load(name, makeRequire(map.parentMap, true), load, config);
+ }
+ }
+
+ /**
+ * Adds the manager to the waiting queue. Only fully
+ * resolved items should be in the waiting queue.
+ */
+ function addWait(manager) {
+ if (!waiting[manager.id]) {
+ waiting[manager.id] = manager;
+ waitAry.push(manager);
+ context.waitCount += 1;
+ }
+ }
+
+ /**
+ * Function added to every manager object. Created out here
+ * to avoid new function creation for each manager instance.
+ */
+ function managerAdd(cb) {
+ this.listeners.push(cb);
+ }
+
+ function getManager(map, shouldQueue) {
+ var fullName = map.fullName,
+ prefix = map.prefix,
+ plugin = prefix ? plugins[prefix] ||
+ (plugins[prefix] = defined[prefix]) : null,
+ manager, created, pluginManager;
+
+ if (fullName) {
+ manager = managerCallbacks[fullName];
+ }
+
+ if (!manager) {
+ created = true;
+ manager = {
+ //ID is just the full name, but if it is a plugin resource
+ //for a plugin that has not been loaded,
+ //then add an ID counter to it.
+ id: (prefix && !plugin ?
+ (managerCounter++) + '__p@:' : '') +
+ (fullName || '__r@' + (managerCounter++)),
+ map: map,
+ depCount: 0,
+ depDone: [],
+ depCallbacks: [],
+ deps: [],
+ listeners: [],
+ add: managerAdd
+ };
+
+ specified[manager.id] = true;
+
+ //Only track the manager/reuse it if this is a non-plugin
+ //resource. Also only track plugin resources once
+ //the plugin has been loaded, and so the fullName is the
+ //true normalized value.
+ if (fullName && (!prefix || plugins[prefix])) {
+ managerCallbacks[fullName] = manager;
+ }
+ }
+
+ //If there is a plugin needed, but it is not loaded,
+ //first load the plugin, then continue on.
+ if (prefix && !plugin) {
+ pluginManager = getManager(makeModuleMap(prefix), true);
+ pluginManager.add(function (plugin) {
+ //Create a new manager for the normalized
+ //resource ID and have it call this manager when
+ //done.
+ var newMap = makeModuleMap(map.originalName, map.parentMap),
+ normalizedManager = getManager(newMap, true);
+
+ //Indicate this manager is a placeholder for the real,
+ //normalized thing. Important for when trying to map
+ //modules and dependencies, for instance, in a build.
+ manager.placeholder = true;
+
+ normalizedManager.add(function (resource) {
+ manager.callback = function () {
+ return resource;
+ };
+ execManager(manager);
+ });
+ });
+ } else if (created && shouldQueue) {
+ //Indicate the resource is not loaded yet if it is to be
+ //queued.
+ loaded[manager.id] = false;
+ queueDependency(manager);
+ addWait(manager);
+ }
+
+ return manager;
}
function main(inName, depArray, callback, relModuleMap) {
var moduleMap = makeModuleMap(inName, relModuleMap),
name = moduleMap.name,
fullName = moduleMap.fullName,
- uniques = {},
- manager = {
- //Use a wait ID because some entries are anon
- //async require calls.
- waitId: name || reqWaitIdPrefix + (waitIdCounter++),
- depCount: 0,
- depMax: 0,
- prefix: moduleMap.prefix,
- name: name,
- fullName: fullName,
- deps: {},
- depArray: depArray,
- callback: callback,
- onDep: function (depName, value) {
- if (!(depName in manager.deps)) {
- manager.deps[depName] = value;
- manager.depCount += 1;
- if (manager.depCount === manager.depMax) {
- //All done, execute!
- execManager(manager);
- }
- }
- }
- },
- i, depArg, depName, cjsMod;
+ manager = getManager(moduleMap),
+ id = manager.id,
+ deps = manager.deps,
+ i, depArg, depName, depPrefix, cjsMod;
if (fullName) {
//If module already defined for context, or already loaded,
//then leave. Also leave if jQuery is registering but it does
//not match the desired version number in the config.
- if (fullName in defined || loaded[fullName] === true ||
+ if (fullName in defined || loaded[id] === true ||
(fullName === "jquery" && config.jQuery &&
config.jQuery !== callback().fn.jquery)) {
return;
@@ -652,8 +720,8 @@ var requirejs, require, define;
//as part of a layer, where onScriptLoad is not fired
//for those cases. Do this after the inline define and
//dependency tracing is done.
- specified[fullName] = true;
- loaded[fullName] = true;
+ specified[id] = true;
+ loaded[id] = true;
//If module is jQuery set up delaying its dom ready listeners.
if (fullName === "jquery" && callback) {
@@ -661,6 +729,13 @@ var requirejs, require, define;
}
}
+ //Attach real depArray and callback to the manager. Do this
+ //only if the module has not been defined already, so do this after
+ //the fullName checks above. IE can call main() more than once
+ //for a module.
+ manager.depArray = depArray;
+ manager.callback = callback;
+
//Add the dependencies to the deps field, and register for callbacks
//on the dependencies.
for (i = 0; i < depArray.length; i++) {
@@ -672,6 +747,7 @@ var requirejs, require, define;
//Split the dependency name into plugin and name parts
depArg = makeModuleMap(depArg, (name ? moduleMap : relModuleMap));
depName = depArg.fullName;
+ depPrefix = depArg.prefix;
//Fix the name in depArray to be just the name, since
//that is how it will be called back later.
@@ -679,46 +755,54 @@ var requirejs, require, define;
//Fast path CommonJS standard dependencies.
if (depName === "require") {
- manager.deps[depName] = makeRequire(moduleMap);
+ deps[i] = makeRequire(moduleMap);
} else if (depName === "exports") {
//CommonJS module spec 1.1
- manager.deps[depName] = defined[fullName] = {};
+ deps[i] = defined[fullName] = {};
manager.usingExports = true;
} else if (depName === "module") {
//CommonJS module spec 1.1
- manager.cjsModule = cjsMod = manager.deps[depName] = {
+ manager.cjsModule = cjsMod = deps[i] = {
id: name,
uri: name ? context.nameToUrl(name, null, relModuleMap) : undefined,
exports: defined[fullName]
};
- cjsMod.setExports = makeSetExports(cjsMod);
- } else if (depName in defined && !(depName in waiting)) {
- //Module already defined, no need to wait for it.
- manager.deps[depName] = defined[depName];
- } else if (!uniques[depName]) {
-
- //A dynamic dependency.
- manager.depMax += 1;
-
- queueDependency(depArg);
-
- //Register to get notification when dependency loads.
- (managerCallbacks[depName] ||
- (managerCallbacks[depName] = [])).push(manager);
+ } else if (depName in defined && !(depName in waiting) &&
+ (!(fullName in needFullExec) ||
+ (fullName in needFullExec && fullExec[depName]))) {
+ //Module already defined, and not in a build situation
+ //where the module is a something that needs full
+ //execution and this dependency has not been fully
+ //executed. See r.js's requirePatch.js for more info
+ //on fullExec.
+ deps[i] = defined[depName];
+ } else {
+ //Mark this dependency as needing full exec if
+ //the current module needs full exec.
+ if (fullName in needFullExec) {
+ needFullExec[depName] = true;
+ //Reset state so fully executed code will get
+ //picked up correctly.
+ delete defined[depName];
+ urlFetched[depArg.url] = false;
+ }
- uniques[depName] = true;
+ //Either a resource that is not loaded yet, or a plugin
+ //resource for either a plugin that has not
+ //loaded yet.
+ manager.depCount += 1;
+ manager.depCallbacks[i] = makeArgCallback(manager, i);
+ getManager(depArg, true).add(manager.depCallbacks[i]);
}
}
}
//Do not bother tracking the manager if it is all done.
- if (manager.depCount === manager.depMax) {
+ if (!manager.depCount) {
//All done, execute!
execManager(manager);
} else {
- waiting[manager.waitId] = manager;
- waitAry.push(manager);
- context.waitCount += 1;
+ addWait(manager);
}
}
@@ -728,10 +812,6 @@ var requirejs, require, define;
*/
function callDefMain(args) {
main.apply(null, args);
- //Mark the module loaded. Must do it here in addition
- //to doing it in define in case a script does
- //not call define
- loaded[args[0]] = true;
}
/**
@@ -780,9 +860,10 @@ var requirejs, require, define;
return undefined;
}
- var fullName = manager.fullName,
+ var fullName = manager.map.fullName,
depArray = manager.depArray,
- depName, i;
+ i, depName, depManager, prefix, prefixManager, value;
+
if (fullName) {
if (traced[fullName]) {
return defined[fullName];
@@ -791,14 +872,24 @@ var requirejs, require, define;
traced[fullName] = true;
}
- //forceExec all of its dependencies.
- for (i = 0; i < depArray.length; i++) {
- //Some array members may be null, like if a trailing comma
- //IE, so do the explicit [i] access and check if it has a value.
- depName = depArray[i];
- if (depName) {
- if (!manager.deps[depName] && waiting[depName]) {
- manager.onDep(depName, forceExec(waiting[depName], traced));
+ //Trace through the dependencies.
+ if (depArray) {
+ for (i = 0; i < depArray.length; i++) {
+ //Some array members may be null, like if a trailing comma
+ //IE, so do the explicit [i] access and check if it has a value.
+ depName = depArray[i];
+ if (depName) {
+ //First, make sure if it is a plugin resource that the
+ //plugin is not blocked.
+ prefix = makeModuleMap(depName).prefix;
+ if (prefix && (prefixManager = waiting[prefix])) {
+ forceExec(prefixManager, traced);
+ }
+ depManager = waiting[depName];
+ if (depManager && !depManager.isDone && loaded[depName]) {
+ value = forceExec(depManager, traced);
+ manager.depCallbacks[i](value);
+ }
}
}
}
@@ -892,6 +983,11 @@ var requirejs, require, define;
forceExec(manager, {});
}
+ //If anything got placed in the paused queue, run it down.
+ if (context.paused.length) {
+ resume();
+ }
+
//Only allow this recursion to a certain depth. Only
//triggered by errors in calling a module in which its
//modules waiting on it cannot finish loading, or some circular
@@ -913,136 +1009,11 @@ var requirejs, require, define;
return undefined;
}
- function callPlugin(pluginName, dep) {
- var name = dep.name,
- fullName = dep.fullName,
- load;
-
- //Do not bother if plugin is already defined or being loaded.
- if (fullName in defined || fullName in loaded) {
- return;
- }
-
- if (!plugins[pluginName]) {
- plugins[pluginName] = defined[pluginName];
- }
-
- //Only set loaded to false for tracking if it has not already been set.
- if (!loaded[fullName]) {
- loaded[fullName] = false;
- }
-
- load = function (ret) {
- //Allow the build process to register plugin-loaded dependencies.
- if (req.onPluginLoad) {
- req.onPluginLoad(context, pluginName, name, ret);
- }
-
- execManager({
- prefix: dep.prefix,
- name: dep.name,
- fullName: dep.fullName,
- callback: function () {
- return ret;
- }
- });
- loaded[fullName] = true;
- };
-
- //Allow plugins to load other code without having to know the
- //context or how to "complete" the load.
- load.fromText = function (moduleName, text) {
- /*jslint evil: true */
- var hasInteractive = useInteractive;
-
- //Indicate a the module is in process of loading.
- context.loaded[moduleName] = false;
- context.scriptCount += 1;
-
- //Turn off interactive script matching for IE for any define
- //calls in the text, then turn it back on at the end.
- if (hasInteractive) {
- useInteractive = false;
- }
-
- req.exec(text);
-
- if (hasInteractive) {
- useInteractive = true;
- }
-
- //Support anonymous modules.
- context.completeLoad(moduleName);
- };
-
- //Use parentName here since the plugin's name is not reliable,
- //could be some weird string with no path that actually wants to
- //reference the parentName's path.
- plugins[pluginName].load(name, makeRequire(dep.parentMap, true), load, config);
- }
-
- function loadPaused(dep) {
- //Renormalize dependency if its name was waiting on a plugin
- //to load, which as since loaded.
- if (dep.prefix && dep.name.indexOf('__$p') === 0 && defined[dep.prefix]) {
- dep = makeModuleMap(dep.originalName, dep.parentMap);
- }
-
- var pluginName = dep.prefix,
- fullName = dep.fullName,
- urlFetched = context.urlFetched;
-
- //Do not bother if the dependency has already been specified.
- if (specified[fullName] || loaded[fullName]) {
- return;
- } else {
- specified[fullName] = true;
- }
-
- if (pluginName) {
- //If plugin not loaded, wait for it.
- //set up callback list. if no list, then register
- //managerCallback for that plugin.
- if (defined[pluginName]) {
- callPlugin(pluginName, dep);
- } else {
- if (!pluginsQueue[pluginName]) {
- pluginsQueue[pluginName] = [];
- (managerCallbacks[pluginName] ||
- (managerCallbacks[pluginName] = [])).push({
- onDep: function (name, value) {
- if (name === pluginName) {
- var i, oldModuleMap, ary = pluginsQueue[pluginName];
-
- //Now update all queued plugin actions.
- for (i = 0; i < ary.length; i++) {
- oldModuleMap = ary[i];
- //Update the moduleMap since the
- //module name may be normalized
- //differently now.
- callPlugin(pluginName,
- makeModuleMap(oldModuleMap.originalName, oldModuleMap.parentMap));
- }
- delete pluginsQueue[pluginName];
- }
- }
- });
- }
- pluginsQueue[pluginName].push(dep);
- }
- } else {
- if (!urlFetched[dep.url]) {
- req.load(context, fullName, dep.url);
- urlFetched[dep.url] = true;
- }
- }
- }
-
/**
* Resumes tracing of dependencies and then checks if everything is loaded.
*/
resume = function () {
- var args, i, p;
+ var manager, map, url, i, p, args, fullName;
resumeDepth += 1;
@@ -1073,9 +1044,33 @@ var requirejs, require, define;
//Reset paused list
context.paused = [];
- for (i = 0; (args = p[i]); i++) {
- loadPaused(args);
+ for (i = 0; (manager = p[i]); i++) {
+ map = manager.map;
+ url = map.url;
+ fullName = map.fullName;
+
+ //If the manager is for a plugin managed resource,
+ //ask the plugin to load it now.
+ if (map.prefix) {
+ callPlugin(map.prefix, manager);
+ } else {
+ //Regular dependency.
+ if (!urlFetched[url] && !loaded[fullName]) {
+ req.load(context, fullName, url);
+
+ //Mark the URL as fetched, but only if it is
+ //not an empty: URL, used by the optimizer.
+ //In that case we need to be sure to call
+ //load() for each module that is mapped to
+ //empty: so that dependencies are satisfied
+ //correctly.
+ if (url.indexOf('empty:') !== 0) {
+ urlFetched[url] = true;
+ }
+ }
+ }
}
+
//Move the start time for timeout forward.
context.startTime = (new Date()).getTime();
context.pausedCount -= p.length;
@@ -1107,12 +1102,15 @@ var requirejs, require, define;
specified: specified,
loaded: loaded,
urlMap: urlMap,
+ urlFetched: urlFetched,
scriptCount: 0,
- urlFetched: {},
defined: defined,
paused: [],
pausedCount: 0,
plugins: plugins,
+ needFullExec: needFullExec,
+ fake: {},
+ fullExec: fullExec,
managerCallbacks: managerCallbacks,
makeModuleMap: makeModuleMap,
normalize: normalize,
@@ -1178,7 +1176,6 @@ var requirejs, require, define;
//Allow tracing some require calls to allow the fetching
//of the priority config.
context.requireWait = false;
-
//But first, call resume to register any defined modules that may
//be in a data-main built file before the priority config
//call. Also grab any waiting define calls for this context.
@@ -1205,12 +1202,6 @@ var requirejs, require, define;
if (cfg.deps || cfg.callback) {
context.require(cfg.deps || [], cfg.callback);
}
-
- //Set up ready callback, if asked. Useful when require is defined as a
- //config object before require.js is loaded.
- if (cfg.ready) {
- req.ready(cfg.ready);
- }
},
requireDefined: function (moduleName, relModuleMap) {
@@ -1224,6 +1215,11 @@ var requirejs, require, define;
require: function (deps, callback, relModuleMap) {
var moduleName, fullName, moduleMap;
if (typeof deps === "string") {
+ if (isFunction(callback)) {
+ //Invalid call
+ return req.onError(makeError("requireargs", "Invalid require call"));
+ }
+
//Synchronous access to one module. If require.get is
//available (as in the Node adapter), prefer that.
//In this case deps is the moduleName and callback is
@@ -1250,7 +1246,11 @@ var requirejs, require, define;
return defined[fullName];
}
- main(null, deps, callback, relModuleMap);
+ //Call main but only if there are dependencies or
+ //a callback to call.
+ if (deps && deps.length || callback) {
+ main(null, deps, callback, relModuleMap);
+ }
//If the require call does not trigger anything new to load,
//then resume the dependency processing.
@@ -1263,7 +1263,7 @@ var requirejs, require, define;
resume();
}
}
- return undefined;
+ return context.require;
},
/**
@@ -1321,11 +1321,6 @@ var requirejs, require, define;
} : null]);
}
- //Mark the script as loaded. Note that this can be different from a
- //moduleName that maps to a define call. This line is important
- //for traditional browser scripts.
- loaded[moduleName] = true;
-
//If a global jQuery is defined, check for it. Need to do it here
//instead of main() since stock jQuery does not register as
//a module via define.
@@ -1476,9 +1471,17 @@ var requirejs, require, define;
};
/**
+ * Support require.config() to make it easier to cooperate with other
+ * AMD loaders on globally agreed names.
+ */
+ req.config = function (config) {
+ return req(config);
+ };
+
+ /**
* Export require as a global, but only if it does not already exist.
*/
- if (typeof require === "undefined") {
+ if (!require) {
require = req;
}
@@ -1491,17 +1494,13 @@ var requirejs, require, define;
};
req.version = version;
- req.isArray = isArray;
- req.isFunction = isFunction;
- req.mixin = mixin;
+
//Used to filter out dependencies that are already paths.
req.jsExtRegExp = /^\/|:|\?|\.js$/;
s = req.s = {
contexts: contexts,
//Stores a list of URLs that should not get async script tag treatment.
- skipAsync: {},
- isPageLoaded: !isBrowser,
- readyCalls: []
+ skipAsync: {}
};
req.isAsync = req.isBrowser = isBrowser;
@@ -1535,14 +1534,7 @@ var requirejs, require, define;
* @param {Object} url the URL to the module.
*/
req.load = function (context, moduleName, url) {
- var loaded = context.loaded;
-
- isDone = false;
-
- //Only set loaded to false for tracking if it has not already been set.
- if (!loaded[moduleName]) {
- loaded[moduleName] = false;
- }
+ req.resourcesReady(false);
context.scriptCount += 1;
req.attach(url, context, moduleName);
@@ -1579,7 +1571,7 @@ var requirejs, require, define;
* return a value to define the module corresponding to the first argument's
* name.
*/
- define = req.def = function (name, deps, callback) {
+ define = function (name, deps, callback) {
var node, context;
//Allow for anonymous functions
@@ -1591,14 +1583,14 @@ var requirejs, require, define;
}
//This module may not have dependencies
- if (!req.isArray(deps)) {
+ if (!isArray(deps)) {
callback = deps;
deps = [];
}
//If no name, and callback is a function, then figure out if it a
//CommonJS thing with dependencies.
- if (!name && !deps.length && req.isFunction(callback)) {
+ if (!deps.length && isFunction(callback)) {
//Remove comments from the callback string,
//look for require calls, and pull them into the dependencies,
//but only if there are function args.
@@ -1623,13 +1615,12 @@ var requirejs, require, define;
//work.
if (useInteractive) {
node = currentlyAddingScript || getInteractiveScript();
- if (!node) {
- return req.onError(makeError("interactive", "No matching script interactive for " + callback));
- }
- if (!name) {
- name = node.getAttribute("data-requiremodule");
+ if (node) {
+ if (!name) {
+ name = node.getAttribute("data-requiremodule");
+ }
+ context = contexts[node.getAttribute("data-requirecontext")];
}
- context = contexts[node.getAttribute("data-requirecontext")];
}
//Always save off evaluating the def call until the script onload handler.
@@ -1669,6 +1660,25 @@ var requirejs, require, define;
return callback.apply(exports, args);
};
+
+ /**
+ * Adds a node to the DOM. Public function since used by the order plugin.
+ * This method should not normally be called by outside code.
+ */
+ req.addScriptToDom = function (node) {
+ //For some cache cases in IE 6-8, the script executes before the end
+ //of the appendChild execution, so to tie an anonymous define
+ //call to the module name (which is stored on the node), hold on
+ //to a reference to this node, but clear after the DOM insertion.
+ currentlyAddingScript = node;
+ if (baseElement) {
+ head.insertBefore(node, baseElement);
+ } else {
+ head.appendChild(node);
+ }
+ currentlyAddingScript = null;
+ };
+
/**
* callback for script loads, used to check status of loading.
*
@@ -1684,7 +1694,7 @@ var requirejs, require, define;
var node = evt.currentTarget || evt.srcElement, contextName, moduleName,
context;
- if (evt.type === "load" || readyRegExp.test(node.readyState)) {
+ if (evt.type === "load" || (node && readyRegExp.test(node.readyState))) {
//Reset interactive script so a script node is not held onto for
//to long.
interactiveScript = null;
@@ -1718,9 +1728,14 @@ var requirejs, require, define;
* @param {moduleName} the name of the module that is associated with the script.
* @param {Function} [callback] optional callback, defaults to require.onScriptLoad
* @param {String} [type] optional type, defaults to text/javascript
+ * @param {Function} [fetchOnlyFunction] optional function to indicate the script node
+ * should be set up to fetch the script but do not attach it to the DOM
+ * so that it can later be attached to execute it. This is a way for the
+ * order plugin to support ordered loading in IE. Once the script is fetched,
+ * but not executed, the fetchOnlyFunction will be called.
*/
- req.attach = function (url, context, moduleName, callback, type) {
- var node, loaded;
+ req.attach = function (url, context, moduleName, callback, type, fetchOnlyFunction) {
+ var node;
if (isBrowser) {
//In the browser so use a script tag
callback = callback || req.onScriptLoad;
@@ -1761,23 +1776,36 @@ var requirejs, require, define;
//However, IE reports the script as being in "interactive"
//readyState at the time of the define call.
useInteractive = true;
- node.attachEvent("onreadystatechange", callback);
+
+
+ if (fetchOnlyFunction) {
+ //Need to use old school onreadystate here since
+ //when the event fires and the node is not attached
+ //to the DOM, the evt.srcElement is null, so use
+ //a closure to remember the node.
+ node.onreadystatechange = function (evt) {
+ //Script loaded but not executed.
+ //Clear loaded handler, set the real one that
+ //waits for script execution.
+ if (node.readyState === 'loaded') {
+ node.onreadystatechange = null;
+ node.attachEvent("onreadystatechange", callback);
+ fetchOnlyFunction(node);
+ }
+ };
+ } else {
+ node.attachEvent("onreadystatechange", callback);
+ }
} else {
node.addEventListener("load", callback, false);
}
node.src = url;
- //For some cache cases in IE 6-8, the script executes before the end
- //of the appendChild execution, so to tie an anonymous define
- //call to the module name (which is stored on the node), hold on
- //to a reference to this node, but clear after the DOM insertion.
- currentlyAddingScript = node;
- if (baseElement) {
- head.insertBefore(node, baseElement);
- } else {
- head.appendChild(node);
+ //Fetch only means waiting to attach to DOM after loaded.
+ if (!fetchOnlyFunction) {
+ req.addScriptToDom(node);
}
- currentlyAddingScript = null;
+
return node;
} else if (isWebWorker) {
//In a web worker, use importScripts. This is not a very
@@ -1786,9 +1814,6 @@ var requirejs, require, define;
//are in play, the expectation that a build has been done so that
//only one script needs to be loaded anyway. This may need to be
//reevaluated if other use cases become common.
- loaded = context.loaded;
- loaded[moduleName] = false;
-
importScripts(url);
//Account for anonymous modules
@@ -1835,36 +1860,8 @@ var requirejs, require, define;
}
}
- //Set baseUrl based on config.
- s.baseUrl = cfg.baseUrl;
-
- //****** START page load functionality ****************
- /**
- * Sets the page as loaded and triggers check for all modules loaded.
- */
- req.pageLoaded = function () {
- if (!s.isPageLoaded) {
- s.isPageLoaded = true;
- if (scrollIntervalId) {
- clearInterval(scrollIntervalId);
- }
-
- //Part of a fix for FF < 3.6 where readyState was not set to
- //complete so libraries like jQuery that check for readyState
- //after page load where not getting initialized correctly.
- //Original approach suggested by Andrea Giammarchi:
- //http://webreflection.blogspot.com/2009/11/195-chars-to-help-lazy-loading.html
- //see other setReadyState reference for the rest of the fix.
- if (setReadyState) {
- document.readyState = "complete";
- }
-
- req.callReady();
- }
- };
-
//See if there is nothing waiting across contexts, and if not, trigger
- //callReady.
+ //resourcesReady.
req.checkReadyState = function () {
var contexts = s.contexts, prop;
for (prop in contexts) {
@@ -1874,26 +1871,22 @@ var requirejs, require, define;
}
}
}
- s.isDone = true;
- req.callReady();
+ req.resourcesReady(true);
};
/**
- * Internal function that calls back any ready functions. If you are
- * integrating RequireJS with another library without require.ready support,
- * you can define this method to call your page ready code instead.
+ * Internal function that is triggered whenever all scripts/resources
+ * have been loaded by the loader. Can be overridden by other, for
+ * instance the domReady plugin, which wants to know when all resources
+ * are loaded.
*/
- req.callReady = function () {
- var callbacks = s.readyCalls, i, callback, contexts, context, prop;
-
- if (s.isPageLoaded && s.isDone) {
- if (callbacks.length) {
- s.readyCalls = [];
- for (i = 0; (callback = callbacks[i]); i++) {
- callback();
- }
- }
+ req.resourcesReady = function (isReady) {
+ var contexts, context, prop;
+
+ //First, set the public variable indicating that resources are loading.
+ req.resourcesDone = isReady;
+ if (req.resourcesDone) {
//If jQuery with DOM ready delayed, release it now.
contexts = s.contexts;
for (prop in contexts) {
@@ -1908,62 +1901,23 @@ var requirejs, require, define;
}
};
- /**
- * Registers functions to call when the page is loaded
- */
- req.ready = function (callback) {
- if (s.isPageLoaded && s.isDone) {
- callback();
- } else {
- s.readyCalls.push(callback);
+ //FF < 3.6 readyState fix. Needed so that domReady plugin
+ //works well in that environment, since require.js is normally
+ //loaded via an HTML script tag so it will be there before window load,
+ //where the domReady plugin is more likely to be loaded after window load.
+ req.pageLoaded = function () {
+ if (document.readyState !== "complete") {
+ document.readyState = "complete";
}
- return req;
};
-
if (isBrowser) {
if (document.addEventListener) {
- //Standards. Hooray! Assumption here that if standards based,
- //it knows about DOMContentLoaded.
- document.addEventListener("DOMContentLoaded", req.pageLoaded, false);
- window.addEventListener("load", req.pageLoaded, false);
- //Part of FF < 3.6 readystate fix (see setReadyState refs for more info)
if (!document.readyState) {
- setReadyState = true;
document.readyState = "loading";
+ window.addEventListener("load", req.pageLoaded, false);
}
- } else if (window.attachEvent) {
- window.attachEvent("onload", req.pageLoaded);
-
- //DOMContentLoaded approximation, as found by Diego Perini:
- //http://javascript.nwbox.com/IEContentLoaded/
- if (self === self.top) {
- scrollIntervalId = setInterval(function () {
- try {
- //From this ticket:
- //http://bugs.dojotoolkit.org/ticket/11106,
- //In IE HTML Application (HTA), such as in a selenium test,
- //javascript in the iframe can't see anything outside
- //of it, so self===self.top is true, but the iframe is
- //not the top window and doScroll will be available
- //before document.body is set. Test document.body
- //before trying the doScroll trick.
- if (document.body) {
- document.documentElement.doScroll("left");
- req.pageLoaded();
- }
- } catch (e) {}
- }, 30);
- }
- }
-
- //Check if document already complete, and if so, just trigger page load
- //listeners. NOTE: does not work with Firefox before 3.6. To support
- //those browsers, manually call require.pageLoaded().
- if (document.readyState === "complete") {
- req.pageLoaded();
}
}
- //****** END page load functionality ****************
//Set up default context. If require was a configuration object, use that as base config.
req(cfg);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]