You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@aurora.apache.org by ma...@apache.org on 2014/05/28 21:27:16 UTC
[05/10] Added tabs for active and completed tasks in Job page.
http://git-wip-us.apache.org/repos/asf/incubator-aurora/blob/b6c71cc0/3rdparty/javascript/bower_components/angular/angular.js
----------------------------------------------------------------------
diff --git a/3rdparty/javascript/bower_components/angular/angular.js b/3rdparty/javascript/bower_components/angular/angular.js
index d4d7abc..197110e 100644
--- a/3rdparty/javascript/bower_components/angular/angular.js
+++ b/3rdparty/javascript/bower_components/angular/angular.js
@@ -1,5 +1,5 @@
/**
- * @license AngularJS v1.2.6
+ * @license AngularJS v1.2.9
* (c) 2010-2014 Google, Inc. http://angularjs.org
* License: MIT
*/
@@ -68,7 +68,7 @@ function minErr(module) {
return match;
});
- message = message + '\nhttp://errors.angularjs.org/1.2.6/' +
+ message = message + '\nhttp://errors.angularjs.org/1.2.9/' +
(module ? module + '/' : '') + code;
for (i = 2; i < arguments.length; i++) {
message = message + (i == 2 ? '?' : '&') + 'p' + (i-2) + '=' +
@@ -271,7 +271,8 @@ function isArrayLike(obj) {
* is the value of an object property or an array element and `key` is the object property key or
* array element index. Specifying a `context` for the function is optional.
*
- * Note: this function was previously known as `angular.foreach`.
+ * It is worth nothing that `.forEach` does not iterate over inherited properties because it filters
+ * using the `hasOwnProperty` method.
*
<pre>
var values = {name: 'misko', gender: 'male'};
@@ -1038,7 +1039,9 @@ function fromJson(json) {
function toBoolean(value) {
- if (value && value.length !== 0) {
+ if (typeof value === 'function') {
+ value = true;
+ } else if (value && value.length !== 0) {
var v = lowercase("" + value);
value = !(v == 'f' || v == '0' || v == 'false' || v == 'no' || v == 'n' || v == '[]');
} else {
@@ -1831,11 +1834,11 @@ function setupModuleLoader(window) {
* - `codeName` – `{string}` – Code name of the release, such as "jiggling-armfat".
*/
var version = {
- full: '1.2.6', // all of these placeholder strings will be replaced by grunt's
+ full: '1.2.9', // all of these placeholder strings will be replaced by grunt's
major: 1, // package task
minor: 2,
- dot: 6,
- codeName: 'taco-salsafication'
+ dot: 9,
+ codeName: 'enchanted-articulacy'
};
@@ -3397,7 +3400,7 @@ function annotate(fn) {
* constructor function that will be used to instantiate the service instance.
*
* You should use {@link AUTO.$provide#methods_service $provide.service(class)} if you define your service
- * as a type/class. This is common when using {@link http://coffeescript.org CoffeeScript}.
+ * as a type/class.
*
* @param {string} name The name of the instance.
* @param {Function} constructor A class (constructor function) that will be instantiated.
@@ -3405,20 +3408,25 @@ function annotate(fn) {
*
* @example
* Here is an example of registering a service using
- * {@link AUTO.$provide#methods_service $provide.service(class)} that is defined as a CoffeeScript class.
+ * {@link AUTO.$provide#methods_service $provide.service(class)}.
* <pre>
- * class Ping
- * constructor: (@$http) ->
- * send: () =>
- * @$http.get('/ping')
- *
- * $provide.service('ping', ['$http', Ping])
+ * $provide.service('ping', ['$http', function($http) {
+ * var Ping = function() {
+ * this.$http = $http;
+ * };
+ *
+ * Ping.prototype.send = function() {
+ * return this.$http.get('/ping');
+ * };
+ *
+ * return Ping;
+ * }]);
* </pre>
* You would then inject and use this service like this:
* <pre>
- * someModule.controller 'Ctrl', ['ping', (ping) ->
- * ping.send()
- * ]
+ * someModule.controller('Ctrl', ['ping', function(ping) {
+ * ping.send();
+ * }]);
* </pre>
*/
@@ -3663,6 +3671,11 @@ function createInjector(modulesToLoad) {
path.unshift(serviceName);
cache[serviceName] = INSTANTIATING;
return cache[serviceName] = factory(serviceName);
+ } catch (err) {
+ if (cache[serviceName] === INSTANTIATING) {
+ delete cache[serviceName];
+ }
+ throw err;
} finally {
path.shift();
}
@@ -4197,8 +4210,9 @@ function Browser(window, document, $log, $sniffer) {
* @param {boolean=} replace Should new url replace current history record ?
*/
self.url = function(url, replace) {
- // Android Browser BFCache causes location reference to become stale.
+ // Android Browser BFCache causes location, history reference to become stale.
if (location !== window.location) location = window.location;
+ if (history !== window.history) history = window.history;
// setter
if (url) {
@@ -4250,7 +4264,7 @@ function Browser(window, document, $log, $sniffer) {
* @description
* Register callback function that will be called, when url changes.
*
- * It's only called when the url is changed by outside of angular:
+ * It's only called when the url is changed from outside of angular:
* - user types different url into address bar
* - user clicks on history (forward/back) button
* - user clicks on a link
@@ -4292,7 +4306,7 @@ function Browser(window, document, $log, $sniffer) {
/**
* @name ng.$browser#baseHref
* @methodOf ng.$browser
- *
+ *
* @description
* Returns current <base href>
* (always relative - without domain)
@@ -4301,7 +4315,7 @@ function Browser(window, document, $log, $sniffer) {
*/
self.baseHref = function() {
var href = baseElement.attr('href');
- return href ? href.replace(/^https?\:\/\/[^\/]*/, '') : '';
+ return href ? href.replace(/^(https?\:)?\/\/[^\/]*/, '') : '';
};
//////////////////////////////////////////////////////////////
@@ -4323,13 +4337,13 @@ function Browser(window, document, $log, $sniffer) {
* It is not meant to be used directly, use the $cookie service instead.
*
* The return values vary depending on the arguments that the method was called with as follows:
- *
+ *
* - cookies() -> hash of all cookies, this is NOT a copy of the internal state, so do not modify
* it
* - cookies(name, value) -> set name to value, if value is undefined delete the cookie
* - cookies(name) -> the same as (name, undefined) == DELETES (no one calls it right now that
* way)
- *
+ *
* @returns {Object} Hash of all cookies (if called without any parameter)
*/
self.cookies = function(name, value) {
@@ -4707,7 +4721,7 @@ function $TemplateCacheProvider() {
* @function
*
* @description
- * Compiles a piece of HTML string or DOM into a template and produces a template function, which
+ * Compiles an HTML string or DOM into a template and produces a template function, which
* can then be used to link {@link ng.$rootScope.Scope `scope`} and the template together.
*
* The compilation is a process of walking the DOM tree and matching DOM elements to
@@ -6640,7 +6654,7 @@ function directiveNormalize(name) {
*
*
* @param {string} name Normalized element attribute name of the property to modify. The name is
- * revers translated using the {@link ng.$compile.directive.Attributes#$attr $attr}
+ * reverse-translated using the {@link ng.$compile.directive.Attributes#$attr $attr}
* property to the original name.
* @param {string} value Value to set the attribute to. The value can be an interpolated string.
*/
@@ -6778,8 +6792,7 @@ function $ControllerProvider() {
* @requires $window
*
* @description
- * A {@link angular.element jQuery (lite)}-wrapped reference to the browser's `window.document`
- * element.
+ * A {@link angular.element jQuery or jqLite} wrapper for the browser's `window.document` object.
*/
function $DocumentProvider(){
this.$get = ['$window', function(window){
@@ -6938,9 +6951,9 @@ function $HttpProvider() {
common: {
'Accept': 'application/json, text/plain, */*'
},
- post: CONTENT_TYPE_APPLICATION_JSON,
- put: CONTENT_TYPE_APPLICATION_JSON,
- patch: CONTENT_TYPE_APPLICATION_JSON
+ post: copy(CONTENT_TYPE_APPLICATION_JSON),
+ put: copy(CONTENT_TYPE_APPLICATION_JSON),
+ patch: copy(CONTENT_TYPE_APPLICATION_JSON)
},
xsrfCookieName: 'XSRF-TOKEN',
@@ -7049,7 +7062,7 @@ function $HttpProvider() {
* will result in the success callback being called. Note that if the response is a redirect,
* XMLHttpRequest will transparently follow it, meaning that the error callback will not be
* called for such responses.
- *
+ *
* # Calling $http from outside AngularJS
* The `$http` service will not actually send the request until the next `$digest()` is
* executed. Normally this is not an issue, since almost all the time your call to `$http` will
@@ -7118,7 +7131,15 @@ function $HttpProvider() {
* `$httpProvider.defaults.headers.get = { 'My-Header' : 'value' }.
*
* The defaults can also be set at runtime via the `$http.defaults` object in the same
- * fashion. In addition, you can supply a `headers` property in the config object passed when
+ * fashion. For example:
+ *
+ * ```
+ * module.run(function($http) {
+ * $http.defaults.headers.common.Authentication = 'Basic YmVlcDpib29w'
+ * });
+ * ```
+ *
+ * In addition, you can supply a `headers` property in the config object passed when
* calling `$http(config)`, which overrides the defaults without changing them globally.
*
*
@@ -7142,7 +7163,9 @@ function $HttpProvider() {
* properties. These properties are by default an array of transform functions, which allows you
* to `push` or `unshift` a new transformation function into the transformation chain. You can
* also decide to completely override any default transformations by assigning your
- * transformation functions to these properties directly without the array wrapper.
+ * transformation functions to these properties directly without the array wrapper. These defaults
+ * are again available on the $http factory at run-time, which may be useful if you have run-time
+ * services you wish to be involved in your transformations.
*
* Similarly, to locally override the request/response transforms, augment the
* `transformRequest` and/or `transformResponse` properties of the configuration object passed
@@ -7236,19 +7259,20 @@ function $HttpProvider() {
* return responseOrNewPromise
* }
* return $q.reject(rejection);
- * };
- * }
+ * }
+ * };
* });
*
* $httpProvider.interceptors.push('myHttpInterceptor');
*
*
- * // register the interceptor via an anonymous factory
+ * // alternatively, register the interceptor via an anonymous factory
* $httpProvider.interceptors.push(function($q, dependency1, dependency2) {
* return {
* 'request': function(config) {
* // same as above
* },
+ *
* 'response': function(response) {
* // same as above
* }
@@ -7355,7 +7379,8 @@ function $HttpProvider() {
* for added security.
*
* The name of the headers can be specified using the xsrfHeaderName and xsrfCookieName
- * properties of either $httpProvider.defaults, or the per-request config object.
+ * properties of either $httpProvider.defaults at config-time, $http.defaults at run-time,
+ * or the per-request config object.
*
*
* @param {object} config Object describing the request to be made and how it should be
@@ -7864,13 +7889,13 @@ function $HttpProvider() {
}];
}
-var XHR = window.XMLHttpRequest || function() {
+function createXhr(method) {
+ // IE8 doesn't support PATCH method, but the ActiveX object does
/* global ActiveXObject */
- try { return new ActiveXObject("Msxml2.XMLHTTP.6.0"); } catch (e1) {}
- try { return new ActiveXObject("Msxml2.XMLHTTP.3.0"); } catch (e2) {}
- try { return new ActiveXObject("Msxml2.XMLHTTP"); } catch (e3) {}
- throw minErr('$httpBackend')('noxhr', "This browser does not support XMLHttpRequest.");
-};
+ return (msie <= 8 && lowercase(method) === 'patch')
+ ? new ActiveXObject('Microsoft.XMLHTTP')
+ : new window.XMLHttpRequest();
+}
/**
@@ -7892,11 +7917,11 @@ var XHR = window.XMLHttpRequest || function() {
*/
function $HttpBackendProvider() {
this.$get = ['$browser', '$window', '$document', function($browser, $window, $document) {
- return createHttpBackend($browser, XHR, $browser.defer, $window.angular.callbacks, $document[0]);
+ return createHttpBackend($browser, createXhr, $browser.defer, $window.angular.callbacks, $document[0]);
}];
}
-function createHttpBackend($browser, XHR, $browserDefer, callbacks, rawDocument) {
+function createHttpBackend($browser, createXhr, $browserDefer, callbacks, rawDocument) {
var ABORTED = -1;
// TODO(vojta): fix the signature
@@ -7918,10 +7943,12 @@ function createHttpBackend($browser, XHR, $browserDefer, callbacks, rawDocument)
} else {
completeRequest(callback, status || -2);
}
- delete callbacks[callbackId];
+ callbacks[callbackId] = angular.noop;
});
} else {
- var xhr = new XHR();
+
+ var xhr = createXhr(method);
+
xhr.open(method, url, true);
forEach(headers, function(value, key) {
if (isDefined(value)) {
@@ -7933,17 +7960,25 @@ function createHttpBackend($browser, XHR, $browserDefer, callbacks, rawDocument)
// response is in the cache. the promise api will ensure that to the app code the api is
// always async
xhr.onreadystatechange = function() {
- if (xhr.readyState == 4) {
+ // onreadystatechange might get called multiple times with readyState === 4 on mobile webkit caused by
+ // xhrs that are resolved while the app is in the background (see #5426).
+ // since calling completeRequest sets the `xhr` variable to null, we just check if it's not null before
+ // continuing
+ //
+ // we can't set xhr.onreadystatechange to undefined or delete it because that breaks IE8 (method=PATCH) and
+ // Safari respectively.
+ if (xhr && xhr.readyState == 4) {
var responseHeaders = null,
response = null;
if(status !== ABORTED) {
responseHeaders = xhr.getAllResponseHeaders();
- response = xhr.responseType ? xhr.response : xhr.responseText;
+
+ // responseText is the old-school way of retrieving response (supported by IE8 & 9)
+ // response/responseType properties were introduced in XHR Level2 spec (supported by IE10)
+ response = ('response' in xhr) ? xhr.response : xhr.responseText;
}
- // responseText is the old-school way of retrieving response (supported by IE8 & 9)
- // response/responseType properties were introduced in XHR Level2 spec (supported by IE10)
completeRequest(callback,
status || xhr.status,
response,
@@ -7976,14 +8011,14 @@ function createHttpBackend($browser, XHR, $browserDefer, callbacks, rawDocument)
}
function completeRequest(callback, status, response, headersString) {
- var protocol = urlResolve(url).protocol;
-
// cancel timeout and subsequent timeout promise resolution
timeoutId && $browserDefer.cancel(timeoutId);
jsonpDone = xhr = null;
- // fix status code for file protocol (it's always 0)
- status = (protocol == 'file' && status === 0) ? (response ? 200 : 404) : status;
+ // fix status code when it is 0 (0 status is undocumented).
+ // Occurs when accessing file resources.
+ // On Android 4.1 stock browser it occurs while retrieving files from application cache.
+ status = (status === 0) ? (response ? 200 : 404) : status;
// normalize IE bug (http://bugs.jquery.com/ticket/1450)
status = status == 1223 ? 204 : status;
@@ -9097,7 +9132,7 @@ function $LocationProvider(){
* Broadcasted before a URL will change. This change can be prevented by calling
* `preventDefault` method of the event. See {@link ng.$rootScope.Scope#$on} for more
* details about event object. Upon successful change
- * {@link ng.$location#$locationChangeSuccess $locationChangeSuccess} is fired.
+ * {@link ng.$location#events_$locationChangeSuccess $locationChangeSuccess} is fired.
*
* @param {Object} angularEvent Synthetic event object.
* @param {string} newUrl New URL
@@ -9180,16 +9215,17 @@ function $LocationProvider(){
// update $location when $browser url changes
$browser.onUrlChange(function(newUrl) {
if ($location.absUrl() != newUrl) {
- if ($rootScope.$broadcast('$locationChangeStart', newUrl,
- $location.absUrl()).defaultPrevented) {
- $browser.url($location.absUrl());
- return;
- }
$rootScope.$evalAsync(function() {
var oldUrl = $location.absUrl();
$location.$$parse(newUrl);
- afterLocationChange(oldUrl);
+ if ($rootScope.$broadcast('$locationChangeStart', newUrl,
+ oldUrl).defaultPrevented) {
+ $location.$$parse(oldUrl);
+ $browser.url(oldUrl);
+ } else {
+ afterLocationChange(oldUrl);
+ }
});
if (!$rootScope.$$phase) $rootScope.$digest();
}
@@ -10287,16 +10323,20 @@ function cspSafeGetterFn(key0, key1, key2, key3, key4, fullExp, options) {
if (pathVal == null) return pathVal;
pathVal = pathVal[key0];
- if (pathVal == null) return key1 ? undefined : pathVal;
+ if (!key1) return pathVal;
+ if (pathVal == null) return undefined;
pathVal = pathVal[key1];
- if (pathVal == null) return key2 ? undefined : pathVal;
+ if (!key2) return pathVal;
+ if (pathVal == null) return undefined;
pathVal = pathVal[key2];
- if (pathVal == null) return key3 ? undefined : pathVal;
+ if (!key3) return pathVal;
+ if (pathVal == null) return undefined;
pathVal = pathVal[key3];
- if (pathVal == null) return key4 ? undefined : pathVal;
+ if (!key4) return pathVal;
+ if (pathVal == null) return undefined;
pathVal = pathVal[key4];
return pathVal;
@@ -10317,8 +10357,9 @@ function cspSafeGetterFn(key0, key1, key2, key3, key4, fullExp, options) {
}
pathVal = pathVal.$$v;
}
- if (pathVal == null) return key1 ? undefined : pathVal;
+ if (!key1) return pathVal;
+ if (pathVal == null) return undefined;
pathVal = pathVal[key1];
if (pathVal && pathVal.then) {
promiseWarning(fullExp);
@@ -10329,8 +10370,9 @@ function cspSafeGetterFn(key0, key1, key2, key3, key4, fullExp, options) {
}
pathVal = pathVal.$$v;
}
- if (pathVal == null) return key2 ? undefined : pathVal;
+ if (!key2) return pathVal;
+ if (pathVal == null) return undefined;
pathVal = pathVal[key2];
if (pathVal && pathVal.then) {
promiseWarning(fullExp);
@@ -10341,8 +10383,9 @@ function cspSafeGetterFn(key0, key1, key2, key3, key4, fullExp, options) {
}
pathVal = pathVal.$$v;
}
- if (pathVal == null) return key3 ? undefined : pathVal;
+ if (!key3) return pathVal;
+ if (pathVal == null) return undefined;
pathVal = pathVal[key3];
if (pathVal && pathVal.then) {
promiseWarning(fullExp);
@@ -10353,8 +10396,9 @@ function cspSafeGetterFn(key0, key1, key2, key3, key4, fullExp, options) {
}
pathVal = pathVal.$$v;
}
- if (pathVal == null) return key4 ? undefined : pathVal;
+ if (!key4) return pathVal;
+ if (pathVal == null) return undefined;
pathVal = pathVal[key4];
if (pathVal && pathVal.then) {
promiseWarning(fullExp);
@@ -11299,6 +11343,7 @@ function $RootScopeProvider(){
this.$$asyncQueue = [];
this.$$postDigestQueue = [];
this.$$listeners = {};
+ this.$$listenerCount = {};
this.$$isolateBindings = {};
}
@@ -11351,13 +11396,14 @@ function $RootScopeProvider(){
} else {
ChildScope = function() {}; // should be anonymous; This is so that when the minifier munges
// the name it does not become random set of chars. This will then show up as class
- // name in the debugger.
+ // name in the web inspector.
ChildScope.prototype = this;
child = new ChildScope();
child.$id = nextUid();
}
child['this'] = child;
child.$$listeners = {};
+ child.$$listenerCount = {};
child.$parent = this;
child.$$watchers = child.$$nextSibling = child.$$childHead = child.$$childTail = null;
child.$$prevSibling = this.$$childTail;
@@ -11451,7 +11497,7 @@ function $RootScopeProvider(){
// No digest has been run so the counter will be zero
expect(scope.foodCounter).toEqual(0);
- // Run the digest but since food has not changed cout will still be zero
+ // Run the digest but since food has not changed count will still be zero
scope.$digest();
expect(scope.foodCounter).toEqual(0);
@@ -11517,6 +11563,7 @@ function $RootScopeProvider(){
return function() {
arrayRemove(array, watcher);
+ lastDirtyWatch = null;
};
},
@@ -11795,7 +11842,7 @@ function $RootScopeProvider(){
// `break traverseScopesLoop;` takes us to here
- if(dirty && !(ttl--)) {
+ if((dirty || asyncQueue.length) && !(ttl--)) {
clearPhase();
throw $rootScopeMinErr('infdig',
'{0} $digest() iterations reached. Aborting!\n' +
@@ -11862,6 +11909,8 @@ function $RootScopeProvider(){
this.$$destroyed = true;
if (this === $rootScope) return;
+ forEach(this.$$listenerCount, bind(null, decrementListenerCount, this));
+
if (parent.$$childHead == this) parent.$$childHead = this.$$nextSibling;
if (parent.$$childTail == this) parent.$$childTail = this.$$prevSibling;
if (this.$$prevSibling) this.$$prevSibling.$$nextSibling = this.$$nextSibling;
@@ -12051,8 +12100,18 @@ function $RootScopeProvider(){
}
namedListeners.push(listener);
+ var current = this;
+ do {
+ if (!current.$$listenerCount[name]) {
+ current.$$listenerCount[name] = 0;
+ }
+ current.$$listenerCount[name]++;
+ } while ((current = current.$parent));
+
+ var self = this;
return function() {
namedListeners[indexOf(namedListeners, listener)] = null;
+ decrementListenerCount(self, 1, name);
};
},
@@ -12164,8 +12223,7 @@ function $RootScopeProvider(){
listeners, i, length;
//down while you can, then up and next sibling or up and next sibling until back at root
- do {
- current = next;
+ while ((current = next)) {
event.currentScope = current;
listeners = current.$$listeners[name] || [];
for (i=0, length = listeners.length; i<length; i++) {
@@ -12187,12 +12245,14 @@ function $RootScopeProvider(){
// Insanity Warning: scope depth-first traversal
// yes, this code is a bit crazy, but it works and we have tests to prove it!
// this piece should be kept in sync with the traversal in $digest
- if (!(next = (current.$$childHead || (current !== target && current.$$nextSibling)))) {
+ // (though it differs due to having the extra check for $$listenerCount)
+ if (!(next = ((current.$$listenerCount[name] && current.$$childHead) ||
+ (current !== target && current.$$nextSibling)))) {
while(current !== target && !(next = current.$$nextSibling)) {
current = current.$parent;
}
}
- } while ((current = next));
+ }
return event;
}
@@ -12221,6 +12281,16 @@ function $RootScopeProvider(){
return fn;
}
+ function decrementListenerCount(current, count, name) {
+ do {
+ current.$$listenerCount[name] -= count;
+
+ if (current.$$listenerCount[name] === 0) {
+ delete current.$$listenerCount[name];
+ }
+ } while ((current = current.$parent));
+ }
+
/**
* function used as an initial value for watchers.
* because it's unique we can easily tell it apart from other values
@@ -12623,7 +12693,7 @@ function $SceDelegateProvider() {
*
* @param {*} value The result of a prior {@link ng.$sceDelegate#methods_trustAs `$sceDelegate.trustAs`}
* call or anything else.
- * @returns {*} The value the was originally provided to {@link ng.$sceDelegate#methods_trustAs
+ * @returns {*} The `value` that was originally provided to {@link ng.$sceDelegate#methods_trustAs
* `$sceDelegate.trustAs`} if `value` is the result of such a call. Otherwise, returns
* `value` unchanged.
*/
@@ -13439,7 +13509,7 @@ function $SnifferProvider() {
// http://code.google.com/p/android/issues/detail?id=17471
// https://github.com/angular/angular.js/issues/904
- // older webit browser (533.9) on Boxee box has exactly the same problem as Android has
+ // older webkit browser (533.9) on Boxee box has exactly the same problem as Android has
// so let's not use the history API also
// We are purposefully using `!(android < 4)` to cover the case when `android` is undefined
// jshint -W018
@@ -13850,8 +13920,8 @@ function $FilterProvider($provide) {
*
* Can be one of:
*
- * - `string`: Predicate that results in a substring match using the value of `expression`
- * string. All strings or objects with string properties in `array` that contain this string
+ * - `string`: The string is evaluated as an expression and the resulting value is used for substring match against
+ * the contents of the `array`. All strings or objects with string properties in `array` that contain this string
* will be returned. The predicate can be negated by prefixing the string with `!`.
*
* - `Object`: A pattern object can be used to filter specific properties on objects contained
@@ -13861,21 +13931,21 @@ function $FilterProvider($provide) {
* property of the object. That's equivalent to the simple substring match with a `string`
* as described above.
*
- * - `function`: A predicate function can be used to write arbitrary filters. The function is
+ * - `function(value)`: A predicate function can be used to write arbitrary filters. The function is
* called for each element of `array`. The final result is an array of those elements that
* the predicate returned true for.
*
- * @param {function(expected, actual)|true|undefined} comparator Comparator which is used in
+ * @param {function(actual, expected)|true|undefined} comparator Comparator which is used in
* determining if the expected value (from the filter expression) and actual value (from
* the object in the array) should be considered a match.
*
* Can be one of:
*
- * - `function(expected, actual)`:
+ * - `function(actual, expected)`:
* The function will be given the object value and the predicate value to compare and
* should return true if the item should be included in filtered result.
*
- * - `true`: A shorthand for `function(expected, actual) { return angular.equals(expected, actual)}`.
+ * - `true`: A shorthand for `function(actual, expected) { return angular.equals(expected, actual)}`.
* this is essentially strict comparison of expected and actual.
*
* - `false|undefined`: A short hand for a function which will look for a substring match in case
@@ -14009,23 +14079,12 @@ function filterFilter() {
case "object":
// jshint +W086
for (var key in expression) {
- if (key == '$') {
- (function() {
- if (!expression[key]) return;
- var path = key;
- predicates.push(function(value) {
- return search(value, expression[path]);
- });
- })();
- } else {
- (function() {
- if (typeof(expression[key]) == 'undefined') { return; }
- var path = key;
- predicates.push(function(value) {
- return search(getter(value,path), expression[path]);
- });
- })();
- }
+ (function(path) {
+ if (typeof expression[path] == 'undefined') return;
+ predicates.push(function(value) {
+ return search(path == '$' ? value : getter(value, path), expression[path]);
+ });
+ })(key);
}
break;
case 'function':
@@ -15146,12 +15205,10 @@ forEach(BOOLEAN_ATTR, function(propName, attrName) {
ngAttributeAliasDirectives[normalized] = function() {
return {
priority: 100,
- compile: function() {
- return function(scope, element, attr) {
- scope.$watch(attr[normalized], function ngBooleanAttrWatchAction(value) {
- attr.$set(attrName, !!value);
- });
- };
+ link: function(scope, element, attr) {
+ scope.$watch(attr[normalized], function ngBooleanAttrWatchAction(value) {
+ attr.$set(attrName, !!value);
+ });
}
};
};
@@ -15431,10 +15488,10 @@ function FormController(element, attrs) {
*
*
* # CSS classes
- * - `ng-valid` Is set if the form is valid.
- * - `ng-invalid` Is set if the form is invalid.
- * - `ng-pristine` Is set if the form is pristine.
- * - `ng-dirty` Is set if the form is dirty.
+ * - `ng-valid` is set if the form is valid.
+ * - `ng-invalid` is set if the form is invalid.
+ * - `ng-pristine` is set if the form is pristine.
+ * - `ng-dirty` is set if the form is dirty.
*
*
* # Submitting a form and preventing the default action
@@ -15951,6 +16008,12 @@ var inputType = {
'reset': noop
};
+// A helper function to call $setValidity and return the value / undefined,
+// a pattern that is repeated a lot in the input validation logic.
+function validate(ctrl, validatorName, validity, value){
+ ctrl.$setValidity(validatorName, validity);
+ return validity ? value : undefined;
+}
function textInputType(scope, element, attr, ctrl, $sniffer, $browser) {
// In composition mode, users are still inputing intermediate text buffer,
@@ -15980,9 +16043,13 @@ function textInputType(scope, element, attr, ctrl, $sniffer, $browser) {
}
if (ctrl.$viewValue !== value) {
- scope.$apply(function() {
+ if (scope.$$phase) {
ctrl.$setViewValue(value);
- });
+ } else {
+ scope.$apply(function() {
+ ctrl.$setViewValue(value);
+ });
+ }
}
};
@@ -16031,22 +16098,15 @@ function textInputType(scope, element, attr, ctrl, $sniffer, $browser) {
patternValidator,
match;
- var validate = function(regexp, value) {
- if (ctrl.$isEmpty(value) || regexp.test(value)) {
- ctrl.$setValidity('pattern', true);
- return value;
- } else {
- ctrl.$setValidity('pattern', false);
- return undefined;
- }
- };
-
if (pattern) {
+ var validateRegex = function(regexp, value) {
+ return validate(ctrl, 'pattern', ctrl.$isEmpty(value) || regexp.test(value), value);
+ };
match = pattern.match(/^\/(.*)\/([gim]*)$/);
if (match) {
pattern = new RegExp(match[1], match[2]);
patternValidator = function(value) {
- return validate(pattern, value);
+ return validateRegex(pattern, value);
};
} else {
patternValidator = function(value) {
@@ -16057,7 +16117,7 @@ function textInputType(scope, element, attr, ctrl, $sniffer, $browser) {
'Expected {0} to be a RegExp but was {1}. Element: {2}', pattern,
patternObj, startingTag(element));
}
- return validate(patternObj, value);
+ return validateRegex(patternObj, value);
};
}
@@ -16069,13 +16129,7 @@ function textInputType(scope, element, attr, ctrl, $sniffer, $browser) {
if (attr.ngMinlength) {
var minlength = int(attr.ngMinlength);
var minLengthValidator = function(value) {
- if (!ctrl.$isEmpty(value) && value.length < minlength) {
- ctrl.$setValidity('minlength', false);
- return undefined;
- } else {
- ctrl.$setValidity('minlength', true);
- return value;
- }
+ return validate(ctrl, 'minlength', ctrl.$isEmpty(value) || value.length >= minlength, value);
};
ctrl.$parsers.push(minLengthValidator);
@@ -16086,13 +16140,7 @@ function textInputType(scope, element, attr, ctrl, $sniffer, $browser) {
if (attr.ngMaxlength) {
var maxlength = int(attr.ngMaxlength);
var maxLengthValidator = function(value) {
- if (!ctrl.$isEmpty(value) && value.length > maxlength) {
- ctrl.$setValidity('maxlength', false);
- return undefined;
- } else {
- ctrl.$setValidity('maxlength', true);
- return value;
- }
+ return validate(ctrl, 'maxlength', ctrl.$isEmpty(value) || value.length <= maxlength, value);
};
ctrl.$parsers.push(maxLengthValidator);
@@ -16121,13 +16169,7 @@ function numberInputType(scope, element, attr, ctrl, $sniffer, $browser) {
if (attr.min) {
var minValidator = function(value) {
var min = parseFloat(attr.min);
- if (!ctrl.$isEmpty(value) && value < min) {
- ctrl.$setValidity('min', false);
- return undefined;
- } else {
- ctrl.$setValidity('min', true);
- return value;
- }
+ return validate(ctrl, 'min', ctrl.$isEmpty(value) || value >= min, value);
};
ctrl.$parsers.push(minValidator);
@@ -16137,13 +16179,7 @@ function numberInputType(scope, element, attr, ctrl, $sniffer, $browser) {
if (attr.max) {
var maxValidator = function(value) {
var max = parseFloat(attr.max);
- if (!ctrl.$isEmpty(value) && value > max) {
- ctrl.$setValidity('max', false);
- return undefined;
- } else {
- ctrl.$setValidity('max', true);
- return value;
- }
+ return validate(ctrl, 'max', ctrl.$isEmpty(value) || value <= max, value);
};
ctrl.$parsers.push(maxValidator);
@@ -16151,14 +16187,7 @@ function numberInputType(scope, element, attr, ctrl, $sniffer, $browser) {
}
ctrl.$formatters.push(function(value) {
-
- if (ctrl.$isEmpty(value) || isNumber(value)) {
- ctrl.$setValidity('number', true);
- return value;
- } else {
- ctrl.$setValidity('number', false);
- return undefined;
- }
+ return validate(ctrl, 'number', ctrl.$isEmpty(value) || isNumber(value), value);
});
}
@@ -16166,13 +16195,7 @@ function urlInputType(scope, element, attr, ctrl, $sniffer, $browser) {
textInputType(scope, element, attr, ctrl, $sniffer, $browser);
var urlValidator = function(value) {
- if (ctrl.$isEmpty(value) || URL_REGEXP.test(value)) {
- ctrl.$setValidity('url', true);
- return value;
- } else {
- ctrl.$setValidity('url', false);
- return undefined;
- }
+ return validate(ctrl, 'url', ctrl.$isEmpty(value) || URL_REGEXP.test(value), value);
};
ctrl.$formatters.push(urlValidator);
@@ -16183,13 +16206,7 @@ function emailInputType(scope, element, attr, ctrl, $sniffer, $browser) {
textInputType(scope, element, attr, ctrl, $sniffer, $browser);
var emailValidator = function(value) {
- if (ctrl.$isEmpty(value) || EMAIL_REGEXP.test(value)) {
- ctrl.$setValidity('email', true);
- return value;
- } else {
- ctrl.$setValidity('email', false);
- return undefined;
- }
+ return validate(ctrl, 'email', ctrl.$isEmpty(value) || EMAIL_REGEXP.test(value), value);
};
ctrl.$formatters.push(emailValidator);
@@ -17793,13 +17810,13 @@ var ngControllerDirective = [function() {
</button>
count: {{count}}
</doc:source>
- <doc:scenario>
+ <doc:protractor>
it('should check ng-click', function() {
- expect(binding('count')).toBe('0');
- element('.doc-example-live :button').click();
- expect(binding('count')).toBe('1');
+ expect(element(by.binding('count')).getText()).toMatch('0');
+ element(by.css('.doc-example-live button')).click();
+ expect(element(by.binding('count')).getText()).toMatch('1');
});
- </doc:scenario>
+ </doc:protractor>
</doc:example>
*/
/*
@@ -18878,6 +18895,8 @@ var ngPluralizeDirective = ['$locale', '$interpolate', function($locale, $interp
* | `$even` | {@type boolean} | true if the iterator position `$index` is even (otherwise false). |
* | `$odd` | {@type boolean} | true if the iterator position `$index` is odd (otherwise false). |
*
+ * Creating aliases for these properties is possible with {@link api/ng.directive:ngInit `ngInit`}.
+ * This may be useful when, for instance, nesting ngRepeats.
*
* # Special repeat start and end points
* To repeat a series of elements instead of just one parent element, ngRepeat (as well as other ng directives) supports extending
@@ -19061,7 +19080,7 @@ var ngRepeatDirective = ['$parse', '$animate', function($parse, $animate) {
$$tlb: true,
link: function($scope, $element, $attr, ctrl, $transclude){
var expression = $attr.ngRepeat;
- var match = expression.match(/^\s*(.+)\s+in\s+([\r\n\s\S]*?)\s*(\s+track\s+by\s+(.+)\s*)?$/),
+ var match = expression.match(/^\s*([\s\S]+?)\s+in\s+([\s\S]+?)(?:\s+track\s+by\s+([\s\S]+?))?\s*$/),
trackByExp, trackByExpGetter, trackByIdExpFn, trackByIdArrayFn, trackByIdObjFn,
lhs, rhs, valueIdentifier, keyIdentifier,
hashFnLocals = {$id: hashKey};
@@ -19073,7 +19092,7 @@ var ngRepeatDirective = ['$parse', '$animate', function($parse, $animate) {
lhs = match[1];
rhs = match[2];
- trackByExp = match[4];
+ trackByExp = match[3];
if (trackByExp) {
trackByExpGetter = $parse(trackByExp);
@@ -19760,11 +19779,9 @@ var ngSwitchWhenDirective = ngDirective({
transclude: 'element',
priority: 800,
require: '^ngSwitch',
- compile: function(element, attrs) {
- return function(scope, element, attr, ctrl, $transclude) {
- ctrl.cases['!' + attrs.ngSwitchWhen] = (ctrl.cases['!' + attrs.ngSwitchWhen] || []);
- ctrl.cases['!' + attrs.ngSwitchWhen].push({ transclude: $transclude, element: element });
- };
+ link: function(scope, element, attrs, ctrl, $transclude) {
+ ctrl.cases['!' + attrs.ngSwitchWhen] = (ctrl.cases['!' + attrs.ngSwitchWhen] || []);
+ ctrl.cases['!' + attrs.ngSwitchWhen].push({ transclude: $transclude, element: element });
}
});
@@ -19859,10 +19876,14 @@ var ngTranscludeDirective = ngDirective({
* @restrict E
*
* @description
- * Load content of a script tag, with type `text/ng-template`, into `$templateCache`, so that the
- * template can be used by `ngInclude`, `ngView` or directive templates.
+ * Load the content of a `<script>` element into {@link api/ng.$templateCache `$templateCache`}, so that the
+ * template can be used by {@link api/ng.directive:ngInclude `ngInclude`},
+ * {@link api/ngRoute.directive:ngView `ngView`}, or {@link guide/directive directives}. The type of the
+ * `<script>` element must be specified as `text/ng-template`, and a cache name for the template must be
+ * assigned through the element's `id`, which can then be used as a directive's `templateUrl`.
*
- * @param {'text/ng-template'} type must be set to `'text/ng-template'`
+ * @param {'text/ng-template'} type Must be set to `'text/ng-template'`.
+ * @param {string} id Cache name of the template.
*
* @example
<doc:example>
@@ -20026,8 +20047,8 @@ var ngOptionsMinErr = minErr('ngOptions');
var ngOptionsDirective = valueFn({ terminal: true });
// jshint maxlen: false
var selectDirective = ['$compile', '$parse', function($compile, $parse) {
- //0000111110000000000022220000000000000000000000333300000000000000444444444444444000000000555555555555555000000066666666666666600000000000000007777000000000000000000088888
- var NG_OPTIONS_REGEXP = /^\s*(.*?)(?:\s+as\s+(.*?))?(?:\s+group\s+by\s+(.*))?\s+for\s+(?:([\$\w][\$\w]*)|(?:\(\s*([\$\w][\$\w]*)\s*,\s*([\$\w][\$\w]*)\s*\)))\s+in\s+(.*?)(?:\s+track\s+by\s+(.*?))?$/,
+ //000011111111110000000000022222222220000000000000000000003333333333000000000000004444444444444440000000005555555555555550000000666666666666666000000000000000777777777700000000000000000008888888888
+ var NG_OPTIONS_REGEXP = /^\s*([\s\S]+?)(?:\s+as\s+([\s\S]+?))?(?:\s+group\s+by\s+([\s\S]+?))?\s+for\s+(?:([\$\w][\$\w]*)|(?:\(\s*([\$\w][\$\w]*)\s*,\s*([\$\w][\$\w]*)\s*\)))\s+in\s+([\s\S]+?)(?:\s+track\s+by\s+([\s\S]+?))?$/,
nullModelCtrl = {$setViewValue: noop};
// jshint maxlen: 100