3
Copyright 2011 Yahoo! Inc. All rights reserved.
4
Licensed under the BSD License.
5
http://yuilibrary.com/license/
8
* The YUI module contains the components required for building the YUI seed
9
* file. This includes the script loading mechanism, a simple queue, and
10
* the core utilities for the library.
15
if (typeof YUI != 'undefined') {
20
The YUI global namespace object. If YUI is already defined, the
21
existing YUI object will not be overwritten so that defined
22
namespaces are preserved. It is the constructor for the object
23
the end user interacts with. As indicated below, each instance
24
has full custom event support, but only if the event system
25
is available. This is a self-instantiable factory function. You
26
can invoke it directly like this:
28
YUI().use('*', function(Y) {
32
But it also works like this:
40
@param o* {Object} 0..n optional configuration objects. these values
41
are store in Y.config. See <a href="config.html">Config</a> for the list of supported
46
var YUI = function() {
51
instanceOf = function(o, type) {
52
return (o && o.hasOwnProperty && (o instanceof type));
54
gconf = (typeof YUI_config !== 'undefined') && YUI_config;
56
if (!(instanceOf(Y, YUI))) {
59
// set up the core environment
63
YUI.GlobalConfig is a master configuration that might span
64
multiple contexts in a non-browser environment. It is applied
65
first to all instances in all contexts.
66
@property GlobalConfig
77
YUI().use('node', function(Y) {
78
//debug files used here
83
}).use('node', function(Y) {
88
if (YUI.GlobalConfig) {
89
Y.applyConfig(YUI.GlobalConfig);
93
YUI_config is a page-level config. It is applied to all
94
instances created on the page. This is applied after
95
YUI.GlobalConfig, and before the instance level configuration
103
//Single global var to include before YUI seed file
108
YUI().use('node', function(Y) {
109
//debug files used here
114
}).use('node', function(Y) {
115
//min files used here
119
Y.applyConfig(gconf);
122
// bind the specified additional modules for this instance
129
// Each instance can accept one or more configuration objects.
130
// These are applied after YUI.GlobalConfig and YUI_Config,
131
// overriding values set in those config files if there is a '
132
// matching property.
134
Y.applyConfig(args[i]);
140
Y.instanceOf = instanceOf;
150
BASE = 'http://yui.yahooapis.com/',
151
DOC_LABEL = 'yui3-js-enabled',
152
NOOP = function() {},
153
SLICE = Array.prototype.slice,
154
APPLY_TO_AUTH = { 'io.xdrReady': 1, // the functions applyTo
155
'io.xdrResponse': 1, // can call. this should
156
'SWF.eventHandler': 1 }, // be done at build time
157
hasWin = (typeof window != 'undefined'),
158
win = (hasWin) ? window : null,
159
doc = (hasWin) ? win.document : null,
160
docEl = doc && doc.documentElement,
161
docClass = docEl && docEl.className,
163
time = new Date().getTime(),
164
add = function(el, type, fn, capture) {
165
if (el && el.addEventListener) {
166
el.addEventListener(type, fn, capture);
167
} else if (el && el.attachEvent) {
168
el.attachEvent('on' + type, fn);
171
remove = function(el, type, fn, capture) {
172
if (el && el.removeEventListener) {
173
// this can throw an uncaught exception in FF
175
el.removeEventListener(type, fn, capture);
177
} else if (el && el.detachEvent) {
178
el.detachEvent('on' + type, fn);
181
handleLoad = function() {
182
YUI.Env.windowLoaded = true;
183
YUI.Env.DOMReady = true;
185
remove(window, 'load', handleLoad);
188
getLoader = function(Y, o) {
189
var loader = Y.Env._loader;
191
//loader._config(Y.config);
192
loader.ignoreRegistered = false;
195
loader.required = [];
196
loader.loadType = null;
198
loader = new Y.Loader(Y.config);
199
Y.Env._loader = loader;
201
YUI.Env.core = Y.Array.dedupe([].concat(YUI.Env.core, [ 'loader-base', 'loader-rollup', 'loader-yui3' ]));
206
clobber = function(r, s) {
208
if (s.hasOwnProperty(i)) {
214
ALREADY_DONE = { success: true };
216
// Stamp the documentElement (HTML) with a class of "yui-loaded" to
217
// enable styles that need to key off of JS being enabled.
218
if (docEl && docClass.indexOf(DOC_LABEL) == -1) {
222
docClass += DOC_LABEL;
223
docEl.className = docClass;
226
if (VERSION.indexOf('@') > -1) {
227
VERSION = '3.3.0'; // dev time hack for cdn test
232
* Applies a new configuration object to the YUI instance config.
233
* This will merge new group/module definitions, and will also
234
* update the loader cache if necessary. Updating Y.config directly
235
* will not update the cache.
236
* @method applyConfig
237
* @param {Object} o the configuration object.
240
applyConfig: function(o) {
247
config = this.config,
248
mods = config.modules,
249
groups = config.groups,
251
loader = this.Env._loader;
254
if (o.hasOwnProperty(name)) {
256
if (mods && name == 'modules') {
258
} else if (groups && name == 'groups') {
259
clobber(groups, attr);
260
} else if (rls && name == 'rls') {
262
} else if (name == 'win') {
263
config[name] = attr.contentWindow || attr;
264
config.doc = config[name].document;
265
} else if (name == '_yuid') {
278
* Old way to apply a config to the instance (calls `applyConfig` under the hood)
281
* @param {Object} o The config to apply
283
_config: function(o) {
288
* Initialize this YUI instance
300
* The version number of the YUI instance.
308
core: ['get','features','intl-base','yui-log','yui-later','loader-base', 'loader-rollup', 'loader-yui3'],
309
mods: {}, // flat module map
310
versions: {}, // version module map
312
cdn: BASE + VERSION + '/build/',
313
// bootstrapped: false,
324
// I'll start at the \b(simpleyui).
325
// 1. Look in the test string for "simpleyui" or "yui" or
326
// "yui-base" or "yui-rls" or "yui-foobar" that comes after a word break. That is, it
327
// can't match "foyui" or "i_heart_simpleyui". This can be anywhere in the string.
328
// 2. After #1 must come a forward slash followed by the string matched in #1, so
329
// "yui-base/yui-base" or "simpleyui/simpleyui" or "yui-pants/yui-pants".
330
// 3. The second occurence of the #1 token can optionally be followed by "-debug" or "-min",
331
// so "yui/yui-min", "yui/yui-debug", "yui-base/yui-base-debug". NOT "yui/yui-tshirt".
332
// 4. This is followed by ".js", so "yui/yui.js", "simpleyui/simpleyui-min.js"
333
// 0. Going back to the beginning, now. If all that stuff in 1-4 comes after a "?" in the string,
334
// then capture the junk between the LAST "&" and the string in 1-4. So
335
// "blah?foo/yui/yui.js" will capture "foo/" and "blah?some/thing.js&3.3.0/build/yui-rls/yui-rls.js"
336
// will capture "3.3.0/build/"
340
// (?:[^&]*&) followed by 0..n characters followed by an &
341
// * in fact, find as many sets of characters followed by a & as you can
342
// ([^&]*) capture the stuff after the last & in \1
343
// )? but it's ok if all this ?junk&more_junk stuff isn't even there
344
// \b(simpleyui| after a word break find either the string "simpleyui" or
345
// yui(?:-\w+)? the string "yui" optionally followed by a -, then more characters
346
// ) and store the simpleyui or yui-* string in \2
347
// \/\2 then comes a / followed by the simpleyui or yui-* string in \2
348
// (?:-(min|debug))? optionally followed by "-min" or "-debug"
349
// .js and ending in ".js"
350
_BASE_RE: /(?:\?(?:[^&]*&)*([^&]*))?\b(simpleyui|yui(?:-\w+)?)\/\2(?:-(min|debug))?\.js/,
351
parseBasePath: function(src, pattern) {
352
var match = src.match(pattern),
356
path = RegExp.leftContext || src.slice(0, src.indexOf(match[0]));
358
// this is to set up the path to the loader. The file
359
// filter for loader should match the yui include.
362
// extract correct path for mixed combo urls
363
// http://yuilibrary.com/projects/yui3/ticket/2528423
365
path += '?' + match[1];
374
getBase: G_ENV && G_ENV.getBase ||
376
var nodes = (doc && doc.getElementsByTagName('script')) || [],
377
path = Env.cdn, parsed,
380
for (i = 0, len = nodes.length; i < len; ++i) {
383
parsed = Y.Env.parseBasePath(src, pattern);
385
filter = parsed.filter;
400
Env._loaded[VERSION] = {};
402
if (G_ENV && Y !== YUI) {
403
Env._yidx = ++G_ENV._yidx;
404
Env._guidp = ('yui_' + VERSION + '_' +
405
Env._yidx + '_' + time).replace(/\./g, '_');
406
} else if (YUI._YUI) {
408
G_ENV = YUI._YUI.Env;
409
Env._yidx += G_ENV._yidx;
410
Env._uidx += G_ENV._uidx;
412
for (prop in G_ENV) {
413
if (!(prop in Env)) {
414
Env[prop] = G_ENV[prop];
428
// configuration defaults
429
Y.config = Y.config || {
433
useBrowserConsole: true,
442
if (YUI.Env.rls_disabled) {
443
Y.config.use_rls = false;
446
Y.config.lang = Y.config.lang || 'en-US';
448
Y.config.base = YUI.config.base || Y.Env.getBase(Y.Env._BASE_RE);
450
if (!filter || (!('mindebug').indexOf(filter))) {
453
filter = (filter) ? '-' + filter : filter;
454
Y.config.loaderPath = YUI.config.loaderPath || 'loader/loader' + filter + '.js';
459
* Finishes the instance setup. Attaches whatever modules were defined
460
* when the yui modules was registered.
464
_setup: function(o) {
468
//extras = Y.config.core || ['get','features','intl-base','yui-log','yui-later','loader-base', 'loader-rollup', 'loader-yui3'];
469
extras = Y.config.core || [].concat(YUI.Env.core); //Clone it..
471
for (i = 0; i < extras.length; i++) {
472
if (mods[extras[i]]) {
473
core.push(extras[i]);
477
Y._attach(['yui-base']);
487
* Executes a method on a YUI instance with
488
* the specified id if the specified method is whitelisted.
490
* @param id {String} the YUI instance id.
491
* @param method {String} the name of the method to exectute.
493
* @param args {Array} the arguments to apply to the method.
494
* @return {Object} the return value from the applied method or null.
496
applyTo: function(id, method, args) {
497
if (!(method in APPLY_TO_AUTH)) {
498
this.log(method + ': applyTo not allowed', 'warn', 'yui');
502
var instance = instances[id], nest, m, i;
504
nest = method.split('.');
506
for (i = 0; i < nest.length; i = i + 1) {
509
this.log('applyTo not found: ' + method, 'warn', 'yui');
512
return m.apply(instance, args);
519
Registers a module with the YUI global. The easiest way to create a
520
first-class YUI module is to use the YUI component build tool.
522
http://yuilibrary.com/projects/builder
524
The build system will produce the `YUI.add` wrapper for you module, along
525
with any configuration info required for the module.
527
@param name {String} module name.
528
@param fn {Function} entry point into the module that is used to bind module to the YUI instance.
529
@param {YUI} fn.Y The YUI instance this module is executed in.
530
@param {String} fn.name The name of the module
531
@param version {String} version string.
532
@param details {Object} optional config data:
533
@param details.requires {Array} features that must be present before this module can be attached.
534
@param details.optional {Array} optional features that should be present if loadOptional
535
is defined. Note: modules are not often loaded this way in YUI 3,
536
but this field is still useful to inform the user that certain
537
features in the component will require additional dependencies.
538
@param details.use {Array} features that are included within this module which need to
539
be attached automatically when this module is attached. This
540
supports the YUI 3 rollup system -- a module with submodules
541
defined will need to have the submodules listed in the 'use'
542
config. The YUI component build tool does this for you.
543
@return {YUI} the YUI instance.
546
YUI.add('davglass', function(Y, name) {
547
Y.davglass = function() {
548
alert('Dav was here!');
550
}, '3.4.0', { requires: ['yui-base', 'harley-davidson', 'mt-dew'] });
553
add: function(name, fn, version, details) {
554
details = details || {};
563
i, versions = env.versions;
565
env.mods[name] = mod;
566
versions[version] = versions[version] || {};
567
versions[version][name] = mod;
569
for (i in instances) {
570
if (instances.hasOwnProperty(i)) {
571
loader = instances[i].Env._loader;
573
if (!loader.moduleInfo[name]) {
574
loader.addModule(details, name);
584
* Executes the function associated with each required
585
* module, binding the module to the YUI instance.
586
* @param {Array} r The array of modules to attach
587
* @param {Boolean} [moot=false] Don't throw a warning if the module is not attached
591
_attach: function(r, moot) {
592
var i, name, mod, details, req, use, after,
594
aliases = YUI.Env.aliases,
596
loader = Y.Env._loader,
597
done = Y.Env._attached,
598
len = r.length, loader,
601
//Check for conditional modules (in a second+ instance) and add their requirements
602
//TODO I hate this entire method, it needs to be fixed ASAP (3.5.0) ^davglass
603
for (i = 0; i < len; i++) {
607
if (loader && loader.conditions[name]) {
608
Y.Object.each(loader.conditions[name], function(def) {
609
var go = def && ((def.ua && Y.UA[def.ua]) || (def.test && def.test(Y)));
619
for (i = 0; i < len; i++) {
624
if (aliases && aliases[name]) {
625
Y._attach(aliases[name]);
629
if (loader && loader.moduleInfo[name]) {
630
mod = loader.moduleInfo[name];
635
//if (!loader || !loader.moduleInfo[name]) {
636
//if ((!loader || !loader.moduleInfo[name]) && !moot) {
638
if ((name.indexOf('skin-') === -1) && (name.indexOf('css') === -1)) {
639
Y.Env._missed.push(name);
640
Y.Env._missed = Y.Array.dedupe(Y.Env._missed);
641
Y.message('NOT loaded: ' + name, 'warn', 'yui');
646
//Don't like this, but in case a mod was asked for once, then we fetch it
647
//We need to remove it from the missed list ^davglass
648
for (j = 0; j < Y.Env._missed.length; j++) {
649
if (Y.Env._missed[j] === name) {
650
Y.message('Found: ' + name + ' (was reported as missing earlier)', 'warn', 'yui');
651
Y.Env._missed.splice(j, 1);
654
details = mod.details;
655
req = details.requires;
657
after = details.after;
660
for (j = 0; j < req.length; j++) {
662
if (!Y._attach(req)) {
671
for (j = 0; j < after.length; j++) {
672
if (!done[after[j]]) {
673
if (!Y._attach(after, true)) {
685
Y.error('Attach error: ' + name, e, name);
691
for (j = 0; j < use.length; j++) {
693
if (!Y._attach(use)) {
711
* Attaches one or more modules to the YUI instance. When this
712
* is executed, the requirements are analyzed, and one of
713
* several things can happen:
715
* * All requirements are available on the page -- The modules
716
* are attached to the instance. If supplied, the use callback
717
* is executed synchronously.
719
* * Modules are missing, the Get utility is not available OR
720
* the 'bootstrap' config is false -- A warning is issued about
721
* the missing modules and all available modules are attached.
723
* * Modules are missing, the Loader is not available but the Get
724
* utility is and boostrap is not false -- The loader is bootstrapped
725
* before doing the following....
727
* * Modules are missing and the Loader is available -- The loader
728
* expands the dependency tree and fetches missing modules. When
729
* the loader is finshed the callback supplied to use is executed
733
* @param modules* {String} 1-n modules to bind (uses arguments array).
734
* @param *callback {Function} callback function executed when
735
* the instance has the required functionality. If included, it
736
* must be the last parameter.
739
* // loads and attaches dd and its dependencies
740
* YUI().use('dd', function(Y) {});
742
* // loads and attaches dd and node as well as all of their dependencies (since 3.4.0)
743
* YUI().use(['dd', 'node'], function(Y) {});
745
* // attaches all modules that are available on the page
746
* YUI().use('*', function(Y) {});
748
* // intrinsic YUI gallery support (since 3.1.0)
749
* YUI().use('gallery-yql', function(Y) {});
751
* // intrinsic YUI 2in3 support (since 3.1.0)
752
* YUI().use('yui2-datatable', function(Y) {});
754
* @return {YUI} the YUI instance.
757
var args = SLICE.call(arguments, 0),
758
callback = args[args.length - 1],
765
// The last argument supplied to use can be a load complete callback
766
if (Y.Lang.isFunction(callback)) {
771
if (Y.Lang.isArray(args[0])) {
775
if (Y.config.cacheUse) {
776
while ((name = args[i++])) {
777
if (!Env._attached[name]) {
786
Y._notify(callback, ALREADY_DONE, args);
792
Y._useQueue = Y._useQueue || new Y.Queue();
793
Y._useQueue.add([args, callback]);
795
Y._use(args, function(Y, response) {
796
Y._notify(callback, response, args);
803
* Notify handler from Loader for attachment/load errors
805
* @param callback {Function} The callback to pass to the `Y.config.loadErrorFn`
806
* @param response {Object} The response returned from Loader
807
* @param args {Array} The aruments passed from Loader
810
_notify: function(callback, response, args) {
811
if (!response.success && this.config.loadErrorFn) {
812
this.config.loadErrorFn.call(this, this, callback, response, args);
813
} else if (callback) {
815
callback(this, response);
817
this.error('use callback error', e, args);
823
* This private method is called from the `use` method queue. To ensure that only one set of loading
824
* logic is performed at a time.
827
* @param args* {String} 1-n modules to bind (uses arguments array).
828
* @param *callback {Function} callback function executed when
829
* the instance has the required functionality. If included, it
830
* must be the last parameter.
832
_use: function(args, callback) {
835
this._attach(['yui-base']);
838
var len, loader, handleBoot, handleRLS,
844
queue = G_ENV._loaderQueue,
848
boot = config.bootstrap,
852
fetchCSS = config.fetchCSS,
853
process = function(names, skip) {
859
YArray.each(names, function(name) {
861
// add this module to full list of things to attach
866
// only attach a module once
871
var m = mods[name], req, use;
875
req = m.details.requires;
878
// CSS files don't register themselves, see if it has
880
if (!G_ENV._loaded[VERSION][name]) {
883
used[name] = true; // probably css
887
// make sure requirements are attached
888
if (req && req.length) {
892
// make sure we grab the submodule dependencies too
893
if (use && use.length) {
899
handleLoader = function(fromLoader) {
900
var response = fromLoader || {
906
data = response.data;
912
origMissing = missing;
916
redo = missing.length;
918
if (missing.sort().join() ==
919
origMissing.sort().join()) {
927
Y._use(args, function() {
928
if (Y._attach(data)) {
929
Y._notify(callback, response, data);
934
ret = Y._attach(data);
937
Y._notify(callback, response, args);
941
if (Y._useQueue && Y._useQueue.size() && !Y._loading) {
942
Y._use.apply(Y, Y._useQueue.next());
948
// YUI().use('*'); // bind everything available
949
if (firstArg === '*') {
950
ret = Y._attach(Y.Object.keys(mods));
958
// use loader to expand dependencies and sort the
959
// requirements if it is available.
960
if (boot && Y.Loader && args.length) {
961
loader = getLoader(Y);
962
loader.require(args);
963
loader.ignoreRegistered = true;
964
loader.calculate(null, (fetchCSS) ? null : 'js');
965
args = loader.sorted;
968
// process each requirement and any additional requirements
969
// the module metadata specifies
972
len = missing.length;
975
missing = Y.Object.keys(YArray.hash(missing));
976
len = missing.length;
981
if (boot && len && Y.Loader) {
983
loader = getLoader(Y);
984
loader.onEnd = handleLoader;
987
loader.ignoreRegistered = false;
988
loader.require(args);
989
loader.insert(null, (fetchCSS) ? null : 'js');
990
// loader.partial(missing, (fetchCSS) ? null : 'js');
992
} else if (len && Y.config.use_rls && !YUI.Env.rls_enabled) {
994
G_ENV._rls_queue = G_ENV._rls_queue || new Y.Queue();
996
// server side loader service
997
handleRLS = function(instance, argz) {
999
var rls_end = function(o) {
1001
instance.rls_advance();
1003
rls_url = instance._rls(argz);
1006
instance.rls_oncomplete(function(o) {
1009
instance.Get.script(rls_url, {
1011
timeout: instance.config.rls_timeout,
1012
onFailure: instance.rls_handleFailure,
1013
onTimeout: instance.rls_handleTimeout
1023
G_ENV._rls_queue.add(function() {
1024
G_ENV._rls_in_progress = true;
1025
Y.rls_callback = callback;
1026
Y.rls_locals(Y, args, handleRLS);
1029
if (!G_ENV._rls_in_progress && G_ENV._rls_queue.size()) {
1030
G_ENV._rls_queue.next()();
1033
} else if (boot && len && Y.Get && !Env.bootstrapped) {
1037
handleBoot = function() {
1039
queue.running = false;
1040
Env.bootstrapped = true;
1041
G_ENV._bootstrapping = false;
1042
if (Y._attach(['loader'])) {
1043
Y._use(args, callback);
1047
if (G_ENV._bootstrapping) {
1048
queue.add(handleBoot);
1050
G_ENV._bootstrapping = true;
1051
Y.Get.script(config.base + config.loaderPath, {
1057
ret = Y._attach(args);
1068
Adds a namespace object onto the YUI global if called statically.
1070
// creates YUI.your.namespace.here as nested objects
1071
YUI.namespace("your.namespace.here");
1073
If called as a method on a YUI <em>instance</em>, it creates the
1074
namespace on the instance.
1076
// creates Y.property.package
1077
Y.namespace("property.package");
1079
Dots in the input string cause `namespace` to create nested objects for
1080
each token. If any part of the requested namespace already exists, the
1081
current object will be left in place. This allows multiple calls to
1082
`namespace` to preserve existing namespaced properties.
1084
If the first token in the namespace string is "YAHOO", the token is
1087
Be careful with namespace tokens. Reserved words may work in some browsers
1088
and not others. For instance, the following will fail in some browsers
1089
because the supported version of JavaScript reserves the word "long":
1091
Y.namespace("really.long.nested.namespace");
1094
@param {String} namespace* namespaces to create.
1095
@return {Object} A reference to the last namespace object created.
1097
namespace: function() {
1098
var a = arguments, o = this, i = 0, j, d, arg;
1099
for (; i < a.length; i++) {
1100
// d = ('' + a[i]).split('.');
1102
if (arg.indexOf(PERIOD)) {
1103
d = arg.split(PERIOD);
1104
for (j = (d[0] == 'YAHOO') ? 1 : 0; j < d.length; j++) {
1105
o[d[j]] = o[d[j]] || {};
1109
o[arg] = o[arg] || {};
1115
// this is replaced if the log module is included
1118
// this is replaced if the dump module is included
1119
dump: function (o) { return ''+o; },
1122
* Report an error. The reporting mechanism is controled by
1123
* the `throwFail` configuration attribute. If throwFail is
1124
* not specified, the message is written to the Logger, otherwise
1125
* a JS error is thrown
1127
* @param msg {String} the error message.
1128
* @param e {Error|String} Optional JS error that was caught, or an error string.
1129
* @param data Optional additional info
1130
* and `throwFail` is specified, this error will be re-thrown.
1131
* @return {YUI} this YUI instance.
1133
error: function(msg, e, data) {
1137
if (Y.config.errorFn) {
1138
ret = Y.config.errorFn.apply(Y, arguments);
1141
if (Y.config.throwFail && !ret) {
1142
throw (e || new Error(msg));
1144
Y.message(msg, 'error'); // don't scrub this one
1151
* Generate an id that is unique among all YUI instances
1153
* @param pre {String} optional guid prefix.
1154
* @return {String} the guid.
1156
guid: function(pre) {
1157
var id = this.Env._guidp + '_' + (++this.Env._uidx);
1158
return (pre) ? (pre + id) : id;
1162
* Returns a `guid` associated with an object. If the object
1163
* does not have one, a new one is created unless `readOnly`
1166
* @param o {Object} The object to stamp.
1167
* @param readOnly {Boolean} if `true`, a valid guid will only
1168
* be returned if the object has one assigned to it.
1169
* @return {String} The object's guid or null.
1171
stamp: function(o, readOnly) {
1177
// IE generates its own unique ID for dom nodes
1178
// The uniqueID property of a document node returns a new ID
1179
if (o.uniqueID && o.nodeType && o.nodeType !== 9) {
1182
uid = (typeof o === 'string') ? o : o._yuid;
1199
* Destroys the YUI instance
1203
destroy: function() {
1208
delete instances[Y.id];
1214
* instanceof check for objects that works around
1215
* memory leak in IE when the item tested is
1217
* @method instanceOf
1224
YUI.prototype = proto;
1226
// inheritance utilities are not available yet
1227
for (prop in proto) {
1228
if (proto.hasOwnProperty(prop)) {
1229
YUI[prop] = proto[prop];
1233
// set up the environment
1237
// add a window load event at load time so we can capture
1238
// the case where it fires before dynamic loading is
1240
add(window, 'load', handleLoad);
1246
YUI.Env.remove = remove;
1249
// Support the CommonJS method for exporting our single global
1250
if (typeof exports == 'object') {
1258
* The config object contains all of the configuration options for
1259
* the `YUI` instance. This object is supplied by the implementer
1260
* when instantiating a `YUI` instance. Some properties have default
1261
* values if they are not supplied by the implementer. This should
1262
* not be updated directly because some values are cached. Use
1263
* `applyConfig()` to update the config object on a YUI instance that
1264
* has already been configured.
1271
* Allows the YUI seed file to fetch the loader component and library
1272
* metadata to dynamically load additional dependencies.
1274
* @property bootstrap
1280
* Log to the browser console if debug is on and the browser has a
1281
* supported console.
1283
* @property useBrowserConsole
1289
* A hash of log sources that should be logged. If specified, only
1290
* log messages from these sources will be logged.
1292
* @property logInclude
1297
* A hash of log sources that should be not be logged. If specified,
1298
* all sources are logged if not on this list.
1300
* @property logExclude
1305
* Set to true if the yui seed file was dynamically loaded in
1306
* order to bootstrap components relying on the window load event
1307
* and the `domready` custom event.
1309
* @property injected
1315
* If `throwFail` is set, `Y.error` will generate or re-throw a JS Error.
1316
* Otherwise the failure is logged.
1318
* @property throwFail
1324
* The window/frame that this instance should operate in.
1328
* @default the window hosting YUI
1332
* The document associated with the 'win' configuration.
1336
* @default the document hosting YUI
1340
* A list of modules that defines the YUI core (overrides the default).
1347
* A list of languages in order of preference. This list is matched against
1348
* the list of available languages in modules that the YUI instance uses to
1349
* determine the best possible localization of language sensitive modules.
1350
* Languages are represented using BCP 47 language tags, such as "en-GB" for
1351
* English as used in the United Kingdom, or "zh-Hans-CN" for simplified
1352
* Chinese as used in China. The list can be provided as a comma-separated
1353
* list or as an array.
1356
* @type string|string[]
1360
* The default date format
1361
* @property dateFormat
1363
* @deprecated use configuration in `DataType.Date.format()` instead.
1367
* The default locale
1370
* @deprecated use `config.lang` instead.
1374
* The default interval when polling in milliseconds.
1375
* @property pollInterval
1381
* The number of dynamic nodes to insert by default before
1382
* automatically removing them. This applies to script nodes
1383
* because removing the node will not make the evaluated script
1384
* unavailable. Dynamic CSS is not auto purged, because removing
1385
* a linked style sheet will also remove the style definitions.
1386
* @property purgethreshold
1392
* The default interval when polling in milliseconds.
1393
* @property windowResizeDelay
1399
* Base directory for dynamic loading
1405
* The secure base dir (not implemented)
1406
* For dynamic loading.
1407
* @property secureBase
1412
* The YUI combo service base dir. Ex: `http://yui.yahooapis.com/combo?`
1413
* For dynamic loading.
1414
* @property comboBase
1419
* The root path to prepend to module path for the combo service.
1420
* Ex: 3.0.0b1/build/
1421
* For dynamic loading.
1427
* A filter to apply to result urls. This filter will modify the default
1428
* path for all modules. The default path for the YUI library is the
1429
* minified version of the files (e.g., event-min.js). The filter property
1430
* can be a predefined filter or a custom filter. The valid predefined
1434
* <dd>Selects the debug versions of the library (e.g., event-debug.js).
1435
* This option will automatically include the Logger widget</dd>
1437
* <dd>Selects the non-minified version of the library (e.g., event.js).</dd>
1439
* You can also define a custom filter, which must be an object literal
1440
* containing a search expression and a replace string:
1443
* 'searchExp': "-min\\.js",
1444
* 'replaceStr': "-debug.js"
1447
* For dynamic loading.
1450
* @type string|object
1454
* The `skin` config let's you configure application level skin
1455
* customizations. It contains the following attributes which
1456
* can be specified to override the defaults:
1458
* // The default skin, which is automatically applied if not
1459
* // overriden by a component-specific skin definition.
1460
* // Change this in to apply a different skin globally
1461
* defaultSkin: 'sam',
1463
* // This is combined with the loader base property to get
1464
* // the default root directory for a skin.
1465
* base: 'assets/skins/',
1467
* // Any component-specific overrides can be specified here,
1468
* // making it possible to load different skins for different
1469
* // components. It is possible to load more than one skin
1470
* // for a given component as well.
1472
* slider: ['capsule', 'round']
1475
* For dynamic loading.
1481
* Hash of per-component filter specification. If specified for a given
1482
* component, this overrides the filter config.
1484
* For dynamic loading.
1490
* Use the YUI combo service to reduce the number of http connections
1491
* required to load your dependencies. Turning this off will
1492
* disable combo handling for YUI and all module groups configured
1493
* with a combo service.
1495
* For dynamic loading.
1499
* @default true if 'base' is not supplied, false if it is.
1503
* A list of modules that should never be dynamically loaded
1510
* A list of modules that should always be loaded when required, even if already
1511
* present on the page.
1518
* Node or id for a node that should be used as the insertion point for new
1519
* nodes. For dynamic loading.
1521
* @property insertBefore
1526
* Object literal containing attributes to add to dynamically loaded script
1528
* @property jsAttributes
1533
* Object literal containing attributes to add to dynamically loaded link
1535
* @property cssAttributes
1540
* Number of milliseconds before a timeout occurs when dynamically
1541
* loading nodes. If not set, there is no timeout.
1547
* Callback for the 'CSSComplete' event. When dynamically loading YUI
1548
* components with CSS, this property fires when the CSS is finished
1549
* loading but script loading is still ongoing. This provides an
1550
* opportunity to enhance the presentation of a loading page a little
1551
* bit before the entire loading process is done.
1558
* A hash of module definitions to add to the list of YUI components.
1559
* These components can then be dynamically loaded side by side with
1560
* YUI via the `use()` method. This is a hash, the key is the module
1561
* name, and the value is an object literal specifying the metdata
1562
* for the module. See `Loader.addModule` for the supported module
1563
* metadata fields. Also see groups, which provides a way to
1564
* configure the base and combo spec for a set of modules.
1568
* requires: ['node'],
1569
* fullpath: 'http://myserver.mydomain.com/mymod1/mymod1.js'
1572
* requires: ['mymod1'],
1573
* fullpath: 'http://myserver.mydomain.com/mymod2/mymod2.js'
1582
* A hash of module group definitions. It for each group you
1583
* can specify a list of modules and the base path and
1584
* combo spec to use when dynamically loading the modules.
1588
* // specify whether or not this group has a combo service
1591
* // the base path for non-combo paths
1592
* base: 'http://yui.yahooapis.com/2.8.0r4/build/',
1594
* // the path to the combo service
1595
* comboBase: 'http://yui.yahooapis.com/combo?',
1597
* // a fragment to prepend to the path attribute when
1598
* // when building combo urls
1599
* root: '2.8.0r4/build/',
1601
* // the module definitions
1604
* path: "yahoo-dom-event/yahoo-dom-event.js"
1607
* path: "animation/animation.js",
1608
* requires: ['yui2_yde']
1619
* The loader 'path' attribute to the loader itself. This is combined
1620
* with the 'base' attribute to dynamically load the loader component
1621
* when boostrapping with the get utility alone.
1623
* @property loaderPath
1625
* @default loader/loader-min.js
1629
* Specifies whether or not YUI().use(...) will attempt to load CSS
1630
* resources at all. Any truthy value will cause CSS dependencies
1631
* to load when fetching script. The special value 'force' will
1632
* cause CSS dependencies to be loaded even if no script is needed.
1634
* @property fetchCSS
1635
* @type boolean|string
1640
* The default gallery version to build gallery module urls
1647
* The default YUI 2 version to build yui2 module urls. This is for
1648
* intrinsic YUI 2 support via the 2in3 project. Also see the '2in3'
1649
* config for pulling different revisions of the wrapped YUI 2
1658
* The 2in3 project is a deployment of the various versions of YUI 2
1659
* deployed as first-class YUI 3 modules. Eventually, the wrapper
1660
* for the modules will change (but the underlying YUI 2 code will
1661
* be the same), and you can select a particular version of
1662
* the wrapper modules via this config.
1670
* Alternative console log function for use in environments without
1671
* a supported native console. The function is executed in the
1672
* YUI instance context.
1679
* A callback to execute when Y.error is called. It receives the
1680
* error message and an javascript error object if Y.error was
1681
* executed because a javascript error was caught. The function
1682
* is executed in the YUI instance context.
1690
* A callback to execute when the loader fails to load one or
1691
* more resource. This could be because of a script load
1692
* failure. It can also fail if a javascript module fails
1693
* to register itself, but only when the 'requireRegistration'
1694
* is true. If this function is defined, the use() callback will
1695
* only be called when the loader succeeds, otherwise it always
1696
* executes unless there was a javascript error when attaching
1700
* @property loadErrorFn
1705
* When set to true, the YUI loader will expect that all modules
1706
* it is responsible for loading will be first-class YUI modules
1707
* that register themselves with the YUI global. If this is
1708
* set to true, loader will fail if the module registration fails
1709
* to happen after the script is loaded.
1712
* @property requireRegistration
1718
* Cache serviced use() requests.
1720
* @property cacheUse
1723
* @deprecated no longer used
1727
* The parameter defaults for the remote loader service. **Requires the rls seed file.** The properties that are supported:
1729
* * `m`: comma separated list of module requirements. This
1730
* must be the param name even for custom implemetations.
1731
* * `v`: the version of YUI to load. Defaults to the version
1732
* of YUI that is being used.
1733
* * `gv`: the version of the gallery to load (see the gallery config)
1734
* * `env`: comma separated list of modules already on the page.
1735
* this must be the param name even for custom implemetations.
1736
* * `lang`: the languages supported on the page (see the lang config)
1737
* * `'2in3v'`: the version of the 2in3 wrapper to use (see the 2in3 config).
1738
* * `'2v'`: the version of yui2 to use in the yui 2in3 wrappers
1739
* * `filt`: a filter def to apply to the urls (see the filter config).
1740
* * `filts`: a list of custom filters to apply per module
1741
* * `tests`: this is a map of conditional module test function id keys
1742
* with the values of 1 if the test passes, 0 if not. This must be
1743
* the name of the querystring param in custom templates.
1751
* The base path to the remote loader service. **Requires the rls seed file.**
1754
* @property rls_base
1759
* The template to use for building the querystring portion
1760
* of the remote loader service url. The default is determined
1761
* by the rls config -- each property that has a value will be
1762
* represented. **Requires the rls seed file.**
1765
* @property rls_tmpl
1768
* m={m}&v={v}&env={env}&lang={lang}&filt={filt}&tests={tests}
1773
* Configure the instance to use a remote loader service instead of
1774
* the client loader. **Requires the rls seed file.**
1780
YUI.add('yui-base', function(Y) {
1785
* @submodule yui-base
1788
* The YUI module contains the components required for building the YUI
1789
* seed file. This includes the script loading mechanism, a simple queue,
1790
* and the core utilities for the library.
1792
* @submodule yui-base
1796
* Provides core language utilites and extensions used throughout YUI.
1802
var L = Y.Lang || (Y.Lang = {}),
1804
STRING_PROTO = String.prototype,
1805
TOSTRING = Object.prototype.toString,
1808
'undefined' : 'undefined',
1809
'number' : 'number',
1810
'boolean' : 'boolean',
1811
'string' : 'string',
1812
'[object Function]': 'function',
1813
'[object RegExp]' : 'regexp',
1814
'[object Array]' : 'array',
1815
'[object Date]' : 'date',
1816
'[object Error]' : 'error'
1819
SUBREGEX = /\{\s*([^|}]+?)\s*(?:\|([^}]*))?\s*\}/g,
1820
TRIMREGEX = /^\s+|\s+$/g,
1822
// If either MooTools or Prototype is on the page, then there's a chance that we
1823
// can't trust "native" language features to actually be native. When this is
1824
// the case, we take the safe route and fall back to our own non-native
1827
unsafeNatives = win && !!(win.MooTools || win.Prototype);
1830
* Determines whether or not the provided item is an array.
1832
* Returns `false` for array-like collections such as the function `arguments`
1833
* collection or `HTMLElement` collections. Use `Y.Array.test()` if you want to
1834
* test for an array-like collection.
1837
* @param o The object to test.
1838
* @return {boolean} true if o is an array.
1841
L.isArray = (!unsafeNatives && Array.isArray) || function (o) {
1842
return L.type(o) === 'array';
1846
* Determines whether or not the provided item is a boolean.
1849
* @param o The object to test.
1850
* @return {boolean} true if o is a boolean.
1852
L.isBoolean = function(o) {
1853
return typeof o === 'boolean';
1858
* Determines whether or not the provided item is a function.
1859
* Note: Internet Explorer thinks certain functions are objects:
1863
* var obj = document.createElement("object");
1864
* Y.Lang.isFunction(obj.getAttribute) // reports false in IE
1866
* var input = document.createElement("input"); // append to body
1867
* Y.Lang.isFunction(input.focus) // reports false in IE
1871
* You will have to implement additional tests if these functions
1875
* @method isFunction
1877
* @param o The object to test.
1878
* @return {boolean} true if o is a function.
1880
L.isFunction = function(o) {
1881
return L.type(o) === 'function';
1885
* Determines whether or not the supplied item is a date instance.
1888
* @param o The object to test.
1889
* @return {boolean} true if o is a date.
1891
L.isDate = function(o) {
1892
return L.type(o) === 'date' && o.toString() !== 'Invalid Date' && !isNaN(o);
1896
* Determines whether or not the provided item is null.
1899
* @param o The object to test.
1900
* @return {boolean} true if o is null.
1902
L.isNull = function(o) {
1907
* Determines whether or not the provided item is a legal number.
1910
* @param o The object to test.
1911
* @return {boolean} true if o is a number.
1913
L.isNumber = function(o) {
1914
return typeof o === 'number' && isFinite(o);
1918
* Determines whether or not the provided item is of type object
1919
* or function. Note that arrays are also objects, so
1920
* <code>Y.Lang.isObject([]) === true</code>.
1923
* @param o The object to test.
1924
* @param failfn {boolean} fail if the input is a function.
1925
* @return {boolean} true if o is an object.
1926
* @see isPlainObject
1928
L.isObject = function(o, failfn) {
1930
return (o && (t === 'object' ||
1931
(!failfn && (t === 'function' || L.isFunction(o))))) || false;
1935
* Determines whether or not the provided item is a string.
1938
* @param o The object to test.
1939
* @return {boolean} true if o is a string.
1941
L.isString = function(o) {
1942
return typeof o === 'string';
1946
* Determines whether or not the provided item is undefined.
1947
* @method isUndefined
1949
* @param o The object to test.
1950
* @return {boolean} true if o is undefined.
1952
L.isUndefined = function(o) {
1953
return typeof o === 'undefined';
1957
* Returns a string without any leading or trailing whitespace. If
1958
* the input is not a string, the input will be returned untouched.
1961
* @param s {string} the string to trim.
1962
* @return {string} the trimmed string.
1964
L.trim = STRING_PROTO.trim ? function(s) {
1965
return s && s.trim ? s.trim() : s;
1968
return s.replace(TRIMREGEX, '');
1975
* Returns a string without any leading whitespace.
1978
* @param s {string} the string to trim.
1979
* @return {string} the trimmed string.
1981
L.trimLeft = STRING_PROTO.trimLeft ? function (s) {
1982
return s.trimLeft();
1984
return s.replace(/^\s+/, '');
1988
* Returns a string without any trailing whitespace.
1991
* @param s {string} the string to trim.
1992
* @return {string} the trimmed string.
1994
L.trimRight = STRING_PROTO.trimRight ? function (s) {
1995
return s.trimRight();
1997
return s.replace(/\s+$/, '');
2001
* A convenience method for detecting a legitimate non-null value.
2002
* Returns false for null/undefined/NaN, true for other values,
2003
* including 0/false/''
2006
* @param o The item to test.
2007
* @return {boolean} true if it is not null/undefined/NaN || false.
2009
L.isValue = function(o) {
2016
case 'null': // fallthru
2027
* Returns a string representing the type of the item passed in.
2036
* <code>typeof HTMLElementCollection</code> returns function in Safari, but
2037
* <code>Y.type()</code> reports object, which could be a good thing --
2038
* but it actually caused the logic in <code>Y.Lang.isObject</code> to fail.
2043
* @param o the item to test.
2044
* @return {string} the detected type.
2047
L.type = function(o) {
2048
return TYPES[typeof o] || TYPES[TOSTRING.call(o)] || (o ? 'object' : 'null');
2052
* Lightweight version of <code>Y.substitute</code>. Uses the same template
2053
* structure as <code>Y.substitute</code>, but doesn't support recursion,
2054
* auto-object coersion, or formats.
2056
* @param {string} s String to be modified.
2057
* @param {object} o Object containing replacement values.
2058
* @return {string} the substitute result.
2062
L.sub = function(s, o) {
2063
return s.replace ? s.replace(SUBREGEX, function (match, key) {
2064
return L.isUndefined(o[key]) ? match : o[key];
2069
* Returns the current time in milliseconds.
2072
* @return {Number} Current time in milliseconds.
2076
L.now = Date.now || function () {
2077
return new Date().getTime();
2085
Native = Array.prototype,
2087
hasOwn = Object.prototype.hasOwnProperty;
2090
Provides utility methods for working with arrays. Additional array helpers can
2091
be found in the `collection` and `array-extras` modules.
2093
`Y.Array(thing)` returns a native array created from _thing_. Depending on
2094
_thing_'s type, one of the following will happen:
2096
* Arrays are returned unmodified unless a non-zero _startIndex_ is
2098
* Array-like collections (see `Array.test()`) are converted to arrays.
2099
* For everything else, a new array is created with _thing_ as the sole
2102
Note: elements that are also collections, such as `<form>` and `<select>`
2103
elements, are not automatically converted to arrays. To force a conversion,
2104
pass `true` as the value of the _force_ parameter.
2108
@param {Any} thing The thing to arrayify.
2109
@param {Number} [startIndex=0] If non-zero and _thing_ is an array or array-like
2110
collection, a subset of items starting at the specified index will be
2112
@param {Boolean} [force=false] If `true`, _thing_ will be treated as an
2113
array-like collection no matter what.
2114
@return {Array} A native array created from _thing_, according to the rules
2117
function YArray(thing, startIndex, force) {
2120
startIndex || (startIndex = 0);
2122
if (force || YArray.test(thing)) {
2123
// IE throws when trying to slice HTMLElement collections.
2125
return Native.slice.call(thing, startIndex);
2129
for (len = thing.length; startIndex < len; ++startIndex) {
2130
result.push(thing[startIndex]);
2143
Dedupes an array of strings, returning an array that's guaranteed to contain
2144
only one copy of a given string.
2146
This method differs from `Array.unique()` in that it's optimized for use only
2147
with strings, whereas `unique` may be used with other types (but is slower).
2148
Using `dedupe()` with non-string values may result in unexpected behavior.
2151
@param {String[]} array Array of strings to dedupe.
2152
@return {Array} Deduped copy of _array_.
2156
YArray.dedupe = function (array) {
2161
for (i = 0, len = array.length; i < len; ++i) {
2164
if (!hasOwn.call(hash, item)) {
2174
Executes the supplied function on each item in the array. This method wraps
2175
the native ES5 `Array.forEach()` method if available.
2178
@param {Array} array Array to iterate.
2179
@param {Function} fn Function to execute on each item in the array. The function
2180
will receive the following arguments:
2181
@param {Any} fn.item Current array item.
2182
@param {Number} fn.index Current array index.
2183
@param {Array} fn.array Array being iterated.
2184
@param {Object} [thisObj] `this` object to use when calling _fn_.
2185
@return {YUI} The YUI instance.
2188
YArray.each = YArray.forEach = Native.forEach ? function (array, fn, thisObj) {
2189
Native.forEach.call(array || [], fn, thisObj || Y);
2191
} : function (array, fn, thisObj) {
2192
for (var i = 0, len = (array && array.length) || 0; i < len; ++i) {
2194
fn.call(thisObj || Y, array[i], i, array);
2209
Returns an object using the first array as keys and the second as values. If
2210
the second array is not provided, or if it doesn't contain the same number of
2211
values as the first array, then `true` will be used in place of the missing
2216
Y.Array.hash(['a', 'b', 'c'], ['foo', 'bar']);
2217
// => {a: 'foo', b: 'bar', c: true}
2220
@param {String[]} keys Array of strings to use as keys.
2221
@param {Array} [values] Array to use as values.
2222
@return {Object} Hash using the first array as keys and the second as values.
2225
YArray.hash = function (keys, values) {
2227
vlen = (values && values.length) || 0,
2230
for (i = 0, len = keys.length; i < len; ++i) {
2232
hash[keys[i]] = vlen > i && i in values ? values[i] : true;
2240
Returns the index of the first item in the array that's equal (using a strict
2241
equality check) to the specified _value_, or `-1` if the value isn't found.
2243
This method wraps the native ES5 `Array.indexOf()` method if available.
2246
@param {Array} array Array to search.
2247
@param {Any} value Value to search for.
2248
@return {Number} Index of the item strictly equal to _value_, or `-1` if not
2252
YArray.indexOf = Native.indexOf ? function (array, value) {
2253
// TODO: support fromIndex
2254
return Native.indexOf.call(array, value);
2255
} : function (array, value) {
2256
for (var i = 0, len = array.length; i < len; ++i) {
2257
if (i in array && array[i] === value) {
2266
Numeric sort convenience function.
2268
The native `Array.prototype.sort()` function converts values to strings and
2269
sorts them in lexicographic order, which is unsuitable for sorting numeric
2270
values. Provide `Array.numericSort` as a custom sort function when you want
2271
to sort values in numeric order.
2275
[42, 23, 8, 16, 4, 15].sort(Y.Array.numericSort);
2276
// => [4, 8, 15, 16, 23, 42]
2279
@param {Number} a First value to compare.
2280
@param {Number} b Second value to compare.
2281
@return {Number} Difference between _a_ and _b_.
2284
YArray.numericSort = function (a, b) {
2289
Executes the supplied function on each item in the array. Returning a truthy
2290
value from the function will stop the processing of remaining items.
2293
@param {Array} array Array to iterate over.
2294
@param {Function} fn Function to execute on each item. The function will receive
2295
the following arguments:
2296
@param {Any} fn.value Current array item.
2297
@param {Number} fn.index Current array index.
2298
@param {Array} fn.array Array being iterated over.
2299
@param {Object} [thisObj] `this` object to use when calling _fn_.
2300
@return {Boolean} `true` if the function returns a truthy value on any of the
2301
items in the array; `false` otherwise.
2304
YArray.some = Native.some ? function (array, fn, thisObj) {
2305
return Native.some.call(array, fn, thisObj);
2306
} : function (array, fn, thisObj) {
2307
for (var i = 0, len = array.length; i < len; ++i) {
2308
if (i in array && fn.call(thisObj, array[i], i, array)) {
2317
Evaluates _obj_ to determine if it's an array, an array-like collection, or
2318
something else. This is useful when working with the function `arguments`
2319
collection and `HTMLElement` collections.
2321
Note: This implementation doesn't consider elements that are also
2322
collections, such as `<form>` and `<select>`, to be array-like.
2325
@param {Object} obj Object to test.
2326
@return {Number} A number indicating the results of the test:
2328
* 0: Neither an array nor an array-like collection.
2330
* 2: Array-like collection.
2334
YArray.test = function (obj) {
2337
if (Lang.isArray(obj)) {
2339
} else if (Lang.isObject(obj)) {
2341
// indexed, but no tagName (element) or alert (window),
2342
// or functions without apply/call (Safari
2343
// HTMLElementCollection bug).
2344
if ('length' in obj && !obj.tagName && !obj.alert && !obj.apply) {
2353
* The YUI module contains the components required for building the YUI
2354
* seed file. This includes the script loading mechanism, a simple queue,
2355
* and the core utilities for the library.
2357
* @submodule yui-base
2361
* A simple FIFO queue. Items are added to the Queue with add(1..n items) and
2362
* removed using next().
2366
* @param {MIXED} item* 0..n items to seed the queue.
2370
this.add.apply(this, arguments);
2375
* Initialize the queue
2382
* The collection of enqueued items
2392
* Get the next item in the queue. FIFO support
2395
* @return {MIXED} the next item in the queue.
2398
return this._q.shift();
2402
* Get the last in the queue. LIFO support.
2405
* @return {MIXED} the last item in the queue.
2408
return this._q.pop();
2412
* Add 0..n items to the end of the queue.
2415
* @param {MIXED} item* 0..n items.
2416
* @return {object} this queue.
2419
this._q.push.apply(this._q, arguments);
2425
* Returns the current number of queued items.
2428
* @return {Number} The size.
2431
return this._q.length;
2437
YUI.Env._loaderQueue = YUI.Env._loaderQueue || new Queue();
2440
The YUI module contains the components required for building the YUI seed file.
2441
This includes the script loading mechanism, a simple queue, and the core
2442
utilities for the library.
2448
var CACHED_DELIMITER = '__',
2450
hasOwn = Object.prototype.hasOwnProperty,
2451
isObject = Y.Lang.isObject;
2454
Returns a wrapper for a function which caches the return value of that function,
2455
keyed off of the combined string representation of the argument values provided
2456
when the wrapper is called.
2458
Calling this function again with the same arguments will return the cached value
2459
rather than executing the wrapped function.
2461
Note that since the cache is keyed off of the string representation of arguments
2462
passed to the wrapper function, arguments that aren't strings and don't provide
2463
a meaningful `toString()` method may result in unexpected caching behavior. For
2464
example, the objects `{}` and `{foo: 'bar'}` would both be converted to the
2465
string `[object Object]` when used as a cache key.
2468
@param {Function} source The function to memoize.
2469
@param {Object} [cache={}] Object in which to store cached values. You may seed
2470
this object with pre-existing cached values if desired.
2471
@param {any} [refetch] If supplied, this value is compared with the cached value
2472
using a `==` comparison. If the values are equal, the wrapped function is
2473
executed again even though a cached value exists.
2474
@return {Function} Wrapped function.
2477
Y.cached = function (source, cache, refetch) {
2478
cache || (cache = {});
2480
return function (arg) {
2481
var key = arguments.length > 1 ?
2482
Array.prototype.join.call(arguments, CACHED_DELIMITER) :
2485
if (!(key in cache) || (refetch && cache[key] == refetch)) {
2486
cache[key] = source.apply(source, arguments);
2494
Returns a new object containing all of the properties of all the supplied
2495
objects. The properties from later objects will overwrite those in earlier
2498
Passing in a single object will create a shallow copy of it. For a deep copy,
2502
@param {Object} objects* One or more objects to merge.
2503
@return {Object} A new merged object.
2505
Y.merge = function () {
2506
var args = arguments,
2511
for (; i < len; ++i) {
2512
Y.mix(result, args[i], true);
2519
Mixes _supplier_'s properties into _receiver_.
2521
Properties on _receiver_ or _receiver_'s prototype will not be overwritten or
2522
shadowed unless the _overwrite_ parameter is `true`, and will not be merged
2523
unless the _merge_ parameter is `true`.
2525
In the default mode (0), only properties the supplier owns are copied (prototype
2526
properties are not copied). The following copying modes are available:
2528
* `0`: _Default_. Object to object.
2529
* `1`: Prototype to prototype.
2530
* `2`: Prototype to prototype and object to object.
2531
* `3`: Prototype to object.
2532
* `4`: Object to prototype.
2535
@param {Function|Object} receiver The object or function to receive the mixed
2537
@param {Function|Object} supplier The object or function supplying the
2538
properties to be mixed.
2539
@param {Boolean} [overwrite=false] If `true`, properties that already exist
2540
on the receiver will be overwritten with properties from the supplier.
2541
@param {String[]} [whitelist] An array of property names to copy. If
2542
specified, only the whitelisted properties will be copied, and all others
2544
@param {Number} [mode=0] Mix mode to use. See above for available modes.
2545
@param {Boolean} [merge=false] If `true`, objects and arrays that already
2546
exist on the receiver will have the corresponding object/array from the
2547
supplier merged into them, rather than being skipped or overwritten. When
2548
both _overwrite_ and _merge_ are `true`, _merge_ takes precedence.
2549
@return {Function|Object|YUI} The receiver, or the YUI instance if the
2550
specified receiver is falsy.
2552
Y.mix = function(receiver, supplier, overwrite, whitelist, mode, merge) {
2553
var alwaysOverwrite, exists, from, i, key, len, to;
2555
// If no supplier is given, we return the receiver. If no receiver is given,
2556
// we return Y. Returning Y doesn't make much sense to me, but it's
2557
// grandfathered in for backcompat reasons.
2558
if (!receiver || !supplier) {
2559
return receiver || Y;
2563
// In mode 2 (prototype to prototype and object to object), we recurse
2564
// once to do the proto to proto mix. The object to object mix will be
2565
// handled later on.
2567
Y.mix(receiver.prototype, supplier.prototype, overwrite,
2568
whitelist, 0, merge);
2571
// Depending on which mode is specified, we may be copying from or to
2572
// the prototypes of the supplier and receiver.
2573
from = mode === 1 || mode === 3 ? supplier.prototype : supplier;
2574
to = mode === 1 || mode === 4 ? receiver.prototype : receiver;
2576
// If either the supplier or receiver doesn't actually have a
2577
// prototype property, then we could end up with an undefined `from`
2578
// or `to`. If that happens, we abort and return the receiver.
2587
// If `overwrite` is truthy and `merge` is falsy, then we can skip a
2588
// property existence check on each iteration and save some time.
2589
alwaysOverwrite = overwrite && !merge;
2592
for (i = 0, len = whitelist.length; i < len; ++i) {
2595
// We call `Object.prototype.hasOwnProperty` instead of calling
2596
// `hasOwnProperty` on the object itself, since the object's
2597
// `hasOwnProperty` method may have been overridden or removed.
2598
// Also, some native objects don't implement a `hasOwnProperty`
2600
if (!hasOwn.call(from, key)) {
2604
// The `key in to` check here is (sadly) intentional for backwards
2605
// compatibility reasons. It prevents undesired shadowing of
2606
// prototype members on `to`.
2607
exists = alwaysOverwrite ? false : key in to;
2609
if (merge && exists && isObject(to[key], true)
2610
&& isObject(from[key], true)) {
2611
// If we're in merge mode, and the key is present on both
2612
// objects, and the value on both objects is either an object or
2613
// an array (but not a function), then we recurse to merge the
2614
// `from` value into the `to` value instead of overwriting it.
2616
// Note: It's intentional that the whitelist isn't passed to the
2617
// recursive call here. This is legacy behavior that lots of
2618
// code still depends on.
2619
Y.mix(to[key], from[key], overwrite, null, 0, merge);
2620
} else if (overwrite || !exists) {
2621
// We're not in merge mode, so we'll only copy the `from` value
2622
// to the `to` value if we're in overwrite mode or if the
2623
// current key doesn't exist on the `to` object.
2624
to[key] = from[key];
2629
// The code duplication here is for runtime performance reasons.
2630
// Combining whitelist and non-whitelist operations into a single
2631
// loop or breaking the shared logic out into a function both result
2632
// in worse performance, and Y.mix is critical enough that the byte
2633
// tradeoff is worth it.
2634
if (!hasOwn.call(from, key)) {
2638
// The `key in to` check here is (sadly) intentional for backwards
2639
// compatibility reasons. It prevents undesired shadowing of
2640
// prototype members on `to`.
2641
exists = alwaysOverwrite ? false : key in to;
2643
if (merge && exists && isObject(to[key], true)
2644
&& isObject(from[key], true)) {
2645
Y.mix(to[key], from[key], overwrite, null, 0, merge);
2646
} else if (overwrite || !exists) {
2647
to[key] = from[key];
2651
// If this is an IE browser with the JScript enumeration bug, force
2652
// enumeration of the buggy properties by making a recursive call with
2653
// the buggy properties as the whitelist.
2654
if (Y.Object._hasEnumBug) {
2655
Y.mix(to, from, overwrite, Y.Object._forceEnum, mode, merge);
2662
* The YUI module contains the components required for building the YUI
2663
* seed file. This includes the script loading mechanism, a simple queue,
2664
* and the core utilities for the library.
2666
* @submodule yui-base
2670
* Adds utilities to the YUI instance for working with objects.
2675
var hasOwn = Object.prototype.hasOwnProperty,
2677
// If either MooTools or Prototype is on the page, then there's a chance that we
2678
// can't trust "native" language features to actually be native. When this is
2679
// the case, we take the safe route and fall back to our own non-native
2682
unsafeNatives = win && !!(win.MooTools || win.Prototype),
2684
UNDEFINED, // <-- Note the comma. We're still declaring vars.
2687
* Returns a new object that uses _obj_ as its prototype. This method wraps the
2688
* native ES5 `Object.create()` method if available, but doesn't currently
2689
* pass through `Object.create()`'s second argument (properties) in order to
2690
* ensure compatibility with older browsers.
2693
* @param {Object} obj Prototype object.
2694
* @return {Object} New object using _obj_ as its prototype.
2697
O = Y.Object = (!unsafeNatives && Object.create) ? function (obj) {
2698
// We currently wrap the native Object.create instead of simply aliasing it
2699
// to ensure consistency with our fallback shim, which currently doesn't
2700
// support Object.create()'s second argument (properties). Once we have a
2701
// safe fallback for the properties arg, we can stop wrapping
2703
return Object.create(obj);
2705
// Reusable constructor function for the Object.create() shim.
2709
return function (obj) {
2716
* Property names that IE doesn't enumerate in for..in loops, even when they
2717
* should be enumerable. When `_hasEnumBug` is `true`, it's necessary to
2718
* manually enumerate these properties.
2720
* @property _forceEnum
2725
forceEnum = O._forceEnum = [
2728
'propertyIsEnumerable',
2735
* `true` if this browser has the JScript enumeration bug that prevents
2736
* enumeration of the properties named in the `_forceEnum` array, `false`
2740
* - <https://developer.mozilla.org/en/ECMAScript_DontEnum_attribute#JScript_DontEnum_Bug>
2741
* - <http://whattheheadsaid.com/2010/10/a-safer-object-keys-compatibility-implementation>
2743
* @property _hasEnumBug
2748
hasEnumBug = O._hasEnumBug = !{valueOf: 0}.propertyIsEnumerable('valueOf'),
2751
* `true` if this browser incorrectly considers the `prototype` property of
2752
* functions to be enumerable. Currently known to affect Opera 11.50.
2754
* @property _hasProtoEnumBug
2759
hasProtoEnumBug = O._hasProtoEnumBug = (function () {}).propertyIsEnumerable('prototype'),
2762
* Returns `true` if _key_ exists on _obj_, `false` if _key_ doesn't exist or
2763
* exists only on _obj_'s prototype. This is essentially a safer version of
2764
* `obj.hasOwnProperty()`.
2767
* @param {Object} obj Object to test.
2768
* @param {String} key Property name to look for.
2769
* @return {Boolean} `true` if _key_ exists on _obj_, `false` otherwise.
2772
owns = O.owns = function (obj, key) {
2773
return !!obj && hasOwn.call(obj, key);
2774
}; // <-- End of var declarations.
2777
* Alias for `owns()`.
2780
* @param {Object} obj Object to test.
2781
* @param {String} key Property name to look for.
2782
* @return {Boolean} `true` if _key_ exists on _obj_, `false` otherwise.
2788
* Returns an array containing the object's enumerable keys. Does not include
2789
* prototype keys or non-enumerable keys.
2791
* Note that keys are returned in enumeration order (that is, in the same order
2792
* that they would be enumerated by a `for-in` loop), which may not be the same
2793
* as the order in which they were defined.
2795
* This method is an alias for the native ES5 `Object.keys()` method if
2800
* Y.Object.keys({a: 'foo', b: 'bar', c: 'baz'});
2801
* // => ['a', 'b', 'c']
2804
* @param {Object} obj An object.
2805
* @return {String[]} Array of keys.
2808
O.keys = (!unsafeNatives && Object.keys) || function (obj) {
2809
if (!Y.Lang.isObject(obj)) {
2810
throw new TypeError('Object.keys called on a non-object');
2816
if (hasProtoEnumBug && typeof obj === 'function') {
2818
if (owns(obj, key) && key !== 'prototype') {
2824
if (owns(obj, key)) {
2831
for (i = 0, len = forceEnum.length; i < len; ++i) {
2834
if (owns(obj, key)) {
2844
* Returns an array containing the values of the object's enumerable keys.
2846
* Note that values are returned in enumeration order (that is, in the same
2847
* order that they would be enumerated by a `for-in` loop), which may not be the
2848
* same as the order in which they were defined.
2852
* Y.Object.values({a: 'foo', b: 'bar', c: 'baz'});
2853
* // => ['foo', 'bar', 'baz']
2856
* @param {Object} obj An object.
2857
* @return {Array} Array of values.
2860
O.values = function (obj) {
2861
var keys = O.keys(obj),
2866
for (; i < len; ++i) {
2867
values.push(obj[keys[i]]);
2874
* Returns the number of enumerable keys owned by an object.
2877
* @param {Object} obj An object.
2878
* @return {Number} The object's size.
2881
O.size = function (obj) {
2883
return O.keys(obj).length;
2885
return 0; // Legacy behavior for non-objects.
2890
* Returns `true` if the object owns an enumerable property with the specified
2894
* @param {Object} obj An object.
2895
* @param {any} value The value to search for.
2896
* @return {Boolean} `true` if _obj_ contains _value_, `false` otherwise.
2899
O.hasValue = function (obj, value) {
2900
return Y.Array.indexOf(O.values(obj), value) > -1;
2904
* Executes a function on each enumerable property in _obj_. The function
2905
* receives the value, the key, and the object itself as parameters (in that
2908
* By default, only properties owned by _obj_ are enumerated. To include
2909
* prototype properties, set the _proto_ parameter to `true`.
2912
* @param {Object} obj Object to enumerate.
2913
* @param {Function} fn Function to execute on each enumerable property.
2914
* @param {mixed} fn.value Value of the current property.
2915
* @param {String} fn.key Key of the current property.
2916
* @param {Object} fn.obj Object being enumerated.
2917
* @param {Object} [thisObj] `this` object to use when calling _fn_.
2918
* @param {Boolean} [proto=false] Include prototype properties.
2919
* @return {YUI} the YUI instance.
2923
O.each = function (obj, fn, thisObj, proto) {
2927
if (proto || owns(obj, key)) {
2928
fn.call(thisObj || Y, obj[key], key, obj);
2936
* Executes a function on each enumerable property in _obj_, but halts if the
2937
* function returns a truthy value. The function receives the value, the key,
2938
* and the object itself as paramters (in that order).
2940
* By default, only properties owned by _obj_ are enumerated. To include
2941
* prototype properties, set the _proto_ parameter to `true`.
2944
* @param {Object} obj Object to enumerate.
2945
* @param {Function} fn Function to execute on each enumerable property.
2946
* @param {mixed} fn.value Value of the current property.
2947
* @param {String} fn.key Key of the current property.
2948
* @param {Object} fn.obj Object being enumerated.
2949
* @param {Object} [thisObj] `this` object to use when calling _fn_.
2950
* @param {Boolean} [proto=false] Include prototype properties.
2951
* @return {Boolean} `true` if any execution of _fn_ returns a truthy value,
2952
* `false` otherwise.
2955
O.some = function (obj, fn, thisObj, proto) {
2959
if (proto || owns(obj, key)) {
2960
if (fn.call(thisObj || Y, obj[key], key, obj)) {
2970
* Retrieves the sub value at the provided path,
2971
* from the value object provided.
2975
* @param o The object from which to extract the property value.
2976
* @param path {Array} A path array, specifying the object traversal path
2977
* from which to obtain the sub value.
2978
* @return {Any} The value stored in the path, undefined if not found,
2979
* undefined if the source is not an object. Returns the source object
2980
* if an empty path is provided.
2982
O.getValue = function(o, path) {
2983
if (!Y.Lang.isObject(o)) {
2991
for (i = 0; o !== UNDEFINED && i < l; i++) {
2999
* Sets the sub-attribute value at the provided path on the
3000
* value object. Returns the modified value object, or
3001
* undefined if the path is invalid.
3005
* @param o The object on which to set the sub value.
3006
* @param path {Array} A path array, specifying the object traversal path
3007
* at which to set the sub value.
3008
* @param val {Any} The new value for the sub-attribute.
3009
* @return {Object} The modified object, with the new sub value set, or
3010
* undefined, if the path was invalid.
3012
O.setValue = function(o, path, val) {
3015
leafIdx = p.length - 1,
3019
for (i = 0; ref !== UNDEFINED && i < leafIdx; i++) {
3023
if (ref !== UNDEFINED) {
3034
* Returns `true` if the object has no enumerable properties of its own.
3037
* @param {Object} obj An object.
3038
* @return {Boolean} `true` if the object is empty.
3042
O.isEmpty = function (obj) {
3043
return !O.keys(obj).length;
3046
* The YUI module contains the components required for building the YUI seed
3047
* file. This includes the script loading mechanism, a simple queue, and the
3048
* core utilities for the library.
3050
* @submodule yui-base
3054
* YUI user agent detection.
3055
* Do not fork for a browser if it can be avoided. Use feature detection when
3056
* you can. Use the user agent as a last resort. For all fields listed
3057
* as @type float, UA stores a version number for the browser engine,
3058
* 0 otherwise. This value may or may not map to the version number of
3059
* the browser using the engine. The value is presented as a float so
3060
* that it can easily be used for boolean evaluation as well as for
3061
* looking for a particular range of versions. Because of this,
3062
* some of the granularity of the version info may be lost. The fields that
3063
* are @type string default to null. The API docs list the values that
3064
* these fields can have.
3070
* Static method on `YUI.Env` for parsing a UA string. Called at instantiation
3071
* to populate `Y.UA`.
3075
* @param {String} [subUA=navigator.userAgent] UA string to parse
3076
* @returns {Object} The Y.UA object
3078
YUI.Env.parseUA = function(subUA) {
3080
var numberify = function(s) {
3082
return parseFloat(s.replace(/\./g, function() {
3083
return (c++ == 1) ? '' : '.';
3089
nav = win && win.navigator,
3094
* Internet Explorer version number or 0. Example: 6
3102
* Opera version number or 0. Example: 9.2
3110
* Gecko engine revision number. Will evaluate to 1 if Gecko
3111
* is detected but the revision could not be found. Other browsers
3112
* will be 0. Example: 1.8
3114
* Firefox 1.0.0.4: 1.7.8 <-- Reports 1.7
3115
* Firefox 1.5.0.9: 1.8.0.9 <-- 1.8
3116
* Firefox 2.0.0.3: 1.8.1.3 <-- 1.81
3117
* Firefox 3.0 <-- 1.9
3118
* Firefox 3.5 <-- 1.91
3127
* AppleWebKit version. KHTML browsers that are not WebKit browsers
3128
* will evaluate to 1, other browsers 0. Example: 418.9
3130
* Safari 1.3.2 (312.6): 312.8.1 <-- Reports 312.8 -- currently the
3131
* latest available for Mac OSX 10.3.
3132
* Safari 2.0.2: 416 <-- hasOwnProperty introduced
3133
* Safari 2.0.4: 418 <-- preventDefault fixed
3134
* Safari 2.0.4 (419.3): 418.9.1 <-- One version of Safari may run
3135
* different versions of webkit
3136
* Safari 2.0.4 (419.3): 419 <-- Tiger installations that have been
3137
* updated, but not updated
3138
* to the latest patch.
3139
* Webkit 212 nightly: 522+ <-- Safari 3.0 precursor (with native
3140
* SVG and many major issues fixed).
3141
* Safari 3.0.4 (523.12) 523.12 <-- First Tiger release - automatic
3142
* update from 2.x via the 10.4.11 OS patch.
3143
* Webkit nightly 1/2008:525+ <-- Supports DOMContentLoaded event.
3144
* yahoo.com user agent hack removed.
3146
* http://en.wikipedia.org/wiki/Safari_version_history
3154
* Safari will be detected as webkit, but this property will also
3155
* be populated with the Safari version number
3163
* Chrome will be detected as webkit, but this property will also
3164
* be populated with the Chrome version number
3172
* The mobile property will be set to a string containing any relevant
3173
* user agent information when a modern mobile browser is detected.
3174
* Currently limited to Safari on the iPhone/iPod Touch, Nokia N-series
3175
* devices with the WebKit-based browser, and Opera Mini.
3184
* Adobe AIR version number or 0. Only populated if webkit is detected.
3191
* Detects Apple iPad's OS version
3198
* Detects Apple iPhone's OS version
3205
* Detects Apples iPod's OS version
3212
* General truthy check for iPad, iPhone or iPod
3220
* Detects Googles Android OS version
3227
* Detects Palms WebOS version
3235
* Google Caja version number or 0.
3239
caja: nav && nav.cajaVersion,
3242
* Set to true if the page appears to be in SSL
3250
* The operating system. Currently only detecting windows or macintosh
3260
ua = subUA || nav && nav.userAgent,
3262
loc = win && win.location,
3264
href = loc && loc.href,
3269
* The User Agent string that was parsed
3270
* @property userAgent
3277
o.secure = href && (href.toLowerCase().indexOf('https') === 0);
3281
if ((/windows|win32/i).test(ua)) {
3283
} else if ((/macintosh/i).test(ua)) {
3285
} else if ((/rhino/i).test(ua)) {
3289
// Modern KHTML browsers should qualify as Safari X-Grade
3290
if ((/KHTML/).test(ua)) {
3293
// Modern WebKit browsers are at least X-Grade
3294
m = ua.match(/AppleWebKit\/([^\s]*)/);
3296
o.webkit = numberify(m[1]);
3297
o.safari = o.webkit;
3299
// Mobile browser check
3300
if (/ Mobile\//.test(ua)) {
3301
o.mobile = 'Apple'; // iPhone or iPod Touch
3303
m = ua.match(/OS ([^\s]*)/);
3305
m = numberify(m[1].replace('_', '.'));
3308
o.ipad = o.ipod = o.iphone = 0;
3310
m = ua.match(/iPad|iPod|iPhone/);
3312
o[m[0].toLowerCase()] = o.ios;
3315
m = ua.match(/NokiaN[^\/]*|webOS\/\d\.\d/);
3317
// Nokia N-series, webOS, ex: NokiaN95
3320
if (/webOS/.test(ua)) {
3322
m = ua.match(/webOS\/([^\s]*);/);
3324
o.webos = numberify(m[1]);
3327
if (/ Android/.test(ua)) {
3328
if (/Mobile/.test(ua)) {
3329
o.mobile = 'Android';
3331
m = ua.match(/Android ([^\s]*);/);
3333
o.android = numberify(m[1]);
3339
m = ua.match(/Chrome\/([^\s]*)/);
3341
o.chrome = numberify(m[1]); // Chrome
3342
o.safari = 0; //Reset safari back to 0
3344
m = ua.match(/AdobeAIR\/([^\s]*)/);
3346
o.air = m[0]; // Adobe AIR 1.0 or better
3351
if (!o.webkit) { // not webkit
3352
// @todo check Opera/8.01 (J2ME/MIDP; Opera Mini/2.0.4509/1316; fi; U; ssr)
3353
m = ua.match(/Opera[\s\/]([^\s]*)/);
3355
o.opera = numberify(m[1]);
3356
m = ua.match(/Version\/([^\s]*)/);
3358
o.opera = numberify(m[1]); // opera 10+
3361
m = ua.match(/Opera Mini[^;]*/);
3364
o.mobile = m[0]; // ex: Opera Mini/2.0.4509/1316
3366
} else { // not opera or webkit
3367
m = ua.match(/MSIE\s([^;]*)/);
3369
o.ie = numberify(m[1]);
3370
} else { // not opera, webkit, or ie
3371
m = ua.match(/Gecko\/([^\s]*)/);
3373
o.gecko = 1; // Gecko detected, look for revision
3374
m = ua.match(/rv:([^\s\)]*)/);
3376
o.gecko = numberify(m[1]);
3384
//It was a parsed UA, do not assign the global value.
3393
Y.UA = YUI.Env.UA || YUI.Env.parseUA();
3395
"anim": ["anim-base","anim-color","anim-curve","anim-easing","anim-node-plugin","anim-scroll","anim-xy"],
3396
"app": ["controller","model","model-list","view"],
3397
"attribute": ["attribute-base","attribute-complex"],
3398
"autocomplete": ["autocomplete-base","autocomplete-sources","autocomplete-list","autocomplete-plugin"],
3399
"base": ["base-base","base-pluginhost","base-build"],
3400
"cache": ["cache-base","cache-offline","cache-plugin"],
3401
"collection": ["array-extras","arraylist","arraylist-add","arraylist-filter","array-invoke"],
3402
"dataschema": ["dataschema-base","dataschema-json","dataschema-xml","dataschema-array","dataschema-text"],
3403
"datasource": ["datasource-local","datasource-io","datasource-get","datasource-function","datasource-cache","datasource-jsonschema","datasource-xmlschema","datasource-arrayschema","datasource-textschema","datasource-polling"],
3404
"datatable": ["datatable-base","datatable-datasource","datatable-sort","datatable-scroll"],
3405
"datatype": ["datatype-number","datatype-date","datatype-xml"],
3406
"datatype-date": ["datatype-date-parse","datatype-date-format"],
3407
"datatype-number": ["datatype-number-parse","datatype-number-format"],
3408
"datatype-xml": ["datatype-xml-parse","datatype-xml-format"],
3409
"dd": ["dd-ddm-base","dd-ddm","dd-ddm-drop","dd-drag","dd-proxy","dd-constrain","dd-drop","dd-scroll","dd-delegate"],
3410
"dom": ["dom-base","dom-screen","dom-style","selector-native","selector"],
3411
"editor": ["frame","selection","exec-command","editor-base","editor-para","editor-br","editor-bidi","editor-tab","createlink-base"],
3412
"event": ["event-base","event-delegate","event-synthetic","event-mousewheel","event-mouseenter","event-key","event-focus","event-resize","event-hover","event-outside"],
3413
"event-custom": ["event-custom-base","event-custom-complex"],
3414
"event-gestures": ["event-flick","event-move"],
3415
"highlight": ["highlight-base","highlight-accentfold"],
3416
"history": ["history-base","history-hash","history-hash-ie","history-html5"],
3417
"io": ["io-base","io-xdr","io-form","io-upload-iframe","io-queue"],
3418
"json": ["json-parse","json-stringify"],
3419
"loader": ["loader-base","loader-rollup","loader-yui3"],
3420
"node": ["node-base","node-event-delegate","node-pluginhost","node-screen","node-style"],
3421
"pluginhost": ["pluginhost-base","pluginhost-config"],
3422
"querystring": ["querystring-parse","querystring-stringify"],
3423
"recordset": ["recordset-base","recordset-sort","recordset-filter","recordset-indexer"],
3424
"resize": ["resize-base","resize-proxy","resize-constrain"],
3425
"slider": ["slider-base","slider-value-range","clickable-rail","range-slider"],
3426
"text": ["text-accentfold","text-wordbreak"],
3427
"widget": ["widget-base","widget-htmlparser","widget-uievents","widget-skin"]
3432
YUI.add('get', function(Y) {
3435
* Provides a mechanism to fetch remote resources and
3436
* insert them into a document.
3442
* Fetches and inserts one or more script or link nodes into the document
3449
TYPE_JS = 'text/javascript',
3450
TYPE_CSS = 'text/css',
3451
STYLESHEET = 'stylesheet',
3453
AUTOPURGE = 'autopurge',
3459
// FireFox does not support the onload event for link nodes, so
3460
// there is no way to make the css requests synchronous. This means
3461
// that the css rules in multiple files could be applied out of order
3462
// in this browser if a later request returns before an earlier one.
3466
ONLOAD_SUPPORTED = {
3468
css: !(ua.webkit || ua.gecko)
3472
* hash of queues to manage multiple requests
3479
* queue index used to generate transaction ids
3487
* interal property used to prevent multiple simultaneous purge
3496
* Clear timeout state
3498
* @method _clearTimeout
3499
* @param {Object} q Queue data
3502
_clearTimeout = function(q) {
3503
var timer = q.timer;
3505
clearTimeout(timer);
3511
* Generates an HTML element, this is not appended to a document
3513
* @param {string} type the type of element.
3514
* @param {Object} attr the fixed set of attribute for the type.
3515
* @param {Object} custAttrs optional Any custom attributes provided by the user.
3516
* @param {Window} win optional window to create the element in.
3517
* @return {HTMLElement} the generated node.
3520
_node = function(type, attr, custAttrs, win) {
3521
var w = win || Y.config.win,
3523
n = d.createElement(type),
3527
Y.mix(attr, custAttrs);
3531
if (attr[i] && attr.hasOwnProperty(i)) {
3532
n.setAttribute(i, attr[i]);
3540
* Generates a link node
3542
* @param {string} url the url for the css file.
3543
* @param {Window} win optional window to create the node in.
3544
* @param {object} attributes optional attributes collection to apply to the
3546
* @return {HTMLElement} the generated node.
3549
_linkNode = function(url, win, attributes) {
3550
return _node(LINK, {
3555
}, attributes, win);
3559
* Generates a script node
3560
* @method _scriptNode
3561
* @param {string} url the url for the script file.
3562
* @param {Window} win optional window to create the node in.
3563
* @param {object} attributes optional attributes collection to apply to the
3565
* @return {HTMLElement} the generated node.
3568
_scriptNode = function(url, win, attributes) {
3569
return _node(SCRIPT, {
3573
}, attributes, win);
3577
* Returns the data payload for callback functions.
3578
* @method _returnData
3579
* @param {object} q the queue.
3580
* @param {string} msg the result message.
3581
* @param {string} result the status message from the request.
3582
* @return {object} the state data from the request.
3585
_returnData = function(q, msg, result) {
3601
* The transaction is finished
3603
* @param {string} id the id of the request.
3604
* @param {string} msg the result message.
3605
* @param {string} result the status message from the request.
3608
_end = function(id, msg, result) {
3610
onEnd = q && q.onEnd;
3615
onEnd.call(q.context, _returnData(q, msg, result));
3620
* The request failed, execute fail handler with whatever
3621
* was accomplished. There isn't a failure case at the
3622
* moment unless you count aborted transactions
3624
* @param {string} id the id of the request
3627
_fail = function(id, msg) {
3630
onFailure = q.onFailure;
3635
onFailure.call(q.context, _returnData(q, msg));
3638
_end(id, msg, 'failure');
3643
* Abort the transaction
3646
* @param {Object} id
3649
_abort = function(id) {
3650
_fail(id, 'transaction ' + id + ' was aborted');
3654
* The request is complete, so executing the requester's callback
3656
* @param {string} id the id of the request.
3659
_complete = function(id) {
3662
onSuccess = q.onSuccess;
3671
onSuccess.call(q.context, _returnData(q));
3674
// 3.3.0 had undefined msg for this path.
3675
_end(id, undefined, 'OK');
3680
* Get node reference, from string
3682
* @method _getNodeRef
3683
* @param {String|HTMLElement} nId The node id to find. If an HTMLElement is passed in, it will be returned.
3684
* @param {String} tId Queue id, used to determine document for queue
3687
_getNodeRef = function(nId, tId) {
3688
var q = queues[tId],
3689
n = (L.isString(nId)) ? q.win.document.getElementById(nId) : nId;
3691
_fail(tId, 'target node not found: ' + nId);
3698
* Removes the nodes for the specified queue
3700
* @param {string} tId the transaction id.
3703
_purge = function(tId) {
3704
var nodes, doc, parent, sibling, node, attr, insertBefore,
3712
// TODO: Why is node.parentNode undefined? Which forces us to do this...
3714
doc = q.win.document;
3715
parent = doc.getElementsByTagName('head')[0];
3716
insertBefore = q.insertBefore || doc.getElementsByTagName('base')[0];
3719
sibling = _getNodeRef(insertBefore, tId);
3721
parent = sibling.parentNode;
3726
for (i = 0; i < l; i++) {
3728
parent = node.parentNode;
3730
if (node.clearAttributes) {
3731
node.clearAttributes();
3733
// This destroys parentNode ref, so we hold onto it above first.
3734
for (attr in node) {
3735
if (node.hasOwnProperty(attr)) {
3741
parent.removeChild(node);
3752
* @param {string} id The id of the request.
3753
* @param {string} The url which just completed.
3756
_progress = function(id, url) {
3758
onProgress = q.onProgress,
3764
onProgress.call(q.context, o);
3771
* @param {string} id the id of the request.
3774
_timeout = function(id) {
3777
onTimeout = q.onTimeout;
3780
onTimeout.call(q.context, _returnData(q));
3783
_end(id, 'timeout', 'timeout');
3789
* @param {string} id the id of the request.
3790
* @return {string} the result.
3793
_loaded = function(id, url) {
3796
sync = (q && !q.async);
3808
// TODO: Cleaning up flow to have a consistent end point
3810
// !q.finished check is for the async case,
3811
// where scripts may still be loading when we've
3812
// already aborted. Ideally there should be a single path
3819
if ((--q.remaining) === 0) {
3829
* Detects when a node has been loaded. In the case of
3830
* script nodes, this does not guarantee that contained
3831
* script is ready to use.
3832
* @method _trackLoad
3833
* @param {string} type the type of node to track.
3834
* @param {HTMLElement} n the node to track.
3835
* @param {string} id the id of the request.
3836
* @param {string} url the url that is being loaded.
3839
_trackLoad = function(type, n, id, url) {
3841
// TODO: Can we massage this to use ONLOAD_SUPPORTED[type]?
3843
// IE supports the readystatechange event for script and css nodes
3844
// Opera only for script nodes. Opera support onload for script
3845
// nodes, but this doesn't fire when there is a load failure.
3846
// The onreadystatechange appears to be a better way to respond
3847
// to both success and failure.
3851
n.onreadystatechange = function() {
3852
var rs = this.readyState;
3853
if ('loaded' === rs || 'complete' === rs) {
3854
n.onreadystatechange = null;
3859
} else if (ua.webkit) {
3861
// webkit prior to 3.x is no longer supported
3862
if (type === SCRIPT) {
3863
// Safari 3.x supports the load event for script nodes (DOM2)
3864
n.addEventListener('load', function() {
3871
// FireFox and Opera support onload (but not DOM2 in FF) handlers for
3872
// script nodes. Opera, but not FF, supports the onload event for link nodes.
3874
n.onload = function() {
3878
n.onerror = function(e) {
3879
_fail(id, e + ': ' + url);
3884
_insertInDoc = function(node, id, win) {
3886
// Add it to the head or insert it before 'insertBefore'.
3887
// Work around IE bug if there is a base tag.
3890
insertBefore = q.insertBefore || doc.getElementsByTagName('base')[0],
3894
sibling = _getNodeRef(insertBefore, id);
3896
sibling.parentNode.insertBefore(node, sibling);
3899
// 3.3.0 assumed head is always around.
3900
doc.getElementsByTagName('head')[0].appendChild(node);
3905
* Loads the next item for a given request
3907
* @param {string} id the id of the request.
3908
* @return {string} the result.
3911
_next = function(id) {
3913
// Assigning out here for readability
3916
attrs = q.attributes,
3918
timeout = q.timeout,
3922
if (q.url.length > 0) {
3924
url = q.url.shift();
3927
// !q.timer ensures that this only happens once for async
3928
if (timeout && !q.timer) {
3929
q.timer = setTimeout(function() {
3934
if (type === SCRIPT) {
3935
node = _scriptNode(url, win, attrs);
3937
node = _linkNode(url, win, attrs);
3940
// add the node to the queue so we can return it in the callback
3943
_trackLoad(type, node, id, url);
3944
_insertInDoc(node, id, win);
3946
if (!ONLOAD_SUPPORTED[type]) {
3951
// For sync, the _next call is chained in _loaded
3958
* Removes processed queues and corresponding nodes
3959
* @method _autoPurge
3962
_autoPurge = function() {
3971
if (queues.hasOwnProperty(i)) {
3973
if (q.autopurge && q.finished) {
3984
* Saves the state for the request and begins loading
3985
* the requested urls
3987
* @param {string} type the type of node to insert.
3988
* @param {string} url the url to load.
3989
* @param {object} opts the hash of options for this request.
3990
* @return {object} transaction object.
3993
_queue = function(type, url, opts) {
3997
var id = 'q' + (qidx++),
3998
thresh = opts.purgethreshold || Y.Get.PURGE_THRESH,
4001
if (qidx % thresh === 0) {
4005
// Merge to protect opts (grandfathered in).
4006
q = queues[id] = Y.merge(opts);
4008
// Avoid mix, merge overhead. Known set of props.
4015
q.win = q.win || Y.config.win;
4016
q.context = q.context || q;
4017
q.autopurge = (AUTOPURGE in q) ? q.autopurge : (type === SCRIPT) ? true : false;
4018
q.attributes = q.attributes || {};
4019
q.attributes.charset = opts.charset || q.attributes.charset || UTF8;
4021
if (ASYNC in q && type === SCRIPT) {
4022
q.attributes.async = q.async;
4025
q.url = (L.isString(q.url)) ? [q.url] : q.url;
4027
// TODO: Do we really need to account for this developer error?
4028
// If the url is undefined, this is probably a trailing comma problem in IE.
4033
q.remaining = q.url.length;
4046
* The number of request required before an automatic purge.
4047
* Can be configured via the 'purgethreshold' config
4048
* @property PURGE_THRESH
4057
* Abort a transaction
4060
* @param {string|object} o Either the tId or the object returned from
4061
* script() or css().
4063
abort : function(o) {
4064
var id = (L.isString(o)) ? o : o.tId,
4073
* Fetches and inserts one or more script nodes into the head
4074
* of the current document or the document in a specified window.
4078
* @param {string|string[]} url the url or urls to the script(s).
4079
* @param {object} opts Options:
4081
* <dt>onSuccess</dt>
4083
* callback to execute when the script(s) are finished loading
4084
* The callback receives an object back with the following
4088
* <dd>the window the script(s) were inserted into</dd>
4090
* <dd>the data object passed in when the request was made</dd>
4092
* <dd>An array containing references to the nodes that were
4095
* <dd>A function that, when executed, will remove the nodes
4096
* that were inserted</dd>
4100
* <dt>onTimeout</dt>
4102
* callback to execute when a timeout occurs.
4103
* The callback receives an object back with the following
4107
* <dd>the window the script(s) were inserted into</dd>
4109
* <dd>the data object passed in when the request was made</dd>
4111
* <dd>An array containing references to the nodes that were
4114
* <dd>A function that, when executed, will remove the nodes
4115
* that were inserted</dd>
4120
* <dd>a function that executes when the transaction finishes,
4121
* regardless of the exit path</dd>
4122
* <dt>onFailure</dt>
4124
* callback to execute when the script load operation fails
4125
* The callback receives an object back with the following
4129
* <dd>the window the script(s) were inserted into</dd>
4131
* <dd>the data object passed in when the request was made</dd>
4133
* <dd>An array containing references to the nodes that were
4134
* inserted successfully</dd>
4136
* <dd>A function that, when executed, will remove any nodes
4137
* that were inserted</dd>
4141
* <dt>onProgress</dt>
4142
* <dd>callback to execute when each individual file is done loading
4143
* (useful when passing in an array of js files). Receives the same
4144
* payload as onSuccess, with the addition of a <code>url</code>
4145
* property, which identifies the file which was loaded.</dd>
4148
* <p>When passing in an array of JS files, setting this flag to true
4149
* will insert them into the document in parallel, as opposed to the
4150
* default behavior, which is to chain load them serially. It will also
4151
* set the async attribute on the script node to true.</p>
4152
* <p>Setting async:true
4153
* will lead to optimal file download performance allowing the browser to
4154
* download multiple scripts in parallel, and execute them as soon as they
4155
* are available.</p>
4156
* <p>Note that async:true does not guarantee execution order of the
4157
* scripts being downloaded. They are executed in whichever order they
4161
* <dd>the execution context for the callbacks</dd>
4163
* <dd>a window other than the one the utility occupies</dd>
4164
* <dt>autopurge</dt>
4166
* setting to true will let the utilities cleanup routine purge
4167
* the script once loaded
4169
* <dt>purgethreshold</dt>
4171
* The number of transaction before autopurge should be initiated
4175
* data that is supplied to the callback when the script(s) are
4178
* <dt>insertBefore</dt>
4179
* <dd>node or node id that will become the new node's nextSibling.
4180
* If this is not specified, nodes will be inserted before a base
4181
* tag should it exist. Otherwise, the nodes will be appended to the
4182
* end of the document head.</dd>
4185
* <dd>Node charset, default utf-8 (deprecated, use the attributes
4187
* <dt>attributes</dt>
4188
* <dd>An object literal containing additional attributes to add to
4189
* the link tags</dd>
4191
* <dd>Number of milliseconds to wait before aborting and firing
4192
* the timeout event</dd>
4194
* Y.Get.script(
4195
* ["http://yui.yahooapis.com/2.5.2/build/yahoo/yahoo-min.js",
4196
* "http://yui.yahooapis.com/2.5.2/build/event/event-min.js"],
4198
* onSuccess: function(o) {
4199
* this.log("won't cause error because Y is the context");
4200
* // immediately
4202
* onFailure: function(o) {
4204
* onTimeout: function(o) {
4206
* data: "foo",
4207
* timeout: 10000, // 10 second timeout
4208
* context: Y, // make the YUI instance
4209
* // win: otherframe // target another window/frame
4210
* autopurge: true // allow the utility to choose when to
4211
* // remove the nodes
4212
* purgetheshold: 1 // purge previous transaction before
4213
* // next transaction
4216
* @return {tId: string} an object containing info about the
4219
script: function(url, opts) {
4220
return _queue(SCRIPT, url, opts);
4224
* Fetches and inserts one or more css link nodes into the
4225
* head of the current document or the document in a specified
4229
* @param {string} url the url or urls to the css file(s).
4230
* @param {object} opts Options:
4232
* <dt>onSuccess</dt>
4234
* callback to execute when the css file(s) are finished loading
4235
* The callback receives an object back with the following
4238
* <dd>the window the link nodes(s) were inserted into</dd>
4240
* <dd>the data object passed in when the request was made</dd>
4242
* <dd>An array containing references to the nodes that were
4245
* <dd>A function that, when executed, will remove the nodes
4246
* that were inserted</dd>
4250
* <dt>onProgress</dt>
4251
* <dd>callback to execute when each individual file is done loading (useful when passing in an array of css files). Receives the same
4252
* payload as onSuccess, with the addition of a <code>url</code> property, which identifies the file which was loaded. Currently only useful for non Webkit/Gecko browsers,
4253
* where onload for css is detected accurately.</dd>
4255
* <dd>When passing in an array of css files, setting this flag to true will insert them
4256
* into the document in parallel, as oppposed to the default behavior, which is to chain load them (where possible).
4257
* This flag is more useful for scripts currently, since for css Get only chains if not Webkit/Gecko.</dd>
4259
* <dd>the execution context for the callbacks</dd>
4261
* <dd>a window other than the one the utility occupies</dd>
4264
* data that is supplied to the callbacks when the nodes(s) are
4267
* <dt>insertBefore</dt>
4268
* <dd>node or node id that will become the new node's nextSibling</dd>
4270
* <dd>Node charset, default utf-8 (deprecated, use the attributes
4272
* <dt>attributes</dt>
4273
* <dd>An object literal containing additional attributes to add to
4274
* the link tags</dd>
4277
* Y.Get.css("http://localhost/css/menu.css");
4281
* ["http://localhost/css/menu.css",
4282
* insertBefore: 'custom-styles' // nodes will be inserted
4283
* // before the specified node
4286
* @return {tId: string} an object containing info about the
4289
css: function(url, opts) {
4290
return _queue('css', url, opts);
4295
}, '3.4.1' ,{requires:['yui-base']});
4296
YUI.add('features', function(Y) {
4298
var feature_tests = {};
4301
Contains the core of YUI's feature test architecture.
4311
Y.mix(Y.namespace('Features'), {
4314
* Object hash of all registered feature tests
4318
tests: feature_tests,
4321
* Add a test to the system
4324
* Y.Features.add("load", "1", {});
4328
* @param {String} cat The category, right now only 'load' is supported
4329
* @param {String} name The number sequence of the test, how it's reported in the URL or config: 1, 2, 3
4330
* @param {Object} o Object containing test properties
4331
* @param {String} o.name The name of the test
4332
* @param {Function} o.test The test function to execute, the only argument to the function is the `Y` instance
4333
* @param {String} o.trigger The module that triggers this test.
4335
add: function(cat, name, o) {
4336
feature_tests[cat] = feature_tests[cat] || {};
4337
feature_tests[cat][name] = o;
4340
* Execute all tests of a given category and return the serialized results
4346
* @param {String} cat The category to execute
4347
* @param {Array} args The arguments to pass to the test function
4348
* @return {String} A semi-colon separated string of tests and their success/failure: 1:1;2:1;3:0
4350
all: function(cat, args) {
4351
var cat_o = feature_tests[cat],
4355
Y.Object.each(cat_o, function(v, k) {
4356
result.push(k + ':' + (Y.Features.test(cat, k, args) ? 1 : 0));
4360
return (result.length) ? result.join(';') : '';
4363
* Run a sepecific test and return a Boolean response.
4366
* Y.Features.test("load", "1");
4370
* @param {String} cat The category of the test to run
4371
* @param {String} name The name of the test to run
4372
* @param {Array} args The arguments to pass to the test function
4373
* @return {Boolean} True or false if the test passed/failed.
4375
test: function(cat, name, args) {
4377
var result, ua, test,
4378
cat_o = feature_tests[cat],
4379
feature = cat_o && cat_o[name];
4384
result = feature.result;
4386
if (Y.Lang.isUndefined(result)) {
4390
result = (Y.UA[ua]);
4393
test = feature.test;
4394
if (test && ((!ua) || result)) {
4395
result = test.apply(Y, args);
4398
feature.result = result;
4406
// Y.Features.add("load", "1", {});
4407
// Y.Features.test("load", "1");
4408
// caps=1:1;2:0;3:1;
4410
/* This file is auto-generated by src/loader/scripts/meta_join.py */
4411
var add = Y.Features.add;
4412
// graphics-canvas-default
4414
"name": "graphics-canvas-default",
4415
"test": function(Y) {
4416
var DOCUMENT = Y.config.doc,
4417
canvas = DOCUMENT && DOCUMENT.createElement("canvas");
4418
return (DOCUMENT && !DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1") && (canvas && canvas.getContext && canvas.getContext("2d")));
4420
"trigger": "graphics"
4422
// autocomplete-list-keys
4424
"name": "autocomplete-list-keys",
4425
"test": function (Y) {
4426
// Only add keyboard support to autocomplete-list if this doesn't appear to
4427
// be an iOS or Android-based mobile device.
4429
// There's currently no feasible way to actually detect whether a device has
4430
// a hardware keyboard, so this sniff will have to do. It can easily be
4431
// overridden by manually loading the autocomplete-list-keys module.
4433
// Worth noting: even though iOS supports bluetooth keyboards, Mobile Safari
4434
// doesn't fire the keyboard events used by AutoCompleteList, so there's
4435
// no point loading the -keys module even when a bluetooth keyboard may be
4437
return !(Y.UA.ios || Y.UA.android);
4439
"trigger": "autocomplete-list"
4443
"name": "graphics-svg",
4444
"test": function(Y) {
4445
var DOCUMENT = Y.config.doc;
4446
return (DOCUMENT && DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1"));
4448
"trigger": "graphics"
4452
"name": "history-hash-ie",
4453
"test": function (Y) {
4454
var docMode = Y.config.doc && Y.config.doc.documentMode;
4456
return Y.UA.ie && (!('onhashchange' in Y.config.win) ||
4457
!docMode || docMode < 8);
4459
"trigger": "history-hash"
4461
// graphics-vml-default
4463
"name": "graphics-vml-default",
4464
"test": function(Y) {
4465
var DOCUMENT = Y.config.doc,
4466
canvas = DOCUMENT && DOCUMENT.createElement("canvas");
4467
return (DOCUMENT && !DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1") && (!canvas || !canvas.getContext || !canvas.getContext("2d")));
4469
"trigger": "graphics"
4471
// graphics-svg-default
4473
"name": "graphics-svg-default",
4474
"test": function(Y) {
4475
var DOCUMENT = Y.config.doc;
4476
return (DOCUMENT && DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1"));
4478
"trigger": "graphics"
4482
"name": "widget-base-ie",
4483
"trigger": "widget-base",
4488
"name": "transition-timer",
4489
"test": function (Y) {
4490
var DOCUMENT = Y.config.doc,
4491
node = (DOCUMENT) ? DOCUMENT.documentElement: null,
4494
if (node && node.style) {
4495
ret = !('MozTransition' in node.style || 'WebkitTransition' in node.style);
4500
"trigger": "transition"
4504
"name": "dom-style-ie",
4505
"test": function (Y) {
4507
var testFeature = Y.Features.test,
4508
addFeature = Y.Features.add,
4509
WINDOW = Y.config.win,
4510
DOCUMENT = Y.config.doc,
4511
DOCUMENT_ELEMENT = 'documentElement',
4514
addFeature('style', 'computedStyle', {
4516
return WINDOW && 'getComputedStyle' in WINDOW;
4520
addFeature('style', 'opacity', {
4522
return DOCUMENT && 'opacity' in DOCUMENT[DOCUMENT_ELEMENT].style;
4526
ret = (!testFeature('style', 'opacity') &&
4527
!testFeature('style', 'computedStyle'));
4531
"trigger": "dom-style"
4535
"name": "selector-css2",
4536
"test": function (Y) {
4537
var DOCUMENT = Y.config.doc,
4538
ret = DOCUMENT && !('querySelectorAll' in DOCUMENT);
4542
"trigger": "selector"
4546
"name": "event-base-ie",
4547
"test": function(Y) {
4548
var imp = Y.config.doc && Y.config.doc.implementation;
4549
return (imp && (!imp.hasFeature('Events', '2.0')));
4551
"trigger": "node-base"
4555
"name": "dd-gestures",
4556
"test": function(Y) {
4557
return (Y.config.win && ('ontouchstart' in Y.config.win && !Y.UA.chrome));
4559
"trigger": "dd-drag"
4561
// scrollview-base-ie
4563
"name": "scrollview-base-ie",
4564
"trigger": "scrollview-base",
4569
"name": "graphics-canvas",
4570
"test": function(Y) {
4571
var DOCUMENT = Y.config.doc,
4572
canvas = DOCUMENT && DOCUMENT.createElement("canvas");
4573
return (DOCUMENT && !DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1") && (canvas && canvas.getContext && canvas.getContext("2d")));
4575
"trigger": "graphics"
4579
"name": "graphics-vml",
4580
"test": function(Y) {
4581
var DOCUMENT = Y.config.doc,
4582
canvas = DOCUMENT && DOCUMENT.createElement("canvas");
4583
return (DOCUMENT && !DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1") && (!canvas || !canvas.getContext || !canvas.getContext("2d")));
4585
"trigger": "graphics"
4589
}, '3.4.1' ,{requires:['yui-base']});
4590
YUI.add('intl-base', function(Y) {
4593
* The Intl utility provides a central location for managing sets of
4594
* localized resources (strings and formatting patterns).
4601
var SPLIT_REGEX = /[, ]/;
4603
Y.mix(Y.namespace('Intl'), {
4606
* Returns the language among those available that
4607
* best matches the preferred language list, using the Lookup
4608
* algorithm of BCP 47.
4609
* If none of the available languages meets the user's preferences,
4610
* then "" is returned.
4611
* Extended language ranges are not supported.
4613
* @method lookupBestLang
4614
* @param {String[] | String} preferredLanguages The list of preferred
4615
* languages in descending preference order, represented as BCP 47
4616
* language tags. A string array or a comma-separated list.
4617
* @param {String[]} availableLanguages The list of languages
4618
* that the application supports, represented as BCP 47 language
4621
* @return {String} The available language that best matches the
4622
* preferred language list, or "".
4625
lookupBestLang: function(preferredLanguages, availableLanguages) {
4627
var i, language, result, index;
4629
// check whether the list of available languages contains language;
4631
function scan(language) {
4633
for (i = 0; i < availableLanguages.length; i += 1) {
4634
if (language.toLowerCase() ===
4635
availableLanguages[i].toLowerCase()) {
4636
return availableLanguages[i];
4641
if (Y.Lang.isString(preferredLanguages)) {
4642
preferredLanguages = preferredLanguages.split(SPLIT_REGEX);
4645
for (i = 0; i < preferredLanguages.length; i += 1) {
4646
language = preferredLanguages[i];
4647
if (!language || language === '*') {
4650
// check the fallback sequence for one language
4651
while (language.length > 0) {
4652
result = scan(language);
4656
index = language.lastIndexOf('-');
4658
language = language.substring(0, index);
4659
// one-character subtags get cut along with the
4661
if (index >= 2 && language.charAt(index - 2) === '-') {
4662
language = language.substring(0, index - 2);
4665
// nothing available for this language
4677
}, '3.4.1' ,{requires:['yui-base']});
4678
YUI.add('yui-log', function(Y) {
4681
* Provides console log capability and exposes a custom event for
4682
* console implementations. This module is a `core` YUI module, <a href="../classes/YUI.html#method_log">it's documentation is located under the YUI class</a>.
4685
* @submodule yui-log
4689
LOGEVENT = 'yui:log',
4690
UNDEFINED = 'undefined',
4691
LEVELS = { debug: 1,
4697
* If the 'debug' config is true, a 'yui:log' event will be
4698
* dispatched, which the Console widget and anything else
4699
* can consume. If the 'useBrowserConsole' config is true, it will
4700
* write to the browser console if available. YUI-specific log
4701
* messages will only be present in the -debug versions of the
4702
* JS files. The build system is supposed to remove log statements
4703
* from the raw and minified versions of the files.
4707
* @param {String} msg The message to log.
4708
* @param {String} cat The log category for the message. Default
4709
* categories are "info", "warn", "error", time".
4710
* Custom categories can be used as well. (opt).
4711
* @param {String} src The source of the the message (opt).
4712
* @param {boolean} silent If true, the log event won't fire.
4713
* @return {YUI} YUI instance.
4715
INSTANCE.log = function(msg, cat, src, silent) {
4716
var bail, excl, incl, m, f,
4719
publisher = (Y.fire) ? Y : YUI.Env.globalEvents;
4720
// suppress log message if the config is off or the event stack
4721
// or the event call stack contains a consumer of the yui:log event
4723
// apply source filters
4725
excl = c.logExclude;
4726
incl = c.logInclude;
4727
if (incl && !(src in incl)) {
4729
} else if (incl && (src in incl)) {
4731
} else if (excl && (src in excl)) {
4736
if (c.useBrowserConsole) {
4737
m = (src) ? src + ': ' + msg : msg;
4738
if (Y.Lang.isFunction(c.logFn)) {
4739
c.logFn.call(Y, msg, cat, src);
4740
} else if (typeof console != UNDEFINED && console.log) {
4741
f = (cat && console[cat] && (cat in LEVELS)) ? cat : 'log';
4743
} else if (typeof opera != UNDEFINED) {
4748
if (publisher && !silent) {
4750
if (publisher == Y && (!publisher.getEvent(LOGEVENT))) {
4751
publisher.publish(LOGEVENT, {
4756
publisher.fire(LOGEVENT, {
4769
* Write a system message. This message will be preserved in the
4770
* minified and raw versions of the YUI files, unlike log statements.
4773
* @param {String} msg The message to log.
4774
* @param {String} cat The log category for the message. Default
4775
* categories are "info", "warn", "error", time".
4776
* Custom categories can be used as well. (opt).
4777
* @param {String} src The source of the the message (opt).
4778
* @param {boolean} silent If true, the log event won't fire.
4779
* @return {YUI} YUI instance.
4781
INSTANCE.message = function() {
4782
return INSTANCE.log.apply(INSTANCE, arguments);
4786
}, '3.4.1' ,{requires:['yui-base']});
4787
YUI.add('yui-later', function(Y) {
4790
* Provides a setTimeout/setInterval wrapper. This module is a `core` YUI module, <a href="../classes/YUI.html#method_later">it's documentation is located under the YUI class</a>.
4793
* @submodule yui-later
4799
* Executes the supplied function in the context of the supplied
4800
* object 'when' milliseconds later. Executes the function a
4801
* single time unless periodic is set to true.
4804
* @param when {int} the number of milliseconds to wait until the fn
4806
* @param o the context object.
4807
* @param fn {Function|String} the function to execute or the name of
4808
* the method in the 'o' object to execute.
4809
* @param data [Array] data that is provided to the function. This
4810
* accepts either a single item or an array. If an array is provided,
4811
* the function is executed with one parameter for each array item.
4812
* If you need to pass a single array parameter, it needs to be wrapped
4813
* in an array [myarray].
4815
* Note: native methods in IE may not have the call and apply methods.
4816
* In this case, it will work, but you are limited to four arguments.
4818
* @param periodic {boolean} if true, executes continuously at supplied
4819
* interval until canceled.
4820
* @return {object} a timer object. Call the cancel() method on this
4821
* object to stop the timer.
4823
Y.later = function(when, o, fn, data, periodic) {
4825
data = (!Y.Lang.isUndefined(data)) ? Y.Array(data) : NO_ARGS;
4826
o = o || Y.config.win || Y;
4828
var cancelled = false,
4829
method = (o && Y.Lang.isString(fn)) ? o[fn] : fn,
4830
wrapper = function() {
4831
// IE 8- may execute a setInterval callback one last time
4832
// after clearInterval was called, so in order to preserve
4833
// the cancel() === no more runny-run, we have to jump through
4836
if (!method.apply) {
4837
method(data[0], data[1], data[2], data[3]);
4839
method.apply(o, data || NO_ARGS);
4843
id = (periodic) ? setInterval(wrapper, when) : setTimeout(wrapper, when);
4848
cancel: function() {
4850
if (this.interval) {
4859
Y.Lang.later = Y.later;
4863
}, '3.4.1' ,{requires:['yui-base']});
4864
YUI.add('loader-base', function(Y) {
4867
* The YUI loader core
4869
* @submodule loader-base
4872
if (!YUI.Env[Y.version]) {
4875
var VERSION = Y.version,
4877
ROOT = VERSION + BUILD,
4878
CDN_BASE = Y.Env.base,
4879
GALLERY_VERSION = 'gallery-2011.09.14-20-40',
4882
YUI2_VERSION = '2.9.0',
4883
COMBO_BASE = CDN_BASE + 'combo?',
4884
META = { version: VERSION,
4887
comboBase: COMBO_BASE,
4888
skin: { defaultSkin: 'sam',
4889
base: 'assets/skins/',
4896
'cssfonts-context']},
4899
groups = META.groups,
4900
yui2Update = function(tnt, yui2) {
4901
var root = TNT + '.' +
4902
(tnt || TNT_VERSION) + '/' +
4903
(yui2 || YUI2_VERSION) + BUILD;
4904
groups.yui2.base = CDN_BASE + root;
4905
groups.yui2.root = root;
4907
galleryUpdate = function(tag) {
4908
var root = (tag || GALLERY_VERSION) + BUILD;
4909
groups.gallery.base = CDN_BASE + root;
4910
groups.gallery.root = root;
4913
groups[VERSION] = {};
4918
comboBase: COMBO_BASE,
4919
update: galleryUpdate,
4920
patterns: { 'gallery-': { },
4921
'lang/gallery-': {},
4922
'gallerycss-': { type: 'css' } }
4928
comboBase: COMBO_BASE,
4932
configFn: function(me) {
4933
if (/-skin|reset|fonts|grids|base/.test(me.name)) {
4935
me.path = me.path.replace(/\.js/, '.css');
4936
// this makes skins in builds earlier than
4937
// 2.6.0 work as long as combine is false
4938
me.path = me.path.replace(/\/yui2-skin/,
4939
'/assets/skins/sam/yui2-skin');
4949
YUI.Env[VERSION] = META;
4955
* Loader dynamically loads script and css files. It includes the dependency
4956
* info for the version of the library in use, and will automatically pull in
4957
* dependencies for the modules requested. It supports rollup files and will
4958
* automatically use these when appropriate in order to minimize the number of
4959
* http connections required to load all of the dependencies. It can load the
4960
* files from the Yahoo! CDN, and it can utilize the combo service provided on
4961
* this network to reduce the number of http connections required to download
4966
* @submodule loader-base
4970
NO_REQUIREMENTS = [],
4971
MAX_URL_LENGTH = 2048,
4972
GLOBAL_ENV = YUI.Env,
4973
GLOBAL_LOADED = GLOBAL_ENV._loaded,
4977
VERSION = Y.version,
4980
oeach = YObject.each,
4982
_queue = GLOBAL_ENV._loaderQueue,
4983
META = GLOBAL_ENV[VERSION],
4984
SKIN_PREFIX = 'skin-',
4986
ON_PAGE = GLOBAL_ENV.mods,
4989
_path = function(dir, file, type, nomin) {
4990
var path = dir + '/' + file;
4994
path += '.' + (type || CSS);
4999
if (YUI.Env.aliases) {
5000
YUI.Env.aliases = {}; //Don't need aliases if Loader is present
5004
* The component metadata is stored in Y.Env.meta.
5005
* Part of the loader module.
5012
* Loader dynamically loads script and css files. It includes the dependency
5013
* info for the version of the library in use, and will automatically pull in
5014
* dependencies for the modules requested. It supports rollup files and will
5015
* automatically use these when appropriate in order to minimize the number of
5016
* http connections required to load all of the dependencies. It can load the
5017
* files from the Yahoo! CDN, and it can utilize the combo service provided on
5018
* this network to reduce the number of http connections required to download
5021
* While the loader can be instantiated by the end user, it normally is not.
5022
* @see YUI.use for the normal use case. The use function automatically will
5023
* pull in missing dependencies.
5027
* @param {object} o an optional set of configuration options. Valid options:
5032
* The YUI combo service base dir. Ex: http://yui.yahooapis.com/combo?</li>
5034
* The root path to prepend to module names for the combo service.
5035
* Ex: 2.5.2/build/</li>
5038
* A filter to apply to result urls. This filter will modify the default
5039
* path for all modules. The default path for the YUI library is the
5040
* minified version of the files (e.g., event-min.js). The filter property
5041
* can be a predefined filter or a custom filter. The valid predefined
5045
* <dd>Selects the debug versions of the library (e.g., event-debug.js).
5046
* This option will automatically include the Logger widget</dd>
5048
* <dd>Selects the non-minified version of the library (e.g., event.js).
5051
* You can also define a custom filter, which must be an object literal
5052
* containing a search expression and a replace string:
5055
* 'searchExp': "-min\\.js",
5056
* 'replaceStr': "-debug.js"
5061
* <li>filters: per-component filter specification. If specified
5062
* for a given component, this overrides the filter config. _Note:_ This does not work on combo urls, use the filter property instead.</li>
5064
* Use the YUI combo service to reduce the number of http connections
5065
* required to load your dependencies</li>
5067
* A list of modules that should never be dynamically loaded</li>
5069
* A list of modules that should always be loaded when required, even if
5070
* already present on the page</li>
5072
* Node or id for a node that should be used as the insertion point for
5075
* charset for dynamic nodes (deprecated, use jsAttributes or cssAttributes)
5077
* <li>jsAttributes: object literal containing attributes to add to script
5079
* <li>cssAttributes: object literal containing attributes to add to link
5082
* The number of milliseconds before a timeout occurs when dynamically
5083
* loading nodes. If not set, there is no timeout</li>
5085
* execution context for all callbacks</li>
5087
* callback for the 'success' event</li>
5088
* <li>onFailure: callback for the 'failure' event</li>
5089
* <li>onCSS: callback for the 'CSSComplete' event. When loading YUI
5090
* components with CSS the CSS is loaded first, then the script. This
5091
* provides a moment you can tie into to improve
5092
* the presentation of the page while the script is loading.</li>
5094
* callback for the 'timeout' event</li>
5096
* callback executed each time a script or css file is loaded</li>
5098
* A list of module definitions. See Loader.addModule for the supported
5099
* module metadata</li>
5101
* A list of group definitions. Each group can contain specific definitions
5102
* for base, comboBase, combine, and accepts a list of modules. See above
5103
* for the description of these properties.</li>
5104
* <li>2in3: the version of the YUI 2 in 3 wrapper to use. The intrinsic
5105
* support for YUI 2 modules in YUI 3 relies on versions of the YUI 2
5106
* components inside YUI 3 module wrappers. These wrappers
5107
* change over time to accomodate the issues that arise from running YUI 2
5108
* in a YUI 3 sandbox.</li>
5109
* <li>yui2: when using the 2in3 project, you can select the version of
5110
* YUI 2 to use. Valid values * are 2.2.2, 2.3.1, 2.4.1, 2.5.2, 2.6.0,
5111
* 2.7.0, 2.8.0, and 2.8.1 [default] -- plus all versions of YUI 2
5112
* going forward.</li>
5115
Y.Loader = function(o) {
5117
var defaults = META.modules,
5120
modulekey = META.md5;
5123
* Internal callback to handle multiple internal insert() calls
5124
* so that css is inserted prior to js
5125
* @property _internalCallback
5128
// self._internalCallback = null;
5131
* Callback that will be executed when the loader is finished
5136
// self.onSuccess = null;
5139
* Callback that will be executed if there is a failure
5143
// self.onFailure = null;
5146
* Callback for the 'CSSComplete' event. When loading YUI components
5147
* with CSS the CSS is loaded first, then the script. This provides
5148
* a moment you can tie into to improve the presentation of the page
5149
* while the script is loading.
5153
// self.onCSS = null;
5156
* Callback executed each time a script or css file is loaded
5157
* @method onProgress
5160
// self.onProgress = null;
5163
* Callback that will be executed if a timeout occurs
5167
// self.onTimeout = null;
5170
* The execution context for all callbacks
5172
* @default {YUI} the YUI instance
5177
* Data that is passed to all callbacks
5180
// self.data = null;
5183
* Node reference or id where new nodes should be inserted before
5184
* @property insertBefore
5185
* @type string|HTMLElement
5187
// self.insertBefore = null;
5190
* The charset attribute for inserted nodes
5193
* @deprecated , use cssAttributes or jsAttributes.
5195
// self.charset = null;
5198
* An object literal containing attributes to add to link nodes
5199
* @property cssAttributes
5202
// self.cssAttributes = null;
5205
* An object literal containing attributes to add to script nodes
5206
* @property jsAttributes
5209
// self.jsAttributes = null;
5212
* The base directory.
5215
* @default http://yui.yahooapis.com/[YUI VERSION]/build/
5217
self.base = Y.Env.meta.base + Y.Env.meta.root;
5220
* Base path for the combo service
5221
* @property comboBase
5223
* @default http://yui.yahooapis.com/combo?
5225
self.comboBase = Y.Env.meta.comboBase;
5228
* Base path for language packs.
5230
// self.langBase = Y.Env.meta.langBase;
5234
* If configured, the loader will attempt to use the combo
5235
* service for YUI resources and configured external resources.
5238
* @default true if a base dir isn't in the config
5240
self.combine = o.base &&
5241
(o.base.indexOf(self.comboBase.substr(0, 20)) > -1);
5244
* The default seperator to use between files in a combo URL
5245
* @property comboSep
5247
* @default Ampersand
5249
self.comboSep = '&';
5251
* Max url length for combo urls. The default is 2048. This is the URL
5252
* limit for the Yahoo! hosted combo servers. If consuming
5253
* a different combo service that has a different URL limit
5254
* it is possible to override this default by supplying
5255
* the maxURLLength config option. The config option will
5256
* only take effect if lower than the default.
5258
* @property maxURLLength
5261
self.maxURLLength = MAX_URL_LENGTH;
5264
* Ignore modules registered on the YUI global
5265
* @property ignoreRegistered
5268
// self.ignoreRegistered = false;
5271
* Root path to prepend to module path for the combo
5275
* @default [YUI VERSION]/build/
5277
self.root = Y.Env.meta.root;
5280
* Timeout value in milliseconds. If set, self value will be used by
5281
* the get utility. the timeout event will fire if
5289
* A list of modules that should not be loaded, even if
5290
* they turn up in the dependency tree
5294
// self.ignore = null;
5297
* A list of modules that should always be loaded, even
5298
* if they have already been inserted into the page.
5302
// self.force = null;
5307
* Should we allow rollups
5308
* @property allowRollup
5312
self.allowRollup = false;
5315
* A filter to apply to result urls. This filter will modify the default
5316
* path for all modules. The default path for the YUI library is the
5317
* minified version of the files (e.g., event-min.js). The filter property
5318
* can be a predefined filter or a custom filter. The valid predefined
5322
* <dd>Selects the debug versions of the library (e.g., event-debug.js).
5323
* This option will automatically include the Logger widget</dd>
5325
* <dd>Selects the non-minified version of the library (e.g., event.js).
5328
* You can also define a custom filter, which must be an object literal
5329
* containing a search expression and a replace string:
5332
* 'searchExp': "-min\\.js",
5333
* 'replaceStr': "-debug.js"
5337
* @type string| {searchExp: string, replaceStr: string}
5339
// self.filter = null;
5342
* per-component filter specification. If specified for a given
5343
* component, this overrides the filter config.
5350
* The list of requested modules
5351
* @property required
5352
* @type {string: boolean}
5357
* If a module name is predefined when requested, it is checked againsts
5358
* the patterns provided in this property. If there is a match, the
5359
* module is added with the default configuration.
5361
* At the moment only supporting module prefixes, but anticipate
5362
* supporting at least regular expressions.
5363
* @property patterns
5366
// self.patterns = Y.merge(Y.Env.meta.patterns);
5370
* The library metadata
5371
* @property moduleInfo
5373
// self.moduleInfo = Y.merge(Y.Env.meta.moduleInfo);
5374
self.moduleInfo = {};
5376
self.groups = Y.merge(Y.Env.meta.groups);
5379
* Provides the information used to skin the skinnable components.
5380
* The following skin definition would result in 'skin1' and 'skin2'
5381
* being loaded for calendar (if calendar was requested), and
5382
* 'sam' for all other skinnable components:
5387
* // The default skin, which is automatically applied if not
5388
* // overriden by a component-specific skin definition.
5389
* // Change this in to apply a different skin globally
5390
* defaultSkin: 'sam',
5392
* // This is combined with the loader base property to get
5393
* // the default root directory for a skin. ex:
5394
* // http://yui.yahooapis.com/2.3.0/build/assets/skins/sam/
5395
* base: 'assets/skins/',
5397
* // Any component-specific overrides can be specified here,
5398
* // making it possible to load different skins for different
5399
* // components. It is possible to load more than one skin
5400
* // for a given component as well.
5402
* calendar: ['skin1', 'skin2']
5408
self.skin = Y.merge(Y.Env.meta.skin);
5411
* Map of conditional modules
5414
self.conditions = {};
5416
// map of modules with a hash of modules that meet the requirement
5417
// self.provides = {};
5420
self._internal = true;
5423
cache = GLOBAL_ENV._renderedMods;
5426
oeach(cache, function modCache(v, k) {
5427
//self.moduleInfo[k] = Y.merge(v);
5428
self.moduleInfo[k] = v;
5431
cache = GLOBAL_ENV._conditions;
5433
oeach(cache, function condCache(v, k) {
5434
//self.conditions[k] = Y.merge(v);
5435
self.conditions[k] = v;
5439
oeach(defaults, self.addModule, self);
5442
if (!GLOBAL_ENV._renderedMods) {
5443
//GLOBAL_ENV._renderedMods = Y.merge(self.moduleInfo);
5444
//GLOBAL_ENV._conditions = Y.merge(self.conditions);
5445
GLOBAL_ENV._renderedMods = self.moduleInfo;
5446
GLOBAL_ENV._conditions = self.conditions;
5449
self._inspectPage();
5451
self._internal = false;
5455
self.testresults = null;
5457
if (Y.config.tests) {
5458
self.testresults = Y.config.tests;
5462
* List of rollup files found in the library metadata
5465
// self.rollups = null;
5468
* Whether or not to load optional dependencies for
5469
* the requested modules
5470
* @property loadOptional
5474
// self.loadOptional = false;
5477
* All of the derived dependencies in sorted order, which
5478
* will be populated when either calculate() or insert()
5486
* Set when beginning to compute the dependency tree.
5487
* Composed of what YUI reports to be loaded combined
5488
* with what has been loaded by any instance on the page
5489
* with the version number specified in the metadata.
5491
* @type {string: boolean}
5493
self.loaded = GLOBAL_LOADED[VERSION];
5496
* A list of modules to attach to the YUI instance when complete.
5497
* If not supplied, the sorted list of dependencies are applied.
5498
* @property attaching
5500
// self.attaching = null;
5503
* Flag to indicate the dependency tree needs to be recomputed
5504
* if insert is called again.
5512
* List of modules inserted by the utility
5513
* @property inserted
5514
* @type {string: boolean}
5519
* List of skipped modules during insert() because the module
5525
// Y.on('yui:load', self.loadNext, self);
5530
* Cached sorted calculate results
5534
//self.results = {};
5538
Y.Loader.prototype = {
5542
'searchExp': '-min\\.js',
5546
'searchExp': '-min\\.js',
5547
'replaceStr': '-debug.js'
5551
* Check the pages meta-data and cache the result.
5552
* @method _inspectPage
5555
_inspectPage: function() {
5556
oeach(ON_PAGE, function(v, k) {
5558
var m = this.moduleInfo[k],
5559
req = v.details.requires,
5560
mr = m && m.requires;
5562
if (!m._inspected && req && mr.length != req.length) {
5563
// console.log('deleting ' + m.name);
5564
// m.requres = YObject.keys(Y.merge(YArray.hash(req), YArray.hash(mr)));
5566
// delete m.expanded_map;
5569
m = this.addModule(v.details, k);
5571
m._inspected = true;
5576
* returns true if b is not loaded, and is required directly or by means of modules it supersedes.
5579
* @param {String} mod1 The first module to compare
5580
* @param {String} mod2 The second module to compare
5582
_requires: function(mod1, mod2) {
5584
var i, rm, after_map, s,
5585
info = this.moduleInfo,
5593
rm = m.expanded_map;
5594
after_map = m.after_map;
5596
// check if this module should be sorted after the other
5597
// do this first to short circut circular deps
5598
if (after_map && (mod2 in after_map)) {
5602
after_map = other.after_map;
5605
if (after_map && (mod1 in after_map)) {
5609
// check if this module requires one the other supersedes
5610
s = info[mod2] && info[mod2].supersedes;
5612
for (i = 0; i < s.length; i++) {
5613
if (this._requires(mod1, s[i])) {
5619
s = info[mod1] && info[mod1].supersedes;
5621
for (i = 0; i < s.length; i++) {
5622
if (this._requires(mod2, s[i])) {
5628
// check if this module requires the other directly
5629
// if (r && YArray.indexOf(r, mod2) > -1) {
5630
if (rm && (mod2 in rm)) {
5634
// external css files should be sorted below yui css
5635
if (m.ext && m.type == CSS && !other.ext && other.type == CSS) {
5642
* Apply a new config to the Loader instance
5644
* @param {Object} o The new configuration
5646
_config: function(o) {
5647
var i, j, val, f, group, groupName, self = this;
5648
// apply config values
5651
if (o.hasOwnProperty(i)) {
5653
if (i == 'require') {
5655
} else if (i == 'skin') {
5656
Y.mix(self.skin, o[i], true);
5657
} else if (i == 'groups') {
5659
if (val.hasOwnProperty(j)) {
5662
self.addGroup(group, groupName);
5666
} else if (i == 'modules') {
5667
// add a hash of module definitions
5668
oeach(val, self.addModule, self);
5669
} else if (i == 'gallery') {
5670
this.groups.gallery.update(val);
5671
} else if (i == 'yui2' || i == '2in3') {
5672
this.groups.yui2.update(o['2in3'], o.yui2);
5673
} else if (i == 'maxURLLength') {
5674
self[i] = Math.min(MAX_URL_LENGTH, val);
5685
if (L.isString(f)) {
5686
f = f.toUpperCase();
5687
self.filterName = f;
5688
self.filter = self.FILTER_DEFS[f];
5690
self.require('yui-log', 'dump');
5695
self.require('intl-base', 'intl');
5701
* Returns the skin module name for the specified skin name. If a
5702
* module name is supplied, the returned skin module name is
5703
* specific to the module passed in.
5704
* @method formatSkin
5705
* @param {string} skin the name of the skin.
5706
* @param {string} mod optional: the name of a module to skin.
5707
* @return {string} the full skin module name.
5709
formatSkin: function(skin, mod) {
5710
var s = SKIN_PREFIX + skin;
5719
* Adds the skin def to the module info
5721
* @param {string} skin the name of the skin.
5722
* @param {string} mod the name of the module.
5723
* @param {string} parent parent module if this is a skin of a
5724
* submodule or plugin.
5725
* @return {string} the module name for the skin.
5728
_addSkin: function(skin, mod, parent) {
5729
var mdef, pkg, name, nmod,
5730
info = this.moduleInfo,
5732
ext = info[mod] && info[mod].ext;
5734
// Add a module definition for the module-specific skin css
5736
name = this.formatSkin(skin, mod);
5739
pkg = mdef.pkg || mod;
5745
path: (parent || pkg) + '/' + sinf.base + skin +
5750
nmod.base = mdef.base;
5752
if (mdef.configFn) {
5753
nmod.configFn = mdef.configFn;
5755
this.addModule(nmod, name);
5764
* Add a new module group
5766
* <dt>name:</dt> <dd>required, the group name</dd>
5767
* <dt>base:</dt> <dd>The base dir for this module group</dd>
5768
* <dt>root:</dt> <dd>The root path to add to each combo
5769
* resource path</dd>
5770
* <dt>combine:</dt> <dd>combo handle</dd>
5771
* <dt>comboBase:</dt> <dd>combo service base path</dd>
5772
* <dt>modules:</dt> <dd>the group of modules</dd>
5775
* @param {object} o An object containing the module data.
5776
* @param {string} name the group name.
5778
addGroup: function(o, name) {
5779
var mods = o.modules,
5781
name = name || o.name;
5783
self.groups[name] = o;
5786
oeach(o.patterns, function(v, k) {
5788
self.patterns[k] = v;
5793
oeach(mods, function(v, k) {
5795
self.addModule(v, k);
5801
* Add a new module to the component metadata.
5803
* <dt>name:</dt> <dd>required, the component name</dd>
5804
* <dt>type:</dt> <dd>required, the component type (js or css)
5806
* <dt>path:</dt> <dd>required, the path to the script from
5808
* <dt>requires:</dt> <dd>array of modules required by this
5810
* <dt>optional:</dt> <dd>array of optional modules for this
5812
* <dt>supersedes:</dt> <dd>array of the modules this component
5814
* <dt>after:</dt> <dd>array of modules the components which, if
5815
* present, should be sorted above this one</dd>
5816
* <dt>after_map:</dt> <dd>faster alternative to 'after' -- supply
5817
* a hash instead of an array</dd>
5818
* <dt>rollup:</dt> <dd>the number of superseded modules required
5819
* for automatic rollup</dd>
5820
* <dt>fullpath:</dt> <dd>If fullpath is specified, this is used
5821
* instead of the configured base + path</dd>
5822
* <dt>skinnable:</dt> <dd>flag to determine if skin assets should
5823
* automatically be pulled in</dd>
5824
* <dt>submodules:</dt> <dd>a hash of submodules</dd>
5825
* <dt>group:</dt> <dd>The group the module belongs to -- this
5826
* is set automatically when it is added as part of a group
5827
* configuration.</dd>
5829
* <dd>array of BCP 47 language tags of languages for which this
5830
* module has localized resource bundles,
5831
* e.g., ["en-GB","zh-Hans-CN"]</dd>
5832
* <dt>condition:</dt>
5833
* <dd>Specifies that the module should be loaded automatically if
5834
* a condition is met. This is an object with up to three fields:
5835
* [trigger] - the name of a module that can trigger the auto-load
5836
* [test] - a function that returns true when the module is to be
5838
* [when] - specifies the load order of the conditional module
5839
* with regard to the position of the trigger module.
5840
* This should be one of three values: 'before', 'after', or
5841
* 'instead'. The default is 'after'.
5843
* <dt>testresults:</dt><dd>a hash of test results from Y.Features.all()</dd>
5846
* @param {object} o An object containing the module data.
5847
* @param {string} name the module name (optional), required if not
5848
* in the module data.
5849
* @return {object} the module definition or null if
5850
* the object passed in did not provide all required attributes.
5852
addModule: function(o, name) {
5853
name = name || o.name;
5855
//Only merge this data if the temp flag is set
5856
//from an earlier pass from a pattern or else
5857
//an override module (YUI_config) can not be used to
5858
//replace a default module.
5859
if (this.moduleInfo[name] && this.moduleInfo[name].temp) {
5860
//This catches temp modules loaded via a pattern
5861
// The module will be added twice, once from the pattern and
5862
// Once from the actual add call, this ensures that properties
5863
// that were added to the module the first time around (group: gallery)
5864
// are also added the second time around too.
5865
o = Y.merge(this.moduleInfo[name], o);
5870
if (!o || !o.name) {
5878
if (!o.path && !o.fullpath) {
5879
o.path = _path(name, name, o.type);
5881
o.supersedes = o.supersedes || o.use;
5883
o.ext = ('ext' in o) ? o.ext : (this._internal) ? false : true;
5884
o.requires = this.filterRequires(o.requires) || [];
5886
// Handle submodule logic
5887
var subs = o.submodules, i, l, t, sup, s, smod, plugins, plug,
5888
j, langs, packName, supName, flatSup, flatLang, lang, ret,
5889
overrides, skinname, when,
5890
conditions = this.conditions, trigger;
5891
// , existing = this.moduleInfo[name], newr;
5893
this.moduleInfo[name] = o;
5895
if (!o.langPack && o.lang) {
5896
langs = YArray(o.lang);
5897
for (j = 0; j < langs.length; j++) {
5899
packName = this.getLangPackName(lang, name);
5900
smod = this.moduleInfo[packName];
5902
smod = this._addLangPack(lang, o, packName);
5908
sup = o.supersedes || [];
5912
if (subs.hasOwnProperty(i)) {
5915
s.path = s.path || _path(name, i, o.type);
5920
sup = sup.concat(s.supersedes);
5923
smod = this.addModule(s, i);
5926
if (smod.skinnable) {
5928
overrides = this.skin.overrides;
5929
if (overrides && overrides[i]) {
5930
for (j = 0; j < overrides[i].length; j++) {
5931
skinname = this._addSkin(overrides[i][j],
5936
skinname = this._addSkin(this.skin.defaultSkin,
5941
// looks like we are expected to work out the metadata
5942
// for the parent module language packs from what is
5943
// specified in the child modules.
5944
if (s.lang && s.lang.length) {
5946
langs = YArray(s.lang);
5947
for (j = 0; j < langs.length; j++) {
5949
packName = this.getLangPackName(lang, name);
5950
supName = this.getLangPackName(lang, i);
5951
smod = this.moduleInfo[packName];
5954
smod = this._addLangPack(lang, o, packName);
5957
flatSup = flatSup || YArray.hash(smod.supersedes);
5959
if (!(supName in flatSup)) {
5960
smod.supersedes.push(supName);
5963
o.lang = o.lang || [];
5965
flatLang = flatLang || YArray.hash(o.lang);
5967
if (!(lang in flatLang)) {
5971
// Add rollup file, need to add to supersedes list too
5974
packName = this.getLangPackName(ROOT_LANG, name);
5975
supName = this.getLangPackName(ROOT_LANG, i);
5977
smod = this.moduleInfo[packName];
5980
smod = this._addLangPack(lang, o, packName);
5983
if (!(supName in flatSup)) {
5984
smod.supersedes.push(supName);
5987
// Add rollup file, need to add to supersedes list too
5995
//o.supersedes = YObject.keys(YArray.hash(sup));
5996
o.supersedes = YArray.dedupe(sup);
5997
if (this.allowRollup) {
5998
o.rollup = (l < 4) ? l : Math.min(l - 1, 4);
6002
plugins = o.plugins;
6004
for (i in plugins) {
6005
if (plugins.hasOwnProperty(i)) {
6008
plug.path = plug.path || _path(name, i, o.type);
6009
plug.requires = plug.requires || [];
6010
plug.group = o.group;
6011
this.addModule(plug, i);
6013
this._addSkin(this.skin.defaultSkin, i, name);
6021
t = o.condition.trigger;
6022
if (YUI.Env.aliases[t]) {
6023
t = YUI.Env.aliases[t];
6025
if (!Y.Lang.isArray(t)) {
6029
for (i = 0; i < t.length; i++) {
6031
when = o.condition.when;
6032
conditions[trigger] = conditions[trigger] || {};
6033
conditions[trigger][name] = o.condition;
6034
// the 'when' attribute can be 'before', 'after', or 'instead'
6035
// the default is after.
6036
if (when && when != 'after') {
6037
if (when == 'instead') { // replace the trigger
6038
o.supersedes = o.supersedes || [];
6039
o.supersedes.push(trigger);
6040
} else { // before the trigger
6041
// the trigger requires the conditional mod,
6042
// so it should appear before the conditional
6043
// mod if we do not intersede.
6045
} else { // after the trigger
6046
o.after = o.after || [];
6047
o.after.push(trigger);
6053
o.after_map = YArray.hash(o.after);
6056
// this.dirty = true;
6059
ret = o.configFn(o);
6060
if (ret === false) {
6061
delete this.moduleInfo[name];
6070
* Add a requirement for one or more module
6072
* @param {string[] | string*} what the modules to load.
6074
require: function(what) {
6075
var a = (typeof what === 'string') ? YArray(arguments) : what;
6077
this.required = Y.merge(this.required, YArray.hash(this.filterRequires(a)));
6079
this._explodeRollups();
6082
* Grab all the items that were asked for, check to see if the Loader
6083
* meta-data contains a "use" array. If it doesm remove the asked item and replace it with
6084
* the content of the "use".
6085
* This will make asking for: "dd"
6086
* Actually ask for: "dd-ddm-base,dd-ddm,dd-ddm-drop,dd-drag,dd-proxy,dd-constrain,dd-drop,dd-scroll,dd-drop-plugin"
6088
* @method _explodeRollups
6090
_explodeRollups: function() {
6093
if (!self.allowRollup) {
6094
oeach(r, function(v, name) {
6095
m = self.getModule(name);
6098
YArray.each(m.use, function(v) {
6099
m = self.getModule(v);
6102
YArray.each(m.use, function(v) {
6116
* Explodes the required array to remove aliases and replace them with real modules
6117
* @method filterRequires
6118
* @param {Array} r The original requires array
6119
* @return {Array} The new array of exploded requirements
6121
filterRequires: function(r) {
6123
if (!Y.Lang.isArray(r)) {
6127
var c = [], i, mod, o, m;
6129
for (i = 0; i < r.length; i++) {
6130
mod = this.getModule(r[i]);
6131
if (mod && mod.use) {
6132
for (o = 0; o < mod.use.length; o++) {
6133
//Must walk the other modules in case a module is a rollup of rollups (datatype)
6134
m = this.getModule(mod.use[o]);
6136
c = Y.Array.dedupe([].concat(c, this.filterRequires(m.use)));
6150
* Returns an object containing properties for all modules required
6151
* in order to load the requested module
6152
* @method getRequires
6153
* @param {object} mod The module definition from moduleInfo.
6154
* @return {array} the expanded requirement list.
6156
getRequires: function(mod) {
6158
if (!mod || mod._parsed) {
6159
return NO_REQUIREMENTS;
6162
var i, m, j, add, packName, lang, testresults = this.testresults,
6163
name = mod.name, cond, go,
6164
adddef = ON_PAGE[name] && ON_PAGE[name].details,
6167
o, skinmod, skindef, skinpar, skinname,
6168
intl = mod.lang || mod.intl,
6169
info = this.moduleInfo,
6170
ftests = Y.Features && Y.Features.tests.load,
6173
// console.log(name);
6175
// pattern match leaves module stub that needs to be filled out
6176
if (mod.temp && adddef) {
6178
mod = this.addModule(adddef, name);
6179
mod.group = old_mod.group;
6180
mod.pkg = old_mod.pkg;
6181
delete mod.expanded;
6184
// console.log('cache: ' + mod.langCache + ' == ' + this.lang);
6186
// if (mod.expanded && (!mod.langCache || mod.langCache == this.lang)) {
6187
if (mod.expanded && (!this.lang || mod.langCache === this.lang)) {
6188
return mod.expanded;
6195
r = this.filterRequires(mod.requires);
6197
//If a module has a lang attribute, auto add the intl requirement.
6202
o = this.filterRequires(mod.optional);
6206
mod.langCache = this.lang;
6208
for (i = 0; i < r.length; i++) {
6212
m = this.getModule(r[i]);
6214
add = this.getRequires(m);
6215
intl = intl || (m.expanded_map &&
6216
(INTL in m.expanded_map));
6217
for (j = 0; j < add.length; j++) {
6224
// get the requirements from superseded modules, if any
6225
r = this.filterRequires(mod.supersedes);
6227
for (i = 0; i < r.length; i++) {
6229
// if this module has submodules, the requirements list is
6230
// expanded to include the submodules. This is so we can
6231
// prevent dups when a submodule is already loaded and the
6232
// parent is requested.
6233
if (mod.submodules) {
6238
m = this.getModule(r[i]);
6241
add = this.getRequires(m);
6242
intl = intl || (m.expanded_map &&
6243
(INTL in m.expanded_map));
6244
for (j = 0; j < add.length; j++) {
6252
if (o && this.loadOptional) {
6253
for (i = 0; i < o.length; i++) {
6259
add = this.getRequires(m);
6260
intl = intl || (m.expanded_map &&
6261
(INTL in m.expanded_map));
6262
for (j = 0; j < add.length; j++) {
6270
cond = this.conditions[name];
6273
if (testresults && ftests) {
6274
oeach(testresults, function(result, id) {
6275
var condmod = ftests[id].name;
6276
if (!hash[condmod] && ftests[id].trigger == name) {
6277
if (result && ftests[id]) {
6278
hash[condmod] = true;
6284
oeach(cond, function(def, condmod) {
6285
if (!hash[condmod]) {
6286
go = def && ((def.ua && Y.UA[def.ua]) ||
6287
(def.test && def.test(Y, r)));
6289
hash[condmod] = true;
6291
m = this.getModule(condmod);
6293
add = this.getRequires(m);
6294
for (j = 0; j < add.length; j++) {
6304
// Create skin modules
6305
if (mod.skinnable) {
6306
skindef = this.skin.overrides;
6307
oeach(YUI.Env.aliases, function(o, n) {
6308
if (Y.Array.indexOf(o, name) > -1) {
6312
if (skindef && (skindef[name] || (skinpar && skindef[skinpar]))) {
6314
if (skindef[skinpar]) {
6317
for (i = 0; i < skindef[skinname].length; i++) {
6318
skinmod = this._addSkin(skindef[skinname][i], name);
6322
skinmod = this._addSkin(this.skin.defaultSkin, name);
6327
mod._parsed = false;
6331
if (mod.lang && !mod.langPack && Y.Intl) {
6332
lang = Y.Intl.lookupBestLang(this.lang || ROOT_LANG, mod.lang);
6333
packName = this.getLangPackName(lang, name);
6335
d.unshift(packName);
6341
mod.expanded_map = YArray.hash(d);
6343
mod.expanded = YObject.keys(mod.expanded_map);
6345
return mod.expanded;
6350
* Returns a hash of module names the supplied module satisfies.
6351
* @method getProvides
6352
* @param {string} name The name of the module.
6353
* @return {object} what this module provides.
6355
getProvides: function(name) {
6356
var m = this.getModule(name), o, s;
6357
// supmap = this.provides;
6363
if (m && !m.provides) {
6368
YArray.each(s, function(v) {
6369
Y.mix(o, this.getProvides(v));
6382
* Calculates the dependency tree, the result is stored in the sorted
6385
* @param {object} o optional options object.
6386
* @param {string} type optional argument to prune modules.
6388
calculate: function(o, type) {
6389
if (o || type || this.dirty) {
6401
if (this.allowRollup) {
6404
this._explodeRollups();
6411
* Creates a "psuedo" package for languages provided in the lang array
6412
* @method _addLangPack
6413
* @param {String} lang The language to create
6414
* @param {Object} m The module definition to create the language pack around
6415
* @param {String} packName The name of the package (e.g: lang/datatype-date-en-US)
6416
* @return {Object} The module definition
6418
_addLangPack: function(lang, m, packName) {
6421
existing = this.moduleInfo[packName];
6425
packPath = _path((m.pkg || name), packName, JS, true);
6427
this.addModule({ path: packPath,
6432
supersedes: [] }, packName);
6435
Y.Env.lang = Y.Env.lang || {};
6436
Y.Env.lang[lang] = Y.Env.lang[lang] || {};
6437
Y.Env.lang[lang][name] = true;
6441
return this.moduleInfo[packName];
6445
* Investigates the current YUI configuration on the page. By default,
6446
* modules already detected will not be loaded again unless a force
6447
* option is encountered. Called by calculate()
6451
_setup: function() {
6452
var info = this.moduleInfo, name, i, j, m, l,
6455
for (name in info) {
6456
if (info.hasOwnProperty(name)) {
6461
//m.requires = YObject.keys(YArray.hash(m.requires));
6462
m.requires = YArray.dedupe(m.requires);
6464
// Create lang pack modules
6465
if (m.lang && m.lang.length) {
6466
// Setup root package if the module has lang defined,
6467
// it needs to provide a root language pack
6468
packName = this.getLangPackName(ROOT_LANG, name);
6469
this._addLangPack(null, m, packName);
6477
//l = Y.merge(this.inserted);
6480
// available modules
6481
if (!this.ignoreRegistered) {
6482
Y.mix(l, GLOBAL_ENV.mods);
6485
// add the ignore list to the list of loaded packages
6487
Y.mix(l, YArray.hash(this.ignore));
6490
// expand the list to include superseded modules
6492
if (l.hasOwnProperty(j)) {
6493
Y.mix(l, this.getProvides(j));
6497
// remove modules on the force list from the loaded list
6499
for (i = 0; i < this.force.length; i++) {
6500
if (this.force[i] in l) {
6501
delete l[this.force[i]];
6506
Y.mix(this.loaded, l);
6512
* Builds a module name for a language pack
6513
* @method getLangPackName
6514
* @param {string} lang the language code.
6515
* @param {string} mname the module to build it for.
6516
* @return {string} the language pack module name.
6518
getLangPackName: function(lang, mname) {
6519
return ('lang/' + mname + ((lang) ? '_' + lang : ''));
6522
* Inspects the required modules list looking for additional
6523
* dependencies. Expands the required list to include all
6524
* required modules. Called by calculate()
6528
_explode: function() {
6529
var r = this.required, m, reqs, done = {},
6532
// the setup phase is over, all modules have been created
6535
self._explodeRollups();
6538
oeach(r, function(v, name) {
6541
m = self.getModule(name);
6543
var expound = m.expound;
6546
r[expound] = self.getModule(expound);
6547
reqs = self.getRequires(r[expound]);
6548
Y.mix(r, YArray.hash(reqs));
6551
reqs = self.getRequires(m);
6552
Y.mix(r, YArray.hash(reqs));
6559
* Get's the loader meta data for the requested module
6561
* @param {String} mname The module name to get
6562
* @return {Object} The module metadata
6564
getModule: function(mname) {
6565
//TODO: Remove name check - it's a quick hack to fix pattern WIP
6570
var p, found, pname,
6571
m = this.moduleInfo[mname],
6572
patterns = this.patterns;
6574
// check the patterns library to see if we should automatically add
6575
// the module with defaults
6577
for (pname in patterns) {
6578
if (patterns.hasOwnProperty(pname)) {
6579
p = patterns[pname];
6581
// use the metadata supplied for the pattern
6582
// as the module definition.
6583
if (mname.indexOf(pname) > -1) {
6592
p.action.call(this, mname, pname);
6594
// ext true or false?
6595
m = this.addModule(Y.merge(found), mname);
6604
// impl in rollup submodule
6605
_rollup: function() { },
6608
* Remove superceded modules and loaded modules. Called by
6609
* calculate() after we have the mega list of all dependencies
6611
* @return {object} the reduced dependency hash.
6614
_reduce: function(r) {
6616
r = r || this.required;
6618
var i, j, s, m, type = this.loadType,
6619
ignore = this.ignore ? YArray.hash(this.ignore) : false;
6622
if (r.hasOwnProperty(i)) {
6623
m = this.getModule(i);
6624
// remove if already loaded
6625
if (((this.loaded[i] || ON_PAGE[i]) &&
6626
!this.forceMap[i] && !this.ignoreRegistered) ||
6627
(type && m && m.type != type)) {
6630
if (ignore && ignore[i]) {
6633
// remove anything this module supersedes
6634
s = m && m.supersedes;
6636
for (j = 0; j < s.length; j++) {
6648
* Handles the queue when a module has been loaded for all cases
6651
* @param {String} msg The message from Loader
6652
* @param {Boolean} success A boolean denoting success or failure
6654
_finish: function(msg, success) {
6656
_queue.running = false;
6658
var onEnd = this.onEnd;
6660
onEnd.call(this.context, {
6669
* The default Loader onSuccess handler, calls this.onSuccess with a payload
6670
* @method _onSuccess
6673
_onSuccess: function() {
6674
var self = this, skipped = Y.merge(self.skipped), fn,
6675
failed = [], rreg = self.requireRegistration,
6678
oeach(skipped, function(k) {
6679
delete self.inserted[k];
6684
oeach(self.inserted, function(v, k) {
6685
var mod = self.getModule(k);
6686
if (mod && rreg && mod.type == JS && !(k in YUI.Env.mods)) {
6689
Y.mix(self.loaded, self.getProvides(k));
6693
fn = self.onSuccess;
6694
msg = (failed.length) ? 'notregistered' : 'success';
6695
success = !(failed.length);
6697
fn.call(self.context, {
6705
self._finish(msg, success);
6708
* The default Loader onFailure handler, calls this.onFailure with a payload
6709
* @method _onFailure
6712
_onFailure: function(o) {
6713
var f = this.onFailure, msg = 'failure: ' + o.msg;
6715
f.call(this.context, {
6721
this._finish(msg, false);
6725
* The default Loader onTimeout handler, calls this.onTimeout with a payload
6726
* @method _onTimeout
6729
_onTimeout: function() {
6730
var f = this.onTimeout;
6732
f.call(this.context, {
6738
this._finish('timeout', false);
6742
* Sorts the dependency tree. The last step of calculate()
6748
// create an indexed list
6749
var s = YObject.keys(this.required),
6750
// loaded = this.loaded,
6752
p = 0, l, a, b, j, k, moved, doneKey;
6754
// keep going until we make a pass without moving anything
6760
// start the loop after items that are already sorted
6761
for (j = p; j < l; j++) {
6763
// check the next module on the list to see if its
6764
// dependencies have been met
6767
// check everything below current item and move if we
6768
// find a requirement for the current item
6769
for (k = j + 1; k < l; k++) {
6772
if (!done[doneKey] && this._requires(a, s[k])) {
6774
// extract the dependency so we can move it up
6777
// insert the dependency above the item that
6779
s.splice(j, 0, b[0]);
6781
// only swap two dependencies once to short circut
6782
// circular dependencies
6783
done[doneKey] = true;
6792
// jump out of loop if we moved something
6795
// this item is sorted, move our pointer and keep going
6801
// when we make it here and moved is false, we are
6816
partial: function(partial, o, type) {
6817
this.sorted = partial;
6818
this.insert(o, type, true);
6821
* Handles the actual insertion of script/link tags
6823
* @param {Object} source The YUI instance the request came from
6824
* @param {Object} o The metadata to include
6825
* @param {String} type JS or CSS
6826
* @param {Boolean} [skipcalc=false] Do a Loader.calculate on the meta
6828
_insert: function(source, o, type, skipcalc) {
6831
// restore the state at the time of the request
6833
this._config(source);
6836
// build the dependency list
6837
// don't include type so we can process CSS and script in
6838
// one pass when the type is not specified.
6843
this.loadType = type;
6849
this._internalCallback = function() {
6851
var f = self.onCSS, n, p, sib;
6853
// IE hack for style overrides that are not being applied
6854
if (this.insertBefore && Y.UA.ie) {
6855
n = Y.config.doc.getElementById(this.insertBefore);
6857
sib = n.nextSibling;
6860
p.insertBefore(n, sib);
6867
f.call(self.context, Y);
6869
self._internalCallback = null;
6871
self._insert(null, null, JS);
6874
this._insert(null, null, CSS);
6879
// set a flag to indicate the load has started
6880
this._loading = true;
6882
// flag to indicate we are done with the combo service
6883
// and any additional files will need to be loaded
6885
this._combineComplete = {};
6892
* Once a loader operation is completely finished, process any additional queued items.
6896
_continue: function() {
6897
if (!(_queue.running) && _queue.size() > 0) {
6898
_queue.running = true;
6904
* inserts the requested modules and their dependencies.
6905
* <code>type</code> can be "js" or "css". Both script and
6906
* css are inserted if type is not provided.
6908
* @param {object} o optional options object.
6909
* @param {string} type the type of dependency to insert.
6911
insert: function(o, type, skipsort) {
6912
var self = this, copy = Y.merge(this);
6913
delete copy.require;
6915
_queue.add(function() {
6916
self._insert(copy, o, type, skipsort);
6922
* Executed every time a module is loaded, and if we are in a load
6923
* cycle, we attempt to load the next script. Public so that it
6924
* is possible to call this if using a method other than
6925
* Y.register to determine when scripts are fully loaded
6927
* @param {string} mname optional the name of the module that has
6928
* been loaded (which is usually why it is time to load the next
6931
loadNext: function(mname) {
6932
// It is possible that this function is executed due to something
6933
// else on the page loading a YUI module. Only react when we
6934
// are actively loading something
6935
if (!this._loading) {
6939
var s, len, i, m, url, fn, msg, attr, group, groupName, j, frag,
6940
comboSource, comboSources, mods, combining, urls, comboBase,
6942
type = self.loadType,
6943
handleSuccess = function(o) {
6944
self.loadNext(o.data);
6946
handleCombo = function(o) {
6947
self._combineComplete[type] = true;
6948
var i, len = combining.length;
6950
for (i = 0; i < len; i++) {
6951
self.inserted[combining[i]] = true;
6957
if (self.combine && (!self._combineComplete[type])) {
6961
self._combining = combining;
6965
// the default combo base
6966
comboBase = self.comboBase;
6973
for (i = 0; i < len; i++) {
6974
comboSource = comboBase;
6975
m = self.getModule(s[i]);
6976
groupName = m && m.group;
6979
group = self.groups[groupName];
6981
if (!group.combine) {
6986
if (group.comboBase) {
6987
comboSource = group.comboBase;
6990
if ("root" in group && L.isValue(group.root)) {
6991
m.root = group.root;
6996
comboSources[comboSource] = comboSources[comboSource] || [];
6997
comboSources[comboSource].push(m);
7000
for (j in comboSources) {
7001
if (comboSources.hasOwnProperty(j)) {
7003
mods = comboSources[j];
7006
for (i = 0; i < len; i++) {
7007
// m = self.getModule(s[i]);
7010
// Do not try to combine non-yui JS unless combo def
7012
if (m && (m.type === type) && (m.combine || !m.ext)) {
7014
frag = ((L.isValue(m.root)) ? m.root : self.root) + m.path;
7015
frag = self._filter(frag, m.name);
7016
if ((url !== j) && (i <= (len - 1)) &&
7017
((frag.length + url.length) > self.maxURLLength)) {
7018
//Hack until this is rewritten to use an array and not string concat:
7019
if (url.substr(url.length - 1, 1) === self.comboSep) {
7020
url = url.substr(0, (url.length - 1));
7022
urls.push(self._filter(url));
7027
if (i < (len - 1)) {
7028
url += self.comboSep;
7031
combining.push(m.name);
7036
if (combining.length && (url != j)) {
7037
//Hack until this is rewritten to use an array and not string concat:
7038
if (url.substr(url.length - 1, 1) === self.comboSep) {
7039
url = url.substr(0, (url.length - 1));
7041
urls.push(self._filter(url));
7046
if (combining.length) {
7049
// if (m.type === CSS) {
7052
attr = self.cssAttributes;
7055
attr = self.jsAttributes;
7059
data: self._loading,
7060
onSuccess: handleCombo,
7061
onFailure: self._onFailure,
7062
onTimeout: self._onTimeout,
7063
insertBefore: self.insertBefore,
7064
charset: self.charset,
7066
timeout: self.timeout,
7074
self._combineComplete[type] = true;
7080
// if the module that was just loaded isn't what we were expecting,
7082
if (mname !== self._loading) {
7087
// The global handler that is called when each module is loaded
7088
// will pass that module name to this function. Storing this
7089
// data to avoid loading the same module multiple times
7090
// centralize this in the callback
7091
self.inserted[mname] = true;
7092
// self.loaded[mname] = true;
7094
// provided = self.getProvides(mname);
7095
// Y.mix(self.loaded, provided);
7096
// Y.mix(self.inserted, provided);
7098
if (self.onProgress) {
7099
self.onProgress.call(self.context, {
7109
for (i = 0; i < len; i = i + 1) {
7110
// this.inserted keeps track of what the loader has loaded.
7111
// move on if this item is done.
7112
if (s[i] in self.inserted) {
7116
// Because rollups will cause multiple load notifications
7117
// from Y, loadNext may be called multiple times for
7118
// the same module when loading a rollup. We can safely
7119
// skip the subsequent requests
7120
if (s[i] === self._loading) {
7124
// log("inserting " + s[i]);
7125
m = self.getModule(s[i]);
7128
if (!self.skipped[s[i]]) {
7129
msg = 'Undefined module ' + s[i] + ' skipped';
7130
// self.inserted[s[i]] = true;
7131
self.skipped[s[i]] = true;
7137
group = (m.group && self.groups[m.group]) || NOT_FOUND;
7139
// The load type is stored to offer the possibility to load
7140
// the css separately from the script.
7141
if (!type || type === m.type) {
7142
self._loading = s[i];
7144
if (m.type === CSS) {
7146
attr = self.cssAttributes;
7149
attr = self.jsAttributes;
7152
url = (m.fullpath) ? self._filter(m.fullpath, s[i]) :
7153
self._url(m.path, s[i], group.base || m.base);
7157
onSuccess: handleSuccess,
7158
insertBefore: self.insertBefore,
7159
charset: self.charset,
7161
onFailure: self._onFailure,
7162
onTimeout: self._onTimeout,
7163
timeout: self.timeout,
7173
self._loading = null;
7175
fn = self._internalCallback;
7177
// internal callback for loading css first
7179
self._internalCallback = null;
7187
* Apply filter defined for this instance to a url/path
7189
* @param {string} u the string to filter.
7190
* @param {string} name the name of the module, if we are processing
7191
* a single module as opposed to a combined url.
7192
* @return {string} the filtered string.
7195
_filter: function(u, name) {
7196
var f = this.filter,
7197
hasFilter = name && (name in this.filters),
7198
modFilter = hasFilter && this.filters[name],
7199
groupName = this.moduleInfo[name] ? this.moduleInfo[name].group:null;
7200
if (groupName && this.groups[groupName].filter) {
7201
modFilter = this.groups[groupName].filter;
7207
f = (L.isString(modFilter)) ?
7208
this.FILTER_DEFS[modFilter.toUpperCase()] || null :
7212
u = u.replace(new RegExp(f.searchExp, 'g'), f.replaceStr);
7220
* Generates the full url for a module
7222
* @param {string} path the path fragment.
7223
* @param {String} name The name of the module
7224
* @pamra {String} [base=self.base] The base url to use
7225
* @return {string} the full url.
7228
_url: function(path, name, base) {
7229
return this._filter((base || this.base || '') + path, name);
7232
* Returns an Object hash of file arrays built from `loader.sorted` or from an arbitrary list of sorted modules.
7234
* @param {Boolean} [calc=false] Perform a loader.calculate() before anything else
7235
* @param {Array} [s=loader.sorted] An override for the loader.sorted array
7236
* @return {Object} Object hash (js and css) of two arrays of file lists
7237
* @example This method can be used as an off-line dep calculator
7240
* var loader = new Y.Loader({
7245
* require: ['node', 'dd', 'console']
7247
* var out = loader.resolve(true);
7250
resolve: function(calc, s) {
7251
var self = this, i, m, url, out = { js: [], css: [] };
7256
s = s || self.sorted;
7258
for (i = 0; i < s.length; i++) {
7259
m = self.getModule(s[i]);
7262
url = self._filter((self.root + m.path), m.name, self.root);
7264
url = self._filter(m.fullpath, m.name, '') || self._url(m.path, m.name);
7266
out[m.type].push(url);
7270
out.js = [self.comboBase + out.js.join(self.comboSep)];
7271
out.css = [self.comboBase + out.css.join(self.comboSep)];
7277
* Returns an Object hash of hashes built from `loader.sorted` or from an arbitrary list of sorted modules.
7280
* @param {Boolean} [calc=false] Perform a loader.calculate() before anything else
7281
* @param {Array} [s=loader.sorted] An override for the loader.sorted array
7282
* @return {Object} Object hash (js and css) of two object hashes of file lists, with the module name as the key
7283
* @example This method can be used as an off-line dep calculator
7286
* var loader = new Y.Loader({
7291
* require: ['node', 'dd', 'console']
7293
* var out = loader.hash(true);
7296
hash: function(calc, s) {
7297
var self = this, i, m, url, out = { js: {}, css: {} };
7302
s = s || self.sorted;
7304
for (i = 0; i < s.length; i++) {
7305
m = self.getModule(s[i]);
7307
url = self._filter(m.fullpath, m.name, '') || self._url(m.path, m.name);
7308
out[m.type][m.name] = url;
7318
}, '3.4.1' ,{requires:['get']});
7319
YUI.add('loader-rollup', function(Y) {
7322
* Optional automatic rollup logic for reducing http connections
7323
* when not using a combo service.
7329
* Look for rollup packages to determine if all of the modules a
7330
* rollup supersedes are required. If so, include the rollup to
7331
* help reduce the total number of connections required. Called
7332
* by calculate(). This is an optional feature, and requires the
7333
* appropriate submodule to function.
7338
Y.Loader.prototype._rollup = function() {
7339
var i, j, m, s, r = this.required, roll,
7340
info = this.moduleInfo, rolled, c, smod;
7342
// find and cache rollup modules
7343
if (this.dirty || !this.rollups) {
7346
if (info.hasOwnProperty(i)) {
7347
m = this.getModule(i);
7348
// if (m && m.rollup && m.supersedes) {
7349
if (m && m.rollup) {
7350
this.rollups[i] = m;
7355
this.forceMap = (this.force) ? Y.Array.hash(this.force) : {};
7358
// make as many passes as needed to pick up rollup rollups
7362
// go through the rollup candidates
7363
for (i in this.rollups) {
7364
if (this.rollups.hasOwnProperty(i)) {
7365
// there can be only one, unless forced
7366
if (!r[i] && ((!this.loaded[i]) || this.forceMap[i])) {
7367
m = this.getModule(i);
7368
s = m.supersedes || [];
7371
// @TODO remove continue
7378
// check the threshold
7379
for (j = 0; j < s.length; j++) {
7382
// if the superseded module is loaded, we can't
7383
// load the rollup unless it has been forced.
7384
if (this.loaded[s[j]] && !this.forceMap[s[j]]) {
7387
// increment the counter if this module is required.
7388
// if we are beyond the rollup threshold, we will
7389
// use the rollup module
7390
} else if (r[s[j]] && m.type == smod.type) {
7392
roll = (c >= m.rollup);
7404
// expand the rollup's dependencies
7405
this.getRequires(m);
7411
// if we made it here w/o rolling up something, we are done
7419
}, '3.4.1' ,{requires:['loader-base']});
7420
YUI.add('loader-yui3', function(Y) {
7422
/* This file is auto-generated by src/loader/scripts/meta_join.py */
7425
* YUI 3 module metadata
7429
YUI.Env[Y.version].modules = YUI.Env[Y.version].modules || {
7468
"anim-node-plugin": {
7513
"arraylist-filter": {
7539
"attribute-complex": {
7546
"autocomplete-base",
7547
"autocomplete-sources",
7548
"autocomplete-list",
7549
"autocomplete-plugin"
7552
"autocomplete-base": {
7554
"autocomplete-sources"
7560
"event-valuechange",
7564
"autocomplete-filters": {
7570
"autocomplete-filters-accentfold": {
7577
"autocomplete-highlighters": {
7583
"autocomplete-highlighters-accentfold": {
7586
"highlight-accentfold"
7589
"autocomplete-list": {
7591
"autocomplete-sources"
7597
"autocomplete-base",
7604
"widget-position-align"
7608
"autocomplete-list-keys": {
7610
"name": "autocomplete-list-keys",
7611
"test": function (Y) {
7612
// Only add keyboard support to autocomplete-list if this doesn't appear to
7613
// be an iOS or Android-based mobile device.
7615
// There's currently no feasible way to actually detect whether a device has
7616
// a hardware keyboard, so this sniff will have to do. It can easily be
7617
// overridden by manually loading the autocomplete-list-keys module.
7619
// Worth noting: even though iOS supports bluetooth keyboards, Mobile Safari
7620
// doesn't fire the keyboard events used by AutoCompleteList, so there's
7621
// no point loading the -keys module even when a bluetooth keyboard may be
7623
return !(Y.UA.ios || Y.UA.android);
7625
"trigger": "autocomplete-list"
7628
"autocomplete-list",
7632
"autocomplete-plugin": {
7634
"autocomplete-list",
7638
"autocomplete-sources": {
7669
"base-pluginhost": {
7721
"datatype-date-math",
7726
"calendarnavigator": {
7749
"classnamemanager": {
7781
"console-filters": {
7803
"createlink-base": {
7819
"cssbase-context": {
7833
"cssfonts-context": {
7846
"cssreset-context": {
7858
"dataschema-array": {
7863
"dataschema-base": {
7868
"dataschema-json": {
7874
"dataschema-text": {
7889
"datasource-function",
7891
"datasource-jsonschema",
7892
"datasource-xmlschema",
7893
"datasource-arrayschema",
7894
"datasource-textschema",
7895
"datasource-polling"
7898
"datasource-arrayschema": {
7905
"datasource-cache": {
7912
"datasource-function": {
7929
"datasource-jsonschema": {
7936
"datasource-local": {
7941
"datasource-polling": {
7946
"datasource-textschema": {
7953
"datasource-xmlschema": {
7963
"datatable-datasource",
7977
"datatable-datasource": {
7984
"datatable-scroll": {
8009
"datatype-date-format"
8012
"datatype-date-parse",
8013
"datatype-date-format"
8016
"datatype-date-format": {
8100
"datatype-date-math": {
8105
"datatype-date-parse": {},
8106
"datatype-number": {
8108
"datatype-number-parse",
8109
"datatype-number-format"
8112
"datatype-number-format": {},
8113
"datatype-number-parse": {},
8116
"datatype-xml-parse",
8117
"datatype-xml-format"
8120
"datatype-xml-format": {},
8121
"datatype-xml-parse": {},
8184
"name": "dd-gestures",
8185
"test": function(Y) {
8186
return (Y.config.win && ('ontouchstart' in Y.config.win && !Y.UA.chrome));
8188
"trigger": "dd-drag"
8270
"name": "dom-style-ie",
8271
"test": function (Y) {
8273
var testFeature = Y.Features.test,
8274
addFeature = Y.Features.add,
8275
WINDOW = Y.config.win,
8276
DOCUMENT = Y.config.doc,
8277
DOCUMENT_ELEMENT = 'documentElement',
8280
addFeature('style', 'computedStyle', {
8282
return WINDOW && 'getComputedStyle' in WINDOW;
8286
addFeature('style', 'opacity', {
8288
return DOCUMENT && 'opacity' in DOCUMENT[DOCUMENT_ELEMENT].style;
8292
ret = (!testFeature('style', 'opacity') &&
8293
!testFeature('style', 'computedStyle'));
8297
"trigger": "dom-style"
8390
"name": "event-base-ie",
8391
"test": function(Y) {
8392
var imp = Y.config.doc && Y.config.doc.implementation;
8393
return (imp && (!imp.hasFeature('Events', '2.0')));
8395
"trigger": "node-base"
8403
"event-custom-base",
8404
"event-custom-complex"
8407
"event-custom-base": {
8412
"event-custom-complex": {
8450
"event-mouseenter": {
8455
"event-mousewheel": {
8483
"event-synthetic": {
8486
"event-custom-complex"
8494
"event-valuechange": {
8531
"graphics-canvas": {
8533
"name": "graphics-canvas",
8534
"test": function(Y) {
8535
var DOCUMENT = Y.config.doc,
8536
canvas = DOCUMENT && DOCUMENT.createElement("canvas");
8537
return (DOCUMENT && !DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1") && (canvas && canvas.getContext && canvas.getContext("2d")));
8539
"trigger": "graphics"
8545
"graphics-canvas-default": {
8547
"name": "graphics-canvas-default",
8548
"test": function(Y) {
8549
var DOCUMENT = Y.config.doc,
8550
canvas = DOCUMENT && DOCUMENT.createElement("canvas");
8551
return (DOCUMENT && !DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1") && (canvas && canvas.getContext && canvas.getContext("2d")));
8553
"trigger": "graphics"
8558
"name": "graphics-svg",
8559
"test": function(Y) {
8560
var DOCUMENT = Y.config.doc;
8561
return (DOCUMENT && DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1"));
8563
"trigger": "graphics"
8569
"graphics-svg-default": {
8571
"name": "graphics-svg-default",
8572
"test": function(Y) {
8573
var DOCUMENT = Y.config.doc;
8574
return (DOCUMENT && DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1"));
8576
"trigger": "graphics"
8581
"name": "graphics-vml",
8582
"test": function(Y) {
8583
var DOCUMENT = Y.config.doc,
8584
canvas = DOCUMENT && DOCUMENT.createElement("canvas");
8585
return (DOCUMENT && !DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1") && (!canvas || !canvas.getContext || !canvas.getContext("2d")));
8587
"trigger": "graphics"
8593
"graphics-vml-default": {
8595
"name": "graphics-vml-default",
8596
"test": function(Y) {
8597
var DOCUMENT = Y.config.doc,
8598
canvas = DOCUMENT && DOCUMENT.createElement("canvas");
8599
return (DOCUMENT && !DOCUMENT.implementation.hasFeature("http://www.w3.org/TR/SVG11/feature#BasicStructure", "1.1") && (!canvas || !canvas.getContext || !canvas.getContext("2d")));
8601
"trigger": "graphics"
8607
"highlight-accentfold"
8610
"highlight-accentfold": {
8634
"event-custom-complex"
8647
"history-hash-ie": {
8649
"name": "history-hash-ie",
8650
"test": function (Y) {
8651
var docMode = Y.config.doc && Y.config.doc.documentMode;
8653
return Y.UA.ie && (!('onhashchange' in Y.config.win) ||
8654
!docMode || docMode < 8);
8656
"trigger": "history-hash"
8702
"event-custom-base",
8703
"querystring-stringify-simple"
8718
"io-upload-iframe": {
8727
"datatype-xml-parse"
8800
"node-event-delegate",
8819
"node-deprecated": {
8824
"node-event-delegate": {
8830
"node-event-html5": {
8835
"node-event-simulate": {
8850
"node-focusmanager": {
8855
"node-event-simulate",
8875
"node-pluginhost": {
8903
"widget-position-align",
8905
"widget-position-constrain"
8914
"widget-position-align",
8916
"widget-position-constrain",
8934
"pluginhost-base": {
8939
"pluginhost-config": {
8951
"querystring-parse",
8952
"querystring-stringify"
8955
"querystring-parse": {
8961
"querystring-parse-simple": {
8966
"querystring-stringify": {
8971
"querystring-stringify-simple": {
8984
"slider-value-range",
9002
"recordset-filter": {
9009
"recordset-indexer": {
9042
"resize-constrain": {
9072
"scrollview-scrollbars"
9075
"scrollview-base": {
9083
"scrollview-base-ie": {
9085
"name": "scrollview-base-ie",
9086
"trigger": "scrollview-base",
9093
"scrollview-list": {
9100
"scrollview-paginator": {
9105
"scrollview-scrollbars": {
9125
"name": "selector-css2",
9126
"test": function (Y) {
9127
var DOCUMENT = Y.config.doc,
9128
ret = DOCUMENT && !('querySelectorAll' in DOCUMENT);
9132
"trigger": "selector"
9144
"selector-native": {
9158
"slider-value-range",
9171
"slider-value-range": {
9183
"sortable-scroll": {
9228
"node-event-delegate",
9253
"text-accentfold": {
9256
"text-data-accentfold"
9259
"text-data-accentfold": {
9264
"text-data-wordbreak": {
9272
"text-data-wordbreak"
9280
"transition-timer": {
9282
"name": "transition-timer",
9283
"test": function (Y) {
9284
var DOCUMENT = Y.config.doc,
9285
node = (DOCUMENT) ? DOCUMENT.documentElement: null,
9288
if (node && node.style) {
9289
ret = !('MozTransition' in node.style || 'WebkitTransition' in node.style);
9294
"trigger": "transition"
9311
"node-event-delegate"
9317
"widget-htmlparser",
9329
"widget-autohide": {
9352
"name": "widget-base-ie",
9353
"trigger": "widget-base",
9374
"widget-htmlparser": {
9384
"widget-modality": {
9399
"widget-position": {
9406
"widget-position-align": {
9411
"widget-position-constrain": {
9434
"widget-uievents": {
9437
"node-event-delegate"
9465
YUI.Env[Y.version].md5 = '105ebffae27a0e3d7331f8cf5c0bb282';
9468
}, '3.4.1' ,{requires:['loader-base']});
9471
YUI.add('yui', function(Y){}, '3.4.1' ,{use:['yui-base','get','features','intl-base','yui-log','yui-later','loader-base', 'loader-rollup', 'loader-yui3' ]});