mirror of
https://github.com/ionic-team/ionic-framework.git
synced 2026-03-13 10:22:08 +08:00
72
js/ext/angular/src/directive/ionicBar.js
vendored
72
js/ext/angular/src/directive/ionicBar.js
vendored
@@ -3,39 +3,8 @@
|
||||
|
||||
angular.module('ionic.ui.header', ['ngAnimate', 'ngSanitize'])
|
||||
|
||||
.directive('ionHeaderBar', ['$document', function($document) {
|
||||
return {
|
||||
restrict: 'E',
|
||||
link: function($scope, $element, $attr, scrollCtrl) {
|
||||
ionic.requestAnimationFrame(function() {
|
||||
var scrollCtrl = $element.controller('$ionicScroll');
|
||||
if (!scrollCtrl) {
|
||||
return;
|
||||
}
|
||||
|
||||
ionic.on('tap', onTap, $element[0]);
|
||||
$scope.$on('$destroy', function() {
|
||||
ionic.off('tap', onTap, $element[0]);
|
||||
});
|
||||
|
||||
function onTap(e) {
|
||||
if (ionic.DomUtil.getParentOrSelfWithClass(e.target, 'button', 4)) {
|
||||
return;
|
||||
}
|
||||
var touch = e.gesture && e.gesture.touches[0] || e.detail.touches[0];
|
||||
var bounds = $element[0].getBoundingClientRect();
|
||||
if(ionic.DomUtil.rectContains(
|
||||
touch.pageX, touch.pageY,
|
||||
bounds.left, bounds.top - 20,
|
||||
bounds.left + bounds.width, bounds.top + bounds.height)
|
||||
) {
|
||||
scrollCtrl.scrollTop(true);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
}])
|
||||
.directive('ionNavBar', TapScrollToTopDirective())
|
||||
.directive('ionHeaderBar', TapScrollToTopDirective())
|
||||
|
||||
/**
|
||||
* @ngdoc directive
|
||||
@@ -111,6 +80,43 @@ angular.module('ionic.ui.header', ['ngAnimate', 'ngSanitize'])
|
||||
*/
|
||||
.directive('ionFooterBar', barDirective(false));
|
||||
|
||||
function TapScrollToTopDirective() {
|
||||
return ['$document', function($document) {
|
||||
return {
|
||||
restrict: 'E',
|
||||
link: function($scope, $element, $attr, scrollCtrl) {
|
||||
ionic.requestAnimationFrame(function() {
|
||||
var scrollCtrl = $element.controller('$ionicScroll');
|
||||
if (!scrollCtrl) {
|
||||
return;
|
||||
}
|
||||
|
||||
ionic.on('tap', onTap, $element[0]);
|
||||
$scope.$on('$destroy', function() {
|
||||
ionic.off('tap', onTap, $element[0]);
|
||||
});
|
||||
|
||||
function onTap(e) {
|
||||
if (ionic.DomUtil.getParentOrSelfWithClass(e.target, 'button', 4)) {
|
||||
return;
|
||||
}
|
||||
var touch = e.gesture && e.gesture.touches[0] || e.detail.touches[0];
|
||||
var bounds = $element[0].getBoundingClientRect();
|
||||
if(ionic.DomUtil.rectContains(
|
||||
touch.pageX, touch.pageY,
|
||||
bounds.left, bounds.top - 20,
|
||||
bounds.left + bounds.width, bounds.top + bounds.height)
|
||||
) {
|
||||
scrollCtrl.scrollTop(true);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
}];
|
||||
}
|
||||
|
||||
|
||||
function barDirective(isHeader) {
|
||||
return ['$parse', function($parse) {
|
||||
return {
|
||||
|
||||
@@ -1,54 +1,56 @@
|
||||
describe('bar directives', function() {
|
||||
beforeEach(module('ionic'));
|
||||
|
||||
describe('tapScrollToTop', function() {
|
||||
function setup() {
|
||||
var el;
|
||||
inject(function($compile, $rootScope) {
|
||||
el = angular.element('<ion-header-bar>')
|
||||
var container = angular.element('<ion-content>').append(el);
|
||||
ionic.requestAnimationFrame = function(cb) { cb(); };
|
||||
$compile(container)($rootScope.$new());
|
||||
container.controller('$ionicScroll').scrollTop = jasmine.createSpy('scrollTop')
|
||||
$rootScope.$apply();
|
||||
['<ion-header-bar>', '<ion-nav-bar>'].forEach(function(tpl) {
|
||||
describe('tapScrollToTop ' + tpl, function() {
|
||||
function setup() {
|
||||
var el;
|
||||
inject(function($compile, $rootScope) {
|
||||
el = angular.element(tpl);
|
||||
var container = angular.element('<ion-content>').append(el);
|
||||
ionic.requestAnimationFrame = function(cb) { cb(); };
|
||||
$compile(container)($rootScope.$new());
|
||||
container.controller('$ionicScroll').scrollTop = jasmine.createSpy('scrollTop');
|
||||
$rootScope.$apply();
|
||||
});
|
||||
return el;
|
||||
}
|
||||
it('should listen for tap, unlisten on destroy', function() {
|
||||
var callback;
|
||||
spyOn(ionic, 'on').andCallFake(function(name, cb) {
|
||||
callback = cb;
|
||||
});
|
||||
spyOn(ionic, 'off');
|
||||
var el = setup();
|
||||
expect(ionic.on).toHaveBeenCalledWith('tap', jasmine.any(Function), el[0]);
|
||||
expect(ionic.off).not.toHaveBeenCalled();
|
||||
el.scope().$destroy();
|
||||
expect(ionic.off).toHaveBeenCalledWith('tap', callback, el[0]);
|
||||
});
|
||||
return el;
|
||||
}
|
||||
it('should listen for tap, unlisten on destroy', function() {
|
||||
var callback;
|
||||
spyOn(ionic, 'on').andCallFake(function(name, cb) {
|
||||
callback = cb;
|
||||
it('should ignore tap if it\'s in a button', function() {
|
||||
var el = setup();
|
||||
spyOn(ionic.DomUtil, 'rectContains');
|
||||
var child = angular.element('<div class="button">');
|
||||
el.append(child);
|
||||
ionic.trigger('tap', { target: child[0] }, true, true);
|
||||
expect(ionic.DomUtil.rectContains).not.toHaveBeenCalled();
|
||||
});
|
||||
spyOn(ionic, 'off');
|
||||
var el = setup();
|
||||
expect(ionic.on).toHaveBeenCalledWith('tap', jasmine.any(Function), el[0]);
|
||||
expect(ionic.off).not.toHaveBeenCalled();
|
||||
el.scope().$destroy();
|
||||
expect(ionic.off).toHaveBeenCalledWith('tap', callback, el[0]);
|
||||
});
|
||||
it('should ignore tap if it\'s in a button', function() {
|
||||
var el = setup();
|
||||
spyOn(ionic.DomUtil, 'rectContains');
|
||||
var child = angular.element('<div class="button">');
|
||||
el.append(child);
|
||||
ionic.trigger('tap', { target: child[0] }, true, true);
|
||||
expect(ionic.DomUtil.rectContains).not.toHaveBeenCalled();
|
||||
});
|
||||
it('should scrollTop if tap is inside headerBar', function() {
|
||||
var el = setup();
|
||||
spyOn(ionic.DomUtil, 'rectContains').andCallFake(function() {
|
||||
return true;
|
||||
it('should scrollTop if tap is inside headerBar', function() {
|
||||
var el = setup();
|
||||
spyOn(ionic.DomUtil, 'rectContains').andCallFake(function() {
|
||||
return true;
|
||||
});
|
||||
ionic.trigger('tap', { target: el[0], touches: [{pageX:0,pageY:0}] });
|
||||
expect(el.controller('$ionicScroll').scrollTop).toHaveBeenCalledWith(true);
|
||||
});
|
||||
ionic.trigger('tap', { target: el[0], touches: [{pageX:0,pageY:0}] });
|
||||
expect(el.controller('$ionicScroll').scrollTop).toHaveBeenCalledWith(true);
|
||||
});
|
||||
it('should not scrollTop if tap isnt inside headerBar', function() {
|
||||
var el = setup();
|
||||
spyOn(ionic.DomUtil, 'rectContains').andCallFake(function() {
|
||||
return false;
|
||||
it('should not scrollTop if tap isnt inside headerBar', function() {
|
||||
var el = setup();
|
||||
spyOn(ionic.DomUtil, 'rectContains').andCallFake(function() {
|
||||
return false;
|
||||
});
|
||||
ionic.trigger('tap', { target: el[0], touches: [{pageX:0,pageY:0}] });
|
||||
expect(el.controller('$ionicScroll').scrollTop).not.toHaveBeenCalled();
|
||||
});
|
||||
ionic.trigger('tap', { target: el[0], touches: [{pageX:0,pageY:0}] });
|
||||
expect(el.controller('$ionicScroll').scrollTop).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
Reference in New Issue
Block a user