Difference between revisions of "Team:SCU China/jquerynav"

(Created page with "/* * jQuery One Page Nav Plugin * http://github.com/davist11/jQuery-One-Page-Nav * * Copyright (c) 2010 Trevor Davis (http://trevordavis.net) * Dual licensed under the...")
 
 
Line 3: Line 3:
 
  * http://github.com/davist11/jQuery-One-Page-Nav
 
  * http://github.com/davist11/jQuery-One-Page-Nav
 
  *
 
  *
  *  
+
  * Copyright (c) 2010 Trevor Davis (http://trevordavis.net)
 
+
  * Dual licensed under the MIT and GPL licenses.
Copyright (c) 2010 Trevor Davis (http://trevordavis.net)
+
  * Dual licensed under the MIT and  
+
 
+
GPL licenses.
+
 
  * Uses the same license as jQuery, see:
 
  * Uses the same license as jQuery, see:
 
  * http://jquery.org/license
 
  * http://jquery.org/license
 
  *
 
  *
  *  
+
  * @version 3.0.0
 
+
@version 3.0.0
+
 
  *
 
  *
 
  * Example usage:
 
  * Example usage:
 
  * $('#nav').onePageNav({
 
  * $('#nav').onePageNav({
 
  *  currentClass: 'current',
 
  *  currentClass: 'current',
  *   
+
  *  changeHash: false,
 
+
changeHash: false,
+
 
  *  scrollSpeed: 750
 
  *  scrollSpeed: 750
 
  * });
 
  * });
Line 28: Line 20:
 
;(function($, window, document, undefined){
 
;(function($, window, document, undefined){
  
+
// our plugin constructor
 
+
// our plugin constructor
+
 
var OnePageNav = function(elem, options){
 
var OnePageNav = function(elem, options){
+
this.elem = elem;
 
+
this.elem = elem;
+
 
this.$elem = $(elem);
 
this.$elem = $(elem);
 
this.options = options;
 
this.options = options;
+
this.metadata = this.$elem.data('plugin-options');
 
+
this.metadata = this.$elem.data('plugin-options');
+
 
this.$win = $(window);
 
this.$win = $(window);
+
this.sections = {};
 
+
this.sections = {};
+
 
this.didScroll = false;
 
this.didScroll = false;
 
this.$doc = $(document);
 
this.$doc = $(document);
+
this.docHeight = this.$doc.height();
 
+
this.docHeight = this.$doc.height();
+
 
};
 
};
  
 
// the plugin prototype
 
// the plugin prototype
+
OnePageNav.prototype = {
 
+
OnePageNav.prototype = {
+
 
defaults: {
 
defaults: {
 
navItems: 'a',
 
navItems: 'a',
+
currentClass: 'current',
 
+
currentClass: 'current',
+
 
changeHash: false,
 
changeHash: false,
+
easing: 'swing',
 
+
easing: 'swing',
+
 
filter: '',
 
filter: '',
 
scrollSpeed: 750,
 
scrollSpeed: 750,
+
scrollThreshold: 0.5,
 
+
scrollThreshold: 0.5,
+
 
begin: false,
 
begin: false,
end:  
+
end: false,
 
+
false,
+
 
scrollChange: false
 
scrollChange: false
 
},
 
},
  
 
init: function() {
 
init: function() {
+
// Introduce defaults that can be extended either
 
+
// globally or using an object literal.
// Introduce defaults that can be extended either
+
this.config = $.extend({}, this.defaults, this.options, this.metadata);
//  
+
 
+
globally or using an object literal.
+
this.config = $.extend({},  
+
 
+
this.defaults, this.options, this.metadata);
+
 
+
this.$nav = this.$elem.find
+
  
(this.config.navItems);
+
this.$nav = this.$elem.find(this.config.navItems);
  
 
//Filter any links out of the nav
 
//Filter any links out of the nav
+
if(this.config.filter !== '') {
 
+
this.$nav = this.$nav.filter(this.config.filter);
if(this.config.filter !== '') {
+
this.$nav = this.$nav.filter
+
 
+
(this.config.filter);
+
 
}
 
}
  
 
//Handle clicks on the nav
 
//Handle clicks on the nav
+
this.$nav.on('click.onePageNav', $.proxy(this.handleClick, this));
  
this.$nav.on('click.onePageNav', $.proxy(this.handleClick, this));
+
//Get the section positions
 
+
+
 
+
//Get the section positions
+
 
this.getPositions();
 
this.getPositions();
  
+
//Handle scroll changes
 
+
//Handle scroll changes
+
 
this.bindInterval();
 
this.bindInterval();
  
//Update the  
+
//Update the positions on resize too
 
+
this.$win.on('resize.onePageNav', $.proxy(this.getPositions, this));
positions on resize too
+
this.$win.on('resize.onePageNav', $.proxy
+
 
+
(this.getPositions, this));
+
  
 
return this;
 
return this;
 
},
 
},
  
+
adjustNav: function(self, $parent) {
 
+
self.$elem.find('.' + self.config.currentClass).removeClass(self.config.currentClass);
adjustNav: function(self, $parent) {
+
$parent.addClass(self.config.currentClass);
self.$elem.find('.' +  
+
 
+
self.config.currentClass).removeClass(self.config.currentClass);
+
+
 
+
$parent.addClass(self.config.currentClass);
+
 
},
 
},
  
bindInterval:  
+
bindInterval: function() {
 
+
function() {
+
 
var self = this;
 
var self = this;
 
var docHeight;
 
var docHeight;
  
+
self.$win.on('scroll.onePageNav', function() {
 
+
self.didScroll = true;
self.$win.on('scroll.onePageNav', function() {
+
+
 
+
self.didScroll = true;
+
 
});
 
});
  
self.t = setInterval
+
self.t = setInterval(function() {
 
+
(function() {
+
 
docHeight = self.$doc.height();
 
docHeight = self.$doc.height();
  
+
//If it was scrolled
 
+
//If it was scrolled
+
 
if(self.didScroll) {
 
if(self.didScroll) {
+
self.didScroll = false;
 
+
self.didScroll = false;
+
 
self.scrollChange();
 
self.scrollChange();
+
}
 
+
}
+
  
 
//If the document height changes
 
//If the document height changes
+
if(docHeight !== self.docHeight) {
 
+
self.docHeight = docHeight;
if(docHeight !== self.docHeight) {
+
+
 
+
self.docHeight = docHeight;
+
 
self.getPositions();
 
self.getPositions();
+
}
 
+
}
+
 
}, 250);
 
}, 250);
 
},
 
},
  
getHash:  
+
getHash: function($link) {
 
+
function($link) {
+
 
return $link.attr('href').split('#')[1];
 
return $link.attr('href').split('#')[1];
+
},
 
+
},
+
  
 
getPositions: function() {
 
getPositions: function() {
 
var self = this;
 
var self = this;
+
var linkHref;
 
+
var linkHref;
+
 
var topPos;
 
var topPos;
 
var $target;
 
var $target;
  
+
self.$nav.each(function() {
 
+
linkHref = self.getHash($(this));
self.$nav.each(function() {
+
linkHref = self.getHash
+
 
+
($(this));
+
 
$target = $('#' + linkHref);
 
$target = $('#' + linkHref);
  
+
if($target.length) {
 
+
if($target.length) {
+
 
topPos = $target.offset().top;
 
topPos = $target.offset().top;
+
self.sections[linkHref] = Math.round(topPos);
 
+
}
self.sections[linkHref] = Math.round(topPos);
+
+
 
+
}
+
 
});
 
});
 
},
 
},
  
 
getSection: function(windowPos) {
 
getSection: function(windowPos) {
+
var returnValue = null;
 +
var windowHeight = Math.round(this.$win.height() * this.config.scrollThreshold);
  
var returnValue = null;
+
for(var section in this.sections) {
var windowHeight = Math.round(this.
+
if((this.sections[section] - windowHeight) < windowPos) {
 
+
$win.height() * this.config.scrollThreshold);
+
 
+
for(var section in  
+
 
+
this.sections) {
+
if((this.sections[section] - windowHeight) <  
+
 
+
windowPos) {
+
 
returnValue = section;
 
returnValue = section;
+
}
 
+
}
+
 
}
 
}
  
Line 241: Line 139:
 
},
 
},
  
+
handleClick: function(e) {
 
+
handleClick: function(e) {
+
 
var self = this;
 
var self = this;
var  
+
var $link = $(e.currentTarget);
 
+
$link = $(e.currentTarget);
+
 
var $parent = $link.parent();
 
var $parent = $link.parent();
+
var newLoc = '#' + self.getHash($link);
  
var newLoc = '#' + self.getHash($link);
+
if(!$parent.hasClass(self.config.currentClass)) {
 
+
if(!$parent.hasClass
+
 
+
(self.config.currentClass)) {
+
 
//Start callback
 
//Start callback
+
if(self.config.begin) {
 
+
if(self.config.begin) {
+
 
self.config.begin();
 
self.config.begin();
+
}
 
+
}
+
  
 
//Change the highlighted nav item
 
//Change the highlighted nav item
+
self.adjustNav(self, $parent);
  
self.adjustNav(self, $parent);
+
//Removing the auto-adjust on scroll
 
+
//Removing the  
+
 
+
auto-adjust on scroll
+
 
self.unbindInterval();
 
self.unbindInterval();
  
+
//Scroll to the correct position
 
+
self.scrollTo(newLoc, function() {
//Scroll to the correct position
+
self.scrollTo(newLoc,  
+
 
+
function() {
+
 
//Do we need to change the hash?
 
//Do we need to change the hash?
+
if(self.config.changeHash) {
 
+
window.location.hash = newLoc;
if(self.config.changeHash) {
+
+
 
+
window.location.hash = newLoc;
+
 
}
 
}
  
+
//Add the auto-adjust on scroll back in
 
+
self.bindInterval();
//Add the auto-adjust on scroll back in
+
+
 
+
self.bindInterval();
+
  
 
//End callback
 
//End callback
+
if(self.config.end) {
 
+
if(self.config.end) {
+
 
self.config.end();
 
self.config.end();
+
}
 
+
}
+
 
});
 
});
 
}
 
}
  
+
e.preventDefault();
 
+
e.preventDefault();
+
 
},
 
},
  
 
scrollChange: function() {
 
scrollChange: function() {
+
var windowTop = this.$win.scrollTop();
 
+
var position = this.getSection(windowTop);
var windowTop = this.$win.scrollTop();
+
var position =  
+
 
+
this.getSection(windowTop);
+
 
var $parent;
 
var $parent;
  
//If the  
+
//If the position is set
 
+
position is set
+
 
if(position !== null) {
 
if(position !== null) {
$parent =  
+
$parent = this.$elem.find('a[href$="#' + position + '"]').parent();
  
this.$elem.find('a[href$="#' + position + '"]').parent();
+
//If it's not already the current section
 
+
if(!$parent.hasClass(this.config.currentClass)) {
//If  
+
//Change the highlighted nav item
 
+
it's not already the current section
+
if(!$parent.hasClass
+
 
+
(this.config.currentClass)) {
+
//Change the highlighted nav  
+
 
+
item
+
 
this.adjustNav(this, $parent);
 
this.adjustNav(this, $parent);
  
+
//If there is a scrollChange callback
 
+
if(this.config.scrollChange) {
//If there is a scrollChange callback
+
this.config.scrollChange($parent);
if
+
 
+
(this.config.scrollChange) {
+
+
 
+
this.config.scrollChange($parent);
+
 
}
 
}
+
}
 
+
}
+
 
}
 
}
 
},
 
},
  
scrollTo: function(target,  
+
scrollTo: function(target, callback) {
 
+
callback) {
+
 
var offset = $(target).offset().top;
 
var offset = $(target).offset().top;
  
+
$('html, body').animate({
 
+
$('html, body').animate({
+
 
scrollTop: offset
 
scrollTop: offset
+
}, this.config.scrollSpeed, this.config.easing, callback);
 
+
}, this.config.scrollSpeed, this.config.easing, callback);
+
 
},
 
},
  
+
unbindInterval: function() {
 
+
unbindInterval: function() {
+
 
clearInterval(this.t);
 
clearInterval(this.t);
+
this.$win.unbind('scroll.onePageNav');
 
+
this.$win.unbind('scroll.onePageNav');
+
 
}
 
}
 
};
 
};
  
OnePageNav.defaults =  
+
OnePageNav.defaults = OnePageNav.prototype.defaults;
 
+
OnePageNav.prototype.defaults;
+
  
 
$.fn.onePageNav = function(options) {
 
$.fn.onePageNav = function(options) {
return  
+
return this.each(function() {
 
+
this.each(function() {
+
 
new OnePageNav(this, options).init();
 
new OnePageNav(this, options).init();
 
});
 
});
+
};
 
+
};
+
  
 
})( jQuery, window , document );
 
})( jQuery, window , document );

Latest revision as of 21:44, 16 September 2015

/*

* jQuery One Page Nav Plugin
* http://github.com/davist11/jQuery-One-Page-Nav
*
* Copyright (c) 2010 Trevor Davis (http://trevordavis.net)
* Dual licensed under the MIT and GPL licenses.
* Uses the same license as jQuery, see:
* http://jquery.org/license
*
* @version 3.0.0
*
* Example usage:
* $('#nav').onePageNav({
*   currentClass: 'current',
*   changeHash: false,
*   scrollSpeed: 750
* });
*/
(function($, window, document, undefined){

// our plugin constructor var OnePageNav = function(elem, options){ this.elem = elem; this.$elem = $(elem); this.options = options; this.metadata = this.$elem.data('plugin-options'); this.$win = $(window); this.sections = {}; this.didScroll = false; this.$doc = $(document); this.docHeight = this.$doc.height(); };

// the plugin prototype OnePageNav.prototype = { defaults: { navItems: 'a', currentClass: 'current', changeHash: false, easing: 'swing', filter: , scrollSpeed: 750, scrollThreshold: 0.5, begin: false, end: false, scrollChange: false },

init: function() { // Introduce defaults that can be extended either // globally or using an object literal. this.config = $.extend({}, this.defaults, this.options, this.metadata);

this.$nav = this.$elem.find(this.config.navItems);

//Filter any links out of the nav if(this.config.filter !== ) { this.$nav = this.$nav.filter(this.config.filter); }

//Handle clicks on the nav this.$nav.on('click.onePageNav', $.proxy(this.handleClick, this));

//Get the section positions this.getPositions();

//Handle scroll changes this.bindInterval();

//Update the positions on resize too this.$win.on('resize.onePageNav', $.proxy(this.getPositions, this));

return this; },

adjustNav: function(self, $parent) { self.$elem.find('.' + self.config.currentClass).removeClass(self.config.currentClass); $parent.addClass(self.config.currentClass); },

bindInterval: function() { var self = this; var docHeight;

self.$win.on('scroll.onePageNav', function() { self.didScroll = true; });

self.t = setInterval(function() { docHeight = self.$doc.height();

//If it was scrolled if(self.didScroll) { self.didScroll = false; self.scrollChange(); }

//If the document height changes if(docHeight !== self.docHeight) { self.docHeight = docHeight; self.getPositions(); } }, 250); },

getHash: function($link) { return $link.attr('href').split('#')[1]; },

getPositions: function() { var self = this; var linkHref; var topPos; var $target;

self.$nav.each(function() { linkHref = self.getHash($(this)); $target = $('#' + linkHref);

if($target.length) { topPos = $target.offset().top; self.sections[linkHref] = Math.round(topPos); } }); },

getSection: function(windowPos) { var returnValue = null; var windowHeight = Math.round(this.$win.height() * this.config.scrollThreshold);

for(var section in this.sections) { if((this.sections[section] - windowHeight) < windowPos) { returnValue = section; } }

return returnValue; },

handleClick: function(e) { var self = this; var $link = $(e.currentTarget); var $parent = $link.parent(); var newLoc = '#' + self.getHash($link);

if(!$parent.hasClass(self.config.currentClass)) { //Start callback if(self.config.begin) { self.config.begin(); }

//Change the highlighted nav item self.adjustNav(self, $parent);

//Removing the auto-adjust on scroll self.unbindInterval();

//Scroll to the correct position self.scrollTo(newLoc, function() { //Do we need to change the hash? if(self.config.changeHash) { window.location.hash = newLoc; }

//Add the auto-adjust on scroll back in self.bindInterval();

//End callback if(self.config.end) { self.config.end(); } }); }

e.preventDefault(); },

scrollChange: function() { var windowTop = this.$win.scrollTop(); var position = this.getSection(windowTop); var $parent;

//If the position is set if(position !== null) { $parent = this.$elem.find('a[href$="#' + position + '"]').parent();

//If it's not already the current section if(!$parent.hasClass(this.config.currentClass)) { //Change the highlighted nav item this.adjustNav(this, $parent);

//If there is a scrollChange callback if(this.config.scrollChange) { this.config.scrollChange($parent); } } } },

scrollTo: function(target, callback) { var offset = $(target).offset().top;

$('html, body').animate({ scrollTop: offset }, this.config.scrollSpeed, this.config.easing, callback); },

unbindInterval: function() { clearInterval(this.t); this.$win.unbind('scroll.onePageNav'); } };

OnePageNav.defaults = OnePageNav.prototype.defaults;

$.fn.onePageNav = function(options) { return this.each(function() { new OnePageNav(this, options).init(); }); };

})( jQuery, window , document );