fix(ngView): ensure ngView is terminal and uses its own manual transclusion system

This commit is contained in:
Matias Niemelä 2013-08-04 11:20:48 -04:00 committed by Misko Hevery
parent 1b5bee4fa1
commit 87405e25ae

View file

@ -1,7 +1,5 @@
'use strict'; 'use strict';
ngRouteModule.directive('ngView', ngViewFactory);
/** /**
* @ngdoc directive * @ngdoc directive
* @name ngRoute.directive:ngView * @name ngRoute.directive:ngView
@ -169,17 +167,22 @@ ngRouteModule.directive('ngView', ngViewFactory);
* @description * @description
* Emitted every time the ngView content is reloaded. * Emitted every time the ngView content is reloaded.
*/ */
ngViewFactory.$inject = ['$route', '$anchorScroll', '$compile', '$controller', '$animate']; var NG_VIEW_PRIORITY = 500;
function ngViewFactory( $route, $anchorScroll, $compile, $controller, $animate) { var ngViewDirective = ['$route', '$anchorScroll', '$compile', '$controller', '$animate',
function($route, $anchorScroll, $compile, $controller, $animate) {
return { return {
restrict: 'ECA', restrict: 'ECA',
terminal: true, terminal: true,
transclude: 'element', priority: NG_VIEW_PRIORITY,
compile: function(element, attr, linker) { compile: function(element, attr) {
return function(scope, $element, attr) { var onloadExp = attr.onload || '';
var currentScope,
currentElement, element.html('');
onloadExp = attr.onload || ''; var anchor = jqLite(document.createComment(' ngView '));
element.replaceWith(anchor);
return function(scope) {
var currentScope, currentElement;
scope.$on('$routeChangeSuccess', update); scope.$on('$routeChangeSuccess', update);
update(); update();
@ -200,36 +203,35 @@ function ngViewFactory( $route, $anchorScroll, $compile, $controller,
template = locals && locals.$template; template = locals && locals.$template;
if (template) { if (template) {
var newScope = scope.$new(); cleanupLastView();
linker(newScope, function(clone) {
cleanupLastView();
clone.html(template); currentScope = scope.$new();
$animate.enter(clone, null, $element); currentElement = element.clone();
currentElement.html(template);
$animate.enter(currentElement, null, anchor);
var link = $compile(clone.contents()), var link = $compile(currentElement, false, NG_VIEW_PRIORITY - 1),
current = $route.current; current = $route.current;
currentScope = current.scope = newScope; if (current.controller) {
currentElement = clone; locals.$scope = currentScope;
var controller = $controller(current.controller, locals);
if (current.controller) { if (current.controllerAs) {
locals.$scope = currentScope; currentScope[current.controllerAs] = controller;
var controller = $controller(current.controller, locals);
if (current.controllerAs) {
currentScope[current.controllerAs] = controller;
}
clone.data('$ngControllerController', controller);
clone.contents().data('$ngControllerController', controller);
} }
currentElement.data('$ngControllerController', controller);
currentElement.children().data('$ngControllerController', controller);
}
link(currentScope); current.scope = currentScope;
currentScope.$emit('$viewContentLoaded');
currentScope.$eval(onloadExp);
// $anchorScroll might listen on event... link(currentScope);
$anchorScroll();
}); currentScope.$emit('$viewContentLoaded');
currentScope.$eval(onloadExp);
// $anchorScroll might listen on event...
$anchorScroll();
} else { } else {
cleanupLastView(); cleanupLastView();
} }
@ -237,4 +239,6 @@ function ngViewFactory( $route, $anchorScroll, $compile, $controller,
} }
} }
}; };
} }];
ngRouteModule.directive('ngView', ngViewDirective);