|
/*global module, $, _, matchMedia*/ |
|
|
|
'use strict'; |
|
|
|
/** |
|
* Navigation |
|
* Disclaimer: This is built with jQuery.mmenu in mind, and so some of the selectors and calls accommodate this |
|
* Shouldn't be too hard to swap this out for a different menu solution |
|
* |
|
* @param config |
|
* @constructor |
|
*/ |
|
var Navigation = function(config) { |
|
this.selector = config.selector; |
|
this.activeClass = config.activeClass || 'is-visible'; |
|
this.hiddenClass = config.hiddenClass || 'is-hidden'; |
|
this.breakpoint = config.breakpoint || '767px'; |
|
this.el = $(config.selector); |
|
this.mobileEl = null; // won't be set until it's generated |
|
|
|
// Kick things off |
|
this.generateMobile(); |
|
}; |
|
|
|
/** |
|
* Generate mobile version |
|
* @function generateMobile |
|
*/ |
|
Navigation.prototype.generateMobile = function() { |
|
var _self = this; |
|
|
|
// Generate mobile nav |
|
this.el.mmenu({}, { |
|
clone: true |
|
}); |
|
|
|
this.mobileEl = $(this.selector + '.mm-menu'); |
|
|
|
this.toggleMobile(); |
|
|
|
// This is probably done arse-ways - trying to keep context bound to 'this', not window event |
|
$(window).on('resize', _.debounce(function() { |
|
_self.toggleMobile.apply(_self); |
|
}, 300)); |
|
}; |
|
|
|
/** |
|
* Check if mobile based on passed in breakpoint |
|
* @function isMobile |
|
*/ |
|
Navigation.prototype.isMobile = function() { |
|
// If Modernizr.mq isn't set, just assign an empty function |
|
return matchMedia('(max-width: ' + this.breakpoint + ')').matches; |
|
}; |
|
|
|
/** |
|
* Show mobile, hide desktop |
|
* @function showMobile |
|
*/ |
|
Navigation.prototype.showMobile = function() { |
|
this.mobileEl.addClass(this.activeClass).removeClass(this.hiddenClass); |
|
this.el.removeClass(this.activeClass).addClass(this.hiddenClass); |
|
}; |
|
|
|
/** |
|
* Show desktop, hide mobile |
|
* @function hideMobile |
|
*/ |
|
Navigation.prototype.hideMobile = function() { |
|
this.mobileEl.removeClass(this.activeClass).addClass(this.hiddenClass); |
|
this.el.addClass(this.activeClass).removeClass(this.hiddenClass); |
|
}; |
|
|
|
/** |
|
* Based on matchMedia we can show/hide the mobile menu |
|
* jQuery performance hit on .hide() or .show() can be avoid by using classes |
|
* @function toggleMobile |
|
*/ |
|
Navigation.prototype.toggleMobile = function() { |
|
// 1. Hide desktop, show mobile |
|
// 2. Hide mobile, show desktop |
|
this.isMobile() ? this.showMobile() : this.hideMobile(); |
|
}; |
|
|
|
var mainNav = new Navigation({ |
|
selector: '.nav--main' |
|
}); |