mirror of
https://github.com/Hopiu/angular.js.git
synced 2026-03-22 01:10:23 +00:00
fix(ngInclude): only run anchorScroll after animation is done
We need to wait until animations have added the content to the document before trying to `autoscroll` to anchors that may have been inserted. Fixes #4723
This commit is contained in:
parent
9470080762
commit
d378f5500a
2 changed files with 92 additions and 30 deletions
|
|
@ -176,6 +176,11 @@ var ngIncludeDirective = ['$http', '$templateCache', '$anchorScroll', '$compile'
|
|||
};
|
||||
|
||||
scope.$watch($sce.parseAsResourceUrl(srcExp), function ngIncludeWatchAction(src) {
|
||||
var afterAnimation = function() {
|
||||
if (isDefined(autoScrollExp) && (!autoScrollExp || scope.$eval(autoScrollExp))) {
|
||||
$anchorScroll();
|
||||
}
|
||||
};
|
||||
var thisChangeId = ++changeCounter;
|
||||
|
||||
if (src) {
|
||||
|
|
@ -190,13 +195,8 @@ var ngIncludeDirective = ['$http', '$templateCache', '$anchorScroll', '$compile'
|
|||
currentElement = clone;
|
||||
|
||||
currentElement.html(response);
|
||||
$animate.enter(currentElement, null, $element);
|
||||
$animate.enter(currentElement, null, $element, afterAnimation);
|
||||
$compile(currentElement.contents())(currentScope);
|
||||
|
||||
if (isDefined(autoScrollExp) && (!autoScrollExp || scope.$eval(autoScrollExp))) {
|
||||
$anchorScroll();
|
||||
}
|
||||
|
||||
currentScope.$emit('$includeContentLoaded');
|
||||
scope.$eval(onloadExp);
|
||||
});
|
||||
|
|
|
|||
|
|
@ -312,7 +312,7 @@ describe('ngInclude', function() {
|
|||
}));
|
||||
|
||||
|
||||
describe('autoscoll', function() {
|
||||
describe('autoscroll', function() {
|
||||
var autoScrollSpy;
|
||||
|
||||
function spyOnAnchorScroll() {
|
||||
|
|
@ -328,33 +328,58 @@ describe('ngInclude', function() {
|
|||
};
|
||||
}
|
||||
|
||||
function changeTplAndValueTo(template, value) {
|
||||
return function($rootScope, $browser) {
|
||||
$rootScope.$apply(function() {
|
||||
$rootScope.tpl = template;
|
||||
$rootScope.value = value;
|
||||
});
|
||||
};
|
||||
}
|
||||
|
||||
beforeEach(module(spyOnAnchorScroll()));
|
||||
beforeEach(module(spyOnAnchorScroll(), 'mock.animate'));
|
||||
beforeEach(inject(
|
||||
putIntoCache('template.html', 'CONTENT'),
|
||||
putIntoCache('another.html', 'CONTENT')));
|
||||
|
||||
|
||||
it('should call $anchorScroll if autoscroll attribute is present', inject(
|
||||
compileAndLink('<div><ng:include src="tpl" autoscroll></ng:include></div>'),
|
||||
changeTplAndValueTo('template.html'), function() {
|
||||
function($rootScope, $animate, $timeout) {
|
||||
|
||||
$rootScope.$apply(function () {
|
||||
$rootScope.tpl = 'template.html';
|
||||
});
|
||||
|
||||
expect(autoScrollSpy).not.toHaveBeenCalled();
|
||||
$animate.flushNext('enter');
|
||||
$timeout.flush();
|
||||
|
||||
expect(autoScrollSpy).toHaveBeenCalledOnce();
|
||||
}));
|
||||
|
||||
|
||||
it('should call $anchorScroll if autoscroll evaluates to true', inject(
|
||||
compileAndLink('<div><ng:include src="tpl" autoscroll="value"></ng:include></div>'),
|
||||
changeTplAndValueTo('template.html', true),
|
||||
changeTplAndValueTo('another.html', 'some-string'),
|
||||
changeTplAndValueTo('template.html', 100), function() {
|
||||
it('should call $anchorScroll if autoscroll evaluates to true',
|
||||
inject(function($rootScope, $compile, $animate, $timeout) {
|
||||
|
||||
element = $compile('<div><ng:include src="tpl" autoscroll="value"></ng:include></div>')($rootScope);
|
||||
|
||||
$rootScope.$apply(function () {
|
||||
$rootScope.tpl = 'template.html';
|
||||
$rootScope.value = true;
|
||||
});
|
||||
|
||||
$animate.flushNext('enter');
|
||||
$timeout.flush();
|
||||
|
||||
$rootScope.$apply(function () {
|
||||
$rootScope.tpl = 'another.html';
|
||||
$rootScope.value = 'some-string';
|
||||
});
|
||||
|
||||
$animate.flushNext('leave');
|
||||
$animate.flushNext('enter');
|
||||
$timeout.flush();
|
||||
|
||||
$rootScope.$apply(function() {
|
||||
$rootScope.tpl = 'template.html';
|
||||
$rootScope.value = 100;
|
||||
});
|
||||
|
||||
$animate.flushNext('leave');
|
||||
$animate.flushNext('enter');
|
||||
$timeout.flush();
|
||||
|
||||
expect(autoScrollSpy).toHaveBeenCalled();
|
||||
expect(autoScrollSpy.callCount).toBe(3);
|
||||
}));
|
||||
|
|
@ -362,18 +387,55 @@ describe('ngInclude', function() {
|
|||
|
||||
it('should not call $anchorScroll if autoscroll attribute is not present', inject(
|
||||
compileAndLink('<div><ng:include src="tpl"></ng:include></div>'),
|
||||
changeTplAndValueTo('template.html'), function() {
|
||||
function($rootScope, $animate, $timeout) {
|
||||
|
||||
$rootScope.$apply(function () {
|
||||
$rootScope.tpl = 'template.html';
|
||||
});
|
||||
|
||||
$animate.flushNext('enter');
|
||||
$timeout.flush();
|
||||
expect(autoScrollSpy).not.toHaveBeenCalled();
|
||||
}));
|
||||
|
||||
|
||||
it('should not call $anchorScroll if autoscroll evaluates to false', inject(
|
||||
compileAndLink('<div><ng:include src="tpl" autoscroll="value"></ng:include></div>'),
|
||||
changeTplAndValueTo('template.html', false),
|
||||
changeTplAndValueTo('template.html', undefined),
|
||||
changeTplAndValueTo('template.html', null), function() {
|
||||
it('should not call $anchorScroll if autoscroll evaluates to false',
|
||||
inject(function($rootScope, $compile, $animate, $timeout) {
|
||||
|
||||
element = $compile('<div><ng:include src="tpl" autoscroll="value"></ng:include></div>')($rootScope);
|
||||
|
||||
$rootScope.$apply(function () {
|
||||
$rootScope.tpl = 'template.html';
|
||||
$rootScope.value = false;
|
||||
});
|
||||
|
||||
$animate.flushNext('enter');
|
||||
$timeout.flush();
|
||||
|
||||
$rootScope.$apply(function () {
|
||||
$rootScope.tpl = 'template.html';
|
||||
$rootScope.value = undefined;
|
||||
});
|
||||
|
||||
$rootScope.$apply(function () {
|
||||
$rootScope.tpl = 'template.html';
|
||||
$rootScope.value = null;
|
||||
});
|
||||
|
||||
expect(autoScrollSpy).not.toHaveBeenCalled();
|
||||
}));
|
||||
|
||||
it('should only call $anchorScroll after the "enter" animation completes', inject(
|
||||
compileAndLink('<div><ng:include src="tpl" autoscroll></ng:include></div>'),
|
||||
function($rootScope, $animate, $timeout) {
|
||||
expect(autoScrollSpy).not.toHaveBeenCalled();
|
||||
|
||||
$rootScope.$apply("tpl = 'template.html'");
|
||||
$animate.flushNext('enter');
|
||||
$timeout.flush();
|
||||
|
||||
expect(autoScrollSpy).toHaveBeenCalledOnce();
|
||||
}));
|
||||
});
|
||||
});
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue