angularjs-rails 1.2.0.rc1 → 1.2.0.rc2

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.
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.2.0rc1
2
+ * @license AngularJS v1.2.0-rc.2
3
3
  * (c) 2010-2012 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -9,8 +9,17 @@
9
9
  * @ngdoc overview
10
10
  * @name ngTouch
11
11
  * @description
12
- * Touch events and other mobile helpers.
13
- * Based on jQuery Mobile touch event handling (jquerymobile.com)
12
+ *
13
+ * # ngTouch
14
+ *
15
+ * `ngTouch` is the name of the optional Angular module that provides touch events and other
16
+ * helpers for touch-enabled devices.
17
+ * The implementation is based on jQuery Mobile touch event handling
18
+ * ([jquerymobile.com](http://jquerymobile.com/))
19
+ *
20
+ * {@installModule touch}
21
+ *
22
+ * See {@link ngTouch.$swipe `$swipe`} for usage.
14
23
  */
15
24
 
16
25
  // define ngTouch module
@@ -24,7 +33,9 @@ var ngTouch = angular.module('ngTouch', []);
24
33
  * The `$swipe` service is a service that abstracts the messier details of hold-and-drag swipe
25
34
  * behavior, to make implementing swipe-related directives more convenient.
26
35
  *
27
- * It is used by the `ngSwipeLeft` and `ngSwipeRight` directives in `ngTouch`, and by
36
+ * Requires the {@link ngTouch `ngTouch`} module to be installed.
37
+ *
38
+ * `$swipe` is used by the `ngSwipeLeft` and `ngSwipeRight` directives in `ngTouch`, and by
28
39
  * `ngCarousel` in a separate component.
29
40
  *
30
41
  * # Usage
@@ -159,6 +170,8 @@ ngTouch.factory('$swipe', [function() {
159
170
  * the click event. This version handles them immediately, and then prevents the
160
171
  * following click event from propagating.
161
172
  *
173
+ * Requires the {@link ngTouch `ngTouch`} module to be installed.
174
+ *
162
175
  * This directive can fall back to using an ordinary click event, and so works on desktop
163
176
  * browsers as well as mobile.
164
177
  *
@@ -428,6 +441,8 @@ ngTouch.directive('ngClick', ['$parse', '$timeout', '$rootElement',
428
441
  * A leftward swipe is a quick, right-to-left slide of the finger.
429
442
  * Though ngSwipeLeft is designed for touch-based devices, it will work with a mouse click and drag too.
430
443
  *
444
+ * Requires the {@link ngTouch `ngTouch`} module to be installed.
445
+ *
431
446
  * @element ANY
432
447
  * @param {expression} ngSwipeLeft {@link guide/expression Expression} to evaluate
433
448
  * upon left swipe. (Event object is available as `$event`)
@@ -455,6 +470,8 @@ ngTouch.directive('ngClick', ['$parse', '$timeout', '$rootElement',
455
470
  * A rightward swipe is a quick, left-to-right slide of the finger.
456
471
  * Though ngSwipeRight is designed for touch-based devices, it will work with a mouse click and drag too.
457
472
  *
473
+ * Requires the {@link ngTouch `ngTouch`} module to be installed.
474
+ *
458
475
  * @element ANY
459
476
  * @param {expression} ngSwipeRight {@link guide/expression Expression} to evaluate
460
477
  * upon right swipe. (Event object is available as `$event`)
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.2.0rc1
2
+ * @license AngularJS v1.2.0-rc.2
3
3
  * (c) 2010-2012 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -35,10 +35,21 @@
35
35
 
36
36
  function minErr(module) {
37
37
  return function () {
38
- var prefix = '[' + (module ? module + ':' : '') + arguments[0] + '] ',
38
+ var code = arguments[0],
39
+ prefix = '[' + (module ? module + ':' : '') + code + '] ',
39
40
  template = arguments[1],
40
41
  templateArgs = arguments,
41
- message;
42
+ stringify = function (obj) {
43
+ if (isFunction(obj)) {
44
+ return obj.toString().replace(/ \{[\s\S]*$/, '');
45
+ } else if (isUndefined(obj)) {
46
+ return 'undefined';
47
+ } else if (!isString(obj)) {
48
+ return JSON.stringify(obj);
49
+ }
50
+ return obj;
51
+ },
52
+ message, i;
42
53
 
43
54
  message = prefix + template.replace(/\{\d+\}/g, function (match) {
44
55
  var index = +match.slice(1, -1), arg;
@@ -57,6 +68,13 @@ function minErr(module) {
57
68
  return match;
58
69
  });
59
70
 
71
+ message = message + '\nhttp://errors.angularjs.org/' + version.full + '/' +
72
+ (module ? module + '/' : '') + code;
73
+ for (i = 2; i < arguments.length; i++) {
74
+ message = message + (i == 2 ? '?' : '&') + 'p' + (i-2) + '=' +
75
+ encodeURIComponent(stringify(arguments[i]));
76
+ }
77
+
60
78
  return new Error(message);
61
79
  };
62
80
  }
@@ -119,7 +137,7 @@ if ('i' !== 'I'.toLowerCase()) {
119
137
 
120
138
 
121
139
  var /** holds major version number for IE or NaN for real browsers */
122
- msie = int((/msie (\d+)/.exec(lowercase(navigator.userAgent)) || [])[1]),
140
+ msie,
123
141
  jqLite, // delay binding since jQuery could be loaded after us.
124
142
  jQuery, // delay binding
125
143
  slice = [].slice,
@@ -135,6 +153,16 @@ var /** holds major version number for IE or NaN for real browsers */
135
153
  nodeName_,
136
154
  uid = ['0', '0', '0'];
137
155
 
156
+ /**
157
+ * IE 11 changed the format of the UserAgent string.
158
+ * See http://msdn.microsoft.com/en-us/library/ms537503.aspx
159
+ */
160
+ msie = int((/msie (\d+)/.exec(lowercase(navigator.userAgent)) || [])[1]);
161
+ if (isNaN(msie)) {
162
+ msie = int((/trident\/.*; rv:(\d+)/.exec(lowercase(navigator.userAgent)) || [])[1]);
163
+ }
164
+
165
+
138
166
  /**
139
167
  * @private
140
168
  * @param {*} obj
@@ -1249,10 +1277,13 @@ function setupModuleLoader(window) {
1249
1277
  * @name angular.module
1250
1278
  * @description
1251
1279
  *
1252
- * The `angular.module` is a global place for creating and registering Angular modules. All
1253
- * modules (angular core or 3rd party) that should be available to an application must be
1280
+ * The `angular.module` is a global place for creating, registering and retrieving Angular modules.
1281
+ * All modules (angular core or 3rd party) that should be available to an application must be
1254
1282
  * registered using this mechanism.
1255
1283
  *
1284
+ * When passed two or more arguments, a new module is created. If passed only one argument, an
1285
+ * existing module (the name passed as the first argument to `module`) is retrieved.
1286
+ *
1256
1287
  *
1257
1288
  * # Module
1258
1289
  *
@@ -1523,11 +1554,11 @@ function setupModuleLoader(window) {
1523
1554
  * - `codeName` – `{string}` – Code name of the release, such as "jiggling-armfat".
1524
1555
  */
1525
1556
  var version = {
1526
- full: '1.2.0rc1', // all of these placeholder strings will be replaced by grunt's
1557
+ full: '1.2.0-rc.2', // all of these placeholder strings will be replaced by grunt's
1527
1558
  major: 1, // package task
1528
1559
  minor: 2,
1529
1560
  dot: 0,
1530
- codeName: 'spooky-giraffe'
1561
+ codeName: 'barehand-atomsplitting'
1531
1562
  };
1532
1563
 
1533
1564
 
@@ -2590,13 +2621,15 @@ function annotate(fn) {
2590
2621
  if (typeof fn == 'function') {
2591
2622
  if (!($inject = fn.$inject)) {
2592
2623
  $inject = [];
2593
- fnText = fn.toString().replace(STRIP_COMMENTS, '');
2594
- argDecl = fnText.match(FN_ARGS);
2595
- forEach(argDecl[1].split(FN_ARG_SPLIT), function(arg){
2596
- arg.replace(FN_ARG, function(all, underscore, name){
2597
- $inject.push(name);
2624
+ if (fn.length) {
2625
+ fnText = fn.toString().replace(STRIP_COMMENTS, '');
2626
+ argDecl = fnText.match(FN_ARGS);
2627
+ forEach(argDecl[1].split(FN_ARG_SPLIT), function(arg){
2628
+ arg.replace(FN_ARG, function(all, underscore, name){
2629
+ $inject.push(name);
2630
+ });
2598
2631
  });
2599
- });
2632
+ }
2600
2633
  fn.$inject = $inject;
2601
2634
  }
2602
2635
  } else if (isArray(fn)) {
@@ -3320,7 +3353,7 @@ var $AnimateProvider = ['$provide', function($provide) {
3320
3353
  forEach(element, function(node) {
3321
3354
  parentNode.insertBefore(node, afterNextSibling);
3322
3355
  });
3323
- $timeout(done || noop, 0, false);
3356
+ done && $timeout(done, 0, false);
3324
3357
  },
3325
3358
 
3326
3359
  /**
@@ -3337,7 +3370,7 @@ var $AnimateProvider = ['$provide', function($provide) {
3337
3370
  */
3338
3371
  leave : function(element, done) {
3339
3372
  element.remove();
3340
- $timeout(done || noop, 0, false);
3373
+ done && $timeout(done, 0, false);
3341
3374
  },
3342
3375
 
3343
3376
  /**
@@ -3379,7 +3412,7 @@ var $AnimateProvider = ['$provide', function($provide) {
3379
3412
  className :
3380
3413
  isArray(className) ? className.join(' ') : '';
3381
3414
  element.addClass(className);
3382
- $timeout(done || noop, 0, false);
3415
+ done && $timeout(done, 0, false);
3383
3416
  },
3384
3417
 
3385
3418
  /**
@@ -3400,7 +3433,7 @@ var $AnimateProvider = ['$provide', function($provide) {
3400
3433
  className :
3401
3434
  isArray(className) ? className.join(' ') : '';
3402
3435
  element.removeClass(className);
3403
- $timeout(done || noop, 0, false);
3436
+ done && $timeout(done, 0, false);
3404
3437
  },
3405
3438
 
3406
3439
  enabled : noop
@@ -5699,7 +5732,7 @@ function $HttpProvider() {
5699
5732
  // strip json vulnerability protection prefix
5700
5733
  data = data.replace(PROTECTION_PREFIX, '');
5701
5734
  if (JSON_START.test(data) && JSON_END.test(data))
5702
- data = fromJson(data, true);
5735
+ data = fromJson(data);
5703
5736
  }
5704
5737
  return data;
5705
5738
  }],
@@ -6015,6 +6048,7 @@ function $HttpProvider() {
6015
6048
  * return function(promise) {
6016
6049
  * return promise.then(function(response) {
6017
6050
  * // do something on success
6051
+ * return response;
6018
6052
  * }, function(response) {
6019
6053
  * // do something on error
6020
6054
  * if (canRecover(response)) {
@@ -6494,7 +6528,7 @@ function $HttpProvider() {
6494
6528
 
6495
6529
  if (cache) {
6496
6530
  cachedResp = cache.get(url);
6497
- if (cachedResp) {
6531
+ if (isDefined(cachedResp)) {
6498
6532
  if (cachedResp.then) {
6499
6533
  // cached request has already been sent, but there is no response yet
6500
6534
  cachedResp.then(removePendingReq, removePendingReq);
@@ -6514,7 +6548,7 @@ function $HttpProvider() {
6514
6548
  }
6515
6549
 
6516
6550
  // if we won't have the response in cache, send the request to the backend
6517
- if (!cachedResp) {
6551
+ if (isUndefined(cachedResp)) {
6518
6552
  $httpBackend(config.method, url, reqData, done, reqHeaders, config.timeout,
6519
6553
  config.withCredentials, config.responseType);
6520
6554
  }
@@ -6764,23 +6798,32 @@ var $interpolateMinErr = minErr('$interpolate');
6764
6798
  * @description
6765
6799
  *
6766
6800
  * Used for configuring the interpolation markup. Defaults to `{{` and `}}`.
6767
- *
6801
+ *
6768
6802
  * @example
6769
- <doc:example>
6803
+ <doc:example module="customInterpolationApp">
6770
6804
  <doc:source>
6771
6805
  <script>
6772
- var myApp = angular.module('App', [], function($interpolateProvider) {
6806
+ var customInterpolationApp = angular.module('customInterpolationApp', []);
6807
+
6808
+ customInterpolationApp.config(function($interpolateProvider) {
6773
6809
  $interpolateProvider.startSymbol('//');
6774
6810
  $interpolateProvider.endSymbol('//');
6775
6811
  });
6776
- function Controller($scope) {
6777
- $scope.label = "Interpolation Provider Sample";
6778
- }
6812
+
6813
+
6814
+ customInterpolationApp.controller('DemoController', function DemoController() {
6815
+ this.label = "This bindings is brought you you by // interpolation symbols.";
6816
+ });
6779
6817
  </script>
6780
- <div ng-app="App" ng-controller="Controller">
6781
- //label//
6818
+ <div ng-app="App" ng-controller="DemoController as demo">
6819
+ //demo.label//
6782
6820
  </div>
6783
6821
  </doc:source>
6822
+ <doc:scenario>
6823
+ it('should interpolate binding with custom symbols', function() {
6824
+ expect(binding('demo.label')).toBe('This bindings is brought you you by // interpolation symbols.');
6825
+ });
6826
+ </doc:scenario>
6784
6827
  </doc:example>
6785
6828
  */
6786
6829
  function $InterpolateProvider() {
@@ -7844,7 +7887,6 @@ var $parseMinErr = minErr('$parse');
7844
7887
  // access to any member named "constructor".
7845
7888
  //
7846
7889
  // For reflective calls (a[b]) we check that the value of the lookup is not the Function constructor while evaluating
7847
- // For reflective calls (a[b]) we check that the value of the lookup is not the Function constructor while evaluating
7848
7890
  // the expression, which is a stronger but more expensive test. Since reflective calls are expensive anyway, this is not
7849
7891
  // such a big deal compared to static dereferencing.
7850
7892
  //
@@ -8518,9 +8560,21 @@ function parser(text, json, $filter, csp){
8518
8560
  }
8519
8561
  var fnPtr = fn(scope, locals, context) || noop;
8520
8562
  // IE stupidity!
8521
- return fnPtr.apply
8563
+ var v = fnPtr.apply
8522
8564
  ? fnPtr.apply(context, args)
8523
8565
  : fnPtr(args[0], args[1], args[2], args[3], args[4]);
8566
+
8567
+ // Check for promise
8568
+ if (v && v.then) {
8569
+ var p = v;
8570
+ if (!('$$v' in v)) {
8571
+ p.$$v = undefined;
8572
+ p.then(function(val) { p.$$v = val; });
8573
+ }
8574
+ v = v.$$v;
8575
+ }
8576
+
8577
+ return v;
8524
8578
  };
8525
8579
  }
8526
8580
 
@@ -8824,6 +8878,8 @@ function $ParseProvider() {
8824
8878
  * // since this fn executes async in a future turn of the event loop, we need to wrap
8825
8879
  * // our code into an $apply call so that the model changes are properly observed.
8826
8880
  * scope.$apply(function() {
8881
+ * deferred.notify('About to greet ' + name + '.');
8882
+ *
8827
8883
  * if (okToGreet(name)) {
8828
8884
  * deferred.resolve('Hello, ' + name + '!');
8829
8885
  * } else {
@@ -8840,6 +8896,8 @@ function $ParseProvider() {
8840
8896
  * alert('Success: ' + greeting);
8841
8897
  * }, function(reason) {
8842
8898
  * alert('Failed: ' + reason);
8899
+ * }, function(update) {
8900
+ * alert('Got notification: ' + update);
8843
8901
  * });
8844
8902
  * </pre>
8845
8903
  *
@@ -8858,7 +8916,8 @@ function $ParseProvider() {
8858
8916
  * A new instance of deferred is constructed by calling `$q.defer()`.
8859
8917
  *
8860
8918
  * The purpose of the deferred object is to expose the associated Promise instance as well as APIs
8861
- * that can be used for signaling the successful or unsuccessful completion of the task.
8919
+ * that can be used for signaling the successful or unsuccessful completion, as well as the status
8920
+ * of the task.
8862
8921
  *
8863
8922
  * **Methods**
8864
8923
  *
@@ -8866,6 +8925,8 @@ function $ParseProvider() {
8866
8925
  * constructed via `$q.reject`, the promise will be rejected instead.
8867
8926
  * - `reject(reason)` – rejects the derived promise with the `reason`. This is equivalent to
8868
8927
  * resolving it with a rejection constructed via `$q.reject`.
8928
+ * - `notify(value)` - provides updates on the status of the promises execution. This may be called
8929
+ * multiple times before the promise is either resolved or rejected.
8869
8930
  *
8870
8931
  * **Properties**
8871
8932
  *
@@ -8882,12 +8943,15 @@ function $ParseProvider() {
8882
8943
  *
8883
8944
  * **Methods**
8884
8945
  *
8885
- * - `then(successCallback, errorCallback)` – regardless of when the promise was or will be resolved
8886
- * or rejected, `then` calls one of the success or error callbacks asynchronously as soon as the result
8887
- * is available. The callbacks are called with a single argument: the result or rejection reason.
8946
+ * - `then(successCallback, errorCallback, notifyCallback)` – regardless of when the promise was or
8947
+ * will be resolved or rejected, `then` calls one of the success or error callbacks asynchronously
8948
+ * as soon as the result is available. The callbacks are called with a single argument: the result
8949
+ * or rejection reason. Additionally, the notify callback may be called zero or more times to
8950
+ * provide a progress indication, before the promise is resolved or rejected.
8888
8951
  *
8889
8952
  * This method *returns a new promise* which is resolved or rejected via the return value of the
8890
- * `successCallback` or `errorCallback`.
8953
+ * `successCallback`, `errorCallback`. It also notifies via the return value of the `notifyCallback`
8954
+ * method. The promise can not be resolved or rejected from the notifyCallback method.
8891
8955
  *
8892
8956
  * - `catch(errorCallback)` – shorthand for `promise.then(null, errorCallback)`
8893
8957
  *
@@ -9039,7 +9103,7 @@ function qFactory(nextTick, exceptionHandler) {
9039
9103
 
9040
9104
  var wrappedCallback = function(value) {
9041
9105
  try {
9042
- result.resolve((callback || defaultCallback)(value));
9106
+ result.resolve((isFunction(callback) ? callback : defaultCallback)(value));
9043
9107
  } catch(e) {
9044
9108
  result.reject(e);
9045
9109
  exceptionHandler(e);
@@ -9048,7 +9112,7 @@ function qFactory(nextTick, exceptionHandler) {
9048
9112
 
9049
9113
  var wrappedErrback = function(reason) {
9050
9114
  try {
9051
- result.resolve((errback || defaultErrback)(reason));
9115
+ result.resolve((isFunction(errback) ? errback : defaultErrback)(reason));
9052
9116
  } catch(e) {
9053
9117
  result.reject(e);
9054
9118
  exceptionHandler(e);
@@ -9057,7 +9121,7 @@ function qFactory(nextTick, exceptionHandler) {
9057
9121
 
9058
9122
  var wrappedProgressback = function(progress) {
9059
9123
  try {
9060
- result.notify((progressback || defaultCallback)(progress));
9124
+ result.notify((isFunction(progressback) ? progressback : defaultCallback)(progress));
9061
9125
  } catch(e) {
9062
9126
  exceptionHandler(e);
9063
9127
  }
@@ -9095,7 +9159,7 @@ function qFactory(nextTick, exceptionHandler) {
9095
9159
  } catch(e) {
9096
9160
  return makePromise(e, false);
9097
9161
  }
9098
- if (callbackOutput && callbackOutput.then) {
9162
+ if (callbackOutput && isFunction(callbackOutput.then)) {
9099
9163
  return callbackOutput.then(function() {
9100
9164
  return makePromise(value, isResolved);
9101
9165
  }, function(error) {
@@ -9120,7 +9184,7 @@ function qFactory(nextTick, exceptionHandler) {
9120
9184
 
9121
9185
 
9122
9186
  var ref = function(value) {
9123
- if (value && value.then) return value;
9187
+ if (value && isFunction(value.then)) return value;
9124
9188
  return {
9125
9189
  then: function(callback) {
9126
9190
  var result = defer();
@@ -9173,7 +9237,12 @@ function qFactory(nextTick, exceptionHandler) {
9173
9237
  then: function(callback, errback) {
9174
9238
  var result = defer();
9175
9239
  nextTick(function() {
9176
- result.resolve((errback || defaultErrback)(reason));
9240
+ try {
9241
+ result.resolve((isFunction(errback) ? errback : defaultErrback)(reason));
9242
+ } catch(e) {
9243
+ result.reject(e);
9244
+ exceptionHandler(e);
9245
+ }
9177
9246
  });
9178
9247
  return result.promise;
9179
9248
  }
@@ -9199,7 +9268,7 @@ function qFactory(nextTick, exceptionHandler) {
9199
9268
 
9200
9269
  var wrappedCallback = function(value) {
9201
9270
  try {
9202
- return (callback || defaultCallback)(value);
9271
+ return (isFunction(callback) ? callback : defaultCallback)(value);
9203
9272
  } catch (e) {
9204
9273
  exceptionHandler(e);
9205
9274
  return reject(e);
@@ -9208,7 +9277,7 @@ function qFactory(nextTick, exceptionHandler) {
9208
9277
 
9209
9278
  var wrappedErrback = function(reason) {
9210
9279
  try {
9211
- return (errback || defaultErrback)(reason);
9280
+ return (isFunction(errback) ? errback : defaultErrback)(reason);
9212
9281
  } catch (e) {
9213
9282
  exceptionHandler(e);
9214
9283
  return reject(e);
@@ -9217,7 +9286,7 @@ function qFactory(nextTick, exceptionHandler) {
9217
9286
 
9218
9287
  var wrappedProgressback = function(progress) {
9219
9288
  try {
9220
- return (progressback || defaultCallback)(progress);
9289
+ return (isFunction(progressback) ? progressback : defaultCallback)(progress);
9221
9290
  } catch (e) {
9222
9291
  exceptionHandler(e);
9223
9292
  }
@@ -9367,8 +9436,8 @@ function $RootScopeProvider(){
9367
9436
  return TTL;
9368
9437
  };
9369
9438
 
9370
- this.$get = ['$injector', '$exceptionHandler', '$parse',
9371
- function( $injector, $exceptionHandler, $parse) {
9439
+ this.$get = ['$injector', '$exceptionHandler', '$parse', '$browser',
9440
+ function( $injector, $exceptionHandler, $parse, $browser) {
9372
9441
 
9373
9442
  /**
9374
9443
  * @ngdoc function
@@ -9417,6 +9486,7 @@ function $RootScopeProvider(){
9417
9486
  this['this'] = this.$root = this;
9418
9487
  this.$$destroyed = false;
9419
9488
  this.$$asyncQueue = [];
9489
+ this.$$postDigestQueue = [];
9420
9490
  this.$$listeners = {};
9421
9491
  this.$$isolateBindings = {};
9422
9492
  }
@@ -9431,6 +9501,7 @@ function $RootScopeProvider(){
9431
9501
 
9432
9502
 
9433
9503
  Scope.prototype = {
9504
+ constructor: Scope,
9434
9505
  /**
9435
9506
  * @ngdoc function
9436
9507
  * @name ng.$rootScope.Scope#$new
@@ -9465,6 +9536,7 @@ function $RootScopeProvider(){
9465
9536
  child.$root = this.$root;
9466
9537
  // ensure that there is just one async queue per $rootScope and it's children
9467
9538
  child.$$asyncQueue = this.$$asyncQueue;
9539
+ child.$$postDigestQueue = this.$$postDigestQueue;
9468
9540
  } else {
9469
9541
  Child = function() {}; // should be anonymous; This is so that when the minifier munges
9470
9542
  // the name it does not become random set of chars. These will then show up as class
@@ -9792,6 +9864,7 @@ function $RootScopeProvider(){
9792
9864
  var watch, value, last,
9793
9865
  watchers,
9794
9866
  asyncQueue = this.$$asyncQueue,
9867
+ postDigestQueue = this.$$postDigestQueue,
9795
9868
  length,
9796
9869
  dirty, ttl = TTL,
9797
9870
  next, current, target = this,
@@ -9864,6 +9937,14 @@ function $RootScopeProvider(){
9864
9937
  } while (dirty || asyncQueue.length);
9865
9938
 
9866
9939
  clearPhase();
9940
+
9941
+ while(postDigestQueue.length) {
9942
+ try {
9943
+ postDigestQueue.shift()();
9944
+ } catch (e) {
9945
+ $exceptionHandler(e);
9946
+ }
9947
+ }
9867
9948
  },
9868
9949
 
9869
9950
 
@@ -9964,13 +10045,16 @@ function $RootScopeProvider(){
9964
10045
  *
9965
10046
  * The `$evalAsync` makes no guarantees as to when the `expression` will be executed, only that:
9966
10047
  *
9967
- * - it will execute in the current script execution context (before any DOM rendering).
9968
- * - at least one {@link ng.$rootScope.Scope#$digest $digest cycle} will be performed after
9969
- * `expression` execution.
10048
+ * - it will execute after the function that schedule the evaluation is done running (preferably before DOM rendering).
10049
+ * - at least one {@link ng.$rootScope.Scope#$digest $digest cycle} will be performed after `expression` execution.
9970
10050
  *
9971
10051
  * Any exceptions from the execution of the expression are forwarded to the
9972
10052
  * {@link ng.$exceptionHandler $exceptionHandler} service.
9973
10053
  *
10054
+ * __Note:__ if this function is called outside of `$digest` cycle, a new $digest cycle will be scheduled.
10055
+ * It is however encouraged to always call code that changes the model from withing an `$apply` call.
10056
+ * That includes code evaluated via `$evalAsync`.
10057
+ *
9974
10058
  * @param {(string|function())=} expression An angular expression to be executed.
9975
10059
  *
9976
10060
  * - `string`: execute using the rules as defined in {@link guide/expression expression}.
@@ -9978,9 +10062,23 @@ function $RootScopeProvider(){
9978
10062
  *
9979
10063
  */
9980
10064
  $evalAsync: function(expr) {
10065
+ // if we are outside of an $digest loop and this is the first time we are scheduling async task also schedule
10066
+ // async auto-flush
10067
+ if (!$rootScope.$$phase && !$rootScope.$$asyncQueue.length) {
10068
+ $browser.defer(function() {
10069
+ if ($rootScope.$$asyncQueue.length) {
10070
+ $rootScope.$digest();
10071
+ }
10072
+ });
10073
+ }
10074
+
9981
10075
  this.$$asyncQueue.push(expr);
9982
10076
  },
9983
10077
 
10078
+ $$postDigest : function(expr) {
10079
+ this.$$postDigestQueue.push(expr);
10080
+ },
10081
+
9984
10082
  /**
9985
10083
  * @ngdoc function
9986
10084
  * @name ng.$rootScope.Scope#$apply
@@ -10649,7 +10747,7 @@ function $SceDelegateProvider() {
10649
10747
  * {@link ng.$sce#getTrusted $sce.getTrusted} behind the scenes on non-constant literals.
10650
10748
  *
10651
10749
  * As an example, {@link ng.directive:ngBindHtml ngBindHtml} uses {@link
10652
- * ng.$sce#parseHtml $sce.parseAsHtml(binding expression)}. Here's the actual code (slightly
10750
+ * ng.$sce#parseAsHtml $sce.parseAsHtml(binding expression)}. Here's the actual code (slightly
10653
10751
  * simplified):
10654
10752
  *
10655
10753
  * <pre class="prettyprint">
@@ -10707,7 +10805,7 @@ function $SceDelegateProvider() {
10707
10805
  * ## What trusted context types are supported?<a name="contexts"></a>
10708
10806
  *
10709
10807
  * | Context | Notes |
10710
- * |=====================|================|
10808
+ * |---------------------|----------------|
10711
10809
  * | `$sce.HTML` | For HTML that's safe to source into the application. The {@link ng.directive:ngBindHtml ngBindHtml} directive uses this context for bindings. |
10712
10810
  * | `$sce.CSS` | For CSS that's safe to source into the application. Currently unused. Feel free to use it in your own directives. |
10713
10811
  * | `$sce.URL` | For URLs that are safe to follow as links. Currently unused (`<a href=` and `<img src=` sanitize their urls and don't consititute an SCE context. |
@@ -11218,6 +11316,7 @@ function $SnifferProvider() {
11218
11316
  this.$get = ['$window', '$document', function($window, $document) {
11219
11317
  var eventSupport = {},
11220
11318
  android = int((/android (\d+)/.exec(lowercase(($window.navigator || {}).userAgent)) || [])[1]),
11319
+ boxee = /Boxee/i.test(($window.navigator || {}).userAgent),
11221
11320
  document = $document[0] || {},
11222
11321
  vendorPrefix,
11223
11322
  vendorRegex = /^(Moz|webkit|O|ms)(?=[A-Z])/,
@@ -11234,12 +11333,17 @@ function $SnifferProvider() {
11234
11333
  break;
11235
11334
  }
11236
11335
  }
11336
+
11337
+ if(!vendorPrefix) {
11338
+ vendorPrefix = ('WebkitOpacity' in bodyStyle) && 'webkit';
11339
+ }
11340
+
11237
11341
  transitions = !!(('transition' in bodyStyle) || (vendorPrefix + 'Transition' in bodyStyle));
11238
11342
  animations = !!(('animation' in bodyStyle) || (vendorPrefix + 'Animation' in bodyStyle));
11239
-
11343
+
11240
11344
  if (android && (!transitions||!animations)) {
11241
- transitions = isString(document.body.style.webkitTransition);
11242
- animations = isString(document.body.style.webkitAnimation);
11345
+ transitions = isString(document.body.style.webkitTransition);
11346
+ animations = isString(document.body.style.webkitAnimation);
11243
11347
  }
11244
11348
  }
11245
11349
 
@@ -11249,7 +11353,10 @@ function $SnifferProvider() {
11249
11353
  // so let's not use the history API at all.
11250
11354
  // http://code.google.com/p/android/issues/detail?id=17471
11251
11355
  // https://github.com/angular/angular.js/issues/904
11252
- history: !!($window.history && $window.history.pushState && !(android < 4)),
11356
+
11357
+ // older webit browser (533.9) on Boxee box has exactly the same problem as Android has
11358
+ // so let's not use the history API also
11359
+ history: !!($window.history && $window.history.pushState && !(android < 4) && !boxee),
11253
11360
  hashchange: 'onhashchange' in $window &&
11254
11361
  // IE8 compatible mode lies
11255
11362
  (!document.documentMode || document.documentMode > 7),
@@ -11309,7 +11416,7 @@ function $TimeoutProvider() {
11309
11416
  var deferred = $q.defer(),
11310
11417
  promise = deferred.promise,
11311
11418
  skipApply = (isDefined(invokeApply) && !invokeApply),
11312
- timeoutId, cleanup;
11419
+ timeoutId;
11313
11420
 
11314
11421
  timeoutId = $browser.defer(function() {
11315
11422
  try {
@@ -11318,17 +11425,15 @@ function $TimeoutProvider() {
11318
11425
  deferred.reject(e);
11319
11426
  $exceptionHandler(e);
11320
11427
  }
11428
+ finally {
11429
+ delete deferreds[promise.$$timeoutId];
11430
+ }
11321
11431
 
11322
11432
  if (!skipApply) $rootScope.$apply();
11323
11433
  }, delay);
11324
11434
 
11325
- cleanup = function() {
11326
- delete deferreds[promise.$$timeoutId];
11327
- };
11328
-
11329
11435
  promise.$$timeoutId = timeoutId;
11330
11436
  deferreds[timeoutId] = deferred;
11331
- promise.then(cleanup, cleanup);
11332
11437
 
11333
11438
  return promise;
11334
11439
  }
@@ -11350,6 +11455,7 @@ function $TimeoutProvider() {
11350
11455
  timeout.cancel = function(promise) {
11351
11456
  if (promise && promise.$$timeoutId in deferreds) {
11352
11457
  deferreds[promise.$$timeoutId].reject('canceled');
11458
+ delete deferreds[promise.$$timeoutId];
11353
11459
  return $browser.defer.cancel(promise.$$timeoutId);
11354
11460
  }
11355
11461
  return false;
@@ -11417,7 +11523,7 @@ function $$UrlUtilsProvider() {
11417
11523
  * Otherwise, returns an object with the following members.
11418
11524
  *
11419
11525
  * | member name | Description |
11420
- * |===============|================|
11526
+ * |---------------|----------------|
11421
11527
  * | href | A normalized version of the provided URL if it was not an absolute URL |
11422
11528
  * | protocol | The protocol including the trailing colon |
11423
11529
  * | host | The host and port (if the port is non-default) of the normalizedUrl |
@@ -11425,7 +11531,7 @@ function $$UrlUtilsProvider() {
11425
11531
  * These fields from the UrlUtils interface are currently not needed and hence not returned.
11426
11532
  *
11427
11533
  * | member name | Description |
11428
- * |===============|================|
11534
+ * |---------------|----------------|
11429
11535
  * | hostname | The host without the port of the normalizedUrl |
11430
11536
  * | pathname | The path following the host in the normalizedUrl |
11431
11537
  * | hash | The URL hash if present |
@@ -11434,7 +11540,7 @@ function $$UrlUtilsProvider() {
11434
11540
  */
11435
11541
  function resolve(url, parse) {
11436
11542
  var href = url;
11437
- if (msie) {
11543
+ if (msie <= 11) {
11438
11544
  // Normalize before parse. Refer Implementation Notes on why this is
11439
11545
  // done in two steps on IE.
11440
11546
  urlParsingNode.setAttribute("href", href);
@@ -11804,7 +11910,7 @@ function filterFilter() {
11804
11910
  })();
11805
11911
  } else {
11806
11912
  (function() {
11807
- if (!expression[key]) return;
11913
+ if (typeof(expression[key]) == 'undefined') { return; }
11808
11914
  var path = key;
11809
11915
  predicates.push(function(value) {
11810
11916
  return search(getter(value,path), expression[path]);
@@ -12533,8 +12639,10 @@ function orderByFilter($parse){
12533
12639
  var t1 = typeof v1;
12534
12640
  var t2 = typeof v2;
12535
12641
  if (t1 == t2) {
12536
- if (t1 == "string") v1 = v1.toLowerCase();
12537
- if (t1 == "string") v2 = v2.toLowerCase();
12642
+ if (t1 == "string") {
12643
+ v1 = v1.toLowerCase();
12644
+ v2 = v2.toLowerCase();
12645
+ }
12538
12646
  if (v1 === v2) return 0;
12539
12647
  return v1 < v2 ? -1 : 1;
12540
12648
  } else {
@@ -14779,8 +14887,8 @@ var ngBindTemplateDirective = ['$interpolate', function($interpolate) {
14779
14887
  var ngBindHtmlDirective = ['$sce', function($sce) {
14780
14888
  return function(scope, element, attr) {
14781
14889
  element.addClass('ng-binding').data('$binding', attr.ngBindHtml);
14782
- scope.$watch($sce.parseAsHtml(attr.ngBindHtml), function ngBindHtmlWatchAction(value) {
14783
- element.html(value || '');
14890
+ scope.$watch(attr.ngBindHtml, function ngBindHtmlWatchAction(value) {
14891
+ element.html($sce.getTrustedHtml(value) || '');
14784
14892
  });
14785
14893
  };
14786
14894
  }];
@@ -14936,7 +15044,7 @@ function classDirective(name, selector) {
14936
15044
 
14937
15045
  ## Animations
14938
15046
 
14939
- Example that demostrates how addition and removal of classes can be animated.
15047
+ The example below demonstrates how to perform animations using ngClass.
14940
15048
 
14941
15049
  <example animations="true">
14942
15050
  <file name="index.html">
@@ -14981,6 +15089,14 @@ function classDirective(name, selector) {
14981
15089
  });
14982
15090
  </file>
14983
15091
  </example>
15092
+
15093
+
15094
+ ## ngClass and pre-existing CSS3 Transitions/Animations
15095
+ The ngClass directive still supports CSS3 Transitions/Animations even if they do not follow the ngAnimate CSS naming structure.
15096
+ Therefore, if any CSS3 Transition/Animation styles (outside of ngAnimate) are set on the element, then, if a ngClass animation
15097
+ is triggered, the ngClass animation will be skipped so that ngAnimate can allow for the pre-existing transition or animation to
15098
+ take over. This restriction allows for ngClass to still work with standard CSS3 Transitions/Animations that are defined
15099
+ outside of ngAnimate.
14984
15100
  */
14985
15101
  var ngClassDirective = classDirective('', true);
14986
15102
 
@@ -15899,23 +16015,18 @@ var ngIfDirective = ['$animate', function($animate) {
15899
16015
  * @description
15900
16016
  * Emitted every time the ngInclude content is reloaded.
15901
16017
  */
15902
- var NG_INCLUDE_PRIORITY = 500;
15903
16018
  var ngIncludeDirective = ['$http', '$templateCache', '$anchorScroll', '$compile', '$animate', '$sce',
15904
16019
  function($http, $templateCache, $anchorScroll, $compile, $animate, $sce) {
15905
16020
  return {
15906
16021
  restrict: 'ECA',
15907
16022
  terminal: true,
15908
- priority: NG_INCLUDE_PRIORITY,
15909
- compile: function(element, attr) {
16023
+ transclude: 'element',
16024
+ compile: function(element, attr, transclusion) {
15910
16025
  var srcExp = attr.ngInclude || attr.src,
15911
16026
  onloadExp = attr.onload || '',
15912
16027
  autoScrollExp = attr.autoscroll;
15913
16028
 
15914
- element.html('');
15915
- var anchor = jqLite(document.createComment(' ngInclude: ' + srcExp + ' '));
15916
- element.replaceWith(anchor);
15917
-
15918
- return function(scope) {
16029
+ return function(scope, $element) {
15919
16030
  var changeCounter = 0,
15920
16031
  currentScope,
15921
16032
  currentElement;
@@ -15939,21 +16050,23 @@ var ngIncludeDirective = ['$http', '$templateCache', '$anchorScroll', '$compile'
15939
16050
  if (thisChangeId !== changeCounter) return;
15940
16051
  var newScope = scope.$new();
15941
16052
 
15942
- cleanupLastIncludeContent();
16053
+ transclusion(newScope, function(clone) {
16054
+ cleanupLastIncludeContent();
15943
16055
 
15944
- currentScope = newScope;
15945
- currentElement = element.clone();
15946
- currentElement.html(response);
15947
- $animate.enter(currentElement, null, anchor);
16056
+ currentScope = newScope;
16057
+ currentElement = clone;
15948
16058
 
15949
- $compile(currentElement, false, NG_INCLUDE_PRIORITY - 1)(currentScope);
16059
+ currentElement.html(response);
16060
+ $animate.enter(currentElement, null, $element);
16061
+ $compile(currentElement.contents())(currentScope);
15950
16062
 
15951
- if (isDefined(autoScrollExp) && (!autoScrollExp || scope.$eval(autoScrollExp))) {
15952
- $anchorScroll();
15953
- }
16063
+ if (isDefined(autoScrollExp) && (!autoScrollExp || scope.$eval(autoScrollExp))) {
16064
+ $anchorScroll();
16065
+ }
15954
16066
 
15955
- currentScope.$emit('$includeContentLoaded');
15956
- scope.$eval(onloadExp);
16067
+ currentScope.$emit('$includeContentLoaded');
16068
+ scope.$eval(onloadExp);
16069
+ });
15957
16070
  }).error(function() {
15958
16071
  if (thisChangeId === changeCounter) cleanupLastIncludeContent();
15959
16072
  });
@@ -17176,7 +17289,9 @@ var ngSwitchDefaultDirective = ngDirective({
17176
17289
  * @name ng.directive:ngTransclude
17177
17290
  *
17178
17291
  * @description
17179
- * Insert the transcluded DOM here.
17292
+ * Directive that marks the insertion point for the transcluded DOM of the nearest parent directive that uses transclusion.
17293
+ *
17294
+ * Any existing content of the element that this directive is placed on will be removed before the transcluded content is inserted.
17180
17295
  *
17181
17296
  * @element ANY
17182
17297
  *
@@ -17220,16 +17335,19 @@ var ngSwitchDefaultDirective = ngDirective({
17220
17335
  *
17221
17336
  */
17222
17337
  var ngTranscludeDirective = ngDirective({
17223
- controller: ['$transclude', '$element', '$scope', function($transclude, $element, $scope) {
17224
- // use evalAsync so that we don't process transclusion before directives on the parent element even when the
17225
- // transclusion replaces the current element. (we can't use priority here because that applies only to compile fns
17226
- // and not controllers
17227
- $scope.$evalAsync(function() {
17228
- $transclude(function(clone) {
17229
- $element.append(clone);
17230
- });
17338
+ controller: ['$transclude', function($transclude) {
17339
+ // remember the transclusion fn but call it during linking so that we don't process transclusion before directives on
17340
+ // the parent element even when the transclusion replaces the current element. (we can't use priority here because
17341
+ // that applies only to compile fns and not controllers
17342
+ this.$transclude = $transclude;
17343
+ }],
17344
+
17345
+ link: function($scope, $element, $attrs, controller) {
17346
+ controller.$transclude(function(clone) {
17347
+ $element.html('');
17348
+ $element.append(clone);
17231
17349
  });
17232
- }]
17350
+ }
17233
17351
  });
17234
17352
 
17235
17353
  /**