angularjs-rails 1.4.4 → 1.4.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/angularjs-rails/version.rb +2 -2
- data/vendor/assets/javascripts/angular-animate.js +266 -123
- data/vendor/assets/javascripts/angular-aria.js +40 -36
- data/vendor/assets/javascripts/angular-cookies.js +2 -2
- data/vendor/assets/javascripts/angular-loader.js +2 -2
- data/vendor/assets/javascripts/angular-message-format.js +1 -1
- data/vendor/assets/javascripts/angular-messages.js +9 -2
- data/vendor/assets/javascripts/angular-mocks.js +62 -25
- data/vendor/assets/javascripts/angular-resource.js +10 -4
- data/vendor/assets/javascripts/angular-route.js +1 -2
- data/vendor/assets/javascripts/angular-sanitize.js +1 -1
- data/vendor/assets/javascripts/angular-scenario.js +625 -325
- data/vendor/assets/javascripts/angular-touch.js +1 -1
- data/vendor/assets/javascripts/angular.js +624 -324
- data/vendor/assets/javascripts/unstable/angular2.js +13370 -14106
- metadata +2 -2
@@ -9190,7 +9190,7 @@ return jQuery;
|
|
9190
9190
|
}));
|
9191
9191
|
|
9192
9192
|
/**
|
9193
|
-
* @license AngularJS v1.4.
|
9193
|
+
* @license AngularJS v1.4.7
|
9194
9194
|
* (c) 2010-2015 Google, Inc. http://angularjs.org
|
9195
9195
|
* License: MIT
|
9196
9196
|
*/
|
@@ -9249,7 +9249,7 @@ function minErr(module, ErrorConstructor) {
|
|
9249
9249
|
return match;
|
9250
9250
|
});
|
9251
9251
|
|
9252
|
-
message += '\nhttp://errors.angularjs.org/1.4.
|
9252
|
+
message += '\nhttp://errors.angularjs.org/1.4.7/' +
|
9253
9253
|
(module ? module + '/' : '') + code;
|
9254
9254
|
|
9255
9255
|
for (i = SKIP_INDEXES, paramPrefix = '?'; i < templateArgs.length; i++, paramPrefix = '&') {
|
@@ -10086,6 +10086,8 @@ function copy(source, destination, stackSource, stackDest) {
|
|
10086
10086
|
} else if (isRegExp(source)) {
|
10087
10087
|
destination = new RegExp(source.source, source.toString().match(/[^\/]*$/)[0]);
|
10088
10088
|
destination.lastIndex = source.lastIndex;
|
10089
|
+
} else if (isFunction(source.cloneNode)) {
|
10090
|
+
destination = source.cloneNode(true);
|
10089
10091
|
} else {
|
10090
10092
|
var emptyObject = Object.create(getPrototypeOf(source));
|
10091
10093
|
return copy(source, emptyObject, stackSource, stackDest);
|
@@ -10236,7 +10238,7 @@ function equals(o1, o2) {
|
|
10236
10238
|
for (key in o2) {
|
10237
10239
|
if (!(key in keySet) &&
|
10238
10240
|
key.charAt(0) !== '$' &&
|
10239
|
-
o2[key]
|
10241
|
+
isDefined(o2[key]) &&
|
10240
10242
|
!isFunction(o2[key])) return false;
|
10241
10243
|
}
|
10242
10244
|
return true;
|
@@ -10932,10 +10934,9 @@ function bindJQuery() {
|
|
10932
10934
|
|
10933
10935
|
// bind to jQuery if present;
|
10934
10936
|
var jqName = jq();
|
10935
|
-
jQuery = window.jQuery
|
10936
|
-
|
10937
|
-
|
10938
|
-
}
|
10937
|
+
jQuery = isUndefined(jqName) ? window.jQuery : // use jQuery (if present)
|
10938
|
+
!jqName ? undefined : // use jqLite
|
10939
|
+
window[jqName]; // use jQuery specified by `ngJq`
|
10939
10940
|
|
10940
10941
|
// Use jQuery if it exists with proper functionality, otherwise default to us.
|
10941
10942
|
// Angular 1.2+ requires jQuery 1.7+ for on()/off() support.
|
@@ -11040,22 +11041,24 @@ function getter(obj, path, bindFnToScope) {
|
|
11040
11041
|
/**
|
11041
11042
|
* Return the DOM siblings between the first and last node in the given array.
|
11042
11043
|
* @param {Array} array like object
|
11043
|
-
* @returns {
|
11044
|
+
* @returns {Array} the inputted object or a jqLite collection containing the nodes
|
11044
11045
|
*/
|
11045
11046
|
function getBlockNodes(nodes) {
|
11046
|
-
// TODO(perf):
|
11047
|
-
// collection, otherwise update the original collection.
|
11047
|
+
// TODO(perf): update `nodes` instead of creating a new object?
|
11048
11048
|
var node = nodes[0];
|
11049
11049
|
var endNode = nodes[nodes.length - 1];
|
11050
|
-
var blockNodes
|
11050
|
+
var blockNodes;
|
11051
11051
|
|
11052
|
-
|
11053
|
-
|
11054
|
-
|
11055
|
-
|
11056
|
-
|
11052
|
+
for (var i = 1; node !== endNode && (node = node.nextSibling); i++) {
|
11053
|
+
if (blockNodes || nodes[i] !== node) {
|
11054
|
+
if (!blockNodes) {
|
11055
|
+
blockNodes = jqLite(slice.call(nodes, 0, i));
|
11056
|
+
}
|
11057
|
+
blockNodes.push(node);
|
11058
|
+
}
|
11059
|
+
}
|
11057
11060
|
|
11058
|
-
return
|
11061
|
+
return blockNodes || nodes;
|
11059
11062
|
}
|
11060
11063
|
|
11061
11064
|
|
@@ -11439,7 +11442,7 @@ function serializeObject(obj) {
|
|
11439
11442
|
val = toJsonReplacer(key, val);
|
11440
11443
|
if (isObject(val)) {
|
11441
11444
|
|
11442
|
-
if (seen.indexOf(val) >= 0) return '
|
11445
|
+
if (seen.indexOf(val) >= 0) return '...';
|
11443
11446
|
|
11444
11447
|
seen.push(val);
|
11445
11448
|
}
|
@@ -11450,7 +11453,7 @@ function serializeObject(obj) {
|
|
11450
11453
|
function toDebugString(obj) {
|
11451
11454
|
if (typeof obj === 'function') {
|
11452
11455
|
return obj.toString().replace(/ \{[\s\S]*$/, '');
|
11453
|
-
} else if (
|
11456
|
+
} else if (isUndefined(obj)) {
|
11454
11457
|
return 'undefined';
|
11455
11458
|
} else if (typeof obj !== 'string') {
|
11456
11459
|
return serializeObject(obj);
|
@@ -11530,6 +11533,7 @@ function toDebugString(obj) {
|
|
11530
11533
|
$HttpParamSerializerProvider,
|
11531
11534
|
$HttpParamSerializerJQLikeProvider,
|
11532
11535
|
$HttpBackendProvider,
|
11536
|
+
$xhrFactoryProvider,
|
11533
11537
|
$LocationProvider,
|
11534
11538
|
$LogProvider,
|
11535
11539
|
$ParseProvider,
|
@@ -11556,8 +11560,9 @@ function toDebugString(obj) {
|
|
11556
11560
|
* @name angular.version
|
11557
11561
|
* @module ng
|
11558
11562
|
* @description
|
11559
|
-
* An object that contains information about the current AngularJS version.
|
11560
|
-
*
|
11563
|
+
* An object that contains information about the current AngularJS version.
|
11564
|
+
*
|
11565
|
+
* This object has the following properties:
|
11561
11566
|
*
|
11562
11567
|
* - `full` – `{string}` – Full version string, such as "0.9.18".
|
11563
11568
|
* - `major` – `{number}` – Major version number, such as "0".
|
@@ -11566,11 +11571,11 @@ function toDebugString(obj) {
|
|
11566
11571
|
* - `codeName` – `{string}` – Code name of the release, such as "jiggling-armfat".
|
11567
11572
|
*/
|
11568
11573
|
var version = {
|
11569
|
-
full: '1.4.
|
11574
|
+
full: '1.4.7', // all of these placeholder strings will be replaced by grunt's
|
11570
11575
|
major: 1, // package task
|
11571
11576
|
minor: 4,
|
11572
|
-
dot:
|
11573
|
-
codeName: '
|
11577
|
+
dot: 7,
|
11578
|
+
codeName: 'dark-luminescence'
|
11574
11579
|
};
|
11575
11580
|
|
11576
11581
|
|
@@ -11687,6 +11692,7 @@ function publishExternalAPI(angular) {
|
|
11687
11692
|
$httpParamSerializer: $HttpParamSerializerProvider,
|
11688
11693
|
$httpParamSerializerJQLike: $HttpParamSerializerJQLikeProvider,
|
11689
11694
|
$httpBackend: $HttpBackendProvider,
|
11695
|
+
$xhrFactory: $xhrFactoryProvider,
|
11690
11696
|
$location: $LocationProvider,
|
11691
11697
|
$log: $LogProvider,
|
11692
11698
|
$parse: $ParseProvider,
|
@@ -11775,7 +11781,7 @@ function publishExternalAPI(angular) {
|
|
11775
11781
|
* - [`html()`](http://api.jquery.com/html/)
|
11776
11782
|
* - [`next()`](http://api.jquery.com/next/) - Does not support selectors
|
11777
11783
|
* - [`on()`](http://api.jquery.com/on/) - Does not support namespaces, selectors or eventData
|
11778
|
-
* - [`off()`](http://api.jquery.com/off/) - Does not support namespaces or
|
11784
|
+
* - [`off()`](http://api.jquery.com/off/) - Does not support namespaces, selectors or event object as parameter
|
11779
11785
|
* - [`one()`](http://api.jquery.com/one/) - Does not support namespaces or selectors
|
11780
11786
|
* - [`parent()`](http://api.jquery.com/parent/) - Does not support selectors
|
11781
11787
|
* - [`prepend()`](http://api.jquery.com/prepend/)
|
@@ -11789,7 +11795,7 @@ function publishExternalAPI(angular) {
|
|
11789
11795
|
* - [`text()`](http://api.jquery.com/text/)
|
11790
11796
|
* - [`toggleClass()`](http://api.jquery.com/toggleClass/)
|
11791
11797
|
* - [`triggerHandler()`](http://api.jquery.com/triggerHandler/) - Passes a dummy event object to handlers.
|
11792
|
-
* - [`unbind()`](http://api.jquery.com/unbind/) - Does not support namespaces
|
11798
|
+
* - [`unbind()`](http://api.jquery.com/unbind/) - Does not support namespaces or event object as parameter
|
11793
11799
|
* - [`val()`](http://api.jquery.com/val/)
|
11794
11800
|
* - [`wrap()`](http://api.jquery.com/wrap/)
|
11795
11801
|
*
|
@@ -11861,10 +11867,10 @@ function camelCase(name) {
|
|
11861
11867
|
replace(MOZ_HACK_REGEXP, 'Moz$1');
|
11862
11868
|
}
|
11863
11869
|
|
11864
|
-
var SINGLE_TAG_REGEXP = /^<(\w+)\s*\/?>(?:<\/\1>|)$/;
|
11870
|
+
var SINGLE_TAG_REGEXP = /^<([\w-]+)\s*\/?>(?:<\/\1>|)$/;
|
11865
11871
|
var HTML_REGEXP = /<|&#?\w+;/;
|
11866
|
-
var TAG_NAME_REGEXP = /<([\w
|
11867
|
-
var XHTML_TAG_REGEXP = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w
|
11872
|
+
var TAG_NAME_REGEXP = /<([\w:-]+)/;
|
11873
|
+
var XHTML_TAG_REGEXP = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:-]+)[^>]*)\/>/gi;
|
11868
11874
|
|
11869
11875
|
var wrapMap = {
|
11870
11876
|
'option': [1, '<select multiple="multiple">', '</select>'],
|
@@ -12160,7 +12166,7 @@ function jqLiteInheritedData(element, name, value) {
|
|
12160
12166
|
|
12161
12167
|
while (element) {
|
12162
12168
|
for (var i = 0, ii = names.length; i < ii; i++) {
|
12163
|
-
if ((value = jqLite.data(element, names[i]))
|
12169
|
+
if (isDefined(value = jqLite.data(element, names[i]))) return value;
|
12164
12170
|
}
|
12165
12171
|
|
12166
12172
|
// If dealing with a document fragment node with a host element, and no parent, use the host
|
@@ -12266,9 +12272,8 @@ function getBooleanAttrName(element, name) {
|
|
12266
12272
|
return booleanAttr && BOOLEAN_ELEMENTS[nodeName_(element)] && booleanAttr;
|
12267
12273
|
}
|
12268
12274
|
|
12269
|
-
function getAliasedAttrName(
|
12270
|
-
|
12271
|
-
return (nodeName === 'INPUT' || nodeName === 'TEXTAREA') && ALIASED_ATTR[name];
|
12275
|
+
function getAliasedAttrName(name) {
|
12276
|
+
return ALIASED_ATTR[name];
|
12272
12277
|
}
|
12273
12278
|
|
12274
12279
|
forEach({
|
@@ -12405,7 +12410,7 @@ forEach({
|
|
12405
12410
|
// in a way that survives minification.
|
12406
12411
|
// jqLiteEmpty takes no arguments but is a setter.
|
12407
12412
|
if (fn !== jqLiteEmpty &&
|
12408
|
-
(((fn.length == 2 && (fn !== jqLiteHasClass && fn !== jqLiteController)) ? arg1 : arg2)
|
12413
|
+
(isUndefined((fn.length == 2 && (fn !== jqLiteHasClass && fn !== jqLiteController)) ? arg1 : arg2))) {
|
12409
12414
|
if (isObject(arg1)) {
|
12410
12415
|
|
12411
12416
|
// we are a write, but the object properties are the key/values
|
@@ -12426,7 +12431,7 @@ forEach({
|
|
12426
12431
|
// TODO: do we still need this?
|
12427
12432
|
var value = fn.$dv;
|
12428
12433
|
// Only if we have $dv do we iterate over all, otherwise it is just the first element.
|
12429
|
-
var jj = (value
|
12434
|
+
var jj = (isUndefined(value)) ? Math.min(nodeCount, 1) : nodeCount;
|
12430
12435
|
for (var j = 0; j < jj; j++) {
|
12431
12436
|
var nodeValue = fn(this[j], arg1, arg2);
|
12432
12437
|
value = value ? value + nodeValue : nodeValue;
|
@@ -14065,61 +14070,66 @@ var $$CoreAnimateQueueProvider = function() {
|
|
14065
14070
|
}
|
14066
14071
|
};
|
14067
14072
|
|
14068
|
-
function addRemoveClassesPostDigest(element, add, remove) {
|
14069
|
-
var classVal, data = postDigestQueue.get(element);
|
14070
14073
|
|
14071
|
-
|
14072
|
-
|
14073
|
-
|
14074
|
+
function updateData(data, classes, value) {
|
14075
|
+
var changed = false;
|
14076
|
+
if (classes) {
|
14077
|
+
classes = isString(classes) ? classes.split(' ') :
|
14078
|
+
isArray(classes) ? classes : [];
|
14079
|
+
forEach(classes, function(className) {
|
14080
|
+
if (className) {
|
14081
|
+
changed = true;
|
14082
|
+
data[className] = value;
|
14083
|
+
}
|
14084
|
+
});
|
14074
14085
|
}
|
14075
|
-
|
14076
|
-
|
14077
|
-
|
14078
|
-
|
14079
|
-
|
14080
|
-
|
14081
|
-
|
14082
|
-
|
14083
|
-
|
14084
|
-
|
14086
|
+
return changed;
|
14087
|
+
}
|
14088
|
+
|
14089
|
+
function handleCSSClassChanges() {
|
14090
|
+
forEach(postDigestElements, function(element) {
|
14091
|
+
var data = postDigestQueue.get(element);
|
14092
|
+
if (data) {
|
14093
|
+
var existing = splitClasses(element.attr('class'));
|
14094
|
+
var toAdd = '';
|
14095
|
+
var toRemove = '';
|
14096
|
+
forEach(data, function(status, className) {
|
14097
|
+
var hasClass = !!existing[className];
|
14098
|
+
if (status !== hasClass) {
|
14099
|
+
if (status) {
|
14100
|
+
toAdd += (toAdd.length ? ' ' : '') + className;
|
14101
|
+
} else {
|
14102
|
+
toRemove += (toRemove.length ? ' ' : '') + className;
|
14103
|
+
}
|
14085
14104
|
}
|
14086
14105
|
});
|
14106
|
+
|
14107
|
+
forEach(element, function(elm) {
|
14108
|
+
toAdd && jqLiteAddClass(elm, toAdd);
|
14109
|
+
toRemove && jqLiteRemoveClass(elm, toRemove);
|
14110
|
+
});
|
14111
|
+
postDigestQueue.remove(element);
|
14087
14112
|
}
|
14088
|
-
|
14089
|
-
|
14113
|
+
});
|
14114
|
+
postDigestElements.length = 0;
|
14115
|
+
}
|
14090
14116
|
|
14091
|
-
var classesAdded = updateData(add, true);
|
14092
|
-
var classesRemoved = updateData(remove, false);
|
14093
|
-
if ((!classesAdded && !classesRemoved) || postDigestElements.length > 1) return;
|
14094
|
-
|
14095
|
-
$rootScope.$$postDigest(function() {
|
14096
|
-
forEach(postDigestElements, function(element) {
|
14097
|
-
var data = postDigestQueue.get(element);
|
14098
|
-
if (data) {
|
14099
|
-
var existing = splitClasses(element.attr('class'));
|
14100
|
-
var toAdd = '';
|
14101
|
-
var toRemove = '';
|
14102
|
-
forEach(data, function(status, className) {
|
14103
|
-
var hasClass = !!existing[className];
|
14104
|
-
if (status !== hasClass) {
|
14105
|
-
if (status) {
|
14106
|
-
toAdd += (toAdd.length ? ' ' : '') + className;
|
14107
|
-
} else {
|
14108
|
-
toRemove += (toRemove.length ? ' ' : '') + className;
|
14109
|
-
}
|
14110
|
-
}
|
14111
|
-
});
|
14112
14117
|
|
14113
|
-
|
14114
|
-
|
14115
|
-
toRemove && jqLiteRemoveClass(elm, toRemove);
|
14116
|
-
});
|
14117
|
-
postDigestQueue.remove(element);
|
14118
|
-
}
|
14119
|
-
});
|
14118
|
+
function addRemoveClassesPostDigest(element, add, remove) {
|
14119
|
+
var data = postDigestQueue.get(element) || {};
|
14120
14120
|
|
14121
|
-
|
14122
|
-
|
14121
|
+
var classesAdded = updateData(data, add, true);
|
14122
|
+
var classesRemoved = updateData(data, remove, false);
|
14123
|
+
|
14124
|
+
if (classesAdded || classesRemoved) {
|
14125
|
+
|
14126
|
+
postDigestQueue.put(element, data);
|
14127
|
+
postDigestElements.push(element);
|
14128
|
+
|
14129
|
+
if (postDigestElements.length === 1) {
|
14130
|
+
$rootScope.$$postDigest(handleCSSClassChanges);
|
14131
|
+
}
|
14132
|
+
}
|
14123
14133
|
}
|
14124
14134
|
}];
|
14125
14135
|
};
|
@@ -14584,14 +14594,21 @@ var $CoreAnimateCssProvider = function() {
|
|
14584
14594
|
return this.getPromise().then(f1,f2);
|
14585
14595
|
},
|
14586
14596
|
'catch': function(f1) {
|
14587
|
-
return this.getPromise()
|
14597
|
+
return this.getPromise()['catch'](f1);
|
14588
14598
|
},
|
14589
14599
|
'finally': function(f1) {
|
14590
|
-
return this.getPromise()
|
14600
|
+
return this.getPromise()['finally'](f1);
|
14591
14601
|
}
|
14592
14602
|
};
|
14593
14603
|
|
14594
14604
|
return function(element, options) {
|
14605
|
+
// there is no point in applying the styles since
|
14606
|
+
// there is no animation that goes on at all in
|
14607
|
+
// this version of $animateCss.
|
14608
|
+
if (options.cleanupStyles) {
|
14609
|
+
options.from = options.to = null;
|
14610
|
+
}
|
14611
|
+
|
14595
14612
|
if (options.from) {
|
14596
14613
|
element.css(options.from);
|
14597
14614
|
options.from = null;
|
@@ -14720,7 +14737,7 @@ function Browser(window, document, $log, $sniffer) {
|
|
14720
14737
|
var cachedState, lastHistoryState,
|
14721
14738
|
lastBrowserUrl = location.href,
|
14722
14739
|
baseElement = document.find('base'),
|
14723
|
-
|
14740
|
+
pendingLocation = null;
|
14724
14741
|
|
14725
14742
|
cacheState();
|
14726
14743
|
lastHistoryState = cachedState;
|
@@ -14780,8 +14797,8 @@ function Browser(window, document, $log, $sniffer) {
|
|
14780
14797
|
// Do the assignment again so that those two variables are referentially identical.
|
14781
14798
|
lastHistoryState = cachedState;
|
14782
14799
|
} else {
|
14783
|
-
if (!sameBase ||
|
14784
|
-
|
14800
|
+
if (!sameBase || pendingLocation) {
|
14801
|
+
pendingLocation = url;
|
14785
14802
|
}
|
14786
14803
|
if (replace) {
|
14787
14804
|
location.replace(url);
|
@@ -14790,14 +14807,18 @@ function Browser(window, document, $log, $sniffer) {
|
|
14790
14807
|
} else {
|
14791
14808
|
location.hash = getHash(url);
|
14792
14809
|
}
|
14810
|
+
if (location.href !== url) {
|
14811
|
+
pendingLocation = url;
|
14812
|
+
}
|
14793
14813
|
}
|
14794
14814
|
return self;
|
14795
14815
|
// getter
|
14796
14816
|
} else {
|
14797
|
-
// -
|
14798
|
-
// the new location.href if a reload happened
|
14817
|
+
// - pendingLocation is needed as browsers don't allow to read out
|
14818
|
+
// the new location.href if a reload happened or if there is a bug like in iOS 9 (see
|
14819
|
+
// https://openradar.appspot.com/22186109).
|
14799
14820
|
// - the replacement is a workaround for https://bugzilla.mozilla.org/show_bug.cgi?id=407172
|
14800
|
-
return
|
14821
|
+
return pendingLocation || location.href.replace(/%27/g,"'");
|
14801
14822
|
}
|
14802
14823
|
};
|
14803
14824
|
|
@@ -14819,6 +14840,7 @@ function Browser(window, document, $log, $sniffer) {
|
|
14819
14840
|
urlChangeInit = false;
|
14820
14841
|
|
14821
14842
|
function cacheStateAndFireUrlChange() {
|
14843
|
+
pendingLocation = null;
|
14822
14844
|
cacheState();
|
14823
14845
|
fireUrlChange();
|
14824
14846
|
}
|
@@ -15054,10 +15076,10 @@ function $BrowserProvider() {
|
|
15054
15076
|
$scope.keys = [];
|
15055
15077
|
$scope.cache = $cacheFactory('cacheId');
|
15056
15078
|
$scope.put = function(key, value) {
|
15057
|
-
if ($scope.cache.get(key)
|
15079
|
+
if (angular.isUndefined($scope.cache.get(key))) {
|
15058
15080
|
$scope.keys.push(key);
|
15059
15081
|
}
|
15060
|
-
$scope.cache.put(key, value
|
15082
|
+
$scope.cache.put(key, angular.isUndefined(value) ? null : value);
|
15061
15083
|
};
|
15062
15084
|
}]);
|
15063
15085
|
</file>
|
@@ -15533,18 +15555,24 @@ function $TemplateCacheProvider() {
|
|
15533
15555
|
* and other directives used in the directive's template will also be excluded from execution.
|
15534
15556
|
*
|
15535
15557
|
* #### `scope`
|
15536
|
-
*
|
15537
|
-
*
|
15538
|
-
*
|
15558
|
+
* The scope property can be `true`, an object or a falsy value:
|
15559
|
+
*
|
15560
|
+
* * **falsy:** No scope will be created for the directive. The directive will use its parent's scope.
|
15561
|
+
*
|
15562
|
+
* * **`true`:** A new child scope that prototypically inherits from its parent will be created for
|
15563
|
+
* the directive's element. If multiple directives on the same element request a new scope,
|
15564
|
+
* only one new scope is created. The new scope rule does not apply for the root of the template
|
15565
|
+
* since the root of the template always gets a new scope.
|
15539
15566
|
*
|
15540
|
-
*
|
15541
|
-
* normal scope in that it does not prototypically inherit from
|
15542
|
-
* when creating reusable components, which should not accidentally read or modify
|
15543
|
-
* parent scope.
|
15567
|
+
* * **`{...}` (an object hash):** A new "isolate" scope is created for the directive's element. The
|
15568
|
+
* 'isolate' scope differs from normal scope in that it does not prototypically inherit from its parent
|
15569
|
+
* scope. This is useful when creating reusable components, which should not accidentally read or modify
|
15570
|
+
* data in the parent scope.
|
15544
15571
|
*
|
15545
|
-
* The 'isolate' scope
|
15546
|
-
*
|
15547
|
-
*
|
15572
|
+
* The 'isolate' scope object hash defines a set of local scope properties derived from attributes on the
|
15573
|
+
* directive's element. These local properties are useful for aliasing values for templates. The keys in
|
15574
|
+
* the object hash map to the name of the property on the isolate scope; the values define how the property
|
15575
|
+
* is bound to the parent scope, via matching attributes on the directive's element:
|
15548
15576
|
*
|
15549
15577
|
* * `@` or `@attr` - bind a local scope property to the value of DOM attribute. The result is
|
15550
15578
|
* always a string since DOM attributes are strings. If no `attr` name is specified then the
|
@@ -15577,6 +15605,20 @@ function $TemplateCacheProvider() {
|
|
15577
15605
|
* For example, if the expression is `increment(amount)` then we can specify the amount value
|
15578
15606
|
* by calling the `localFn` as `localFn({amount: 22})`.
|
15579
15607
|
*
|
15608
|
+
* In general it's possible to apply more than one directive to one element, but there might be limitations
|
15609
|
+
* depending on the type of scope required by the directives. The following points will help explain these limitations.
|
15610
|
+
* For simplicity only two directives are taken into account, but it is also applicable for several directives:
|
15611
|
+
*
|
15612
|
+
* * **no scope** + **no scope** => Two directives which don't require their own scope will use their parent's scope
|
15613
|
+
* * **child scope** + **no scope** => Both directives will share one single child scope
|
15614
|
+
* * **child scope** + **child scope** => Both directives will share one single child scope
|
15615
|
+
* * **isolated scope** + **no scope** => The isolated directive will use it's own created isolated scope. The other directive will use
|
15616
|
+
* its parent's scope
|
15617
|
+
* * **isolated scope** + **child scope** => **Won't work!** Only one scope can be related to one element. Therefore these directives cannot
|
15618
|
+
* be applied to the same element.
|
15619
|
+
* * **isolated scope** + **isolated scope** => **Won't work!** Only one scope can be related to one element. Therefore these directives
|
15620
|
+
* cannot be applied to the same element.
|
15621
|
+
*
|
15580
15622
|
*
|
15581
15623
|
* #### `bindToController`
|
15582
15624
|
* When an isolate scope is used for a component (see above), and `controllerAs` is used, `bindToController: true` will
|
@@ -15585,7 +15627,7 @@ function $TemplateCacheProvider() {
|
|
15585
15627
|
*
|
15586
15628
|
* #### `controller`
|
15587
15629
|
* Controller constructor function. The controller is instantiated before the
|
15588
|
-
* pre-linking phase and
|
15630
|
+
* pre-linking phase and can be accessed by other directives (see
|
15589
15631
|
* `require` attribute). This allows the directives to communicate with each other and augment
|
15590
15632
|
* each other's behavior. The controller is injectable (and supports bracket notation) with the following locals:
|
15591
15633
|
*
|
@@ -15625,9 +15667,10 @@ function $TemplateCacheProvider() {
|
|
15625
15667
|
*
|
15626
15668
|
* #### `controllerAs`
|
15627
15669
|
* Identifier name for a reference to the controller in the directive's scope.
|
15628
|
-
* This allows the controller to be referenced from the directive template.
|
15629
|
-
*
|
15630
|
-
* directive
|
15670
|
+
* This allows the controller to be referenced from the directive template. This is especially
|
15671
|
+
* useful when a directive is used as component, i.e. with an `isolate` scope. It's also possible
|
15672
|
+
* to use it in a directive without an `isolate` / `new` scope, but you need to be aware that the
|
15673
|
+
* `controllerAs` reference might overwrite a property that already exists on the parent scope.
|
15631
15674
|
*
|
15632
15675
|
*
|
15633
15676
|
* #### `restrict`
|
@@ -16464,7 +16507,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
|
|
16464
16507
|
|
16465
16508
|
var node = this.$$element[0],
|
16466
16509
|
booleanKey = getBooleanAttrName(node, key),
|
16467
|
-
aliasedKey = getAliasedAttrName(
|
16510
|
+
aliasedKey = getAliasedAttrName(key),
|
16468
16511
|
observer = key,
|
16469
16512
|
nodeName;
|
16470
16513
|
|
@@ -16531,7 +16574,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
|
|
16531
16574
|
}
|
16532
16575
|
|
16533
16576
|
if (writeAttr !== false) {
|
16534
|
-
if (value === null || value
|
16577
|
+
if (value === null || isUndefined(value)) {
|
16535
16578
|
this.$$element.removeAttr(attrName);
|
16536
16579
|
} else {
|
16537
16580
|
this.$$element.attr(attrName, value);
|
@@ -17497,7 +17540,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
|
|
17497
17540
|
i = 0, ii = directives.length; i < ii; i++) {
|
17498
17541
|
try {
|
17499
17542
|
directive = directives[i];
|
17500
|
-
if ((maxPriority
|
17543
|
+
if ((isUndefined(maxPriority) || maxPriority > directive.priority) &&
|
17501
17544
|
directive.restrict.indexOf(location) != -1) {
|
17502
17545
|
if (startAttrName) {
|
17503
17546
|
directive = inherit(directive, {$$start: startAttrName, $$end: endAttrName});
|
@@ -17793,7 +17836,7 @@ function $CompileProvider($provide, $$sanitizeUriProvider) {
|
|
17793
17836
|
compile: function() {
|
17794
17837
|
return {
|
17795
17838
|
pre: function attrInterpolatePreLinkFn(scope, element, attr) {
|
17796
|
-
var $$observers = (attr.$$observers || (attr.$$observers =
|
17839
|
+
var $$observers = (attr.$$observers || (attr.$$observers = createMap()));
|
17797
17840
|
|
17798
17841
|
if (EVENT_HANDLER_ATTR_REGEXP.test(name)) {
|
17799
17842
|
throw $compileMinErr('nodomevents',
|
@@ -18845,28 +18888,18 @@ function $HttpProvider() {
|
|
18845
18888
|
*
|
18846
18889
|
*
|
18847
18890
|
* ## General usage
|
18848
|
-
* The `$http` service is a function which takes a single argument — a configuration object —
|
18891
|
+
* The `$http` service is a function which takes a single argument — a {@link $http#usage configuration object} —
|
18849
18892
|
* that is used to generate an HTTP request and returns a {@link ng.$q promise}.
|
18850
18893
|
*
|
18851
18894
|
* ```js
|
18852
|
-
* // Simple GET request example
|
18853
|
-
* $http
|
18854
|
-
*
|
18855
|
-
*
|
18856
|
-
*
|
18857
|
-
* }, function(response) {
|
18858
|
-
* // called asynchronously if an error occurs
|
18859
|
-
* // or server returns response with an error status.
|
18860
|
-
* });
|
18861
|
-
* ```
|
18862
|
-
*
|
18863
|
-
* ```js
|
18864
|
-
* // Simple POST request example (passing data) :
|
18865
|
-
* $http.post('/someUrl', {msg:'hello word!'}).
|
18866
|
-
* then(function(response) {
|
18895
|
+
* // Simple GET request example:
|
18896
|
+
* $http({
|
18897
|
+
* method: 'GET',
|
18898
|
+
* url: '/someUrl'
|
18899
|
+
* }).then(function successCallback(response) {
|
18867
18900
|
* // this callback will be called asynchronously
|
18868
18901
|
* // when the response is available
|
18869
|
-
* }, function(response) {
|
18902
|
+
* }, function errorCallback(response) {
|
18870
18903
|
* // called asynchronously if an error occurs
|
18871
18904
|
* // or server returns response with an error status.
|
18872
18905
|
* });
|
@@ -18886,25 +18919,16 @@ function $HttpProvider() {
|
|
18886
18919
|
* XMLHttpRequest will transparently follow it, meaning that the error callback will not be
|
18887
18920
|
* called for such responses.
|
18888
18921
|
*
|
18889
|
-
* ## Writing Unit Tests that use $http
|
18890
|
-
* When unit testing (using {@link ngMock ngMock}), it is necessary to call
|
18891
|
-
* {@link ngMock.$httpBackend#flush $httpBackend.flush()} to flush each pending
|
18892
|
-
* request using trained responses.
|
18893
|
-
*
|
18894
|
-
* ```
|
18895
|
-
* $httpBackend.expectGET(...);
|
18896
|
-
* $http.get(...);
|
18897
|
-
* $httpBackend.flush();
|
18898
|
-
* ```
|
18899
18922
|
*
|
18900
18923
|
* ## Shortcut methods
|
18901
18924
|
*
|
18902
18925
|
* Shortcut methods are also available. All shortcut methods require passing in the URL, and
|
18903
|
-
* request data must be passed in for POST/PUT requests.
|
18926
|
+
* request data must be passed in for POST/PUT requests. An optional config can be passed as the
|
18927
|
+
* last argument.
|
18904
18928
|
*
|
18905
18929
|
* ```js
|
18906
|
-
* $http.get('/someUrl').then(successCallback);
|
18907
|
-
* $http.post('/someUrl', data).then(successCallback);
|
18930
|
+
* $http.get('/someUrl', config).then(successCallback, errorCallback);
|
18931
|
+
* $http.post('/someUrl', data, config).then(successCallback, errorCallback);
|
18908
18932
|
* ```
|
18909
18933
|
*
|
18910
18934
|
* Complete list of shortcut methods:
|
@@ -18918,6 +18942,17 @@ function $HttpProvider() {
|
|
18918
18942
|
* - {@link ng.$http#patch $http.patch}
|
18919
18943
|
*
|
18920
18944
|
*
|
18945
|
+
* ## Writing Unit Tests that use $http
|
18946
|
+
* When unit testing (using {@link ngMock ngMock}), it is necessary to call
|
18947
|
+
* {@link ngMock.$httpBackend#flush $httpBackend.flush()} to flush each pending
|
18948
|
+
* request using trained responses.
|
18949
|
+
*
|
18950
|
+
* ```
|
18951
|
+
* $httpBackend.expectGET(...);
|
18952
|
+
* $http.get(...);
|
18953
|
+
* $httpBackend.flush();
|
18954
|
+
* ```
|
18955
|
+
*
|
18921
18956
|
* ## Deprecation Notice
|
18922
18957
|
* <div class="alert alert-danger">
|
18923
18958
|
* The `$http` legacy promise methods `success` and `error` have been deprecated.
|
@@ -19075,7 +19110,7 @@ function $HttpProvider() {
|
|
19075
19110
|
*
|
19076
19111
|
* There are two kinds of interceptors (and two kinds of rejection interceptors):
|
19077
19112
|
*
|
19078
|
-
* * `request`: interceptors get called with a http
|
19113
|
+
* * `request`: interceptors get called with a http {@link $http#usage config} object. The function is free to
|
19079
19114
|
* modify the `config` object or create a new one. The function needs to return the `config`
|
19080
19115
|
* object directly, or a promise containing the `config` or a new `config` object.
|
19081
19116
|
* * `requestError`: interceptor gets called when a previous interceptor threw an error or
|
@@ -19709,8 +19744,8 @@ function $HttpProvider() {
|
|
19709
19744
|
* Resolves the raw $http promise.
|
19710
19745
|
*/
|
19711
19746
|
function resolvePromise(response, status, headers, statusText) {
|
19712
|
-
//
|
19713
|
-
status =
|
19747
|
+
//status: HTTP response status code, 0, -1 (aborted by timeout / promise)
|
19748
|
+
status = status >= -1 ? status : 0;
|
19714
19749
|
|
19715
19750
|
(isSuccess(status) ? deferred.resolve : deferred.reject)({
|
19716
19751
|
data: response,
|
@@ -19741,8 +19776,33 @@ function $HttpProvider() {
|
|
19741
19776
|
}];
|
19742
19777
|
}
|
19743
19778
|
|
19744
|
-
|
19745
|
-
|
19779
|
+
/**
|
19780
|
+
* @ngdoc service
|
19781
|
+
* @name $xhrFactory
|
19782
|
+
*
|
19783
|
+
* @description
|
19784
|
+
* Factory function used to create XMLHttpRequest objects.
|
19785
|
+
*
|
19786
|
+
* Replace or decorate this service to create your own custom XMLHttpRequest objects.
|
19787
|
+
*
|
19788
|
+
* ```
|
19789
|
+
* angular.module('myApp', [])
|
19790
|
+
* .factory('$xhrFactory', function() {
|
19791
|
+
* return function createXhr(method, url) {
|
19792
|
+
* return new window.XMLHttpRequest({mozSystem: true});
|
19793
|
+
* };
|
19794
|
+
* });
|
19795
|
+
* ```
|
19796
|
+
*
|
19797
|
+
* @param {string} method HTTP method of the request (GET, POST, PUT, ..)
|
19798
|
+
* @param {string} url URL of the request.
|
19799
|
+
*/
|
19800
|
+
function $xhrFactoryProvider() {
|
19801
|
+
this.$get = function() {
|
19802
|
+
return function createXhr() {
|
19803
|
+
return new window.XMLHttpRequest();
|
19804
|
+
};
|
19805
|
+
};
|
19746
19806
|
}
|
19747
19807
|
|
19748
19808
|
/**
|
@@ -19750,6 +19810,7 @@ function createXhr() {
|
|
19750
19810
|
* @name $httpBackend
|
19751
19811
|
* @requires $window
|
19752
19812
|
* @requires $document
|
19813
|
+
* @requires $xhrFactory
|
19753
19814
|
*
|
19754
19815
|
* @description
|
19755
19816
|
* HTTP backend used by the {@link ng.$http service} that delegates to
|
@@ -19762,8 +19823,8 @@ function createXhr() {
|
|
19762
19823
|
* $httpBackend} which can be trained with responses.
|
19763
19824
|
*/
|
19764
19825
|
function $HttpBackendProvider() {
|
19765
|
-
this.$get = ['$browser', '$window', '$document', function($browser, $window, $document) {
|
19766
|
-
return createHttpBackend($browser,
|
19826
|
+
this.$get = ['$browser', '$window', '$document', '$xhrFactory', function($browser, $window, $document, $xhrFactory) {
|
19827
|
+
return createHttpBackend($browser, $xhrFactory, $browser.defer, $window.angular.callbacks, $document[0]);
|
19767
19828
|
}];
|
19768
19829
|
}
|
19769
19830
|
|
@@ -19787,7 +19848,7 @@ function createHttpBackend($browser, createXhr, $browserDefer, callbacks, rawDoc
|
|
19787
19848
|
});
|
19788
19849
|
} else {
|
19789
19850
|
|
19790
|
-
var xhr = createXhr();
|
19851
|
+
var xhr = createXhr(method, url);
|
19791
19852
|
|
19792
19853
|
xhr.open(method, url, true);
|
19793
19854
|
forEach(headers, function(value, key) {
|
@@ -19850,7 +19911,7 @@ function createHttpBackend($browser, createXhr, $browserDefer, callbacks, rawDoc
|
|
19850
19911
|
}
|
19851
19912
|
}
|
19852
19913
|
|
19853
|
-
xhr.send(post);
|
19914
|
+
xhr.send(isUndefined(post) ? null : post);
|
19854
19915
|
}
|
19855
19916
|
|
19856
19917
|
if (timeout > 0) {
|
@@ -19867,7 +19928,7 @@ function createHttpBackend($browser, createXhr, $browserDefer, callbacks, rawDoc
|
|
19867
19928
|
|
19868
19929
|
function completeRequest(callback, status, response, headersString, statusText) {
|
19869
19930
|
// cancel timeout and subsequent timeout promise resolution
|
19870
|
-
if (timeoutId
|
19931
|
+
if (isDefined(timeoutId)) {
|
19871
19932
|
$browserDefer.cancel(timeoutId);
|
19872
19933
|
}
|
19873
19934
|
jsonpDone = xhr = null;
|
@@ -20053,7 +20114,7 @@ function $InterpolateProvider() {
|
|
20053
20114
|
* ```js
|
20054
20115
|
* var $interpolate = ...; // injected
|
20055
20116
|
* var exp = $interpolate('Hello {{name | uppercase}}!');
|
20056
|
-
* expect(exp({name:'Angular'}).toEqual('Hello ANGULAR!');
|
20117
|
+
* expect(exp({name:'Angular'})).toEqual('Hello ANGULAR!');
|
20057
20118
|
* ```
|
20058
20119
|
*
|
20059
20120
|
* `$interpolate` takes an optional fourth argument, `allOrNothing`. If `allOrNothing` is
|
@@ -20606,14 +20667,14 @@ function LocationHtml5Url(appBase, appBaseNoFile, basePrefix) {
|
|
20606
20667
|
var appUrl, prevAppUrl;
|
20607
20668
|
var rewrittenUrl;
|
20608
20669
|
|
20609
|
-
if ((appUrl = beginsWith(appBase, url))
|
20670
|
+
if (isDefined(appUrl = beginsWith(appBase, url))) {
|
20610
20671
|
prevAppUrl = appUrl;
|
20611
|
-
if ((appUrl = beginsWith(basePrefix, appUrl))
|
20672
|
+
if (isDefined(appUrl = beginsWith(basePrefix, appUrl))) {
|
20612
20673
|
rewrittenUrl = appBaseNoFile + (beginsWith('/', appUrl) || appUrl);
|
20613
20674
|
} else {
|
20614
20675
|
rewrittenUrl = appBase + prevAppUrl;
|
20615
20676
|
}
|
20616
|
-
} else if ((appUrl = beginsWith(appBaseNoFile, url))
|
20677
|
+
} else if (isDefined(appUrl = beginsWith(appBaseNoFile, url))) {
|
20617
20678
|
rewrittenUrl = appBaseNoFile + appUrl;
|
20618
20679
|
} else if (appBaseNoFile == url + '/') {
|
20619
20680
|
rewrittenUrl = appBaseNoFile;
|
@@ -21666,6 +21727,25 @@ function ensureSafeMemberName(name, fullExpression) {
|
|
21666
21727
|
return name;
|
21667
21728
|
}
|
21668
21729
|
|
21730
|
+
function getStringValue(name, fullExpression) {
|
21731
|
+
// From the JavaScript docs:
|
21732
|
+
// Property names must be strings. This means that non-string objects cannot be used
|
21733
|
+
// as keys in an object. Any non-string object, including a number, is typecasted
|
21734
|
+
// into a string via the toString method.
|
21735
|
+
//
|
21736
|
+
// So, to ensure that we are checking the same `name` that JavaScript would use,
|
21737
|
+
// we cast it to a string, if possible.
|
21738
|
+
// Doing `name + ''` can cause a repl error if the result to `toString` is not a string,
|
21739
|
+
// this is, this will handle objects that misbehave.
|
21740
|
+
name = name + '';
|
21741
|
+
if (!isString(name)) {
|
21742
|
+
throw $parseMinErr('iseccst',
|
21743
|
+
'Cannot convert object to primitive value! '
|
21744
|
+
+ 'Expression: {0}', fullExpression);
|
21745
|
+
}
|
21746
|
+
return name;
|
21747
|
+
}
|
21748
|
+
|
21669
21749
|
function ensureSafeObject(obj, fullExpression) {
|
21670
21750
|
// nifty check if obj is Function that is fast and works across iframes and other contexts
|
21671
21751
|
if (obj) {
|
@@ -21711,6 +21791,16 @@ function ensureSafeFunction(obj, fullExpression) {
|
|
21711
21791
|
}
|
21712
21792
|
}
|
21713
21793
|
|
21794
|
+
function ensureSafeAssignContext(obj, fullExpression) {
|
21795
|
+
if (obj) {
|
21796
|
+
if (obj === (0).constructor || obj === (false).constructor || obj === ''.constructor ||
|
21797
|
+
obj === {}.constructor || obj === [].constructor || obj === Function.constructor) {
|
21798
|
+
throw $parseMinErr('isecaf',
|
21799
|
+
'Assigning to a constructor is disallowed! Expression: {0}', fullExpression);
|
21800
|
+
}
|
21801
|
+
}
|
21802
|
+
}
|
21803
|
+
|
21714
21804
|
var OPERATORS = createMap();
|
21715
21805
|
forEach('+ - * / % === !== == != < > <= >= && || ! = |'.split(' '), function(operator) { OPERATORS[operator] = true; });
|
21716
21806
|
var ESCAPE = {"n":"\n", "f":"\f", "r":"\r", "t":"\t", "v":"\v", "'":"'", '"':'"'};
|
@@ -22392,6 +22482,7 @@ ASTCompiler.prototype = {
|
|
22392
22482
|
this.state.computing = 'assign';
|
22393
22483
|
var result = this.nextId();
|
22394
22484
|
this.recurse(assignable, result);
|
22485
|
+
this.return_(result);
|
22395
22486
|
extra = 'fn.assign=' + this.generateFunction('assign', 's,v,l');
|
22396
22487
|
}
|
22397
22488
|
var toWatch = getInputs(ast.body);
|
@@ -22424,6 +22515,8 @@ ASTCompiler.prototype = {
|
|
22424
22515
|
'ensureSafeMemberName',
|
22425
22516
|
'ensureSafeObject',
|
22426
22517
|
'ensureSafeFunction',
|
22518
|
+
'getStringValue',
|
22519
|
+
'ensureSafeAssignContext',
|
22427
22520
|
'ifDefined',
|
22428
22521
|
'plus',
|
22429
22522
|
'text',
|
@@ -22432,6 +22525,8 @@ ASTCompiler.prototype = {
|
|
22432
22525
|
ensureSafeMemberName,
|
22433
22526
|
ensureSafeObject,
|
22434
22527
|
ensureSafeFunction,
|
22528
|
+
getStringValue,
|
22529
|
+
ensureSafeAssignContext,
|
22435
22530
|
ifDefined,
|
22436
22531
|
plusFn,
|
22437
22532
|
expression);
|
@@ -22575,6 +22670,7 @@ ASTCompiler.prototype = {
|
|
22575
22670
|
if (ast.computed) {
|
22576
22671
|
right = self.nextId();
|
22577
22672
|
self.recurse(ast.property, right);
|
22673
|
+
self.getStringValue(right);
|
22578
22674
|
self.addEnsureSafeMemberName(right);
|
22579
22675
|
if (create && create !== 1) {
|
22580
22676
|
self.if_(self.not(self.computedMember(left, right)), self.lazyAssign(self.computedMember(left, right), '{}'));
|
@@ -22658,6 +22754,7 @@ ASTCompiler.prototype = {
|
|
22658
22754
|
self.if_(self.notNull(left.context), function() {
|
22659
22755
|
self.recurse(ast.right, right);
|
22660
22756
|
self.addEnsureSafeObject(self.member(left.context, left.name, left.computed));
|
22757
|
+
self.addEnsureSafeAssignContext(left.context);
|
22661
22758
|
expression = self.member(left.context, left.name, left.computed) + ast.operator + right;
|
22662
22759
|
self.assign(intoId, expression);
|
22663
22760
|
recursionFn(intoId || expression);
|
@@ -22783,6 +22880,10 @@ ASTCompiler.prototype = {
|
|
22783
22880
|
this.current().body.push(this.ensureSafeFunction(item), ';');
|
22784
22881
|
},
|
22785
22882
|
|
22883
|
+
addEnsureSafeAssignContext: function(item) {
|
22884
|
+
this.current().body.push(this.ensureSafeAssignContext(item), ';');
|
22885
|
+
},
|
22886
|
+
|
22786
22887
|
ensureSafeObject: function(item) {
|
22787
22888
|
return 'ensureSafeObject(' + item + ',text)';
|
22788
22889
|
},
|
@@ -22795,6 +22896,14 @@ ASTCompiler.prototype = {
|
|
22795
22896
|
return 'ensureSafeFunction(' + item + ',text)';
|
22796
22897
|
},
|
22797
22898
|
|
22899
|
+
getStringValue: function(item) {
|
22900
|
+
this.assign(item, 'getStringValue(' + item + ',text)');
|
22901
|
+
},
|
22902
|
+
|
22903
|
+
ensureSafeAssignContext: function(item) {
|
22904
|
+
return 'ensureSafeAssignContext(' + item + ',text)';
|
22905
|
+
},
|
22906
|
+
|
22798
22907
|
lazyRecurse: function(ast, intoId, nameId, recursionFn, create, skipWatchIdCheck) {
|
22799
22908
|
var self = this;
|
22800
22909
|
return function() {
|
@@ -22972,6 +23081,7 @@ ASTInterpreter.prototype = {
|
|
22972
23081
|
var lhs = left(scope, locals, assign, inputs);
|
22973
23082
|
var rhs = right(scope, locals, assign, inputs);
|
22974
23083
|
ensureSafeObject(lhs.value, self.expression);
|
23084
|
+
ensureSafeAssignContext(lhs.context);
|
22975
23085
|
lhs.context[lhs.name] = rhs;
|
22976
23086
|
return context ? {value: rhs} : rhs;
|
22977
23087
|
};
|
@@ -23169,6 +23279,7 @@ ASTInterpreter.prototype = {
|
|
23169
23279
|
var value;
|
23170
23280
|
if (lhs != null) {
|
23171
23281
|
rhs = right(scope, locals, assign, inputs);
|
23282
|
+
rhs = getStringValue(rhs);
|
23172
23283
|
ensureSafeMemberName(rhs, expression);
|
23173
23284
|
if (create && create !== 1 && lhs && !(lhs[rhs])) {
|
23174
23285
|
lhs[rhs] = {};
|
@@ -24109,7 +24220,7 @@ function $$RAFProvider() { //rAF
|
|
24109
24220
|
$window.webkitCancelRequestAnimationFrame;
|
24110
24221
|
|
24111
24222
|
var rafSupported = !!requestAnimationFrame;
|
24112
|
-
var
|
24223
|
+
var raf = rafSupported
|
24113
24224
|
? function(fn) {
|
24114
24225
|
var id = requestAnimationFrame(fn);
|
24115
24226
|
return function() {
|
@@ -24123,47 +24234,9 @@ function $$RAFProvider() { //rAF
|
|
24123
24234
|
};
|
24124
24235
|
};
|
24125
24236
|
|
24126
|
-
|
24127
|
-
|
24128
|
-
var cancelLastRAF;
|
24129
|
-
var taskCount = 0;
|
24130
|
-
var taskQueue = [];
|
24131
|
-
return queueFn;
|
24132
|
-
|
24133
|
-
function flush() {
|
24134
|
-
for (var i = 0; i < taskQueue.length; i++) {
|
24135
|
-
var task = taskQueue[i];
|
24136
|
-
if (task) {
|
24137
|
-
taskQueue[i] = null;
|
24138
|
-
task();
|
24139
|
-
}
|
24140
|
-
}
|
24141
|
-
taskCount = taskQueue.length = 0;
|
24142
|
-
}
|
24143
|
-
|
24144
|
-
function queueFn(asyncFn) {
|
24145
|
-
var index = taskQueue.length;
|
24237
|
+
raf.supported = rafSupported;
|
24146
24238
|
|
24147
|
-
|
24148
|
-
taskQueue.push(asyncFn);
|
24149
|
-
|
24150
|
-
if (index === 0) {
|
24151
|
-
cancelLastRAF = rafFn(flush);
|
24152
|
-
}
|
24153
|
-
|
24154
|
-
return function cancelQueueFn() {
|
24155
|
-
if (index >= 0) {
|
24156
|
-
taskQueue[index] = null;
|
24157
|
-
index = null;
|
24158
|
-
|
24159
|
-
if (--taskCount === 0 && cancelLastRAF) {
|
24160
|
-
cancelLastRAF();
|
24161
|
-
cancelLastRAF = null;
|
24162
|
-
taskQueue.length = 0;
|
24163
|
-
}
|
24164
|
-
}
|
24165
|
-
};
|
24166
|
-
}
|
24239
|
+
return raf;
|
24167
24240
|
}];
|
24168
24241
|
}
|
24169
24242
|
|
@@ -24420,10 +24493,10 @@ function $RootScopeProvider() {
|
|
24420
24493
|
* Registers a `listener` callback to be executed whenever the `watchExpression` changes.
|
24421
24494
|
*
|
24422
24495
|
* - The `watchExpression` is called on every call to {@link ng.$rootScope.Scope#$digest
|
24423
|
-
* $digest()} and should return the value that will be watched. (
|
24424
|
-
*
|
24425
|
-
* `watchExpression`
|
24426
|
-
*
|
24496
|
+
* $digest()} and should return the value that will be watched. (`watchExpression` should not change
|
24497
|
+
* its value when executed multiple times with the same input because it may be executed multiple
|
24498
|
+
* times by {@link ng.$rootScope.Scope#$digest $digest()}. That is, `watchExpression` should be
|
24499
|
+
* [idempotent](http://en.wikipedia.org/wiki/Idempotence).
|
24427
24500
|
* - The `listener` is called only when the value from the current `watchExpression` and the
|
24428
24501
|
* previous call to `watchExpression` are not equal (with the exception of the initial run,
|
24429
24502
|
* see below). Inequality is determined according to reference inequality,
|
@@ -24772,7 +24845,7 @@ function $RootScopeProvider() {
|
|
24772
24845
|
// copy the items to oldValue and look for changes.
|
24773
24846
|
newLength = 0;
|
24774
24847
|
for (key in newValue) {
|
24775
|
-
if (
|
24848
|
+
if (hasOwnProperty.call(newValue, key)) {
|
24776
24849
|
newLength++;
|
24777
24850
|
newItem = newValue[key];
|
24778
24851
|
oldItem = oldValue[key];
|
@@ -24794,7 +24867,7 @@ function $RootScopeProvider() {
|
|
24794
24867
|
// we used to have more keys, need to find them and destroy them.
|
24795
24868
|
changeDetected++;
|
24796
24869
|
for (key in oldValue) {
|
24797
|
-
if (!
|
24870
|
+
if (!hasOwnProperty.call(newValue, key)) {
|
24798
24871
|
oldLength--;
|
24799
24872
|
delete oldValue[key];
|
24800
24873
|
}
|
@@ -25879,7 +25952,7 @@ function $SceDelegateProvider() {
|
|
25879
25952
|
'Attempted to trust a value in invalid context. Context: {0}; Value: {1}',
|
25880
25953
|
type, trustedValue);
|
25881
25954
|
}
|
25882
|
-
if (trustedValue === null || trustedValue
|
25955
|
+
if (trustedValue === null || isUndefined(trustedValue) || trustedValue === '') {
|
25883
25956
|
return trustedValue;
|
25884
25957
|
}
|
25885
25958
|
// All the current contexts in SCE_CONTEXTS happen to be strings. In order to avoid trusting
|
@@ -25934,7 +26007,7 @@ function $SceDelegateProvider() {
|
|
25934
26007
|
* `$sceDelegate.trustAs`} if valid in this context. Otherwise, throws an exception.
|
25935
26008
|
*/
|
25936
26009
|
function getTrusted(type, maybeTrusted) {
|
25937
|
-
if (maybeTrusted === null || maybeTrusted
|
26010
|
+
if (maybeTrusted === null || isUndefined(maybeTrusted) || maybeTrusted === '') {
|
25938
26011
|
return maybeTrusted;
|
25939
26012
|
}
|
25940
26013
|
var constructor = (byType.hasOwnProperty(type) ? byType[type] : null);
|
@@ -27195,7 +27268,7 @@ function $$CookieReader($document) {
|
|
27195
27268
|
// the first value that is seen for a cookie is the most
|
27196
27269
|
// specific one. values for the same cookie name that
|
27197
27270
|
// follow are for less specific paths.
|
27198
|
-
if (lastCookies[name]
|
27271
|
+
if (isUndefined(lastCookies[name])) {
|
27199
27272
|
lastCookies[name] = safeDecodeURIComponent(cookie.substring(index + 1));
|
27200
27273
|
}
|
27201
27274
|
}
|
@@ -27843,6 +27916,7 @@ function formatNumber(number, pattern, groupSep, decimalSep, fractionSize) {
|
|
27843
27916
|
if (fractionSize > 0 && number < 1) {
|
27844
27917
|
formatedText = number.toFixed(fractionSize);
|
27845
27918
|
number = parseFloat(formatedText);
|
27919
|
+
formatedText = formatedText.replace(DECIMAL_SEP, decimalSep);
|
27846
27920
|
}
|
27847
27921
|
}
|
27848
27922
|
|
@@ -29141,6 +29215,7 @@ function nullFormRenameControl(control, name) {
|
|
29141
29215
|
* @property {boolean} $dirty True if user has already interacted with the form.
|
29142
29216
|
* @property {boolean} $valid True if all of the containing forms and controls are valid.
|
29143
29217
|
* @property {boolean} $invalid True if at least one containing control or form is invalid.
|
29218
|
+
* @property {boolean} $pending True if at least one containing control or form is pending.
|
29144
29219
|
* @property {boolean} $submitted True if user has submitted the form even if its invalid.
|
29145
29220
|
*
|
29146
29221
|
* @property {Object} $error Is an object hash, containing references to controls or
|
@@ -29180,8 +29255,6 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29180
29255
|
var form = this,
|
29181
29256
|
controls = [];
|
29182
29257
|
|
29183
|
-
var parentForm = form.$$parentForm = element.parent().controller('form') || nullFormCtrl;
|
29184
|
-
|
29185
29258
|
// init state
|
29186
29259
|
form.$error = {};
|
29187
29260
|
form.$$success = {};
|
@@ -29192,8 +29265,7 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29192
29265
|
form.$valid = true;
|
29193
29266
|
form.$invalid = false;
|
29194
29267
|
form.$submitted = false;
|
29195
|
-
|
29196
|
-
parentForm.$addControl(form);
|
29268
|
+
form.$$parentForm = nullFormCtrl;
|
29197
29269
|
|
29198
29270
|
/**
|
29199
29271
|
* @ngdoc method
|
@@ -29232,11 +29304,23 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29232
29304
|
/**
|
29233
29305
|
* @ngdoc method
|
29234
29306
|
* @name form.FormController#$addControl
|
29307
|
+
* @param {object} control control object, either a {@link form.FormController} or an
|
29308
|
+
* {@link ngModel.NgModelController}
|
29235
29309
|
*
|
29236
29310
|
* @description
|
29237
|
-
* Register a control with the form.
|
29311
|
+
* Register a control with the form. Input elements using ngModelController do this automatically
|
29312
|
+
* when they are linked.
|
29238
29313
|
*
|
29239
|
-
*
|
29314
|
+
* Note that the current state of the control will not be reflected on the new parent form. This
|
29315
|
+
* is not an issue with normal use, as freshly compiled and linked controls are in a `$pristine`
|
29316
|
+
* state.
|
29317
|
+
*
|
29318
|
+
* However, if the method is used programmatically, for example by adding dynamically created controls,
|
29319
|
+
* or controls that have been previously removed without destroying their corresponding DOM element,
|
29320
|
+
* it's the developers responsiblity to make sure the current state propagates to the parent form.
|
29321
|
+
*
|
29322
|
+
* For example, if an input control is added that is already `$dirty` and has `$error` properties,
|
29323
|
+
* calling `$setDirty()` and `$validate()` afterwards will propagate the state to the parent form.
|
29240
29324
|
*/
|
29241
29325
|
form.$addControl = function(control) {
|
29242
29326
|
// Breaking change - before, inputs whose name was "hasOwnProperty" were quietly ignored
|
@@ -29247,6 +29331,8 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29247
29331
|
if (control.$name) {
|
29248
29332
|
form[control.$name] = control;
|
29249
29333
|
}
|
29334
|
+
|
29335
|
+
control.$$parentForm = form;
|
29250
29336
|
};
|
29251
29337
|
|
29252
29338
|
// Private API: rename a form control
|
@@ -29263,11 +29349,18 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29263
29349
|
/**
|
29264
29350
|
* @ngdoc method
|
29265
29351
|
* @name form.FormController#$removeControl
|
29352
|
+
* @param {object} control control object, either a {@link form.FormController} or an
|
29353
|
+
* {@link ngModel.NgModelController}
|
29266
29354
|
*
|
29267
29355
|
* @description
|
29268
29356
|
* Deregister a control from the form.
|
29269
29357
|
*
|
29270
29358
|
* Input elements using ngModelController do this automatically when they are destroyed.
|
29359
|
+
*
|
29360
|
+
* Note that only the removed control's validation state (`$errors`etc.) will be removed from the
|
29361
|
+
* form. `$dirty`, `$submitted` states will not be changed, because the expected behavior can be
|
29362
|
+
* different from case to case. For example, removing the only `$dirty` control from a form may or
|
29363
|
+
* may not mean that the form is still `$dirty`.
|
29271
29364
|
*/
|
29272
29365
|
form.$removeControl = function(control) {
|
29273
29366
|
if (control.$name && form[control.$name] === control) {
|
@@ -29284,6 +29377,7 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29284
29377
|
});
|
29285
29378
|
|
29286
29379
|
arrayRemove(controls, control);
|
29380
|
+
control.$$parentForm = nullFormCtrl;
|
29287
29381
|
};
|
29288
29382
|
|
29289
29383
|
|
@@ -29320,7 +29414,6 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29320
29414
|
delete object[property];
|
29321
29415
|
}
|
29322
29416
|
},
|
29323
|
-
parentForm: parentForm,
|
29324
29417
|
$animate: $animate
|
29325
29418
|
});
|
29326
29419
|
|
@@ -29339,7 +29432,7 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29339
29432
|
$animate.addClass(element, DIRTY_CLASS);
|
29340
29433
|
form.$dirty = true;
|
29341
29434
|
form.$pristine = false;
|
29342
|
-
parentForm.$setDirty();
|
29435
|
+
form.$$parentForm.$setDirty();
|
29343
29436
|
};
|
29344
29437
|
|
29345
29438
|
/**
|
@@ -29395,7 +29488,7 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29395
29488
|
form.$setSubmitted = function() {
|
29396
29489
|
$animate.addClass(element, SUBMITTED_CLASS);
|
29397
29490
|
form.$submitted = true;
|
29398
|
-
parentForm.$setSubmitted();
|
29491
|
+
form.$$parentForm.$setSubmitted();
|
29399
29492
|
};
|
29400
29493
|
}
|
29401
29494
|
|
@@ -29445,6 +29538,7 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29445
29538
|
* # CSS classes
|
29446
29539
|
* - `ng-valid` is set if the form is valid.
|
29447
29540
|
* - `ng-invalid` is set if the form is invalid.
|
29541
|
+
* - `ng-pending` is set if the form is pending.
|
29448
29542
|
* - `ng-pristine` is set if the form is pristine.
|
29449
29543
|
* - `ng-dirty` is set if the form is dirty.
|
29450
29544
|
* - `ng-submitted` is set if the form was submitted.
|
@@ -29520,7 +29614,6 @@ function FormController(element, attrs, $scope, $animate, $interpolate) {
|
|
29520
29614
|
</script>
|
29521
29615
|
<style>
|
29522
29616
|
.my-form {
|
29523
|
-
-webkit-transition:all linear 0.5s;
|
29524
29617
|
transition:all linear 0.5s;
|
29525
29618
|
background: transparent;
|
29526
29619
|
}
|
@@ -29569,6 +29662,7 @@ var formDirectiveFactory = function(isNgForm) {
|
|
29569
29662
|
var formDirective = {
|
29570
29663
|
name: 'form',
|
29571
29664
|
restrict: isNgForm ? 'EAC' : 'E',
|
29665
|
+
require: ['form', '^^?form'], //first is the form's own ctrl, second is an optional parent form
|
29572
29666
|
controller: FormController,
|
29573
29667
|
compile: function ngFormCompile(formElement, attr) {
|
29574
29668
|
// Setup initial state of the control
|
@@ -29577,7 +29671,9 @@ var formDirectiveFactory = function(isNgForm) {
|
|
29577
29671
|
var nameAttr = attr.name ? 'name' : (isNgForm && attr.ngForm ? 'ngForm' : false);
|
29578
29672
|
|
29579
29673
|
return {
|
29580
|
-
pre: function ngFormPreLink(scope, formElement, attr,
|
29674
|
+
pre: function ngFormPreLink(scope, formElement, attr, ctrls) {
|
29675
|
+
var controller = ctrls[0];
|
29676
|
+
|
29581
29677
|
// if `action` attr is not present on the form, prevent the default action (submission)
|
29582
29678
|
if (!('action' in attr)) {
|
29583
29679
|
// we can't use jq events because if a form is destroyed during submission the default
|
@@ -29606,7 +29702,9 @@ var formDirectiveFactory = function(isNgForm) {
|
|
29606
29702
|
});
|
29607
29703
|
}
|
29608
29704
|
|
29609
|
-
var parentFormCtrl = controller.$$parentForm;
|
29705
|
+
var parentFormCtrl = ctrls[1] || controller.$$parentForm;
|
29706
|
+
parentFormCtrl.$addControl(controller);
|
29707
|
+
|
29610
29708
|
var setter = nameAttr ? getSetter(controller.$name) : noop;
|
29611
29709
|
|
29612
29710
|
if (nameAttr) {
|
@@ -29614,13 +29712,13 @@ var formDirectiveFactory = function(isNgForm) {
|
|
29614
29712
|
attr.$observe(nameAttr, function(newValue) {
|
29615
29713
|
if (controller.$name === newValue) return;
|
29616
29714
|
setter(scope, undefined);
|
29617
|
-
|
29715
|
+
controller.$$parentForm.$$renameControl(controller, newValue);
|
29618
29716
|
setter = getSetter(controller.$name);
|
29619
29717
|
setter(scope, controller);
|
29620
29718
|
});
|
29621
29719
|
}
|
29622
29720
|
formElement.on('$destroy', function() {
|
29623
|
-
|
29721
|
+
controller.$$parentForm.$removeControl(controller);
|
29624
29722
|
setter(scope, undefined);
|
29625
29723
|
extend(controller, nullFormCtrl); //stop propagating child destruction handlers upwards
|
29626
29724
|
});
|
@@ -29782,9 +29880,17 @@ var inputType = {
|
|
29782
29880
|
* @param {string} ngModel Assignable angular expression to data-bind to.
|
29783
29881
|
* @param {string=} name Property name of the form under which the control is published.
|
29784
29882
|
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`. This must be a
|
29785
|
-
*
|
29883
|
+
* valid ISO date string (yyyy-MM-dd). You can also use interpolation inside this attribute
|
29884
|
+
* (e.g. `min="{{minDate | date:'yyyy-MM-dd'}}"`). Note that `min` will also add native HTML5
|
29885
|
+
* constraint validation.
|
29786
29886
|
* @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`. This must be
|
29787
|
-
*
|
29887
|
+
* a valid ISO date string (yyyy-MM-dd). You can also use interpolation inside this attribute
|
29888
|
+
* (e.g. `max="{{maxDate | date:'yyyy-MM-dd'}}"`). Note that `max` will also add native HTML5
|
29889
|
+
* constraint validation.
|
29890
|
+
* @param {(date|string)=} ngMin Sets the `min` validation constraint to the Date / ISO date string
|
29891
|
+
* the `ngMin` expression evaluates to. Note that it does not set the `min` attribute.
|
29892
|
+
* @param {(date|string)=} ngMax Sets the `max` validation constraint to the Date / ISO date string
|
29893
|
+
* the `ngMax` expression evaluates to. Note that it does not set the `max` attribute.
|
29788
29894
|
* @param {string=} required Sets `required` validation error key if the value is not entered.
|
29789
29895
|
* @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to
|
29790
29896
|
* the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of
|
@@ -29876,10 +29982,18 @@ var inputType = {
|
|
29876
29982
|
*
|
29877
29983
|
* @param {string} ngModel Assignable angular expression to data-bind to.
|
29878
29984
|
* @param {string=} name Property name of the form under which the control is published.
|
29879
|
-
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
|
29880
|
-
* valid ISO datetime format (yyyy-MM-ddTHH:mm:ss).
|
29881
|
-
*
|
29882
|
-
*
|
29985
|
+
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
|
29986
|
+
* This must be a valid ISO datetime format (yyyy-MM-ddTHH:mm:ss). You can also use interpolation
|
29987
|
+
* inside this attribute (e.g. `min="{{minDatetimeLocal | date:'yyyy-MM-ddTHH:mm:ss'}}"`).
|
29988
|
+
* Note that `min` will also add native HTML5 constraint validation.
|
29989
|
+
* @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.
|
29990
|
+
* This must be a valid ISO datetime format (yyyy-MM-ddTHH:mm:ss). You can also use interpolation
|
29991
|
+
* inside this attribute (e.g. `max="{{maxDatetimeLocal | date:'yyyy-MM-ddTHH:mm:ss'}}"`).
|
29992
|
+
* Note that `max` will also add native HTML5 constraint validation.
|
29993
|
+
* @param {(date|string)=} ngMin Sets the `min` validation error key to the Date / ISO datetime string
|
29994
|
+
* the `ngMin` expression evaluates to. Note that it does not set the `min` attribute.
|
29995
|
+
* @param {(date|string)=} ngMax Sets the `max` validation error key to the Date / ISO datetime string
|
29996
|
+
* the `ngMax` expression evaluates to. Note that it does not set the `max` attribute.
|
29883
29997
|
* @param {string=} required Sets `required` validation error key if the value is not entered.
|
29884
29998
|
* @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to
|
29885
29999
|
* the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of
|
@@ -29972,10 +30086,18 @@ var inputType = {
|
|
29972
30086
|
*
|
29973
30087
|
* @param {string} ngModel Assignable angular expression to data-bind to.
|
29974
30088
|
* @param {string=} name Property name of the form under which the control is published.
|
29975
|
-
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
|
29976
|
-
* valid ISO time format (HH:mm:ss).
|
29977
|
-
*
|
29978
|
-
*
|
30089
|
+
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
|
30090
|
+
* This must be a valid ISO time format (HH:mm:ss). You can also use interpolation inside this
|
30091
|
+
* attribute (e.g. `min="{{minTime | date:'HH:mm:ss'}}"`). Note that `min` will also add
|
30092
|
+
* native HTML5 constraint validation.
|
30093
|
+
* @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.
|
30094
|
+
* This must be a valid ISO time format (HH:mm:ss). You can also use interpolation inside this
|
30095
|
+
* attribute (e.g. `max="{{maxTime | date:'HH:mm:ss'}}"`). Note that `max` will also add
|
30096
|
+
* native HTML5 constraint validation.
|
30097
|
+
* @param {(date|string)=} ngMin Sets the `min` validation constraint to the Date / ISO time string the
|
30098
|
+
* `ngMin` expression evaluates to. Note that it does not set the `min` attribute.
|
30099
|
+
* @param {(date|string)=} ngMax Sets the `max` validation constraint to the Date / ISO time string the
|
30100
|
+
* `ngMax` expression evaluates to. Note that it does not set the `max` attribute.
|
29979
30101
|
* @param {string=} required Sets `required` validation error key if the value is not entered.
|
29980
30102
|
* @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to
|
29981
30103
|
* the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of
|
@@ -30067,10 +30189,18 @@ var inputType = {
|
|
30067
30189
|
*
|
30068
30190
|
* @param {string} ngModel Assignable angular expression to data-bind to.
|
30069
30191
|
* @param {string=} name Property name of the form under which the control is published.
|
30070
|
-
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
|
30071
|
-
* valid ISO week format (yyyy-W##).
|
30072
|
-
*
|
30073
|
-
*
|
30192
|
+
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
|
30193
|
+
* This must be a valid ISO week format (yyyy-W##). You can also use interpolation inside this
|
30194
|
+
* attribute (e.g. `min="{{minWeek | date:'yyyy-Www'}}"`). Note that `min` will also add
|
30195
|
+
* native HTML5 constraint validation.
|
30196
|
+
* @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.
|
30197
|
+
* This must be a valid ISO week format (yyyy-W##). You can also use interpolation inside this
|
30198
|
+
* attribute (e.g. `max="{{maxWeek | date:'yyyy-Www'}}"`). Note that `max` will also add
|
30199
|
+
* native HTML5 constraint validation.
|
30200
|
+
* @param {(date|string)=} ngMin Sets the `min` validation constraint to the Date / ISO week string
|
30201
|
+
* the `ngMin` expression evaluates to. Note that it does not set the `min` attribute.
|
30202
|
+
* @param {(date|string)=} ngMax Sets the `max` validation constraint to the Date / ISO week string
|
30203
|
+
* the `ngMax` expression evaluates to. Note that it does not set the `max` attribute.
|
30074
30204
|
* @param {string=} required Sets `required` validation error key if the value is not entered.
|
30075
30205
|
* @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to
|
30076
30206
|
* the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of
|
@@ -30164,10 +30294,19 @@ var inputType = {
|
|
30164
30294
|
*
|
30165
30295
|
* @param {string} ngModel Assignable angular expression to data-bind to.
|
30166
30296
|
* @param {string=} name Property name of the form under which the control is published.
|
30167
|
-
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
|
30168
|
-
* a valid ISO month format (yyyy-MM).
|
30169
|
-
*
|
30170
|
-
*
|
30297
|
+
* @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.
|
30298
|
+
* This must be a valid ISO month format (yyyy-MM). You can also use interpolation inside this
|
30299
|
+
* attribute (e.g. `min="{{minMonth | date:'yyyy-MM'}}"`). Note that `min` will also add
|
30300
|
+
* native HTML5 constraint validation.
|
30301
|
+
* @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.
|
30302
|
+
* This must be a valid ISO month format (yyyy-MM). You can also use interpolation inside this
|
30303
|
+
* attribute (e.g. `max="{{maxMonth | date:'yyyy-MM'}}"`). Note that `max` will also add
|
30304
|
+
* native HTML5 constraint validation.
|
30305
|
+
* @param {(date|string)=} ngMin Sets the `min` validation constraint to the Date / ISO week string
|
30306
|
+
* the `ngMin` expression evaluates to. Note that it does not set the `min` attribute.
|
30307
|
+
* @param {(date|string)=} ngMax Sets the `max` validation constraint to the Date / ISO week string
|
30308
|
+
* the `ngMax` expression evaluates to. Note that it does not set the `max` attribute.
|
30309
|
+
|
30171
30310
|
* @param {string=} required Sets `required` validation error key if the value is not entered.
|
30172
30311
|
* @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to
|
30173
30312
|
* the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of
|
@@ -30929,7 +31068,7 @@ function createDateInputType(type, regexp, parseDate, format) {
|
|
30929
31068
|
}
|
30930
31069
|
|
30931
31070
|
function parseObservedDateValue(val) {
|
30932
|
-
return isDefined(val)
|
31071
|
+
return isDefined(val) && !isDate(val) ? parseDate(val) || undefined : val;
|
30933
31072
|
}
|
30934
31073
|
};
|
30935
31074
|
}
|
@@ -31424,7 +31563,7 @@ var ngBindDirective = ['$compile', function($compile) {
|
|
31424
31563
|
$compile.$$addBindingInfo(element, attr.ngBind);
|
31425
31564
|
element = element[0];
|
31426
31565
|
scope.$watch(attr.ngBind, function ngBindWatchAction(value) {
|
31427
|
-
element.textContent = value
|
31566
|
+
element.textContent = isUndefined(value) ? '' : value;
|
31428
31567
|
});
|
31429
31568
|
};
|
31430
31569
|
}
|
@@ -31492,7 +31631,7 @@ var ngBindTemplateDirective = ['$interpolate', '$compile', function($interpolate
|
|
31492
31631
|
$compile.$$addBindingInfo(element, interpolateFn.expressions);
|
31493
31632
|
element = element[0];
|
31494
31633
|
attr.$observe('ngBindTemplate', function(value) {
|
31495
|
-
element.textContent = value
|
31634
|
+
element.textContent = isUndefined(value) ? '' : value;
|
31496
31635
|
});
|
31497
31636
|
};
|
31498
31637
|
}
|
@@ -31909,7 +32048,6 @@ function classDirective(name, selector) {
|
|
31909
32048
|
</file>
|
31910
32049
|
<file name="style.css">
|
31911
32050
|
.base-class {
|
31912
|
-
-webkit-transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;
|
31913
32051
|
transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;
|
31914
32052
|
}
|
31915
32053
|
|
@@ -33084,7 +33222,6 @@ forEach(
|
|
33084
33222
|
}
|
33085
33223
|
|
33086
33224
|
.animate-if.ng-enter, .animate-if.ng-leave {
|
33087
|
-
-webkit-transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;
|
33088
33225
|
transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;
|
33089
33226
|
}
|
33090
33227
|
|
@@ -33233,7 +33370,6 @@ var ngIfDirective = ['$animate', function($animate) {
|
|
33233
33370
|
}
|
33234
33371
|
|
33235
33372
|
.slide-animate.ng-enter, .slide-animate.ng-leave {
|
33236
|
-
-webkit-transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;
|
33237
33373
|
transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;
|
33238
33374
|
|
33239
33375
|
position:absolute;
|
@@ -33452,16 +33588,18 @@ var ngIncludeFillContentDirective = ['$compile',
|
|
33452
33588
|
* current scope.
|
33453
33589
|
*
|
33454
33590
|
* <div class="alert alert-danger">
|
33455
|
-
*
|
33456
|
-
*
|
33457
|
-
*
|
33458
|
-
*
|
33591
|
+
* This directive can be abused to add unnecessary amounts of logic into your templates.
|
33592
|
+
* There are only a few appropriate uses of `ngInit`, such as for aliasing special properties of
|
33593
|
+
* {@link ng.directive:ngRepeat `ngRepeat`}, as seen in the demo below; and for injecting data via
|
33594
|
+
* server side scripting. Besides these few cases, you should use {@link guide/controller controllers}
|
33595
|
+
* rather than `ngInit` to initialize values on a scope.
|
33459
33596
|
* </div>
|
33597
|
+
*
|
33460
33598
|
* <div class="alert alert-warning">
|
33461
|
-
* **Note**: If you have assignment in `ngInit` along with {@link ng.$filter
|
33462
|
-
* sure you have
|
33599
|
+
* **Note**: If you have assignment in `ngInit` along with a {@link ng.$filter `filter`}, make
|
33600
|
+
* sure you have parentheses to ensure correct operator precedence:
|
33463
33601
|
* <pre class="prettyprint">
|
33464
|
-
* `<div ng-init="test1 = (
|
33602
|
+
* `<div ng-init="test1 = ($index | toString)"></div>`
|
33465
33603
|
* </pre>
|
33466
33604
|
* </div>
|
33467
33605
|
*
|
@@ -33574,7 +33712,7 @@ var ngInitDirective = ngDirective({
|
|
33574
33712
|
* </file>
|
33575
33713
|
* </example>
|
33576
33714
|
*
|
33577
|
-
* ### Example - splitting on
|
33715
|
+
* ### Example - splitting on newline
|
33578
33716
|
* <example name="ngList-directive-newlines">
|
33579
33717
|
* <file name="index.html">
|
33580
33718
|
* <textarea ng-model="list" ng-list=" " ng-trim="false"></textarea>
|
@@ -33659,7 +33797,9 @@ var ngModelMinErr = minErr('ngModel');
|
|
33659
33797
|
* @ngdoc type
|
33660
33798
|
* @name ngModel.NgModelController
|
33661
33799
|
*
|
33662
|
-
* @property {
|
33800
|
+
* @property {*} $viewValue The actual value from the control's view. For `input` elements, this is a
|
33801
|
+
* String. See {@link ngModel.NgModelController#$setViewValue} for information about when the $viewValue
|
33802
|
+
* is set.
|
33663
33803
|
* @property {*} $modelValue The value in the model that the control is bound to.
|
33664
33804
|
* @property {Array.<Function>} $parsers Array of functions to execute, as a pipeline, whenever
|
33665
33805
|
the control reads value from the DOM. The functions are called in array order, each passing
|
@@ -33873,7 +34013,7 @@ var NgModelController = ['$scope', '$exceptionHandler', '$attrs', '$element', '$
|
|
33873
34013
|
this.$$success = {}; // keep valid keys here
|
33874
34014
|
this.$pending = undefined; // keep pending keys here
|
33875
34015
|
this.$name = $interpolate($attr.name || '', false)($scope);
|
33876
|
-
|
34016
|
+
this.$$parentForm = nullFormCtrl;
|
33877
34017
|
|
33878
34018
|
var parsedNgModel = $parse($attr.ngModel),
|
33879
34019
|
parsedNgModelAssign = parsedNgModel.assign,
|
@@ -33953,8 +34093,7 @@ var NgModelController = ['$scope', '$exceptionHandler', '$attrs', '$element', '$
|
|
33953
34093
|
return isUndefined(value) || value === '' || value === null || value !== value;
|
33954
34094
|
};
|
33955
34095
|
|
33956
|
-
var
|
33957
|
-
currentValidationRunId = 0;
|
34096
|
+
var currentValidationRunId = 0;
|
33958
34097
|
|
33959
34098
|
/**
|
33960
34099
|
* @ngdoc method
|
@@ -33987,7 +34126,6 @@ var NgModelController = ['$scope', '$exceptionHandler', '$attrs', '$element', '$
|
|
33987
34126
|
unset: function(object, property) {
|
33988
34127
|
delete object[property];
|
33989
34128
|
},
|
33990
|
-
parentForm: parentForm,
|
33991
34129
|
$animate: $animate
|
33992
34130
|
});
|
33993
34131
|
|
@@ -34025,7 +34163,7 @@ var NgModelController = ['$scope', '$exceptionHandler', '$attrs', '$element', '$
|
|
34025
34163
|
ctrl.$pristine = false;
|
34026
34164
|
$animate.removeClass($element, PRISTINE_CLASS);
|
34027
34165
|
$animate.addClass($element, DIRTY_CLASS);
|
34028
|
-
parentForm.$setDirty();
|
34166
|
+
ctrl.$$parentForm.$setDirty();
|
34029
34167
|
};
|
34030
34168
|
|
34031
34169
|
/**
|
@@ -34195,7 +34333,7 @@ var NgModelController = ['$scope', '$exceptionHandler', '$attrs', '$element', '$
|
|
34195
34333
|
|
34196
34334
|
function processParseErrors() {
|
34197
34335
|
var errorKey = ctrl.$$parserName || 'parse';
|
34198
|
-
if (parserValid
|
34336
|
+
if (isUndefined(parserValid)) {
|
34199
34337
|
setValidity(errorKey, null);
|
34200
34338
|
} else {
|
34201
34339
|
if (!parserValid) {
|
@@ -34365,37 +34503,47 @@ var NgModelController = ['$scope', '$exceptionHandler', '$attrs', '$element', '$
|
|
34365
34503
|
* @description
|
34366
34504
|
* Update the view value.
|
34367
34505
|
*
|
34368
|
-
* This method should be called when
|
34369
|
-
* this is done from within a DOM event handler.
|
34370
|
-
*
|
34371
|
-
*
|
34372
|
-
* {@link ng.directive:select select} calls it when an option is selected.
|
34373
|
-
*
|
34374
|
-
* If the new `value` is an object (rather than a string or a number), we should make a copy of the
|
34375
|
-
* object before passing it to `$setViewValue`. This is because `ngModel` does not perform a deep
|
34376
|
-
* watch of objects, it only looks for a change of identity. If you only change the property of
|
34377
|
-
* the object then ngModel will not realise that the object has changed and will not invoke the
|
34378
|
-
* `$parsers` and `$validators` pipelines.
|
34379
|
-
*
|
34380
|
-
* For this reason, you should not change properties of the copy once it has been passed to
|
34381
|
-
* `$setViewValue`. Otherwise you may cause the model value on the scope to change incorrectly.
|
34506
|
+
* This method should be called when a control wants to change the view value; typically,
|
34507
|
+
* this is done from within a DOM event handler. For example, the {@link ng.directive:input input}
|
34508
|
+
* directive calls it when the value of the input changes and {@link ng.directive:select select}
|
34509
|
+
* calls it when an option is selected.
|
34382
34510
|
*
|
34383
|
-
* When
|
34511
|
+
* When `$setViewValue` is called, the new `value` will be staged for committing through the `$parsers`
|
34384
34512
|
* and `$validators` pipelines. If there are no special {@link ngModelOptions} specified then the staged
|
34385
34513
|
* value sent directly for processing, finally to be applied to `$modelValue` and then the
|
34386
|
-
* **expression** specified in the `ng-model` attribute.
|
34387
|
-
*
|
34388
|
-
* Lastly, all the registered change listeners, in the `$viewChangeListeners` list, are called.
|
34514
|
+
* **expression** specified in the `ng-model` attribute. Lastly, all the registered change listeners,
|
34515
|
+
* in the `$viewChangeListeners` list, are called.
|
34389
34516
|
*
|
34390
34517
|
* In case the {@link ng.directive:ngModelOptions ngModelOptions} directive is used with `updateOn`
|
34391
34518
|
* and the `default` trigger is not listed, all those actions will remain pending until one of the
|
34392
34519
|
* `updateOn` events is triggered on the DOM element.
|
34393
34520
|
* All these actions will be debounced if the {@link ng.directive:ngModelOptions ngModelOptions}
|
34394
34521
|
* directive is used with a custom debounce for this particular event.
|
34522
|
+
* Note that a `$digest` is only triggered once the `updateOn` events are fired, or if `debounce`
|
34523
|
+
* is specified, once the timer runs out.
|
34524
|
+
*
|
34525
|
+
* When used with standard inputs, the view value will always be a string (which is in some cases
|
34526
|
+
* parsed into another type, such as a `Date` object for `input[date]`.)
|
34527
|
+
* However, custom controls might also pass objects to this method. In this case, we should make
|
34528
|
+
* a copy of the object before passing it to `$setViewValue`. This is because `ngModel` does not
|
34529
|
+
* perform a deep watch of objects, it only looks for a change of identity. If you only change
|
34530
|
+
* the property of the object then ngModel will not realise that the object has changed and
|
34531
|
+
* will not invoke the `$parsers` and `$validators` pipelines. For this reason, you should
|
34532
|
+
* not change properties of the copy once it has been passed to `$setViewValue`.
|
34533
|
+
* Otherwise you may cause the model value on the scope to change incorrectly.
|
34534
|
+
*
|
34535
|
+
* <div class="alert alert-info">
|
34536
|
+
* In any case, the value passed to the method should always reflect the current value
|
34537
|
+
* of the control. For example, if you are calling `$setViewValue` for an input element,
|
34538
|
+
* you should pass the input DOM value. Otherwise, the control and the scope model become
|
34539
|
+
* out of sync. It's also important to note that `$setViewValue` does not call `$render` or change
|
34540
|
+
* the control's DOM value in any way. If we want to change the control's DOM value
|
34541
|
+
* programmatically, we should update the `ngModel` scope expression. Its new value will be
|
34542
|
+
* picked up by the model controller, which will run it through the `$formatters`, `$render` it
|
34543
|
+
* to update the DOM, and finally call `$validate` on it.
|
34544
|
+
* </div>
|
34395
34545
|
*
|
34396
|
-
*
|
34397
|
-
*
|
34398
|
-
* @param {string} value Value from the view.
|
34546
|
+
* @param {*} value value from the view.
|
34399
34547
|
* @param {string} trigger Event that triggered the update.
|
34400
34548
|
*/
|
34401
34549
|
this.$setViewValue = function(value, trigger) {
|
@@ -34572,7 +34720,6 @@ var NgModelController = ['$scope', '$exceptionHandler', '$attrs', '$element', '$
|
|
34572
34720
|
</script>
|
34573
34721
|
<style>
|
34574
34722
|
.my-input {
|
34575
|
-
-webkit-transition:all linear 0.5s;
|
34576
34723
|
transition:all linear 0.5s;
|
34577
34724
|
background: transparent;
|
34578
34725
|
}
|
@@ -34659,7 +34806,7 @@ var ngModelDirective = ['$rootScope', function($rootScope) {
|
|
34659
34806
|
return {
|
34660
34807
|
pre: function ngModelPreLink(scope, element, attr, ctrls) {
|
34661
34808
|
var modelCtrl = ctrls[0],
|
34662
|
-
formCtrl = ctrls[1] ||
|
34809
|
+
formCtrl = ctrls[1] || modelCtrl.$$parentForm;
|
34663
34810
|
|
34664
34811
|
modelCtrl.$$setOptions(ctrls[2] && ctrls[2].$options);
|
34665
34812
|
|
@@ -34668,12 +34815,12 @@ var ngModelDirective = ['$rootScope', function($rootScope) {
|
|
34668
34815
|
|
34669
34816
|
attr.$observe('name', function(newValue) {
|
34670
34817
|
if (modelCtrl.$name !== newValue) {
|
34671
|
-
|
34818
|
+
modelCtrl.$$parentForm.$$renameControl(modelCtrl, newValue);
|
34672
34819
|
}
|
34673
34820
|
});
|
34674
34821
|
|
34675
34822
|
scope.$on('$destroy', function() {
|
34676
|
-
|
34823
|
+
modelCtrl.$$parentForm.$removeControl(modelCtrl);
|
34677
34824
|
});
|
34678
34825
|
},
|
34679
34826
|
post: function ngModelPostLink(scope, element, attr, ctrls) {
|
@@ -34868,7 +35015,7 @@ var ngModelOptionsDirective = function() {
|
|
34868
35015
|
var that = this;
|
34869
35016
|
this.$options = copy($scope.$eval($attrs.ngModelOptions));
|
34870
35017
|
// Allow adding/overriding bound events
|
34871
|
-
if (this.$options.updateOn
|
35018
|
+
if (isDefined(this.$options.updateOn)) {
|
34872
35019
|
this.$options.updateOnDefault = false;
|
34873
35020
|
// extract "default" pseudo-event from list of events that can trigger a model update
|
34874
35021
|
this.$options.updateOn = trim(this.$options.updateOn.replace(DEFAULT_REGEXP, function() {
|
@@ -34891,7 +35038,6 @@ function addSetValidityMethod(context) {
|
|
34891
35038
|
classCache = {},
|
34892
35039
|
set = context.set,
|
34893
35040
|
unset = context.unset,
|
34894
|
-
parentForm = context.parentForm,
|
34895
35041
|
$animate = context.$animate;
|
34896
35042
|
|
34897
35043
|
classCache[INVALID_CLASS] = !(classCache[VALID_CLASS] = $element.hasClass(VALID_CLASS));
|
@@ -34899,7 +35045,7 @@ function addSetValidityMethod(context) {
|
|
34899
35045
|
ctrl.$setValidity = setValidity;
|
34900
35046
|
|
34901
35047
|
function setValidity(validationErrorKey, state, controller) {
|
34902
|
-
if (state
|
35048
|
+
if (isUndefined(state)) {
|
34903
35049
|
createAndSet('$pending', validationErrorKey, controller);
|
34904
35050
|
} else {
|
34905
35051
|
unsetAndCleanup('$pending', validationErrorKey, controller);
|
@@ -34943,7 +35089,7 @@ function addSetValidityMethod(context) {
|
|
34943
35089
|
}
|
34944
35090
|
|
34945
35091
|
toggleValidationCss(validationErrorKey, combinedState);
|
34946
|
-
parentForm.$setValidity(validationErrorKey, combinedState, ctrl);
|
35092
|
+
ctrl.$$parentForm.$setValidity(validationErrorKey, combinedState, ctrl);
|
34947
35093
|
}
|
34948
35094
|
|
34949
35095
|
function createAndSet(name, value, controller) {
|
@@ -35604,11 +35750,16 @@ var ngOptionsDirective = ['$compile', '$parse', function($compile, $parse) {
|
|
35604
35750
|
function updateOptionElement(option, element) {
|
35605
35751
|
option.element = element;
|
35606
35752
|
element.disabled = option.disabled;
|
35607
|
-
|
35753
|
+
// NOTE: The label must be set before the value, otherwise IE10/11/EDGE create unresponsive
|
35754
|
+
// selects in certain circumstances when multiple selects are next to each other and display
|
35755
|
+
// the option list in listbox style, i.e. the select is [multiple], or specifies a [size].
|
35756
|
+
// See https://github.com/angular/angular.js/issues/11314 for more info.
|
35757
|
+
// This is unfortunately untestable with unit / e2e tests
|
35608
35758
|
if (option.label !== element.label) {
|
35609
35759
|
element.label = option.label;
|
35610
35760
|
element.textContent = option.label;
|
35611
35761
|
}
|
35762
|
+
if (option.value !== element.value) element.value = option.selectValue;
|
35612
35763
|
}
|
35613
35764
|
|
35614
35765
|
function addOrReuseElement(parent, current, type, templateElement) {
|
@@ -35649,7 +35800,10 @@ var ngOptionsDirective = ['$compile', '$parse', function($compile, $parse) {
|
|
35649
35800
|
if (emptyOption_ || unknownOption_) {
|
35650
35801
|
while (current &&
|
35651
35802
|
(current === emptyOption_ ||
|
35652
|
-
current === unknownOption_
|
35803
|
+
current === unknownOption_ ||
|
35804
|
+
emptyOption_ && emptyOption_.nodeType === NODE_TYPE_COMMENT)) {
|
35805
|
+
// Empty options might have directives that transclude
|
35806
|
+
// and insert comments (e.g. ngIf)
|
35653
35807
|
current = current.nextSibling;
|
35654
35808
|
}
|
35655
35809
|
}
|
@@ -36011,8 +36165,10 @@ var ngPluralizeDirective = ['$locale', '$interpolate', '$log', function($locale,
|
|
36011
36165
|
* | `$even` | {@type boolean} | true if the iterator position `$index` is even (otherwise false). |
|
36012
36166
|
* | `$odd` | {@type boolean} | true if the iterator position `$index` is odd (otherwise false). |
|
36013
36167
|
*
|
36014
|
-
*
|
36015
|
-
*
|
36168
|
+
* <div class="alert alert-info">
|
36169
|
+
* Creating aliases for these properties is possible with {@link ng.directive:ngInit `ngInit`}.
|
36170
|
+
* This may be useful when, for instance, nesting ngRepeats.
|
36171
|
+
* </div>
|
36016
36172
|
*
|
36017
36173
|
*
|
36018
36174
|
* # Iterating over object properties
|
@@ -36246,7 +36402,6 @@ var ngPluralizeDirective = ['$locale', '$interpolate', '$log', function($locale,
|
|
36246
36402
|
.animate-repeat.ng-move,
|
36247
36403
|
.animate-repeat.ng-enter,
|
36248
36404
|
.animate-repeat.ng-leave {
|
36249
|
-
-webkit-transition:all linear 0.5s;
|
36250
36405
|
transition:all linear 0.5s;
|
36251
36406
|
}
|
36252
36407
|
|
@@ -36418,7 +36573,7 @@ var ngRepeatDirective = ['$parse', '$animate', function($parse, $animate) {
|
|
36418
36573
|
// if object, extract keys, in enumeration order, unsorted
|
36419
36574
|
collectionKeys = [];
|
36420
36575
|
for (var itemKey in collection) {
|
36421
|
-
if (
|
36576
|
+
if (hasOwnProperty.call(collection, itemKey) && itemKey.charAt(0) !== '$') {
|
36422
36577
|
collectionKeys.push(itemKey);
|
36423
36578
|
}
|
36424
36579
|
}
|
@@ -36643,9 +36798,7 @@ var NG_HIDE_IN_PROGRESS_CLASS = 'ng-hide-animate';
|
|
36643
36798
|
background: white;
|
36644
36799
|
}
|
36645
36800
|
|
36646
|
-
.animate-show.ng-hide-add.ng-hide-
|
36647
|
-
.animate-show.ng-hide-remove.ng-hide-remove-active {
|
36648
|
-
-webkit-transition: all linear 0.5s;
|
36801
|
+
.animate-show.ng-hide-add, .animate-show.ng-hide-remove {
|
36649
36802
|
transition: all linear 0.5s;
|
36650
36803
|
}
|
36651
36804
|
|
@@ -36802,7 +36955,6 @@ var ngShowDirective = ['$animate', function($animate) {
|
|
36802
36955
|
</file>
|
36803
36956
|
<file name="animations.css">
|
36804
36957
|
.animate-hide {
|
36805
|
-
-webkit-transition: all linear 0.5s;
|
36806
36958
|
transition: all linear 0.5s;
|
36807
36959
|
line-height: 20px;
|
36808
36960
|
opacity: 1;
|
@@ -37001,7 +37153,6 @@ var ngStyleDirective = ngDirective(function(scope, element, attr) {
|
|
37001
37153
|
}
|
37002
37154
|
|
37003
37155
|
.animate-switch.ng-animate {
|
37004
|
-
-webkit-transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;
|
37005
37156
|
transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;
|
37006
37157
|
|
37007
37158
|
position:absolute;
|
@@ -37342,31 +37493,162 @@ var SelectController =
|
|
37342
37493
|
* @description
|
37343
37494
|
* HTML `SELECT` element with angular data-binding.
|
37344
37495
|
*
|
37345
|
-
*
|
37346
|
-
*
|
37347
|
-
*
|
37348
|
-
*
|
37349
|
-
* comprehension expression.
|
37496
|
+
* The `select` directive is used together with {@link ngModel `ngModel`} to provide data-binding
|
37497
|
+
* between the scope and the `<select>` control (including setting default values).
|
37498
|
+
* Ìt also handles dynamic `<option>` elements, which can be added using the {@link ngRepeat `ngRepeat}` or
|
37499
|
+
* {@link ngOptions `ngOptions`} directives.
|
37350
37500
|
*
|
37351
|
-
* When an item in the `<select>` menu is selected, the
|
37352
|
-
*
|
37353
|
-
*
|
37501
|
+
* When an item in the `<select>` menu is selected, the value of the selected option will be bound
|
37502
|
+
* to the model identified by the `ngModel` directive. With static or repeated options, this is
|
37503
|
+
* the content of the `value` attribute or the textContent of the `<option>`, if the value attribute is missing.
|
37504
|
+
* If you want dynamic value attributes, you can use interpolation inside the value attribute.
|
37354
37505
|
*
|
37355
|
-
*
|
37356
|
-
*
|
37506
|
+
* <div class="alert alert-warning">
|
37507
|
+
* Note that the value of a `select` directive used without `ngOptions` is always a string.
|
37508
|
+
* When the model needs to be bound to a non-string value, you must either explictly convert it
|
37509
|
+
* using a directive (see example below) or use `ngOptions` to specify the set of options.
|
37510
|
+
* This is because an option element can only be bound to string values at present.
|
37511
|
+
* </div>
|
37512
|
+
*
|
37513
|
+
* If the viewValue of `ngModel` does not match any of the options, then the control
|
37514
|
+
* will automatically add an "unknown" option, which it then removes when the mismatch is resolved.
|
37357
37515
|
*
|
37358
37516
|
* Optionally, a single hard-coded `<option>` element, with the value set to an empty string, can
|
37359
37517
|
* be nested into the `<select>` element. This element will then represent the `null` or "not selected"
|
37360
37518
|
* option. See example below for demonstration.
|
37361
37519
|
*
|
37362
37520
|
* <div class="alert alert-info">
|
37363
|
-
*
|
37364
|
-
*
|
37365
|
-
*
|
37366
|
-
*
|
37521
|
+
* In many cases, `ngRepeat` can be used on `<option>` elements instead of {@link ng.directive:ngOptions
|
37522
|
+
* ngOptions} to achieve a similar result. However, `ngOptions` provides some benefits, such as
|
37523
|
+
* more flexibility in how the `<select>`'s model is assigned via the `select` **`as`** part of the
|
37524
|
+
* comprehension expression, and additionally in reducing memory and increasing speed by not creating
|
37525
|
+
* a new scope for each repeated instance.
|
37526
|
+
* </div>
|
37527
|
+
*
|
37528
|
+
*
|
37529
|
+
* @param {string} ngModel Assignable angular expression to data-bind to.
|
37530
|
+
* @param {string=} name Property name of the form under which the control is published.
|
37531
|
+
* @param {string=} required Sets `required` validation error key if the value is not entered.
|
37532
|
+
* @param {string=} ngRequired Adds required attribute and required validation constraint to
|
37533
|
+
* the element when the ngRequired expression evaluates to true. Use ngRequired instead of required
|
37534
|
+
* when you want to data-bind to the required attribute.
|
37535
|
+
* @param {string=} ngChange Angular expression to be executed when selected option(s) changes due to user
|
37536
|
+
* interaction with the select element.
|
37537
|
+
* @param {string=} ngOptions sets the options that the select is populated with and defines what is
|
37538
|
+
* set on the model on selection. See {@link ngOptions `ngOptions`}.
|
37539
|
+
*
|
37540
|
+
* @example
|
37541
|
+
* ### Simple `select` elements with static options
|
37542
|
+
*
|
37543
|
+
* <example name="static-select" module="staticSelect">
|
37544
|
+
* <file name="index.html">
|
37545
|
+
* <div ng-controller="ExampleController">
|
37546
|
+
* <form name="myForm">
|
37547
|
+
* <label for="singleSelect"> Single select: </label><br>
|
37548
|
+
* <select name="singleSelect" ng-model="data.singleSelect">
|
37549
|
+
* <option value="option-1">Option 1</option>
|
37550
|
+
* <option value="option-2">Option 2</option>
|
37551
|
+
* </select><br>
|
37552
|
+
*
|
37553
|
+
* <label for="singleSelect"> Single select with "not selected" option and dynamic option values: </label><br>
|
37554
|
+
* <select name="singleSelect" id="singleSelect" ng-model="data.singleSelect">
|
37555
|
+
* <option value="">---Please select---</option> <!-- not selected / blank option -->
|
37556
|
+
* <option value="{{data.option1}}">Option 1</option> <!-- interpolation -->
|
37557
|
+
* <option value="option-2">Option 2</option>
|
37558
|
+
* </select><br>
|
37559
|
+
* <button ng-click="forceUnknownOption()">Force unknown option</button><br>
|
37560
|
+
* <tt>singleSelect = {{data.singleSelect}}</tt>
|
37561
|
+
*
|
37562
|
+
* <hr>
|
37563
|
+
* <label for="multipleSelect"> Multiple select: </label><br>
|
37564
|
+
* <select name="multipleSelect" id="multipleSelect" ng-model="data.multipleSelect" multiple>
|
37565
|
+
* <option value="option-1">Option 1</option>
|
37566
|
+
* <option value="option-2">Option 2</option>
|
37567
|
+
* <option value="option-3">Option 3</option>
|
37568
|
+
* </select><br>
|
37569
|
+
* <tt>multipleSelect = {{data.multipleSelect}}</tt><br/>
|
37570
|
+
* </form>
|
37571
|
+
* </div>
|
37572
|
+
* </file>
|
37573
|
+
* <file name="app.js">
|
37574
|
+
* angular.module('staticSelect', [])
|
37575
|
+
* .controller('ExampleController', ['$scope', function($scope) {
|
37576
|
+
* $scope.data = {
|
37577
|
+
* singleSelect: null,
|
37578
|
+
* multipleSelect: [],
|
37579
|
+
* option1: 'option-1',
|
37580
|
+
* };
|
37581
|
+
*
|
37582
|
+
* $scope.forceUnknownOption = function() {
|
37583
|
+
* $scope.data.singleSelect = 'nonsense';
|
37584
|
+
* };
|
37585
|
+
* }]);
|
37586
|
+
* </file>
|
37587
|
+
*</example>
|
37588
|
+
*
|
37589
|
+
* ### Using `ngRepeat` to generate `select` options
|
37590
|
+
* <example name="ngrepeat-select" module="ngrepeatSelect">
|
37591
|
+
* <file name="index.html">
|
37592
|
+
* <div ng-controller="ExampleController">
|
37593
|
+
* <form name="myForm">
|
37594
|
+
* <label for="repeatSelect"> Repeat select: </label>
|
37595
|
+
* <select name="repeatSelect" id="repeatSelect" ng-model="data.repeatSelect">
|
37596
|
+
* <option ng-repeat="option in data.availableOptions" value="{{option.id}}">{{option.name}}</option>
|
37597
|
+
* </select>
|
37598
|
+
* </form>
|
37599
|
+
* <hr>
|
37600
|
+
* <tt>repeatSelect = {{data.repeatSelect}}</tt><br/>
|
37367
37601
|
* </div>
|
37602
|
+
* </file>
|
37603
|
+
* <file name="app.js">
|
37604
|
+
* angular.module('ngrepeatSelect', [])
|
37605
|
+
* .controller('ExampleController', ['$scope', function($scope) {
|
37606
|
+
* $scope.data = {
|
37607
|
+
* repeatSelect: null,
|
37608
|
+
* availableOptions: [
|
37609
|
+
* {id: '1', name: 'Option A'},
|
37610
|
+
* {id: '2', name: 'Option B'},
|
37611
|
+
* {id: '3', name: 'Option C'}
|
37612
|
+
* ],
|
37613
|
+
* };
|
37614
|
+
* }]);
|
37615
|
+
* </file>
|
37616
|
+
*</example>
|
37368
37617
|
*
|
37369
|
-
*
|
37618
|
+
*
|
37619
|
+
* ### Using `select` with `ngOptions` and setting a default value
|
37620
|
+
* See the {@link ngOptions ngOptions documentation} for more `ngOptions` usage examples.
|
37621
|
+
*
|
37622
|
+
* <example name="select-with-default-values" module="defaultValueSelect">
|
37623
|
+
* <file name="index.html">
|
37624
|
+
* <div ng-controller="ExampleController">
|
37625
|
+
* <form name="myForm">
|
37626
|
+
* <label for="mySelect">Make a choice:</label>
|
37627
|
+
* <select name="mySelect" id="mySelect"
|
37628
|
+
* ng-options="option.name for option in data.availableOptions track by option.id"
|
37629
|
+
* ng-model="data.selectedOption"></select>
|
37630
|
+
* </form>
|
37631
|
+
* <hr>
|
37632
|
+
* <tt>option = {{data.selectedOption}}</tt><br/>
|
37633
|
+
* </div>
|
37634
|
+
* </file>
|
37635
|
+
* <file name="app.js">
|
37636
|
+
* angular.module('defaultValueSelect', [])
|
37637
|
+
* .controller('ExampleController', ['$scope', function($scope) {
|
37638
|
+
* $scope.data = {
|
37639
|
+
* availableOptions: [
|
37640
|
+
* {id: '1', name: 'Option A'},
|
37641
|
+
* {id: '2', name: 'Option B'},
|
37642
|
+
* {id: '3', name: 'Option C'}
|
37643
|
+
* ],
|
37644
|
+
* selectedOption: {id: '3', name: 'Option C'} //This sets the default value of the select in the ui
|
37645
|
+
* };
|
37646
|
+
* }]);
|
37647
|
+
* </file>
|
37648
|
+
*</example>
|
37649
|
+
*
|
37650
|
+
*
|
37651
|
+
* ### Binding `select` to a non-string value via `ngModel` parsing / formatting
|
37370
37652
|
*
|
37371
37653
|
* <example name="select-with-non-string-options" module="nonStringSelect">
|
37372
37654
|
* <file name="index.html">
|
@@ -37504,9 +37786,12 @@ var optionDirective = ['$interpolate', function($interpolate) {
|
|
37504
37786
|
priority: 100,
|
37505
37787
|
compile: function(element, attr) {
|
37506
37788
|
|
37507
|
-
|
37508
|
-
|
37509
|
-
|
37789
|
+
if (isDefined(attr.value)) {
|
37790
|
+
// If the value attribute is defined, check if it contains an interpolation
|
37791
|
+
var valueInterpolated = $interpolate(attr.value, true);
|
37792
|
+
} else {
|
37793
|
+
// If the value attribute is not defined then we fall back to the
|
37794
|
+
// text content of the option element, which may be interpolated
|
37510
37795
|
var interpolateFn = $interpolate(element.text(), true);
|
37511
37796
|
if (!interpolateFn) {
|
37512
37797
|
attr.$set('value', element.text());
|
@@ -37522,24 +37807,38 @@ var optionDirective = ['$interpolate', function($interpolate) {
|
|
37522
37807
|
selectCtrl = parent.data(selectCtrlName) ||
|
37523
37808
|
parent.parent().data(selectCtrlName); // in case we are in optgroup
|
37524
37809
|
|
37810
|
+
function addOption(optionValue) {
|
37811
|
+
selectCtrl.addOption(optionValue, element);
|
37812
|
+
selectCtrl.ngModelCtrl.$render();
|
37813
|
+
chromeHack(element);
|
37814
|
+
}
|
37815
|
+
|
37525
37816
|
// Only update trigger option updates if this is an option within a `select`
|
37526
37817
|
// that also has `ngModel` attached
|
37527
37818
|
if (selectCtrl && selectCtrl.ngModelCtrl) {
|
37528
37819
|
|
37529
|
-
if (
|
37820
|
+
if (valueInterpolated) {
|
37821
|
+
// The value attribute is interpolated
|
37822
|
+
var oldVal;
|
37823
|
+
attr.$observe('value', function valueAttributeObserveAction(newVal) {
|
37824
|
+
if (isDefined(oldVal)) {
|
37825
|
+
selectCtrl.removeOption(oldVal);
|
37826
|
+
}
|
37827
|
+
oldVal = newVal;
|
37828
|
+
addOption(newVal);
|
37829
|
+
});
|
37830
|
+
} else if (interpolateFn) {
|
37831
|
+
// The text content is interpolated
|
37530
37832
|
scope.$watch(interpolateFn, function interpolateWatchAction(newVal, oldVal) {
|
37531
37833
|
attr.$set('value', newVal);
|
37532
37834
|
if (oldVal !== newVal) {
|
37533
37835
|
selectCtrl.removeOption(oldVal);
|
37534
37836
|
}
|
37535
|
-
|
37536
|
-
selectCtrl.ngModelCtrl.$render();
|
37537
|
-
chromeHack(element);
|
37837
|
+
addOption(newVal);
|
37538
37838
|
});
|
37539
37839
|
} else {
|
37540
|
-
|
37541
|
-
|
37542
|
-
chromeHack(element);
|
37840
|
+
// The value attribute is static
|
37841
|
+
addOption(attr.value);
|
37543
37842
|
}
|
37544
37843
|
|
37545
37844
|
element.on('$destroy', function() {
|
@@ -37600,8 +37899,9 @@ var patternDirective = function() {
|
|
37600
37899
|
ctrl.$validate();
|
37601
37900
|
});
|
37602
37901
|
|
37603
|
-
ctrl.$validators.pattern = function(
|
37604
|
-
|
37902
|
+
ctrl.$validators.pattern = function(modelValue, viewValue) {
|
37903
|
+
// HTML5 pattern constraint validates the input value, so we validate the viewValue
|
37904
|
+
return ctrl.$isEmpty(viewValue) || isUndefined(regexp) || regexp.test(viewValue);
|
37605
37905
|
};
|
37606
37906
|
}
|
37607
37907
|
};
|
@@ -38079,7 +38379,7 @@ _jQuery.fn.bindings = function(windowJquery, bindExp) {
|
|
38079
38379
|
}
|
38080
38380
|
|
38081
38381
|
function push(value) {
|
38082
|
-
if (value
|
38382
|
+
if (angular.isUndefined(value)) {
|
38083
38383
|
value = '';
|
38084
38384
|
} else if (typeof value !== 'string') {
|
38085
38385
|
value = angular.toJson(value);
|