angularjs-rails 1.0.3 → 1.0.4
Sign up to get free protection for your applications and to get access to all the features.
- data/lib/angularjs-rails/version.rb +1 -1
- data/vendor/assets/javascripts/angular-bootstrap-prettify.js +5 -5
- data/vendor/assets/javascripts/angular-bootstrap.js +1 -1
- data/vendor/assets/javascripts/angular-cookies.js +1 -1
- data/vendor/assets/javascripts/angular-loader.js +1 -1
- data/vendor/assets/javascripts/angular-mocks.js +29 -6
- data/vendor/assets/javascripts/angular-resource.js +59 -49
- data/vendor/assets/javascripts/angular-sanitize.js +1 -1
- data/vendor/assets/javascripts/angular-scenario.js +215 -296
- data/vendor/assets/javascripts/angular.js +213 -140
- data/vendor/assets/javascripts/jstd-scenario-adapter.js +1 -1
- metadata +2 -2
@@ -1,5 +1,5 @@
|
|
1
1
|
/**
|
2
|
-
* @license AngularJS v1.0.
|
2
|
+
* @license AngularJS v1.0.4
|
3
3
|
* (c) 2010-2012 Google, Inc. http://angularjs.org
|
4
4
|
* License: MIT
|
5
5
|
*/
|
@@ -627,13 +627,15 @@ function equals(o1, o2) {
|
|
627
627
|
if (isScope(o1) || isScope(o2) || isWindow(o1) || isWindow(o2)) return false;
|
628
628
|
keySet = {};
|
629
629
|
for(key in o1) {
|
630
|
-
if (key.charAt(0)
|
631
|
-
|
632
|
-
}
|
630
|
+
if (key.charAt(0) === '$' || isFunction(o1[key])) continue;
|
631
|
+
if (!equals(o1[key], o2[key])) return false;
|
633
632
|
keySet[key] = true;
|
634
633
|
}
|
635
634
|
for(key in o2) {
|
636
|
-
if (!keySet[key] &&
|
635
|
+
if (!keySet[key] &&
|
636
|
+
key.charAt(0) !== '$' &&
|
637
|
+
o2[key] !== undefined &&
|
638
|
+
!isFunction(o2[key])) return false;
|
637
639
|
}
|
638
640
|
return true;
|
639
641
|
}
|
@@ -1247,11 +1249,11 @@ function setupModuleLoader(window) {
|
|
1247
1249
|
* - `codeName` – `{string}` – Code name of the release, such as "jiggling-armfat".
|
1248
1250
|
*/
|
1249
1251
|
var version = {
|
1250
|
-
full: '1.0.
|
1252
|
+
full: '1.0.4', // all of these placeholder strings will be replaced by rake's
|
1251
1253
|
major: 1, // compile task
|
1252
1254
|
minor: 0,
|
1253
|
-
dot:
|
1254
|
-
codeName: '
|
1255
|
+
dot: 4,
|
1256
|
+
codeName: 'bewildering-hair'
|
1255
1257
|
};
|
1256
1258
|
|
1257
1259
|
|
@@ -1423,7 +1425,7 @@ function publishExternalAPI(angular){
|
|
1423
1425
|
* - [val()](http://api.jquery.com/val/)
|
1424
1426
|
* - [wrap()](http://api.jquery.com/wrap/)
|
1425
1427
|
*
|
1426
|
-
* ## In addtion to the above, Angular
|
1428
|
+
* ## In addtion to the above, Angular provides additional methods to both jQuery and jQuery lite:
|
1427
1429
|
*
|
1428
1430
|
* - `controller(name)` - retrieves the controller of the current element or its parent. By default
|
1429
1431
|
* retrieves controller associated with the `ngController` directive. If `name` is provided as
|
@@ -2011,14 +2013,14 @@ forEach({
|
|
2011
2013
|
children: function(element) {
|
2012
2014
|
var children = [];
|
2013
2015
|
forEach(element.childNodes, function(element){
|
2014
|
-
if (element.
|
2016
|
+
if (element.nodeType === 1)
|
2015
2017
|
children.push(element);
|
2016
2018
|
});
|
2017
2019
|
return children;
|
2018
2020
|
},
|
2019
2021
|
|
2020
2022
|
contents: function(element) {
|
2021
|
-
return element.childNodes;
|
2023
|
+
return element.childNodes || [];
|
2022
2024
|
},
|
2023
2025
|
|
2024
2026
|
append: function(element, node) {
|
@@ -2081,7 +2083,16 @@ forEach({
|
|
2081
2083
|
},
|
2082
2084
|
|
2083
2085
|
next: function(element) {
|
2084
|
-
|
2086
|
+
if (element.nextElementSibling) {
|
2087
|
+
return element.nextElementSibling;
|
2088
|
+
}
|
2089
|
+
|
2090
|
+
// IE8 doesn't have nextElementSibling
|
2091
|
+
var elm = element.nextSibling;
|
2092
|
+
while (elm != null && elm.nodeType !== 1) {
|
2093
|
+
elm = elm.nextSibling;
|
2094
|
+
}
|
2095
|
+
return elm;
|
2085
2096
|
},
|
2086
2097
|
|
2087
2098
|
find: function(element, selector) {
|
@@ -2667,7 +2678,7 @@ function createInjector(modulesToLoad) {
|
|
2667
2678
|
}
|
2668
2679
|
|
2669
2680
|
function provider(name, provider_) {
|
2670
|
-
if (isFunction(provider_)) {
|
2681
|
+
if (isFunction(provider_) || isArray(provider_)) {
|
2671
2682
|
provider_ = providerInjector.instantiate(provider_);
|
2672
2683
|
}
|
2673
2684
|
if (!provider_.$get) {
|
@@ -2784,7 +2795,7 @@ function createInjector(modulesToLoad) {
|
|
2784
2795
|
args.push(
|
2785
2796
|
locals && locals.hasOwnProperty(key)
|
2786
2797
|
? locals[key]
|
2787
|
-
: getService(key
|
2798
|
+
: getService(key)
|
2788
2799
|
);
|
2789
2800
|
}
|
2790
2801
|
if (!fn.$inject) {
|
@@ -2884,7 +2895,7 @@ function $AnchorScrollProvider() {
|
|
2884
2895
|
}
|
2885
2896
|
|
2886
2897
|
// does not scroll when user clicks on anchor link that is currently on
|
2887
|
-
// (no url change, no $
|
2898
|
+
// (no url change, no $location.hash() change), browser native does scroll
|
2888
2899
|
if (autoScrollingEnabled) {
|
2889
2900
|
$rootScope.$watch(function autoScrollWatch() {return $location.hash();},
|
2890
2901
|
function autoScrollWatchAction() {
|
@@ -3172,14 +3183,15 @@ function Browser(window, document, $log, $sniffer) {
|
|
3172
3183
|
} else {
|
3173
3184
|
if (isString(value)) {
|
3174
3185
|
cookieLength = (rawDocument.cookie = escape(name) + '=' + escape(value) + ';path=' + cookiePath).length + 1;
|
3186
|
+
|
3187
|
+
// per http://www.ietf.org/rfc/rfc2109.txt browser must allow at minimum:
|
3188
|
+
// - 300 cookies
|
3189
|
+
// - 20 cookies per unique domain
|
3190
|
+
// - 4096 bytes per cookie
|
3175
3191
|
if (cookieLength > 4096) {
|
3176
3192
|
$log.warn("Cookie '"+ name +"' possibly not set or overflowed because it was too large ("+
|
3177
3193
|
cookieLength + " > 4096 bytes)!");
|
3178
3194
|
}
|
3179
|
-
if (lastCookies.length > 20) {
|
3180
|
-
$log.warn("Cookie '"+ name +"' possibly not set or overflowed because too many cookies " +
|
3181
|
-
"were already set (" + lastCookies.length + " > 20 )");
|
3182
|
-
}
|
3183
3195
|
}
|
3184
3196
|
}
|
3185
3197
|
} else {
|
@@ -3745,7 +3757,7 @@ function $CompileProvider($provide) {
|
|
3745
3757
|
// We can not compile top level text elements since text nodes can be merged and we will
|
3746
3758
|
// not be able to attach scope data to them, so we will wrap them in <span>
|
3747
3759
|
forEach($compileNodes, function(node, index){
|
3748
|
-
if (node.nodeType == 3 /* text node */) {
|
3760
|
+
if (node.nodeType == 3 /* text node */ && node.nodeValue.match(/\S+/) /* non-empty */ ) {
|
3749
3761
|
$compileNodes[index] = jqLite(node).wrap('<span></span>').parent()[0];
|
3750
3762
|
}
|
3751
3763
|
});
|
@@ -3794,68 +3806,74 @@ function $CompileProvider($provide) {
|
|
3794
3806
|
* @returns {?function} A composite linking function of all of the matched directives or null.
|
3795
3807
|
*/
|
3796
3808
|
function compileNodes(nodeList, transcludeFn, $rootElement, maxPriority) {
|
3797
|
-
|
3798
|
-
|
3809
|
+
var linkFns = [],
|
3810
|
+
nodeLinkFn, childLinkFn, directives, attrs, linkFnFound;
|
3799
3811
|
|
3800
|
-
|
3801
|
-
|
3812
|
+
for(var i = 0; i < nodeList.length; i++) {
|
3813
|
+
attrs = new Attributes();
|
3802
3814
|
|
3803
|
-
|
3804
|
-
|
3815
|
+
// we must always refer to nodeList[i] since the nodes can be replaced underneath us.
|
3816
|
+
directives = collectDirectives(nodeList[i], [], attrs, maxPriority);
|
3805
3817
|
|
3806
|
-
|
3807
|
-
|
3808
|
-
|
3818
|
+
nodeLinkFn = (directives.length)
|
3819
|
+
? applyDirectivesToNode(directives, nodeList[i], attrs, transcludeFn, $rootElement)
|
3820
|
+
: null;
|
3809
3821
|
|
3810
|
-
|
3811
|
-
|
3812
|
-
|
3813
|
-
|
3822
|
+
childLinkFn = (nodeLinkFn && nodeLinkFn.terminal || !nodeList[i].childNodes.length)
|
3823
|
+
? null
|
3824
|
+
: compileNodes(nodeList[i].childNodes,
|
3825
|
+
nodeLinkFn ? nodeLinkFn.transclude : transcludeFn);
|
3814
3826
|
|
3815
|
-
|
3816
|
-
|
3817
|
-
|
3818
|
-
|
3827
|
+
linkFns.push(nodeLinkFn);
|
3828
|
+
linkFns.push(childLinkFn);
|
3829
|
+
linkFnFound = (linkFnFound || nodeLinkFn || childLinkFn);
|
3830
|
+
}
|
3819
3831
|
|
3820
|
-
|
3821
|
-
|
3832
|
+
// return a linking function if we have found anything, null otherwise
|
3833
|
+
return linkFnFound ? compositeLinkFn : null;
|
3822
3834
|
|
3823
|
-
|
3824
|
-
|
3835
|
+
function compositeLinkFn(scope, nodeList, $rootElement, boundTranscludeFn) {
|
3836
|
+
var nodeLinkFn, childLinkFn, node, childScope, childTranscludeFn, i, ii, n;
|
3825
3837
|
|
3826
|
-
|
3827
|
-
|
3828
|
-
|
3829
|
-
|
3838
|
+
// copy nodeList so that linking doesn't break due to live list updates.
|
3839
|
+
var stableNodeList = [];
|
3840
|
+
for (i = 0, ii = nodeList.length; i < ii; i++) {
|
3841
|
+
stableNodeList.push(nodeList[i]);
|
3842
|
+
}
|
3830
3843
|
|
3831
|
-
|
3832
|
-
|
3833
|
-
|
3834
|
-
|
3835
|
-
|
3836
|
-
|
3837
|
-
|
3838
|
-
|
3839
|
-
|
3840
|
-
|
3841
|
-
|
3842
|
-
|
3843
|
-
|
3844
|
-
|
3845
|
-
|
3846
|
-
|
3844
|
+
for(i = 0, n = 0, ii = linkFns.length; i < ii; n++) {
|
3845
|
+
node = stableNodeList[n];
|
3846
|
+
nodeLinkFn = linkFns[i++];
|
3847
|
+
childLinkFn = linkFns[i++];
|
3848
|
+
|
3849
|
+
if (nodeLinkFn) {
|
3850
|
+
if (nodeLinkFn.scope) {
|
3851
|
+
childScope = scope.$new(isObject(nodeLinkFn.scope));
|
3852
|
+
jqLite(node).data('$scope', childScope);
|
3853
|
+
} else {
|
3854
|
+
childScope = scope;
|
3855
|
+
}
|
3856
|
+
childTranscludeFn = nodeLinkFn.transclude;
|
3857
|
+
if (childTranscludeFn || (!boundTranscludeFn && transcludeFn)) {
|
3858
|
+
nodeLinkFn(childLinkFn, childScope, node, $rootElement,
|
3859
|
+
(function(transcludeFn) {
|
3860
|
+
return function(cloneFn) {
|
3861
|
+
var transcludeScope = scope.$new();
|
3862
|
+
|
3863
|
+
return transcludeFn(transcludeScope, cloneFn).
|
3864
|
+
bind('$destroy', bind(transcludeScope, transcludeScope.$destroy));
|
3847
3865
|
};
|
3848
3866
|
})(childTranscludeFn || transcludeFn)
|
3849
|
-
|
3850
|
-
|
3851
|
-
|
3852
|
-
|
3853
|
-
|
3854
|
-
|
3855
|
-
|
3856
|
-
|
3857
|
-
|
3858
|
-
|
3867
|
+
);
|
3868
|
+
} else {
|
3869
|
+
nodeLinkFn(childLinkFn, childScope, node, undefined, boundTranscludeFn);
|
3870
|
+
}
|
3871
|
+
} else if (childLinkFn) {
|
3872
|
+
childLinkFn(scope, node.childNodes, undefined, boundTranscludeFn);
|
3873
|
+
}
|
3874
|
+
}
|
3875
|
+
}
|
3876
|
+
}
|
3859
3877
|
|
3860
3878
|
|
3861
3879
|
/**
|
@@ -4002,7 +4020,7 @@ function $CompileProvider($provide) {
|
|
4002
4020
|
if (directiveValue == 'element') {
|
4003
4021
|
$template = jqLite(compileNode);
|
4004
4022
|
$compileNode = templateAttrs.$$element =
|
4005
|
-
jqLite('
|
4023
|
+
jqLite(document.createComment(' ' + directiveName + ': ' + templateAttrs[directiveName] + ' '));
|
4006
4024
|
compileNode = $compileNode[0];
|
4007
4025
|
replaceWith($rootElement, jqLite($template[0]), compileNode);
|
4008
4026
|
childTranscludeFn = compile($template, transcludeFn, terminalPriority);
|
@@ -4667,11 +4685,12 @@ function $DocumentProvider(){
|
|
4667
4685
|
* the browser console.
|
4668
4686
|
*
|
4669
4687
|
* In unit tests, if `angular-mocks.js` is loaded, this service is overridden by
|
4670
|
-
* {@link ngMock.$exceptionHandler mock $exceptionHandler}
|
4688
|
+
* {@link ngMock.$exceptionHandler mock $exceptionHandler} which aids in testing.
|
4671
4689
|
*
|
4672
4690
|
* @param {Error} exception Exception associated with the error.
|
4673
4691
|
* @param {string=} cause optional information about the context in which
|
4674
4692
|
* the error was thrown.
|
4693
|
+
*
|
4675
4694
|
*/
|
4676
4695
|
function $ExceptionHandlerProvider() {
|
4677
4696
|
this.$get = ['$log', function($log){
|
@@ -6471,7 +6490,7 @@ function $ParseProvider() {
|
|
6471
6490
|
* performed asynchronously, and may or may not be finished at any given point in time.
|
6472
6491
|
*
|
6473
6492
|
* From the perspective of dealing with error handling, deferred and promise apis are to
|
6474
|
-
* asynchronous
|
6493
|
+
* asynchronous programming what `try`, `catch` and `throw` keywords are to synchronous programming.
|
6475
6494
|
*
|
6476
6495
|
* <pre>
|
6477
6496
|
* // for the purpose of this example let's assume that variables `$q` and `scope` are
|
@@ -6581,6 +6600,30 @@ function $ParseProvider() {
|
|
6581
6600
|
* you can treat promises attached to a scope as if they were the resulting values.
|
6582
6601
|
* - Q has many more features that $q, but that comes at a cost of bytes. $q is tiny, but contains
|
6583
6602
|
* all the important functionality needed for common async tasks.
|
6603
|
+
*
|
6604
|
+
* # Testing
|
6605
|
+
*
|
6606
|
+
* <pre>
|
6607
|
+
* it('should simulate promise', inject(function($q, $rootSCope) {
|
6608
|
+
* var deferred = $q.defer();
|
6609
|
+
* var promise = deferred.promise;
|
6610
|
+
* var resolvedValue;
|
6611
|
+
*
|
6612
|
+
* promise.then(function(value) { resolvedValue = value; });
|
6613
|
+
* expect(resolvedValue).toBeUndefined();
|
6614
|
+
*
|
6615
|
+
* // Simulate resolving of promise
|
6616
|
+
* defered.resolve(123);
|
6617
|
+
* // Note that the 'then' function does not get called synchronously.
|
6618
|
+
* // This is because we want the promise API to always be async, whether or not
|
6619
|
+
* // it got called synchronously or asynchronously.
|
6620
|
+
* expect(resolvedValue).toBeUndefined();
|
6621
|
+
*
|
6622
|
+
* // Propagate promise resolution to 'then' functions using $apply().
|
6623
|
+
* $rootScope.$apply();
|
6624
|
+
* expect(resolvedValue).toEqual(123);
|
6625
|
+
* });
|
6626
|
+
* </pre>
|
6584
6627
|
*/
|
6585
6628
|
function $QProvider() {
|
6586
6629
|
|
@@ -6867,8 +6910,13 @@ function $RouteProvider(){
|
|
6867
6910
|
*
|
6868
6911
|
* @param {string} path Route path (matched against `$location.path`). If `$location.path`
|
6869
6912
|
* contains redundant trailing slash or is missing one, the route will still match and the
|
6870
|
-
* `$location.path` will be updated to add or drop the trailing slash to
|
6913
|
+
* `$location.path` will be updated to add or drop the trailing slash to exactly match the
|
6871
6914
|
* route definition.
|
6915
|
+
*
|
6916
|
+
* `path` can contain named groups starting with a colon (`:name`). All characters up to the
|
6917
|
+
* next slash are matched and stored in `$routeParams` under the given `name` when the route
|
6918
|
+
* matches.
|
6919
|
+
*
|
6872
6920
|
* @param {Object} route Mapping information to be assigned to `$route.current` on route
|
6873
6921
|
* match.
|
6874
6922
|
*
|
@@ -7133,8 +7181,7 @@ function $RouteProvider(){
|
|
7133
7181
|
* instance of the Controller.
|
7134
7182
|
*/
|
7135
7183
|
|
7136
|
-
var
|
7137
|
-
forceReload = false,
|
7184
|
+
var forceReload = false,
|
7138
7185
|
$route = {
|
7139
7186
|
routes: routes,
|
7140
7187
|
|
@@ -7162,21 +7209,36 @@ function $RouteProvider(){
|
|
7162
7209
|
|
7163
7210
|
/////////////////////////////////////////////////////
|
7164
7211
|
|
7212
|
+
/**
|
7213
|
+
* @param on {string} current url
|
7214
|
+
* @param when {string} route when template to match the url against
|
7215
|
+
* @return {?Object}
|
7216
|
+
*/
|
7165
7217
|
function switchRouteMatcher(on, when) {
|
7166
7218
|
// TODO(i): this code is convoluted and inefficient, we should construct the route matching
|
7167
7219
|
// regex only once and then reuse it
|
7168
|
-
|
7220
|
+
|
7221
|
+
// Escape regexp special characters.
|
7222
|
+
when = '^' + when.replace(/[-\/\\^$*+?.()|[\]{}]/g, "\\$&") + '$';
|
7223
|
+
var regex = '',
|
7169
7224
|
params = [],
|
7170
7225
|
dst = {};
|
7171
|
-
|
7172
|
-
|
7173
|
-
|
7174
|
-
|
7175
|
-
|
7176
|
-
|
7177
|
-
|
7178
|
-
|
7179
|
-
|
7226
|
+
|
7227
|
+
var re = /:(\w+)/g,
|
7228
|
+
paramMatch,
|
7229
|
+
lastMatchedIndex = 0;
|
7230
|
+
|
7231
|
+
while ((paramMatch = re.exec(when)) !== null) {
|
7232
|
+
// Find each :param in `when` and replace it with a capturing group.
|
7233
|
+
// Append all other sections of when unchanged.
|
7234
|
+
regex += when.slice(lastMatchedIndex, paramMatch.index);
|
7235
|
+
regex += '([^\\/]*)';
|
7236
|
+
params.push(paramMatch[1]);
|
7237
|
+
lastMatchedIndex = re.lastIndex;
|
7238
|
+
}
|
7239
|
+
// Append trailing path part.
|
7240
|
+
regex += when.substr(lastMatchedIndex);
|
7241
|
+
|
7180
7242
|
var match = on.match(new RegExp(regex));
|
7181
7243
|
if (match) {
|
7182
7244
|
forEach(params, function(name, index) {
|
@@ -7265,7 +7327,7 @@ function $RouteProvider(){
|
|
7265
7327
|
// Match a route
|
7266
7328
|
var params, match;
|
7267
7329
|
forEach(routes, function(route, path) {
|
7268
|
-
if (!match && (params =
|
7330
|
+
if (!match && (params = switchRouteMatcher($location.path(), path))) {
|
7269
7331
|
match = inherit(route, {
|
7270
7332
|
params: extend({}, $location.search(), params),
|
7271
7333
|
pathParams: params});
|
@@ -7417,7 +7479,7 @@ function $RootScopeProvider(){
|
|
7417
7479
|
expect(scope.greeting).toEqual(undefined);
|
7418
7480
|
|
7419
7481
|
scope.$watch('name', function() {
|
7420
|
-
|
7482
|
+
scope.greeting = scope.salutation + ' ' + scope.name + '!';
|
7421
7483
|
}); // initialize the watch
|
7422
7484
|
|
7423
7485
|
expect(scope.greeting).toEqual(undefined);
|
@@ -7460,6 +7522,7 @@ function $RootScopeProvider(){
|
|
7460
7522
|
this.$$nextSibling = this.$$prevSibling =
|
7461
7523
|
this.$$childHead = this.$$childTail = null;
|
7462
7524
|
this['this'] = this.$root = this;
|
7525
|
+
this.$$destroyed = false;
|
7463
7526
|
this.$$asyncQueue = [];
|
7464
7527
|
this.$$listeners = {};
|
7465
7528
|
}
|
@@ -7578,7 +7641,7 @@ function $RootScopeProvider(){
|
|
7578
7641
|
scope.counter = 0;
|
7579
7642
|
|
7580
7643
|
expect(scope.counter).toEqual(0);
|
7581
|
-
scope.$watch('name', function(newValue, oldValue) { counter = counter + 1; });
|
7644
|
+
scope.$watch('name', function(newValue, oldValue) { scope.counter = scope.counter + 1; });
|
7582
7645
|
expect(scope.counter).toEqual(0);
|
7583
7646
|
|
7584
7647
|
scope.$digest();
|
@@ -7671,7 +7734,7 @@ function $RootScopeProvider(){
|
|
7671
7734
|
|
7672
7735
|
expect(scope.counter).toEqual(0);
|
7673
7736
|
scope.$watch('name', function(newValue, oldValue) {
|
7674
|
-
counter = counter + 1;
|
7737
|
+
scope.counter = scope.counter + 1;
|
7675
7738
|
});
|
7676
7739
|
expect(scope.counter).toEqual(0);
|
7677
7740
|
|
@@ -7793,10 +7856,12 @@ function $RootScopeProvider(){
|
|
7793
7856
|
* perform any necessary cleanup.
|
7794
7857
|
*/
|
7795
7858
|
$destroy: function() {
|
7796
|
-
|
7859
|
+
// we can't destroy the root scope or a scope that has been already destroyed
|
7860
|
+
if ($rootScope == this || this.$$destroyed) return;
|
7797
7861
|
var parent = this.$parent;
|
7798
7862
|
|
7799
7863
|
this.$broadcast('$destroy');
|
7864
|
+
this.$$destroyed = true;
|
7800
7865
|
|
7801
7866
|
if (parent.$$childHead == this) parent.$$childHead = this.$$nextSibling;
|
7802
7867
|
if (parent.$$childTail == this) parent.$$childTail = this.$$prevSibling;
|
@@ -8346,7 +8411,7 @@ function $HttpProvider() {
|
|
8346
8411
|
/**
|
8347
8412
|
* @ngdoc function
|
8348
8413
|
* @name ng.$http
|
8349
|
-
* @requires $
|
8414
|
+
* @requires $httpBackend
|
8350
8415
|
* @requires $browser
|
8351
8416
|
* @requires $cacheFactory
|
8352
8417
|
* @requires $rootScope
|
@@ -8382,8 +8447,7 @@ function $HttpProvider() {
|
|
8382
8447
|
* }).
|
8383
8448
|
* error(function(data, status, headers, config) {
|
8384
8449
|
* // called asynchronously if an error occurs
|
8385
|
-
* // or server returns response with status
|
8386
|
-
* // code outside of the <200, 400) range
|
8450
|
+
* // or server returns response with an error status.
|
8387
8451
|
* });
|
8388
8452
|
* </pre>
|
8389
8453
|
*
|
@@ -8392,6 +8456,10 @@ function $HttpProvider() {
|
|
8392
8456
|
* an object representing the response. See the api signature and type info below for more
|
8393
8457
|
* details.
|
8394
8458
|
*
|
8459
|
+
* A response status code that falls in the [200, 300) range is considered a success status and
|
8460
|
+
* will result in the success callback being called. Note that if the response is a redirect,
|
8461
|
+
* XMLHttpRequest will transparently follow it, meaning that the error callback will not be
|
8462
|
+
* called for such responses.
|
8395
8463
|
*
|
8396
8464
|
* # Shortcut methods
|
8397
8465
|
*
|
@@ -10229,7 +10297,6 @@ var htmlAnchorDirective = valueFn({
|
|
10229
10297
|
// if we have no href url, then don't navigate anywhere.
|
10230
10298
|
if (!element.attr('href')) {
|
10231
10299
|
event.preventDefault();
|
10232
|
-
return false; // Needed for opera
|
10233
10300
|
}
|
10234
10301
|
});
|
10235
10302
|
}
|
@@ -10566,13 +10633,13 @@ var nullFormCtrl = {
|
|
10566
10633
|
*
|
10567
10634
|
* @property {boolean} $pristine True if user has not interacted with the form yet.
|
10568
10635
|
* @property {boolean} $dirty True if user has already interacted with the form.
|
10569
|
-
* @property {boolean} $valid True if all of the
|
10636
|
+
* @property {boolean} $valid True if all of the containing forms and controls are valid.
|
10570
10637
|
* @property {boolean} $invalid True if at least one containing control or form is invalid.
|
10571
10638
|
*
|
10572
10639
|
* @property {Object} $error Is an object hash, containing references to all invalid controls or
|
10573
10640
|
* forms, where:
|
10574
10641
|
*
|
10575
|
-
* - keys are validation tokens (error names) — such as `
|
10642
|
+
* - keys are validation tokens (error names) — such as `required`, `url` or `email`),
|
10576
10643
|
* - values are arrays of controls or forms that are invalid with given error.
|
10577
10644
|
*
|
10578
10645
|
* @description
|
@@ -10685,7 +10752,7 @@ function FormController(element, attrs) {
|
|
10685
10752
|
* does not allow nesting of form elements. It is useful to nest forms, for example if the validity of a
|
10686
10753
|
* sub-group of controls needs to be determined.
|
10687
10754
|
*
|
10688
|
-
* @param {string=} ngForm
|
10755
|
+
* @param {string=} name|ngForm Name of the form. If specified, the form controller will be published into
|
10689
10756
|
* related scope, under this name.
|
10690
10757
|
*
|
10691
10758
|
*/
|
@@ -10758,12 +10825,12 @@ function FormController(element, attrs) {
|
|
10758
10825
|
</script>
|
10759
10826
|
<form name="myForm" ng-controller="Ctrl">
|
10760
10827
|
userType: <input name="input" ng-model="userType" required>
|
10761
|
-
<span class="error" ng-show="myForm.input.$error.
|
10828
|
+
<span class="error" ng-show="myForm.input.$error.required">Required!</span><br>
|
10762
10829
|
<tt>userType = {{userType}}</tt><br>
|
10763
10830
|
<tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br>
|
10764
10831
|
<tt>myForm.input.$error = {{myForm.input.$error}}</tt><br>
|
10765
10832
|
<tt>myForm.$valid = {{myForm.$valid}}</tt><br>
|
10766
|
-
<tt>myForm.$error.
|
10833
|
+
<tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br>
|
10767
10834
|
</form>
|
10768
10835
|
</doc:source>
|
10769
10836
|
<doc:scenario>
|
@@ -13353,14 +13420,17 @@ var ngRepeatDirective = ngDirective({
|
|
13353
13420
|
scope.$watch(function ngRepeatWatch(scope){
|
13354
13421
|
var index, length,
|
13355
13422
|
collection = scope.$eval(rhs),
|
13356
|
-
|
13357
|
-
childScope,
|
13423
|
+
cursor = iterStartElement, // current position of the node
|
13358
13424
|
// Same as lastOrder but it has the current state. It will become the
|
13359
13425
|
// lastOrder on the next iteration.
|
13360
13426
|
nextOrder = new HashQueueMap(),
|
13427
|
+
arrayLength,
|
13428
|
+
childScope,
|
13361
13429
|
key, value, // key/value of iteration
|
13362
|
-
array,
|
13363
|
-
|
13430
|
+
array,
|
13431
|
+
last; // last object information {scope, element, index}
|
13432
|
+
|
13433
|
+
|
13364
13434
|
|
13365
13435
|
if (!isArray(collection)) {
|
13366
13436
|
// if object, extract keys, sort them and use to determine order of iteration over obj props
|
@@ -13375,6 +13445,8 @@ var ngRepeatDirective = ngDirective({
|
|
13375
13445
|
array = collection || [];
|
13376
13446
|
}
|
13377
13447
|
|
13448
|
+
arrayLength = array.length;
|
13449
|
+
|
13378
13450
|
// we are not using forEach for perf reasons (trying to avoid #call)
|
13379
13451
|
for (index = 0, length = array.length; index < length; index++) {
|
13380
13452
|
key = (collection === array) ? index : array[index];
|
@@ -13410,7 +13482,7 @@ var ngRepeatDirective = ngDirective({
|
|
13410
13482
|
childScope.$index = index;
|
13411
13483
|
|
13412
13484
|
childScope.$first = (index === 0);
|
13413
|
-
childScope.$last = (index === (
|
13485
|
+
childScope.$last = (index === (arrayLength - 1));
|
13414
13486
|
childScope.$middle = !(childScope.$first || childScope.$last);
|
13415
13487
|
|
13416
13488
|
if (!last) {
|
@@ -13631,52 +13703,53 @@ var ngStyleDirective = ngDirective(function(scope, element, attr) {
|
|
13631
13703
|
var NG_SWITCH = 'ng-switch';
|
13632
13704
|
var ngSwitchDirective = valueFn({
|
13633
13705
|
restrict: 'EA',
|
13634
|
-
|
13706
|
+
require: 'ngSwitch',
|
13707
|
+
controller: function ngSwitchController() {
|
13708
|
+
this.cases = {};
|
13709
|
+
},
|
13710
|
+
link: function(scope, element, attr, ctrl) {
|
13635
13711
|
var watchExpr = attr.ngSwitch || attr.on,
|
13636
|
-
|
13637
|
-
|
13638
|
-
|
13639
|
-
|
13640
|
-
|
13641
|
-
|
13642
|
-
|
13643
|
-
|
13644
|
-
|
13645
|
-
|
13646
|
-
|
13647
|
-
|
13648
|
-
|
13649
|
-
|
13650
|
-
|
13651
|
-
|
13652
|
-
|
13653
|
-
|
13654
|
-
|
13655
|
-
element.append(caseElement);
|
13656
|
-
});
|
13657
|
-
}
|
13658
|
-
});
|
13659
|
-
};
|
13712
|
+
selectedTransclude,
|
13713
|
+
selectedElement,
|
13714
|
+
selectedScope;
|
13715
|
+
|
13716
|
+
scope.$watch(watchExpr, function ngSwitchWatchAction(value) {
|
13717
|
+
if (selectedElement) {
|
13718
|
+
selectedScope.$destroy();
|
13719
|
+
selectedElement.remove();
|
13720
|
+
selectedElement = selectedScope = null;
|
13721
|
+
}
|
13722
|
+
if ((selectedTransclude = ctrl.cases['!' + value] || ctrl.cases['?'])) {
|
13723
|
+
scope.$eval(attr.change);
|
13724
|
+
selectedScope = scope.$new();
|
13725
|
+
selectedTransclude(selectedScope, function(caseElement) {
|
13726
|
+
selectedElement = caseElement;
|
13727
|
+
element.append(caseElement);
|
13728
|
+
});
|
13729
|
+
}
|
13730
|
+
});
|
13660
13731
|
}
|
13661
13732
|
});
|
13662
13733
|
|
13663
13734
|
var ngSwitchWhenDirective = ngDirective({
|
13664
13735
|
transclude: 'element',
|
13665
13736
|
priority: 500,
|
13737
|
+
require: '^ngSwitch',
|
13666
13738
|
compile: function(element, attrs, transclude) {
|
13667
|
-
|
13668
|
-
|
13669
|
-
|
13739
|
+
return function(scope, element, attr, ctrl) {
|
13740
|
+
ctrl.cases['!' + attrs.ngSwitchWhen] = transclude;
|
13741
|
+
};
|
13670
13742
|
}
|
13671
13743
|
});
|
13672
13744
|
|
13673
13745
|
var ngSwitchDefaultDirective = ngDirective({
|
13674
13746
|
transclude: 'element',
|
13675
13747
|
priority: 500,
|
13748
|
+
require: '^ngSwitch',
|
13676
13749
|
compile: function(element, attrs, transclude) {
|
13677
|
-
|
13678
|
-
|
13679
|
-
|
13750
|
+
return function(scope, element, attr, ctrl) {
|
13751
|
+
ctrl.cases['?'] = transclude;
|
13752
|
+
};
|
13680
13753
|
}
|
13681
13754
|
});
|
13682
13755
|
|
@@ -13765,7 +13838,7 @@ var ngTranscludeDirective = ngDirective({
|
|
13765
13838
|
<hr />
|
13766
13839
|
|
13767
13840
|
<pre>$location.path() = {{$location.path()}}</pre>
|
13768
|
-
<pre>$route.current.
|
13841
|
+
<pre>$route.current.templateUrl = {{$route.current.templateUrl}}</pre>
|
13769
13842
|
<pre>$route.current.params = {{$route.current.params}}</pre>
|
13770
13843
|
<pre>$route.current.scope.name = {{$route.current.scope.name}}</pre>
|
13771
13844
|
<pre>$routeParams = {{$routeParams}}</pre>
|
@@ -14211,7 +14284,7 @@ var selectDirective = ['$compile', '$parse', function($compile, $parse) {
|
|
14211
14284
|
var lastView;
|
14212
14285
|
ctrl.$render = function() {
|
14213
14286
|
var items = new HashMap(ctrl.$viewValue);
|
14214
|
-
forEach(selectElement.
|
14287
|
+
forEach(selectElement.find('option'), function(option) {
|
14215
14288
|
option.selected = isDefined(items.get(option.value));
|
14216
14289
|
});
|
14217
14290
|
};
|
@@ -14228,7 +14301,7 @@ var selectDirective = ['$compile', '$parse', function($compile, $parse) {
|
|
14228
14301
|
selectElement.bind('change', function() {
|
14229
14302
|
scope.$apply(function() {
|
14230
14303
|
var array = [];
|
14231
|
-
forEach(selectElement.
|
14304
|
+
forEach(selectElement.find('option'), function(option) {
|
14232
14305
|
if (option.selected) {
|
14233
14306
|
array.push(option.value);
|
14234
14307
|
}
|