2016-09-07 10:58:25 +00:00
! function ( $ ) {
"use strict" ;
var FOUNDATION _VERSION = '6.2.3' ;
// Global Foundation object
// This is attached to the window, or used as a module for AMD/Browserify
var Foundation = {
version : FOUNDATION _VERSION ,
/ * *
* Stores initialized plugins .
* /
_plugins : { } ,
/ * *
* Stores generated unique ids for plugin instances
* /
_uuids : [ ] ,
/ * *
* Returns a boolean for RTL support
* /
rtl : function ( ) {
return $ ( 'html' ) . attr ( 'dir' ) === 'rtl' ;
} ,
/ * *
* Defines a Foundation plugin , adding it to the ` Foundation ` namespace and the list of plugins to initialize when reflowing .
* @ param { Object } plugin - The constructor of the plugin .
* /
plugin : function ( plugin , name ) {
// Object key to use when adding to global Foundation object
// Examples: Foundation.Reveal, Foundation.OffCanvas
var className = name || functionName ( plugin ) ;
// Object key to use when storing the plugin, also used to create the identifying data attribute for the plugin
// Examples: data-reveal, data-off-canvas
var attrName = hyphenate ( className ) ;
// Add to the Foundation object and the plugins list (for reflowing)
this . _plugins [ attrName ] = this [ className ] = plugin ;
} ,
/ * *
* @ function
* Populates the _uuids array with pointers to each individual plugin instance .
* Adds the ` zfPlugin ` data - attribute to programmatically created plugins to allow use of $ ( selector ) . foundation ( method ) calls .
* Also fires the initialization event for each plugin , consolidating repetitive code .
* @ param { Object } plugin - an instance of a plugin , usually ` this ` in context .
* @ param { String } name - the name of the plugin , passed as a camelCased string .
* @ fires Plugin # init
* /
registerPlugin : function ( plugin , name ) {
var pluginName = name ? hyphenate ( name ) : functionName ( plugin . constructor ) . toLowerCase ( ) ;
plugin . uuid = this . GetYoDigits ( 6 , pluginName ) ;
if ( ! plugin . $element . attr ( 'data-' + pluginName ) ) {
plugin . $element . attr ( 'data-' + pluginName , plugin . uuid ) ;
}
if ( ! plugin . $element . data ( 'zfPlugin' ) ) {
plugin . $element . data ( 'zfPlugin' , plugin ) ;
}
/ * *
* Fires when the plugin has initialized .
* @ event Plugin # init
* /
plugin . $element . trigger ( 'init.zf.' + pluginName ) ;
this . _uuids . push ( plugin . uuid ) ;
return ;
} ,
/ * *
* @ function
* Removes the plugins uuid from the _uuids array .
* Removes the zfPlugin data attribute , as well as the data - plugin - name attribute .
* Also fires the destroyed event for the plugin , consolidating repetitive code .
* @ param { Object } plugin - an instance of a plugin , usually ` this ` in context .
* @ fires Plugin # destroyed
* /
unregisterPlugin : function ( plugin ) {
var pluginName = hyphenate ( functionName ( plugin . $element . data ( 'zfPlugin' ) . constructor ) ) ;
this . _uuids . splice ( this . _uuids . indexOf ( plugin . uuid ) , 1 ) ;
plugin . $element . removeAttr ( 'data-' + pluginName ) . removeData ( 'zfPlugin' )
/ * *
* Fires when the plugin has been destroyed .
* @ event Plugin # destroyed
* /
. trigger ( 'destroyed.zf.' + pluginName ) ;
for ( var prop in plugin ) {
plugin [ prop ] = null ; //clean up script to prep for garbage collection.
}
return ;
} ,
/ * *
* @ function
* Causes one or more active plugins to re - initialize , resetting event listeners , recalculating positions , etc .
* @ param { String } plugins - optional string of an individual plugin key , attained by calling ` $ (element).data('pluginName') ` , or string of a plugin class i . e . ` 'dropdown' `
* @ default If no argument is passed , reflow all currently active plugins .
* /
reInit : function ( plugins ) {
var isJQ = plugins instanceof $ ;
try {
if ( isJQ ) {
plugins . each ( function ( ) {
$ ( this ) . data ( 'zfPlugin' ) . _init ( ) ;
} ) ;
} else {
var type = typeof plugins ,
_this = this ,
fns = {
'object' : function ( plgs ) {
plgs . forEach ( function ( p ) {
p = hyphenate ( p ) ;
$ ( '[data-' + p + ']' ) . foundation ( '_init' ) ;
} ) ;
} ,
'string' : function ( ) {
plugins = hyphenate ( plugins ) ;
$ ( '[data-' + plugins + ']' ) . foundation ( '_init' ) ;
} ,
'undefined' : function ( ) {
this [ 'object' ] ( Object . keys ( _this . _plugins ) ) ;
}
} ;
fns [ type ] ( plugins ) ;
}
} catch ( err ) {
console . error ( err ) ;
} finally {
return plugins ;
}
} ,
/ * *
* returns a random base - 36 uid with namespacing
* @ function
* @ param { Number } length - number of random base - 36 digits desired . Increase for more random strings .
* @ param { String } namespace - name of plugin to be incorporated in uid , optional .
* @ default { String } '' - if no plugin name is provided , nothing is appended to the uid .
* @ returns { String } - unique id
* /
GetYoDigits : function ( length , namespace ) {
length = length || 6 ;
return Math . round ( Math . pow ( 36 , length + 1 ) - Math . random ( ) * Math . pow ( 36 , length ) ) . toString ( 36 ) . slice ( 1 ) + ( namespace ? '-' + namespace : '' ) ;
} ,
/ * *
* Initialize plugins on any elements within ` elem ` ( and ` elem ` itself ) that aren ' t already initialized .
* @ param { Object } elem - jQuery object containing the element to check inside . Also checks the element itself , unless it ' s the ` document ` object .
* @ param { String | Array } plugins - A list of plugins to initialize . Leave this out to initialize everything .
* /
reflow : function ( elem , plugins ) {
// If plugins is undefined, just grab everything
if ( typeof plugins === 'undefined' ) {
plugins = Object . keys ( this . _plugins ) ;
}
// If plugins is a string, convert it to an array with one item
else if ( typeof plugins === 'string' ) {
plugins = [ plugins ] ;
}
var _this = this ;
// Iterate through each plugin
$ . each ( plugins , function ( i , name ) {
// Get the current plugin
var plugin = _this . _plugins [ name ] ;
// Localize the search to all elements inside elem, as well as elem itself, unless elem === document
var $elem = $ ( elem ) . find ( '[data-' + name + ']' ) . addBack ( '[data-' + name + ']' ) ;
// For each plugin found, initialize it
$elem . each ( function ( ) {
var $el = $ ( this ) ,
opts = { } ;
// Don't double-dip on plugins
if ( $el . data ( 'zfPlugin' ) ) {
console . warn ( "Tried to initialize " + name + " on an element that already has a Foundation plugin." ) ;
return ;
}
if ( $el . attr ( 'data-options' ) ) {
var thing = $el . attr ( 'data-options' ) . split ( ';' ) . forEach ( function ( e , i ) {
var opt = e . split ( ':' ) . map ( function ( el ) {
return el . trim ( ) ;
} ) ;
if ( opt [ 0 ] ) opts [ opt [ 0 ] ] = parseValue ( opt [ 1 ] ) ;
} ) ;
}
try {
$el . data ( 'zfPlugin' , new plugin ( $ ( this ) , opts ) ) ;
} catch ( er ) {
console . error ( er ) ;
} finally {
return ;
}
} ) ;
} ) ;
} ,
getFnName : functionName ,
transitionend : function ( $elem ) {
var transitions = {
'transition' : 'transitionend' ,
'WebkitTransition' : 'webkitTransitionEnd' ,
'MozTransition' : 'transitionend' ,
'OTransition' : 'otransitionend'
} ;
var elem = document . createElement ( 'div' ) ,
end ;
for ( var t in transitions ) {
if ( typeof elem . style [ t ] !== 'undefined' ) {
end = transitions [ t ] ;
}
}
if ( end ) {
return end ;
} else {
end = setTimeout ( function ( ) {
$elem . triggerHandler ( 'transitionend' , [ $elem ] ) ;
} , 1 ) ;
return 'transitionend' ;
}
}
} ;
Foundation . util = {
/ * *
* Function for applying a debounce effect to a function call .
* @ function
* @ param { Function } func - Function to be called at end of timeout .
* @ param { Number } delay - Time in ms to delay the call of ` func ` .
* @ returns function
* /
throttle : function ( func , delay ) {
var timer = null ;
return function ( ) {
var context = this ,
args = arguments ;
if ( timer === null ) {
timer = setTimeout ( function ( ) {
func . apply ( context , args ) ;
timer = null ;
} , delay ) ;
}
} ;
}
} ;
// TODO: consider not making this a jQuery function
// TODO: need way to reflow vs. re-initialize
/ * *
* The Foundation jQuery method .
* @ param { String | Array } method - An action to perform on the current jQuery object .
* /
var foundation = function ( method ) {
var type = typeof method ,
$meta = $ ( 'meta.foundation-mq' ) ,
$noJS = $ ( '.no-js' ) ;
if ( ! $meta . length ) {
$ ( '<meta class="foundation-mq">' ) . appendTo ( document . head ) ;
}
if ( $noJS . length ) {
$noJS . removeClass ( 'no-js' ) ;
}
if ( type === 'undefined' ) {
//needs to initialize the Foundation object, or an individual plugin.
Foundation . MediaQuery . _init ( ) ;
Foundation . reflow ( this ) ;
} else if ( type === 'string' ) {
//an individual method to invoke on a plugin or group of plugins
var args = Array . prototype . slice . call ( arguments , 1 ) ; //collect all the arguments, if necessary
var plugClass = this . data ( 'zfPlugin' ) ; //determine the class of plugin
if ( plugClass !== undefined && plugClass [ method ] !== undefined ) {
//make sure both the class and method exist
if ( this . length === 1 ) {
//if there's only one, call it directly.
plugClass [ method ] . apply ( plugClass , args ) ;
} else {
this . each ( function ( i , el ) {
//otherwise loop through the jQuery collection and invoke the method on each
plugClass [ method ] . apply ( $ ( el ) . data ( 'zfPlugin' ) , args ) ;
} ) ;
}
} else {
//error for no class or no method
throw new ReferenceError ( "We're sorry, '" + method + "' is not an available method for " + ( plugClass ? functionName ( plugClass ) : 'this element' ) + '.' ) ;
}
} else {
//error for invalid argument type
throw new TypeError ( 'We\'re sorry, ' + type + ' is not a valid parameter. You must use a string representing the method you wish to invoke.' ) ;
}
return this ;
} ;
window . Foundation = Foundation ;
$ . fn . foundation = foundation ;
// Polyfill for requestAnimationFrame
( function ( ) {
if ( ! Date . now || ! window . Date . now ) window . Date . now = Date . now = function ( ) {
return new Date ( ) . getTime ( ) ;
} ;
var vendors = [ 'webkit' , 'moz' ] ;
for ( var i = 0 ; i < vendors . length && ! window . requestAnimationFrame ; ++ i ) {
var vp = vendors [ i ] ;
window . requestAnimationFrame = window [ vp + 'RequestAnimationFrame' ] ;
window . cancelAnimationFrame = window [ vp + 'CancelAnimationFrame' ] || window [ vp + 'CancelRequestAnimationFrame' ] ;
}
if ( /iP(ad|hone|od).*OS 6/ . test ( window . navigator . userAgent ) || ! window . requestAnimationFrame || ! window . cancelAnimationFrame ) {
var lastTime = 0 ;
window . requestAnimationFrame = function ( callback ) {
var now = Date . now ( ) ;
var nextTime = Math . max ( lastTime + 16 , now ) ;
return setTimeout ( function ( ) {
callback ( lastTime = nextTime ) ;
} , nextTime - now ) ;
} ;
window . cancelAnimationFrame = clearTimeout ;
}
/ * *
* Polyfill for performance . now , required by rAF
* /
if ( ! window . performance || ! window . performance . now ) {
window . performance = {
start : Date . now ( ) ,
now : function ( ) {
return Date . now ( ) - this . start ;
}
} ;
}
} ) ( ) ;
if ( ! Function . prototype . bind ) {
Function . prototype . bind = function ( oThis ) {
if ( typeof this !== 'function' ) {
// closest thing possible to the ECMAScript 5
// internal IsCallable function
throw new TypeError ( 'Function.prototype.bind - what is trying to be bound is not callable' ) ;
}
var aArgs = Array . prototype . slice . call ( arguments , 1 ) ,
fToBind = this ,
fNOP = function ( ) { } ,
fBound = function ( ) {
return fToBind . apply ( this instanceof fNOP ? this : oThis , aArgs . concat ( Array . prototype . slice . call ( arguments ) ) ) ;
} ;
if ( this . prototype ) {
// native functions don't have a prototype
fNOP . prototype = this . prototype ;
}
fBound . prototype = new fNOP ( ) ;
return fBound ;
} ;
}
// Polyfill to get the name of a function in IE9
function functionName ( fn ) {
if ( Function . prototype . name === undefined ) {
var funcNameRegex = /function\s([^(]{1,})\(/ ;
var results = funcNameRegex . exec ( fn . toString ( ) ) ;
return results && results . length > 1 ? results [ 1 ] . trim ( ) : "" ;
} else if ( fn . prototype === undefined ) {
return fn . constructor . name ;
} else {
return fn . prototype . constructor . name ;
}
}
function parseValue ( str ) {
if ( /true/ . test ( str ) ) return true ; else if ( /false/ . test ( str ) ) return false ; else if ( ! isNaN ( str * 1 ) ) return parseFloat ( str ) ;
return str ;
}
// Convert PascalCase to kebab-case
// Thank you: http://stackoverflow.com/a/8955580
function hyphenate ( str ) {
return str . replace ( /([a-z])([A-Z])/g , '$1-$2' ) . toLowerCase ( ) ;
}
} ( jQuery ) ;
'use strict' ;
! function ( $ ) {
Foundation . Box = {
ImNotTouchingYou : ImNotTouchingYou ,
GetDimensions : GetDimensions ,
GetOffsets : GetOffsets
} ;
/ * *
* Compares the dimensions of an element to a container and determines collision events with container .
* @ function
* @ param { jQuery } element - jQuery object to test for collisions .
* @ param { jQuery } parent - jQuery object to use as bounding container .
* @ param { Boolean } lrOnly - set to true to check left and right values only .
* @ param { Boolean } tbOnly - set to true to check top and bottom values only .
* @ default if no parent object passed , detects collisions with ` window ` .
* @ returns { Boolean } - true if collision free , false if a collision in any direction .
* /
function ImNotTouchingYou ( element , parent , lrOnly , tbOnly ) {
var eleDims = GetDimensions ( element ) ,
top ,
bottom ,
left ,
right ;
if ( parent ) {
var parDims = GetDimensions ( parent ) ;
bottom = eleDims . offset . top + eleDims . height <= parDims . height + parDims . offset . top ;
top = eleDims . offset . top >= parDims . offset . top ;
left = eleDims . offset . left >= parDims . offset . left ;
right = eleDims . offset . left + eleDims . width <= parDims . width + parDims . offset . left ;
} else {
bottom = eleDims . offset . top + eleDims . height <= eleDims . windowDims . height + eleDims . windowDims . offset . top ;
top = eleDims . offset . top >= eleDims . windowDims . offset . top ;
left = eleDims . offset . left >= eleDims . windowDims . offset . left ;
right = eleDims . offset . left + eleDims . width <= eleDims . windowDims . width ;
}
var allDirs = [ bottom , top , left , right ] ;
if ( lrOnly ) {
return left === right === true ;
}
if ( tbOnly ) {
return top === bottom === true ;
}
return allDirs . indexOf ( false ) === - 1 ;
} ;
/ * *
* Uses native methods to return an object of dimension values .
* @ function
* @ param { jQuery || HTML } element - jQuery object or DOM element for which to get the dimensions . Can be any element other that document or window .
* @ returns { Object } - nested object of integer pixel values
* TODO - if element is window , return only those values .
* /
function GetDimensions ( elem , test ) {
elem = elem . length ? elem [ 0 ] : elem ;
if ( elem === window || elem === document ) {
throw new Error ( "I'm sorry, Dave. I'm afraid I can't do that." ) ;
}
var rect = elem . getBoundingClientRect ( ) ,
parRect = elem . parentNode . getBoundingClientRect ( ) ,
winRect = document . body . getBoundingClientRect ( ) ,
winY = window . pageYOffset ,
winX = window . pageXOffset ;
return {
width : rect . width ,
height : rect . height ,
offset : {
top : rect . top + winY ,
left : rect . left + winX
} ,
parentDims : {
width : parRect . width ,
height : parRect . height ,
offset : {
top : parRect . top + winY ,
left : parRect . left + winX
}
} ,
windowDims : {
width : winRect . width ,
height : winRect . height ,
offset : {
top : winY ,
left : winX
}
}
} ;
}
/ * *
* Returns an object of top and left integer pixel values for dynamically rendered elements ,
* such as : Tooltip , Reveal , and Dropdown
* @ function
* @ param { jQuery } element - jQuery object for the element being positioned .
* @ param { jQuery } anchor - jQuery object for the element ' s anchor point .
* @ param { String } position - a string relating to the desired position of the element , relative to it ' s anchor
* @ param { Number } vOffset - integer pixel value of desired vertical separation between anchor and element .
* @ param { Number } hOffset - integer pixel value of desired horizontal separation between anchor and element .
* @ param { Boolean } isOverflow - if a collision event is detected , sets to true to default the element to full width - any desired offset .
* TODO alter / rewrite to work with ` em ` values as well / instead of pixels
* /
function GetOffsets ( element , anchor , position , vOffset , hOffset , isOverflow ) {
var $eleDims = GetDimensions ( element ) ,
$anchorDims = anchor ? GetDimensions ( anchor ) : null ;
switch ( position ) {
case 'top' :
return {
left : Foundation . rtl ( ) ? $anchorDims . offset . left - $eleDims . width + $anchorDims . width : $anchorDims . offset . left ,
top : $anchorDims . offset . top - ( $eleDims . height + vOffset )
} ;
break ;
case 'left' :
return {
left : $anchorDims . offset . left - ( $eleDims . width + hOffset ) ,
top : $anchorDims . offset . top
} ;
break ;
case 'right' :
return {
left : $anchorDims . offset . left + $anchorDims . width + hOffset ,
top : $anchorDims . offset . top
} ;
break ;
case 'center top' :
return {
left : $anchorDims . offset . left + $anchorDims . width / 2 - $eleDims . width / 2 ,
top : $anchorDims . offset . top - ( $eleDims . height + vOffset )
} ;
break ;
case 'center bottom' :
return {
left : isOverflow ? hOffset : $anchorDims . offset . left + $anchorDims . width / 2 - $eleDims . width / 2 ,
top : $anchorDims . offset . top + $anchorDims . height + vOffset
} ;
break ;
case 'center left' :
return {
left : $anchorDims . offset . left - ( $eleDims . width + hOffset ) ,
top : $anchorDims . offset . top + $anchorDims . height / 2 - $eleDims . height / 2
} ;
break ;
case 'center right' :
return {
left : $anchorDims . offset . left + $anchorDims . width + hOffset + 1 ,
top : $anchorDims . offset . top + $anchorDims . height / 2 - $eleDims . height / 2
} ;
break ;
case 'center' :
return {
left : $eleDims . windowDims . offset . left + $eleDims . windowDims . width / 2 - $eleDims . width / 2 ,
top : $eleDims . windowDims . offset . top + $eleDims . windowDims . height / 2 - $eleDims . height / 2
} ;
break ;
case 'reveal' :
return {
left : ( $eleDims . windowDims . width - $eleDims . width ) / 2 ,
top : $eleDims . windowDims . offset . top + vOffset
} ;
case 'reveal full' :
return {
left : $eleDims . windowDims . offset . left ,
top : $eleDims . windowDims . offset . top
} ;
break ;
case 'left bottom' :
return {
left : $anchorDims . offset . left - ( $eleDims . width + hOffset ) ,
top : $anchorDims . offset . top + $anchorDims . height
} ;
break ;
case 'right bottom' :
return {
left : $anchorDims . offset . left + $anchorDims . width + hOffset - $eleDims . width ,
top : $anchorDims . offset . top + $anchorDims . height
} ;
break ;
default :
return {
left : Foundation . rtl ( ) ? $anchorDims . offset . left - $eleDims . width + $anchorDims . width : $anchorDims . offset . left ,
top : $anchorDims . offset . top + $anchorDims . height + vOffset
} ;
}
}
} ( jQuery ) ;
/ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
* *
* This util was created by Marius Olbertz *
* Please thank Marius on GitHub / owlbertz *
* or the web http : //www.mariusolbertz.de/ *
* *
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * /
'use strict' ;
! function ( $ ) {
var keyCodes = {
9 : 'TAB' ,
13 : 'ENTER' ,
27 : 'ESCAPE' ,
32 : 'SPACE' ,
37 : 'ARROW_LEFT' ,
38 : 'ARROW_UP' ,
39 : 'ARROW_RIGHT' ,
40 : 'ARROW_DOWN'
} ;
var commands = { } ;
var Keyboard = {
keys : getKeyCodes ( keyCodes ) ,
/ * *
* Parses the ( keyboard ) event and returns a String that represents its key
* Can be used like Foundation . parseKey ( event ) === Foundation . keys . SPACE
* @ param { Event } event - the event generated by the event handler
* @ return String key - String that represents the key pressed
* /
parseKey : function ( event ) {
var key = keyCodes [ event . which || event . keyCode ] || String . fromCharCode ( event . which ) . toUpperCase ( ) ;
if ( event . shiftKey ) key = 'SHIFT_' + key ;
if ( event . ctrlKey ) key = 'CTRL_' + key ;
if ( event . altKey ) key = 'ALT_' + key ;
return key ;
} ,
/ * *
* Handles the given ( keyboard ) event
* @ param { Event } event - the event generated by the event handler
* @ param { String } component - Foundation component ' s name , e . g . Slider or Reveal
* @ param { Objects } functions - collection of functions that are to be executed
* /
handleKey : function ( event , component , functions ) {
var commandList = commands [ component ] ,
keyCode = this . parseKey ( event ) ,
cmds ,
command ,
fn ;
if ( ! commandList ) return console . warn ( 'Component not defined!' ) ;
if ( typeof commandList . ltr === 'undefined' ) {
// this component does not differentiate between ltr and rtl
cmds = commandList ; // use plain list
} else {
// merge ltr and rtl: if document is rtl, rtl overwrites ltr and vice versa
if ( Foundation . rtl ( ) ) cmds = $ . extend ( { } , commandList . ltr , commandList . rtl ) ; else cmds = $ . extend ( { } , commandList . rtl , commandList . ltr ) ;
}
command = cmds [ keyCode ] ;
fn = functions [ command ] ;
if ( fn && typeof fn === 'function' ) {
// execute function if exists
var returnValue = fn . apply ( ) ;
if ( functions . handled || typeof functions . handled === 'function' ) {
// execute function when event was handled
functions . handled ( returnValue ) ;
}
} else {
if ( functions . unhandled || typeof functions . unhandled === 'function' ) {
// execute function when event was not handled
functions . unhandled ( ) ;
}
}
} ,
/ * *
* Finds all focusable elements within the given ` $ element `
* @ param { jQuery } $element - jQuery object to search within
* @ return { jQuery } $focusable - all focusable elements within ` $ element `
* /
findFocusable : function ( $element ) {
return $element . find ( 'a[href], area[href], input:not([disabled]), select:not([disabled]), textarea:not([disabled]), button:not([disabled]), iframe, object, embed, *[tabindex], *[contenteditable]' ) . filter ( function ( ) {
if ( ! $ ( this ) . is ( ':visible' ) || $ ( this ) . attr ( 'tabindex' ) < 0 ) {
return false ;
} //only have visible elements and those that have a tabindex greater or equal 0
return true ;
} ) ;
} ,
/ * *
* Returns the component name name
* @ param { Object } component - Foundation component , e . g . Slider or Reveal
* @ return String componentName
* /
register : function ( componentName , cmds ) {
commands [ componentName ] = cmds ;
}
} ;
/ *
* Constants for easier comparing .
* Can be used like Foundation . parseKey ( event ) === Foundation . keys . SPACE
* /
function getKeyCodes ( kcs ) {
var k = { } ;
for ( var kc in kcs ) {
k [ kcs [ kc ] ] = kcs [ kc ] ;
} return k ;
}
Foundation . Keyboard = Keyboard ;
} ( jQuery ) ;
'use strict' ;
! function ( $ ) {
// Default set of media queries
var defaultQueries = {
'default' : 'only screen' ,
landscape : 'only screen and (orientation: landscape)' ,
portrait : 'only screen and (orientation: portrait)' ,
retina : 'only screen and (-webkit-min-device-pixel-ratio: 2),' + 'only screen and (min--moz-device-pixel-ratio: 2),' + 'only screen and (-o-min-device-pixel-ratio: 2/1),' + 'only screen and (min-device-pixel-ratio: 2),' + 'only screen and (min-resolution: 192dpi),' + 'only screen and (min-resolution: 2dppx)'
} ;
var MediaQuery = {
queries : [ ] ,
current : '' ,
/ * *
* Initializes the media query helper , by extracting the breakpoint list from the CSS and activating the breakpoint watcher .
* @ function
* @ private
* /
_init : function ( ) {
var self = this ;
var extractedStyles = $ ( '.foundation-mq' ) . css ( 'font-family' ) ;
var namedQueries ;
namedQueries = parseStyleToObject ( extractedStyles ) ;
for ( var key in namedQueries ) {
if ( namedQueries . hasOwnProperty ( key ) ) {
self . queries . push ( {
name : key ,
value : 'only screen and (min-width: ' + namedQueries [ key ] + ')'
} ) ;
}
}
this . current = this . _getCurrentSize ( ) ;
this . _watcher ( ) ;
} ,
/ * *
* Checks if the screen is at least as wide as a breakpoint .
* @ function
* @ param { String } size - Name of the breakpoint to check .
* @ returns { Boolean } ` true ` if the breakpoint matches , ` false ` if it ' s smaller .
* /
atLeast : function ( size ) {
var query = this . get ( size ) ;
if ( query ) {
return window . matchMedia ( query ) . matches ;
}
return false ;
} ,
/ * *
* Gets the media query of a breakpoint .
* @ function
* @ param { String } size - Name of the breakpoint to get .
* @ returns { String | null } - The media query of the breakpoint , or ` null ` if the breakpoint doesn ' t exist .
* /
get : function ( size ) {
for ( var i in this . queries ) {
if ( this . queries . hasOwnProperty ( i ) ) {
var query = this . queries [ i ] ;
if ( size === query . name ) return query . value ;
}
}
return null ;
} ,
/ * *
* Gets the current breakpoint name by testing every breakpoint and returning the last one to match ( the biggest one ) .
* @ function
* @ private
* @ returns { String } Name of the current breakpoint .
* /
_getCurrentSize : function ( ) {
var matched ;
for ( var i = 0 ; i < this . queries . length ; i ++ ) {
var query = this . queries [ i ] ;
if ( window . matchMedia ( query . value ) . matches ) {
matched = query ;
}
}
if ( typeof matched === 'object' ) {
return matched . name ;
} else {
return matched ;
}
} ,
/ * *
* Activates the breakpoint watcher , which fires an event on the window whenever the breakpoint changes .
* @ function
* @ private
* /
_watcher : function ( ) {
var _this = this ;
$ ( window ) . on ( 'resize.zf.mediaquery' , function ( ) {
var newSize = _this . _getCurrentSize ( ) ,
currentSize = _this . current ;
if ( newSize !== currentSize ) {
// Change the current media query
_this . current = newSize ;
// Broadcast the media query change on the window
$ ( window ) . trigger ( 'changed.zf.mediaquery' , [ newSize , currentSize ] ) ;
}
} ) ;
}
} ;
Foundation . MediaQuery = MediaQuery ;
// matchMedia() polyfill - Test a CSS media type/query in JS.
// Authors & copyright (c) 2012: Scott Jehl, Paul Irish, Nicholas Zakas, David Knight. Dual MIT/BSD license
window . matchMedia || ( window . matchMedia = function ( ) {
'use strict' ;
// For browsers that support matchMedium api such as IE 9 and webkit
var styleMedia = window . styleMedia || window . media ;
// For those that don't support matchMedium
if ( ! styleMedia ) {
var style = document . createElement ( 'style' ) ,
script = document . getElementsByTagName ( 'script' ) [ 0 ] ,
info = null ;
style . type = 'text/css' ;
style . id = 'matchmediajs-test' ;
script . parentNode . insertBefore ( style , script ) ;
// 'style.currentStyle' is used by IE <= 8 and 'window.getComputedStyle' for all other browsers
info = 'getComputedStyle' in window && window . getComputedStyle ( style , null ) || style . currentStyle ;
styleMedia = {
matchMedium : function ( media ) {
var text = '@media ' + media + '{ #matchmediajs-test { width: 1px; } }' ;
// 'style.styleSheet' is used by IE <= 8 and 'style.textContent' for all other browsers
if ( style . styleSheet ) {
style . styleSheet . cssText = text ;
} else {
style . textContent = text ;
}
// Test if media query is true or false
return info . width === '1px' ;
}
} ;
}
return function ( media ) {
return {
matches : styleMedia . matchMedium ( media || 'all' ) ,
media : media || 'all'
} ;
} ;
} ( ) ) ;
// Thank you: https://github.com/sindresorhus/query-string
function parseStyleToObject ( str ) {
var styleObject = { } ;
if ( typeof str !== 'string' ) {
return styleObject ;
}
str = str . trim ( ) . slice ( 1 , - 1 ) ; // browsers re-quote string style values
if ( ! str ) {
return styleObject ;
}
styleObject = str . split ( '&' ) . reduce ( function ( ret , param ) {
var parts = param . replace ( /\+/g , ' ' ) . split ( '=' ) ;
var key = parts [ 0 ] ;
var val = parts [ 1 ] ;
key = decodeURIComponent ( key ) ;
// missing `=` should be `null`:
// http://w3.org/TR/2012/WD-url-20120524/#collect-url-parameters
val = val === undefined ? null : decodeURIComponent ( val ) ;
if ( ! ret . hasOwnProperty ( key ) ) {
ret [ key ] = val ;
} else if ( Array . isArray ( ret [ key ] ) ) {
ret [ key ] . push ( val ) ;
} else {
ret [ key ] = [ ret [ key ] , val ] ;
}
return ret ;
} , { } ) ;
return styleObject ;
}
Foundation . MediaQuery = MediaQuery ;
} ( jQuery ) ;
'use strict' ;
! function ( $ ) {
/ * *
* Motion module .
* @ module foundation . motion
* /
var initClasses = [ 'mui-enter' , 'mui-leave' ] ;
var activeClasses = [ 'mui-enter-active' , 'mui-leave-active' ] ;
var Motion = {
animateIn : function ( element , animation , cb ) {
animate ( true , element , animation , cb ) ;
} ,
animateOut : function ( element , animation , cb ) {
animate ( false , element , animation , cb ) ;
}
} ;
function Move ( duration , elem , fn ) {
var anim ,
prog ,
start = null ;
// console.log('called');
function move ( ts ) {
if ( ! start ) start = window . performance . now ( ) ;
// console.log(start, ts);
prog = ts - start ;
fn . apply ( elem ) ;
if ( prog < duration ) {
anim = window . requestAnimationFrame ( move , elem ) ;
} else {
window . cancelAnimationFrame ( anim ) ;
elem . trigger ( 'finished.zf.animate' , [ elem ] ) . triggerHandler ( 'finished.zf.animate' , [ elem ] ) ;
}
}
anim = window . requestAnimationFrame ( move ) ;
}
/ * *
* Animates an element in or out using a CSS transition class .
* @ function
* @ private
* @ param { Boolean } isIn - Defines if the animation is in or out .
* @ param { Object } element - jQuery or HTML object to animate .
* @ param { String } animation - CSS class to use .
* @ param { Function } cb - Callback to run when animation is finished .
* /
function animate ( isIn , element , animation , cb ) {
element = $ ( element ) . eq ( 0 ) ;
if ( ! element . length ) return ;
var initClass = isIn ? initClasses [ 0 ] : initClasses [ 1 ] ;
var activeClass = isIn ? activeClasses [ 0 ] : activeClasses [ 1 ] ;
// Set up the animation
reset ( ) ;
element . addClass ( animation ) . css ( 'transition' , 'none' ) ;
requestAnimationFrame ( function ( ) {
element . addClass ( initClass ) ;
if ( isIn ) element . show ( ) ;
} ) ;
// Start the animation
requestAnimationFrame ( function ( ) {
element [ 0 ] . offsetWidth ;
element . css ( 'transition' , '' ) . addClass ( activeClass ) ;
} ) ;
// Clean up the animation when it finishes
element . one ( Foundation . transitionend ( element ) , finish ) ;
// Hides the element (for out animations), resets the element, and runs a callback
function finish ( ) {
if ( ! isIn ) element . hide ( ) ;
reset ( ) ;
if ( cb ) cb . apply ( element ) ;
}
// Resets transitions and removes motion-specific classes
function reset ( ) {
element [ 0 ] . style . transitionDuration = 0 ;
element . removeClass ( initClass + ' ' + activeClass + ' ' + animation ) ;
}
}
Foundation . Move = Move ;
Foundation . Motion = Motion ;
} ( jQuery ) ;
'use strict' ;
! function ( $ ) {
var Nest = {
Feather : function ( menu ) {
var type = arguments . length <= 1 || arguments [ 1 ] === undefined ? 'zf' : arguments [ 1 ] ;
menu . attr ( 'role' , 'menubar' ) ;
var items = menu . find ( 'li' ) . attr ( { 'role' : 'menuitem' } ) ,
subMenuClass = 'is-' + type + '-submenu' ,
subItemClass = subMenuClass + '-item' ,
hasSubClass = 'is-' + type + '-submenu-parent' ;
menu . find ( 'a:first' ) . attr ( 'tabindex' , 0 ) ;
items . each ( function ( ) {
var $item = $ ( this ) ,
$sub = $item . children ( 'ul' ) ;
if ( $sub . length ) {
$item . addClass ( hasSubClass ) . attr ( {
'aria-haspopup' : true ,
'aria-expanded' : false ,
'aria-label' : $item . children ( 'a:first' ) . text ( )
} ) ;
$sub . addClass ( 'submenu ' + subMenuClass ) . attr ( {
'data-submenu' : '' ,
'aria-hidden' : true ,
'role' : 'menu'
} ) ;
}
if ( $item . parent ( '[data-submenu]' ) . length ) {
$item . addClass ( 'is-submenu-item ' + subItemClass ) ;
}
} ) ;
return ;
} ,
Burn : function ( menu , type ) {
var items = menu . find ( 'li' ) . removeAttr ( 'tabindex' ) ,
subMenuClass = 'is-' + type + '-submenu' ,
subItemClass = subMenuClass + '-item' ,
hasSubClass = 'is-' + type + '-submenu-parent' ;
menu . find ( '*' ) . removeClass ( subMenuClass + ' ' + subItemClass + ' ' + hasSubClass + ' is-submenu-item submenu is-active' ) . removeAttr ( 'data-submenu' ) . css ( 'display' , '' ) ;
// console.log( menu.find('.' + subMenuClass + ', .' + subItemClass + ', .has-submenu, .is-submenu-item, .submenu, [data-submenu]')
// .removeClass(subMenuClass + ' ' + subItemClass + ' has-submenu is-submenu-item submenu')
// .removeAttr('data-submenu'));
// items.each(function(){
// var $item = $(this),
// $sub = $item.children('ul');
// if($item.parent('[data-submenu]').length){
// $item.removeClass('is-submenu-item ' + subItemClass);
// }
// if($sub.length){
// $item.removeClass('has-submenu');
// $sub.removeClass('submenu ' + subMenuClass).removeAttr('data-submenu');
// }
// });
}
} ;
Foundation . Nest = Nest ;
} ( jQuery ) ;
'use strict' ;
! function ( $ ) {
function Timer ( elem , options , cb ) {
var _this = this ,
duration = options . duration ,
//options is an object for easily adding features later.
nameSpace = Object . keys ( elem . data ( ) ) [ 0 ] || 'timer' ,
remain = - 1 ,
start ,
timer ;
this . isPaused = false ;
this . restart = function ( ) {
remain = - 1 ;
clearTimeout ( timer ) ;
this . start ( ) ;
} ;
this . start = function ( ) {
this . isPaused = false ;
// if(!elem.data('paused')){ return false; }//maybe implement this sanity check if used for other things.
clearTimeout ( timer ) ;
remain = remain <= 0 ? duration : remain ;
elem . data ( 'paused' , false ) ;
start = Date . now ( ) ;
timer = setTimeout ( function ( ) {
if ( options . infinite ) {
_this . restart ( ) ; //rerun the timer.
}
cb ( ) ;
} , remain ) ;
elem . trigger ( 'timerstart.zf.' + nameSpace ) ;
} ;
this . pause = function ( ) {
this . isPaused = true ;
//if(elem.data('paused')){ return false; }//maybe implement this sanity check if used for other things.
clearTimeout ( timer ) ;
elem . data ( 'paused' , true ) ;
var end = Date . now ( ) ;
remain = remain - ( end - start ) ;
elem . trigger ( 'timerpaused.zf.' + nameSpace ) ;
} ;
}
/ * *
* Runs a callback function when images are fully loaded .
* @ param { Object } images - Image ( s ) to check if loaded .
* @ param { Func } callback - Function to execute when image is fully loaded .
* /
function onImagesLoaded ( images , callback ) {
var self = this ,
unloaded = images . length ;
if ( unloaded === 0 ) {
callback ( ) ;
}
images . each ( function ( ) {
if ( this . complete ) {
singleImageLoaded ( ) ;
} else if ( typeof this . naturalWidth !== 'undefined' && this . naturalWidth > 0 ) {
singleImageLoaded ( ) ;
} else {
$ ( this ) . one ( 'load' , function ( ) {
singleImageLoaded ( ) ;
} ) ;
}
} ) ;
function singleImageLoaded ( ) {
unloaded -- ;
if ( unloaded === 0 ) {
callback ( ) ;
}
}
}
Foundation . Timer = Timer ;
Foundation . onImagesLoaded = onImagesLoaded ;
} ( jQuery ) ;
//**************************************************
//**Work inspired by multiple jquery swipe plugins**
//**Done by Yohai Ararat ***************************
//**************************************************
( function ( $ ) {
$ . spotSwipe = {
version : '1.0.0' ,
enabled : 'ontouchstart' in document . documentElement ,
preventDefault : false ,
moveThreshold : 75 ,
timeThreshold : 200
} ;
var startPosX ,
startPosY ,
startTime ,
elapsedTime ,
isMoving = false ;
function onTouchEnd ( ) {
// alert(this);
this . removeEventListener ( 'touchmove' , onTouchMove ) ;
this . removeEventListener ( 'touchend' , onTouchEnd ) ;
isMoving = false ;
}
function onTouchMove ( e ) {
if ( $ . spotSwipe . preventDefault ) {
e . preventDefault ( ) ;
}
if ( isMoving ) {
var x = e . touches [ 0 ] . pageX ;
var y = e . touches [ 0 ] . pageY ;
var dx = startPosX - x ;
var dy = startPosY - y ;
var dir ;
elapsedTime = new Date ( ) . getTime ( ) - startTime ;
if ( Math . abs ( dx ) >= $ . spotSwipe . moveThreshold && elapsedTime <= $ . spotSwipe . timeThreshold ) {
dir = dx > 0 ? 'left' : 'right' ;
}
// else if(Math.abs(dy) >= $.spotSwipe.moveThreshold && elapsedTime <= $.spotSwipe.timeThreshold) {
// dir = dy > 0 ? 'down' : 'up';
// }
if ( dir ) {
e . preventDefault ( ) ;
onTouchEnd . call ( this ) ;
$ ( this ) . trigger ( 'swipe' , dir ) . trigger ( 'swipe' + dir ) ;
}
}
}
function onTouchStart ( e ) {
if ( e . touches . length == 1 ) {
startPosX = e . touches [ 0 ] . pageX ;
startPosY = e . touches [ 0 ] . pageY ;
isMoving = true ;
startTime = new Date ( ) . getTime ( ) ;
this . addEventListener ( 'touchmove' , onTouchMove , false ) ;
this . addEventListener ( 'touchend' , onTouchEnd , false ) ;
}
}
function init ( ) {
this . addEventListener && this . addEventListener ( 'touchstart' , onTouchStart , false ) ;
}
function teardown ( ) {
this . removeEventListener ( 'touchstart' , onTouchStart ) ;
}
$ . event . special . swipe = { setup : init } ;
$ . each ( [ 'left' , 'up' , 'down' , 'right' ] , function ( ) {
$ . event . special [ 'swipe' + this ] = { setup : function ( ) {
$ ( this ) . on ( 'swipe' , $ . noop ) ;
} } ;
} ) ;
} ) ( jQuery ) ;
/ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
* Method for adding psuedo drag events to elements *
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * /
! function ( $ ) {
$ . fn . addTouch = function ( ) {
this . each ( function ( i , el ) {
$ ( el ) . bind ( 'touchstart touchmove touchend touchcancel' , function ( ) {
//we pass the original event object because the jQuery event
//object is normalized to w3c specs and does not provide the TouchList
handleTouch ( event ) ;
} ) ;
} ) ;
var handleTouch = function ( event ) {
var touches = event . changedTouches ,
first = touches [ 0 ] ,
eventTypes = {
touchstart : 'mousedown' ,
touchmove : 'mousemove' ,
touchend : 'mouseup'
} ,
type = eventTypes [ event . type ] ,
simulatedEvent ;
if ( 'MouseEvent' in window && typeof window . MouseEvent === 'function' ) {
simulatedEvent = new window . MouseEvent ( type , {
'bubbles' : true ,
'cancelable' : true ,
'screenX' : first . screenX ,
'screenY' : first . screenY ,
'clientX' : first . clientX ,
'clientY' : first . clientY
} ) ;
} else {
simulatedEvent = document . createEvent ( 'MouseEvent' ) ;
simulatedEvent . initMouseEvent ( type , true , true , window , 1 , first . screenX , first . screenY , first . clientX , first . clientY , false , false , false , false , 0 /*left*/ , null ) ;
}
first . target . dispatchEvent ( simulatedEvent ) ;
} ;
} ;
} ( jQuery ) ;
//**********************************
//**From the jQuery Mobile Library**
//**need to recreate functionality**
//**and try to improve if possible**
//**********************************
/ * R e m o v i n g t h e j Q u e r y f u n c t i o n * * * *
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
( function ( $ , window , undefined ) {
var $document = $ ( document ) ,
// supportTouch = $.mobile.support.touch,
touchStartEvent = 'touchstart' //supportTouch ? "touchstart" : "mousedown",
touchStopEvent = 'touchend' //supportTouch ? "touchend" : "mouseup",
touchMoveEvent = 'touchmove' //supportTouch ? "touchmove" : "mousemove";
// setup new event shortcuts
$ . each ( ( "touchstart touchmove touchend " +
"swipe swipeleft swiperight" ) . split ( " " ) , function ( i , name ) {
$ . fn [ name ] = function ( fn ) {
return fn ? this . bind ( name , fn ) : this . trigger ( name ) ;
} ;
// jQuery < 1.8
if ( $ . attrFn ) {
$ . attrFn [ name ] = true ;
}
} ) ;
function triggerCustomEvent ( obj , eventType , event , bubble ) {
var originalType = event . type ;
event . type = eventType ;
if ( bubble ) {
$ . event . trigger ( event , undefined , obj ) ;
} else {
$ . event . dispatch . call ( obj , event ) ;
}
event . type = originalType ;
}
// also handles taphold
// Also handles swipeleft, swiperight
$ . event . special . swipe = {
// More than this horizontal displacement, and we will suppress scrolling.
scrollSupressionThreshold : 30 ,
// More time than this, and it isn't a swipe.
durationThreshold : 1000 ,
// Swipe horizontal displacement must be more than this.
horizontalDistanceThreshold : window . devicePixelRatio >= 2 ? 15 : 30 ,
// Swipe vertical displacement must be less than this.
verticalDistanceThreshold : window . devicePixelRatio >= 2 ? 15 : 30 ,
getLocation : function ( event ) {
var winPageX = window . pageXOffset ,
winPageY = window . pageYOffset ,
x = event . clientX ,
y = event . clientY ;
if ( event . pageY === 0 && Math . floor ( y ) > Math . floor ( event . pageY ) ||
event . pageX === 0 && Math . floor ( x ) > Math . floor ( event . pageX ) ) {
// iOS4 clientX/clientY have the value that should have been
// in pageX/pageY. While pageX/page/ have the value 0
x = x - winPageX ;
y = y - winPageY ;
} else if ( y < ( event . pageY - winPageY ) || x < ( event . pageX - winPageX ) ) {
// Some Android browsers have totally bogus values for clientX/Y
// when scrolling/zooming a page. Detectable since clientX/clientY
// should never be smaller than pageX/pageY minus page scroll
x = event . pageX - winPageX ;
y = event . pageY - winPageY ;
}
return {
x : x ,
y : y
} ;
} ,
start : function ( event ) {
var data = event . originalEvent . touches ?
event . originalEvent . touches [ 0 ] : event ,
location = $ . event . special . swipe . getLocation ( data ) ;
return {
time : ( new Date ( ) ) . getTime ( ) ,
coords : [ location . x , location . y ] ,
origin : $ ( event . target )
} ;
} ,
stop : function ( event ) {
var data = event . originalEvent . touches ?
event . originalEvent . touches [ 0 ] : event ,
location = $ . event . special . swipe . getLocation ( data ) ;
return {
time : ( new Date ( ) ) . getTime ( ) ,
coords : [ location . x , location . y ]
} ;
} ,
handleSwipe : function ( start , stop , thisObject , origTarget ) {
if ( stop . time - start . time < $ . event . special . swipe . durationThreshold &&
Math . abs ( start . coords [ 0 ] - stop . coords [ 0 ] ) > $ . event . special . swipe . horizontalDistanceThreshold &&
Math . abs ( start . coords [ 1 ] - stop . coords [ 1 ] ) < $ . event . special . swipe . verticalDistanceThreshold ) {
var direction = start . coords [ 0 ] > stop . coords [ 0 ] ? "swipeleft" : "swiperight" ;
triggerCustomEvent ( thisObject , "swipe" , $ . Event ( "swipe" , { target : origTarget , swipestart : start , swipestop : stop } ) , true ) ;
triggerCustomEvent ( thisObject , direction , $ . Event ( direction , { target : origTarget , swipestart : start , swipestop : stop } ) , true ) ;
return true ;
}
return false ;
} ,
// This serves as a flag to ensure that at most one swipe event event is
// in work at any given time
eventInProgress : false ,
setup : function ( ) {
var events ,
thisObject = this ,
$this = $ ( thisObject ) ,
context = { } ;
// Retrieve the events data for this element and add the swipe context
events = $ . data ( this , "mobile-events" ) ;
if ( ! events ) {
events = { length : 0 } ;
$ . data ( this , "mobile-events" , events ) ;
}
events . length ++ ;
events . swipe = context ;
context . start = function ( event ) {
// Bail if we're already working on a swipe event
if ( $ . event . special . swipe . eventInProgress ) {
return ;
}
$ . event . special . swipe . eventInProgress = true ;
var stop ,
start = $ . event . special . swipe . start ( event ) ,
origTarget = event . target ,
emitted = false ;
context . move = function ( event ) {
if ( ! start || event . isDefaultPrevented ( ) ) {
return ;
}
stop = $ . event . special . swipe . stop ( event ) ;
if ( ! emitted ) {
emitted = $ . event . special . swipe . handleSwipe ( start , stop , thisObject , origTarget ) ;
if ( emitted ) {
// Reset the context to make way for the next swipe event
$ . event . special . swipe . eventInProgress = false ;
}
}
// prevent scrolling
if ( Math . abs ( start . coords [ 0 ] - stop . coords [ 0 ] ) > $ . event . special . swipe . scrollSupressionThreshold ) {
event . preventDefault ( ) ;
}
} ;
context . stop = function ( ) {
emitted = true ;
// Reset the context to make way for the next swipe event
$ . event . special . swipe . eventInProgress = false ;
$document . off ( touchMoveEvent , context . move ) ;
context . move = null ;
} ;
$document . on ( touchMoveEvent , context . move )
. one ( touchStopEvent , context . stop ) ;
} ;
$this . on ( touchStartEvent , context . start ) ;
} ,
teardown : function ( ) {
var events , context ;
events = $ . data ( this , "mobile-events" ) ;
if ( events ) {
context = events . swipe ;
delete events . swipe ;
events . length -- ;
if ( events . length === 0 ) {
$ . removeData ( this , "mobile-events" ) ;
}
}
if ( context ) {
if ( context . start ) {
$ ( this ) . off ( touchStartEvent , context . start ) ;
}
if ( context . move ) {
$document . off ( touchMoveEvent , context . move ) ;
}
if ( context . stop ) {
$document . off ( touchStopEvent , context . stop ) ;
}
}
}
} ;
$ . each ( {
swipeleft : "swipe.left" ,
swiperight : "swipe.right"
} , function ( event , sourceEvent ) {
$ . event . special [ event ] = {
setup : function ( ) {
$ ( this ) . bind ( sourceEvent , $ . noop ) ;
} ,
teardown : function ( ) {
$ ( this ) . unbind ( sourceEvent ) ;
}
} ;
} ) ;
} ) ( jQuery , this ) ;
* /
'use strict' ;
! function ( $ ) {
var MutationObserver = function ( ) {
var prefixes = [ 'WebKit' , 'Moz' , 'O' , 'Ms' , '' ] ;
for ( var i = 0 ; i < prefixes . length ; i ++ ) {
if ( prefixes [ i ] + 'MutationObserver' in window ) {
return window [ prefixes [ i ] + 'MutationObserver' ] ;
}
}
return false ;
} ( ) ;
var triggers = function ( el , type ) {
el . data ( type ) . split ( ' ' ) . forEach ( function ( id ) {
$ ( '#' + id ) [ type === 'close' ? 'trigger' : 'triggerHandler' ] ( type + '.zf.trigger' , [ el ] ) ;
} ) ;
} ;
// Elements with [data-open] will reveal a plugin that supports it when clicked.
$ ( document ) . on ( 'click.zf.trigger' , '[data-open]' , function ( ) {
triggers ( $ ( this ) , 'open' ) ;
} ) ;
// Elements with [data-close] will close a plugin that supports it when clicked.
// If used without a value on [data-close], the event will bubble, allowing it to close a parent component.
$ ( document ) . on ( 'click.zf.trigger' , '[data-close]' , function ( ) {
var id = $ ( this ) . data ( 'close' ) ;
if ( id ) {
triggers ( $ ( this ) , 'close' ) ;
} else {
$ ( this ) . trigger ( 'close.zf.trigger' ) ;
}
} ) ;
// Elements with [data-toggle] will toggle a plugin that supports it when clicked.
$ ( document ) . on ( 'click.zf.trigger' , '[data-toggle]' , function ( ) {
triggers ( $ ( this ) , 'toggle' ) ;
} ) ;
// Elements with [data-closable] will respond to close.zf.trigger events.
$ ( document ) . on ( 'close.zf.trigger' , '[data-closable]' , function ( e ) {
e . stopPropagation ( ) ;
var animation = $ ( this ) . data ( 'closable' ) ;
if ( animation !== '' ) {
Foundation . Motion . animateOut ( $ ( this ) , animation , function ( ) {
$ ( this ) . trigger ( 'closed.zf' ) ;
} ) ;
} else {
$ ( this ) . fadeOut ( ) . trigger ( 'closed.zf' ) ;
}
} ) ;
$ ( document ) . on ( 'focus.zf.trigger blur.zf.trigger' , '[data-toggle-focus]' , function ( ) {
var id = $ ( this ) . data ( 'toggle-focus' ) ;
$ ( '#' + id ) . triggerHandler ( 'toggle.zf.trigger' , [ $ ( this ) ] ) ;
} ) ;
/ * *
* Fires once after all other scripts have loaded
* @ function
* @ private
* /
2016-09-08 07:52:22 +00:00
$ ( window ) . on ( 'load' , function ( ) {
2016-09-07 10:58:25 +00:00
checkListeners ( ) ;
} ) ;
function checkListeners ( ) {
eventsListener ( ) ;
resizeListener ( ) ;
scrollListener ( ) ;
closemeListener ( ) ;
}
//******** only fires this function once on load, if there's something to watch ********
function closemeListener ( pluginName ) {
var yetiBoxes = $ ( '[data-yeti-box]' ) ,
plugNames = [ 'dropdown' , 'tooltip' , 'reveal' ] ;
if ( pluginName ) {
if ( typeof pluginName === 'string' ) {
plugNames . push ( pluginName ) ;
} else if ( typeof pluginName === 'object' && typeof pluginName [ 0 ] === 'string' ) {
plugNames . concat ( pluginName ) ;
} else {
console . error ( 'Plugin names must be strings' ) ;
}
}
if ( yetiBoxes . length ) {
var listeners = plugNames . map ( function ( name ) {
return 'closeme.zf.' + name ;
} ) . join ( ' ' ) ;
$ ( window ) . off ( listeners ) . on ( listeners , function ( e , pluginId ) {
var plugin = e . namespace . split ( '.' ) [ 0 ] ;
var plugins = $ ( '[data-' + plugin + ']' ) . not ( '[data-yeti-box="' + pluginId + '"]' ) ;
plugins . each ( function ( ) {
var _this = $ ( this ) ;
_this . triggerHandler ( 'close.zf.trigger' , [ _this ] ) ;
} ) ;
} ) ;
}
}
function resizeListener ( debounce ) {
var timer = void 0 ,
$nodes = $ ( '[data-resize]' ) ;
if ( $nodes . length ) {
$ ( window ) . off ( 'resize.zf.trigger' ) . on ( 'resize.zf.trigger' , function ( e ) {
if ( timer ) {
clearTimeout ( timer ) ;
}
timer = setTimeout ( function ( ) {
if ( ! MutationObserver ) {
//fallback for IE 9
$nodes . each ( function ( ) {
$ ( this ) . triggerHandler ( 'resizeme.zf.trigger' ) ;
} ) ;
}
//trigger all listening elements and signal a resize event
$nodes . attr ( 'data-events' , "resize" ) ;
} , debounce || 10 ) ; //default time to emit resize event
} ) ;
}
}
function scrollListener ( debounce ) {
var timer = void 0 ,
$nodes = $ ( '[data-scroll]' ) ;
if ( $nodes . length ) {
$ ( window ) . off ( 'scroll.zf.trigger' ) . on ( 'scroll.zf.trigger' , function ( e ) {
if ( timer ) {
clearTimeout ( timer ) ;
}
timer = setTimeout ( function ( ) {
if ( ! MutationObserver ) {
//fallback for IE 9
$nodes . each ( function ( ) {
$ ( this ) . triggerHandler ( 'scrollme.zf.trigger' ) ;
} ) ;
}
//trigger all listening elements and signal a scroll event
$nodes . attr ( 'data-events' , "scroll" ) ;
} , debounce || 10 ) ; //default time to emit scroll event
} ) ;
}
}
function eventsListener ( ) {
if ( ! MutationObserver ) {
return false ;
}
var nodes = document . querySelectorAll ( '[data-resize], [data-scroll], [data-mutate]' ) ;
//element callback
var listeningElementsMutation = function ( mutationRecordsList ) {
var $target = $ ( mutationRecordsList [ 0 ] . target ) ;
//trigger the event handler for the element depending on type
switch ( $target . attr ( "data-events" ) ) {
case "resize" :
$target . triggerHandler ( 'resizeme.zf.trigger' , [ $target ] ) ;
break ;
case "scroll" :
$target . triggerHandler ( 'scrollme.zf.trigger' , [ $target , window . pageYOffset ] ) ;
break ;
// case "mutate" :
// console.log('mutate', $target);
// $target.triggerHandler('mutate.zf.trigger');
//
// //make sure we don't get stuck in an infinite loop from sloppy codeing
// if ($target.index('[data-mutate]') == $("[data-mutate]").length-1) {
// domMutationObserver();
// }
// break;
default :
return false ;
//nothing
}
} ;
if ( nodes . length ) {
//for each element that needs to listen for resizing, scrolling, (or coming soon mutation) add a single observer
for ( var i = 0 ; i <= nodes . length - 1 ; i ++ ) {
var elementObserver = new MutationObserver ( listeningElementsMutation ) ;
elementObserver . observe ( nodes [ i ] , { attributes : true , childList : false , characterData : false , subtree : false , attributeFilter : [ "data-events" ] } ) ;
}
}
}
// ------------------------------------
// [PH]
// Foundation.CheckWatchers = checkWatchers;
Foundation . IHearYou = checkListeners ;
// Foundation.ISeeYou = scrollListener;
// Foundation.IFeelYou = closemeListener;
} ( jQuery ) ;
// function domMutationObserver(debounce) {
// // !!! This is coming soon and needs more work; not active !!! //
// var timer,
// nodes = document.querySelectorAll('[data-mutate]');
// //
// if (nodes.length) {
// // var MutationObserver = (function () {
// // var prefixes = ['WebKit', 'Moz', 'O', 'Ms', ''];
// // for (var i=0; i < prefixes.length; i++) {
// // if (prefixes[i] + 'MutationObserver' in window) {
// // return window[prefixes[i] + 'MutationObserver'];
// // }
// // }
// // return false;
// // }());
//
//
// //for the body, we need to listen for all changes effecting the style and class attributes
// var bodyObserver = new MutationObserver(bodyMutation);
// bodyObserver.observe(document.body, { attributes: true, childList: true, characterData: false, subtree:true, attributeFilter:["style", "class"]});
//
//
// //body callback
// function bodyMutation(mutate) {
// //trigger all listening elements and signal a mutation event
// if (timer) { clearTimeout(timer); }
//
// timer = setTimeout(function() {
// bodyObserver.disconnect();
// $('[data-mutate]').attr('data-events',"mutate");
// }, debounce || 150);
// }
// }
// }
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Abide module .
* @ module foundation . abide
* /
var Abide = function ( ) {
/ * *
* Creates a new instance of Abide .
* @ class
* @ fires Abide # init
* @ param { Object } element - jQuery object to add the trigger to .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Abide ( element ) {
var options = arguments . length <= 1 || arguments [ 1 ] === undefined ? { } : arguments [ 1 ] ;
_classCallCheck ( this , Abide ) ;
this . $element = element ;
this . options = $ . extend ( { } , Abide . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Abide' ) ;
}
/ * *
* Initializes the Abide plugin and calls functions to get Abide functioning on load .
* @ private
* /
_createClass ( Abide , [ {
key : '_init' ,
value : function _init ( ) {
this . $inputs = this . $element . find ( 'input, textarea, select' ) ;
this . _events ( ) ;
}
/ * *
* Initializes events for Abide .
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this2 = this ;
this . $element . off ( '.abide' ) . on ( 'reset.zf.abide' , function ( ) {
_this2 . resetForm ( ) ;
} ) . on ( 'submit.zf.abide' , function ( ) {
return _this2 . validateForm ( ) ;
} ) ;
if ( this . options . validateOn === 'fieldChange' ) {
this . $inputs . off ( 'change.zf.abide' ) . on ( 'change.zf.abide' , function ( e ) {
_this2 . validateInput ( $ ( e . target ) ) ;
} ) ;
}
if ( this . options . liveValidate ) {
this . $inputs . off ( 'input.zf.abide' ) . on ( 'input.zf.abide' , function ( e ) {
_this2 . validateInput ( $ ( e . target ) ) ;
} ) ;
}
}
/ * *
* Calls necessary functions to update Abide upon DOM change
* @ private
* /
} , {
key : '_reflow' ,
value : function _reflow ( ) {
this . _init ( ) ;
}
/ * *
* Checks whether or not a form element has the required attribute and if it ' s checked or not
* @ param { Object } element - jQuery object to check for required attribute
* @ returns { Boolean } Boolean value depends on whether or not attribute is checked or empty
* /
} , {
key : 'requiredCheck' ,
value : function requiredCheck ( $el ) {
if ( ! $el . attr ( 'required' ) ) return true ;
var isGood = true ;
switch ( $el [ 0 ] . type ) {
case 'checkbox' :
isGood = $el [ 0 ] . checked ;
break ;
case 'select' :
case 'select-one' :
case 'select-multiple' :
var opt = $el . find ( 'option:selected' ) ;
if ( ! opt . length || ! opt . val ( ) ) isGood = false ;
break ;
default :
if ( ! $el . val ( ) || ! $el . val ( ) . length ) isGood = false ;
}
return isGood ;
}
/ * *
* Based on $el , get the first element with selector in this order :
* 1. The element 's direct sibling(' s ) .
* 3. The element 's parent' s children .
*
* This allows for multiple form errors per input , though if none are found , no form errors will be shown .
*
* @ param { Object } $el - jQuery object to use as reference to find the form error selector .
* @ returns { Object } jQuery object with the selector .
* /
} , {
key : 'findFormError' ,
value : function findFormError ( $el ) {
var $error = $el . siblings ( this . options . formErrorSelector ) ;
if ( ! $error . length ) {
$error = $el . parent ( ) . find ( this . options . formErrorSelector ) ;
}
return $error ;
}
/ * *
* Get the first element in this order :
* 2. The < label > with the attribute ` [for="someInputId"] `
* 3. The ` .closest() ` < label >
*
* @ param { Object } $el - jQuery object to check for required attribute
* @ returns { Boolean } Boolean value depends on whether or not attribute is checked or empty
* /
} , {
key : 'findLabel' ,
value : function findLabel ( $el ) {
var id = $el [ 0 ] . id ;
var $label = this . $element . find ( 'label[for="' + id + '"]' ) ;
if ( ! $label . length ) {
return $el . closest ( 'label' ) ;
}
return $label ;
}
/ * *
* Get the set of labels associated with a set of radio els in this order
* 2. The < label > with the attribute ` [for="someInputId"] `
* 3. The ` .closest() ` < label >
*
* @ param { Object } $el - jQuery object to check for required attribute
* @ returns { Boolean } Boolean value depends on whether or not attribute is checked or empty
* /
} , {
key : 'findRadioLabels' ,
value : function findRadioLabels ( $els ) {
var _this3 = this ;
var labels = $els . map ( function ( i , el ) {
var id = el . id ;
var $label = _this3 . $element . find ( 'label[for="' + id + '"]' ) ;
if ( ! $label . length ) {
$label = $ ( el ) . closest ( 'label' ) ;
}
return $label [ 0 ] ;
} ) ;
return $ ( labels ) ;
}
/ * *
* Adds the CSS error class as specified by the Abide settings to the label , input , and the form
* @ param { Object } $el - jQuery object to add the class to
* /
} , {
key : 'addErrorClasses' ,
value : function addErrorClasses ( $el ) {
var $label = this . findLabel ( $el ) ;
var $formError = this . findFormError ( $el ) ;
if ( $label . length ) {
$label . addClass ( this . options . labelErrorClass ) ;
}
if ( $formError . length ) {
$formError . addClass ( this . options . formErrorClass ) ;
}
$el . addClass ( this . options . inputErrorClass ) . attr ( 'data-invalid' , '' ) ;
}
/ * *
* Remove CSS error classes etc from an entire radio button group
* @ param { String } groupName - A string that specifies the name of a radio button group
*
* /
} , {
key : 'removeRadioErrorClasses' ,
value : function removeRadioErrorClasses ( groupName ) {
var $els = this . $element . find ( ':radio[name="' + groupName + '"]' ) ;
var $labels = this . findRadioLabels ( $els ) ;
var $formErrors = this . findFormError ( $els ) ;
if ( $labels . length ) {
$labels . removeClass ( this . options . labelErrorClass ) ;
}
if ( $formErrors . length ) {
$formErrors . removeClass ( this . options . formErrorClass ) ;
}
$els . removeClass ( this . options . inputErrorClass ) . removeAttr ( 'data-invalid' ) ;
}
/ * *
* Removes CSS error class as specified by the Abide settings from the label , input , and the form
* @ param { Object } $el - jQuery object to remove the class from
* /
} , {
key : 'removeErrorClasses' ,
value : function removeErrorClasses ( $el ) {
// radios need to clear all of the els
if ( $el [ 0 ] . type == 'radio' ) {
return this . removeRadioErrorClasses ( $el . attr ( 'name' ) ) ;
}
var $label = this . findLabel ( $el ) ;
var $formError = this . findFormError ( $el ) ;
if ( $label . length ) {
$label . removeClass ( this . options . labelErrorClass ) ;
}
if ( $formError . length ) {
$formError . removeClass ( this . options . formErrorClass ) ;
}
$el . removeClass ( this . options . inputErrorClass ) . removeAttr ( 'data-invalid' ) ;
}
/ * *
* Goes through a form to find inputs and proceeds to validate them in ways specific to their type
* @ fires Abide # invalid
* @ fires Abide # valid
* @ param { Object } element - jQuery object to validate , should be an HTML input
* @ returns { Boolean } goodToGo - If the input is valid or not .
* /
} , {
key : 'validateInput' ,
value : function validateInput ( $el ) {
var clearRequire = this . requiredCheck ( $el ) ,
validated = false ,
customValidator = true ,
validator = $el . attr ( 'data-validator' ) ,
equalTo = true ;
// don't validate ignored inputs or hidden inputs
if ( $el . is ( '[data-abide-ignore]' ) || $el . is ( '[type="hidden"]' ) ) {
return true ;
}
switch ( $el [ 0 ] . type ) {
case 'radio' :
validated = this . validateRadio ( $el . attr ( 'name' ) ) ;
break ;
case 'checkbox' :
validated = clearRequire ;
break ;
case 'select' :
case 'select-one' :
case 'select-multiple' :
validated = clearRequire ;
break ;
default :
validated = this . validateText ( $el ) ;
}
if ( validator ) {
customValidator = this . matchValidation ( $el , validator , $el . attr ( 'required' ) ) ;
}
if ( $el . attr ( 'data-equalto' ) ) {
equalTo = this . options . validators . equalTo ( $el ) ;
}
var goodToGo = [ clearRequire , validated , customValidator , equalTo ] . indexOf ( false ) === - 1 ;
var message = ( goodToGo ? 'valid' : 'invalid' ) + '.zf.abide' ;
this [ goodToGo ? 'removeErrorClasses' : 'addErrorClasses' ] ( $el ) ;
/ * *
* Fires when the input is done checking for validation . Event trigger is either ` valid.zf.abide ` or ` invalid.zf.abide `
* Trigger includes the DOM element of the input .
* @ event Abide # valid
* @ event Abide # invalid
* /
$el . trigger ( message , [ $el ] ) ;
return goodToGo ;
}
/ * *
* Goes through a form and if there are any invalid inputs , it will display the form error element
* @ returns { Boolean } noError - true if no errors were detected ...
* @ fires Abide # formvalid
* @ fires Abide # forminvalid
* /
} , {
key : 'validateForm' ,
value : function validateForm ( ) {
var acc = [ ] ;
var _this = this ;
this . $inputs . each ( function ( ) {
acc . push ( _this . validateInput ( $ ( this ) ) ) ;
} ) ;
var noError = acc . indexOf ( false ) === - 1 ;
this . $element . find ( '[data-abide-error]' ) . css ( 'display' , noError ? 'none' : 'block' ) ;
/ * *
* Fires when the form is finished validating . Event trigger is either ` formvalid.zf.abide ` or ` forminvalid.zf.abide ` .
* Trigger includes the element of the form .
* @ event Abide # formvalid
* @ event Abide # forminvalid
* /
this . $element . trigger ( ( noError ? 'formvalid' : 'forminvalid' ) + '.zf.abide' , [ this . $element ] ) ;
return noError ;
}
/ * *
* Determines whether or a not a text input is valid based on the pattern specified in the attribute . If no matching pattern is found , returns true .
* @ param { Object } $el - jQuery object to validate , should be a text input HTML element
* @ param { String } pattern - string value of one of the RegEx patterns in Abide . options . patterns
* @ returns { Boolean } Boolean value depends on whether or not the input value matches the pattern specified
* /
} , {
key : 'validateText' ,
value : function validateText ( $el , pattern ) {
// A pattern can be passed to this function, or it will be infered from the input's "pattern" attribute, or it's "type" attribute
pattern = pattern || $el . attr ( 'pattern' ) || $el . attr ( 'type' ) ;
var inputText = $el . val ( ) ;
var valid = false ;
if ( inputText . length ) {
// If the pattern attribute on the element is in Abide's list of patterns, then test that regexp
if ( this . options . patterns . hasOwnProperty ( pattern ) ) {
valid = this . options . patterns [ pattern ] . test ( inputText ) ;
}
// If the pattern name isn't also the type attribute of the field, then test it as a regexp
else if ( pattern !== $el . attr ( 'type' ) ) {
valid = new RegExp ( pattern ) . test ( inputText ) ;
} else {
valid = true ;
}
}
// An empty field is valid if it's not required
else if ( ! $el . prop ( 'required' ) ) {
valid = true ;
}
return valid ;
}
/ * *
* Determines whether or a not a radio input is valid based on whether or not it is required and selected . Although the function targets a single ` <input> ` , it validates by checking the ` required ` and ` checked ` properties of all radio buttons in its group .
* @ param { String } groupName - A string that specifies the name of a radio button group
* @ returns { Boolean } Boolean value depends on whether or not at least one radio input has been selected ( if it ' s required )
* /
} , {
key : 'validateRadio' ,
value : function validateRadio ( groupName ) {
// If at least one radio in the group has the `required` attribute, the group is considered required
// Per W3C spec, all radio buttons in a group should have `required`, but we're being nice
var $group = this . $element . find ( ':radio[name="' + groupName + '"]' ) ;
var valid = false ,
required = false ;
// For the group to be required, at least one radio needs to be required
$group . each ( function ( i , e ) {
if ( $ ( e ) . attr ( 'required' ) ) {
required = true ;
}
} ) ;
if ( ! required ) valid = true ;
if ( ! valid ) {
// For the group to be valid, at least one radio needs to be checked
$group . each ( function ( i , e ) {
if ( $ ( e ) . prop ( 'checked' ) ) {
valid = true ;
}
} ) ;
} ;
return valid ;
}
/ * *
* Determines if a selected input passes a custom validation function . Multiple validations can be used , if passed to the element with ` data-validator="foo bar baz" ` in a space separated listed .
* @ param { Object } $el - jQuery input element .
* @ param { String } validators - a string of function names matching functions in the Abide . options . validators object .
* @ param { Boolean } required - self explanatory ?
* @ returns { Boolean } - true if validations passed .
* /
} , {
key : 'matchValidation' ,
value : function matchValidation ( $el , validators , required ) {
var _this4 = this ;
required = required ? true : false ;
var clear = validators . split ( ' ' ) . map ( function ( v ) {
return _this4 . options . validators [ v ] ( $el , required , $el . parent ( ) ) ;
} ) ;
return clear . indexOf ( false ) === - 1 ;
}
/ * *
* Resets form inputs and styles
* @ fires Abide # formreset
* /
} , {
key : 'resetForm' ,
value : function resetForm ( ) {
var $form = this . $element ,
opts = this . options ;
$ ( '.' + opts . labelErrorClass , $form ) . not ( 'small' ) . removeClass ( opts . labelErrorClass ) ;
$ ( '.' + opts . inputErrorClass , $form ) . not ( 'small' ) . removeClass ( opts . inputErrorClass ) ;
$ ( opts . formErrorSelector + '.' + opts . formErrorClass ) . removeClass ( opts . formErrorClass ) ;
$form . find ( '[data-abide-error]' ) . css ( 'display' , 'none' ) ;
$ ( ':input' , $form ) . not ( ':button, :submit, :reset, :hidden, :radio, :checkbox, [data-abide-ignore]' ) . val ( '' ) . removeAttr ( 'data-invalid' ) ;
$ ( ':input:radio' , $form ) . not ( '[data-abide-ignore]' ) . prop ( 'checked' , false ) . removeAttr ( 'data-invalid' ) ;
$ ( ':input:checkbox' , $form ) . not ( '[data-abide-ignore]' ) . prop ( 'checked' , false ) . removeAttr ( 'data-invalid' ) ;
/ * *
* Fires when the form has been reset .
* @ event Abide # formreset
* /
$form . trigger ( 'formreset.zf.abide' , [ $form ] ) ;
}
/ * *
* Destroys an instance of Abide .
* Removes error styles and classes from elements , without resetting their values .
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
var _this = this ;
this . $element . off ( '.abide' ) . find ( '[data-abide-error]' ) . css ( 'display' , 'none' ) ;
this . $inputs . off ( '.abide' ) . each ( function ( ) {
_this . removeErrorClasses ( $ ( this ) ) ;
} ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Abide ;
} ( ) ;
/ * *
* Default settings for plugin
* /
Abide . defaults = {
/ * *
* The default event to validate inputs . Checkboxes and radios validate immediately .
* Remove or change this value for manual validation .
* @ option
* @ example 'fieldChange'
* /
validateOn : 'fieldChange' ,
/ * *
* Class to be applied to input labels on failed validation .
* @ option
* @ example 'is-invalid-label'
* /
labelErrorClass : 'is-invalid-label' ,
/ * *
* Class to be applied to inputs on failed validation .
* @ option
* @ example 'is-invalid-input'
* /
inputErrorClass : 'is-invalid-input' ,
/ * *
* Class selector to use to target Form Errors for show / hide .
* @ option
* @ example '.form-error'
* /
formErrorSelector : '.form-error' ,
/ * *
* Class added to Form Errors on failed validation .
* @ option
* @ example 'is-visible'
* /
formErrorClass : 'is-visible' ,
/ * *
* Set to true to validate text inputs on any value change .
* @ option
* @ example false
* /
liveValidate : false ,
patterns : {
alpha : /^[a-zA-Z]+$/ ,
alpha _numeric : /^[a-zA-Z0-9]+$/ ,
integer : /^[-+]?\d+$/ ,
number : /^[-+]?\d*(?:[\.\,]\d+)?$/ ,
// amex, visa, diners
card : /^(?:4[0-9]{12}(?:[0-9]{3})?|5[1-5][0-9]{14}|6(?:011|5[0-9][0-9])[0-9]{12}|3[47][0-9]{13}|3(?:0[0-5]|[68][0-9])[0-9]{11}|(?:2131|1800|35\d{3})\d{11})$/ ,
cvv : /^([0-9]){3,4}$/ ,
// http://www.whatwg.org/specs/web-apps/current-work/multipage/states-of-the-type-attribute.html#valid-e-mail-address
email : /^[a-zA-Z0-9.!#$%&'*+\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)+$/ ,
url : /^(https?|ftp|file|ssh):\/\/(((([a-zA-Z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:)*@)?(((\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5]))|((([a-zA-Z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-zA-Z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-zA-Z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-zA-Z]|\d|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.)+(([a-zA-Z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(([a-zA-Z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])([a-zA-Z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])*([a-zA-Z]|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])))\.?)(:\d*)?)(\/((([a-zA-Z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)+(\/(([a-zA-Z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)*)*)?)?(\?((([a-zA-Z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|[\uE000-\uF8FF]|\/|\?)*)?(\#((([a-zA-Z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|\/|\?)*)?$/ ,
// abc.de
domain : /^([a-zA-Z0-9]([a-zA-Z0-9\-]{0,61}[a-zA-Z0-9])?\.)+[a-zA-Z]{2,8}$/ ,
datetime : /^([0-2][0-9]{3})\-([0-1][0-9])\-([0-3][0-9])T([0-5][0-9])\:([0-5][0-9])\:([0-5][0-9])(Z|([\-\+]([0-1][0-9])\:00))$/ ,
// YYYY-MM-DD
date : /(?:19|20)[0-9]{2}-(?:(?:0[1-9]|1[0-2])-(?:0[1-9]|1[0-9]|2[0-9])|(?:(?!02)(?:0[1-9]|1[0-2])-(?:30))|(?:(?:0[13578]|1[02])-31))$/ ,
// HH:MM:SS
time : /^(0[0-9]|1[0-9]|2[0-3])(:[0-5][0-9]){2}$/ ,
dateISO : /^\d{4}[\/\-]\d{1,2}[\/\-]\d{1,2}$/ ,
// MM/DD/YYYY
month _day _year : /^(0[1-9]|1[012])[- \/.](0[1-9]|[12][0-9]|3[01])[- \/.]\d{4}$/ ,
// DD/MM/YYYY
day _month _year : /^(0[1-9]|[12][0-9]|3[01])[- \/.](0[1-9]|1[012])[- \/.]\d{4}$/ ,
// #FFF or #FFFFFF
color : /^#?([a-fA-F0-9]{6}|[a-fA-F0-9]{3})$/
} ,
/ * *
* Optional validation functions to be used . ` equalTo ` being the only default included function .
* Functions should return only a boolean if the input is valid or not . Functions are given the following arguments :
* el : The jQuery element to validate .
* required : Boolean value of the required attribute be present or not .
* parent : The direct parent of the input .
* @ option
* /
validators : {
equalTo : function ( el , required , parent ) {
return $ ( '#' + el . attr ( 'data-equalto' ) ) . val ( ) === el . val ( ) ;
}
}
} ;
// Window exports
Foundation . plugin ( Abide , 'Abide' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Accordion module .
* @ module foundation . accordion
* @ requires foundation . util . keyboard
* @ requires foundation . util . motion
* /
var Accordion = function ( ) {
/ * *
* Creates a new instance of an accordion .
* @ class
* @ fires Accordion # init
* @ param { jQuery } element - jQuery object to make into an accordion .
* @ param { Object } options - a plain object with settings to override the default options .
* /
function Accordion ( element , options ) {
_classCallCheck ( this , Accordion ) ;
this . $element = element ;
this . options = $ . extend ( { } , Accordion . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Accordion' ) ;
Foundation . Keyboard . register ( 'Accordion' , {
'ENTER' : 'toggle' ,
'SPACE' : 'toggle' ,
'ARROW_DOWN' : 'next' ,
'ARROW_UP' : 'previous'
} ) ;
}
/ * *
* Initializes the accordion by animating the preset active pane ( s ) .
* @ private
* /
_createClass ( Accordion , [ {
key : '_init' ,
value : function _init ( ) {
this . $element . attr ( 'role' , 'tablist' ) ;
this . $tabs = this . $element . children ( 'li, [data-accordion-item]' ) ;
this . $tabs . each ( function ( idx , el ) {
var $el = $ ( el ) ,
$content = $el . children ( '[data-tab-content]' ) ,
id = $content [ 0 ] . id || Foundation . GetYoDigits ( 6 , 'accordion' ) ,
linkId = el . id || id + '-label' ;
$el . find ( 'a:first' ) . attr ( {
'aria-controls' : id ,
'role' : 'tab' ,
'id' : linkId ,
'aria-expanded' : false ,
'aria-selected' : false
} ) ;
$content . attr ( { 'role' : 'tabpanel' , 'aria-labelledby' : linkId , 'aria-hidden' : true , 'id' : id } ) ;
} ) ;
var $initActive = this . $element . find ( '.is-active' ) . children ( '[data-tab-content]' ) ;
if ( $initActive . length ) {
this . down ( $initActive , true ) ;
}
this . _events ( ) ;
}
/ * *
* Adds event handlers for items within the accordion .
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ;
this . $tabs . each ( function ( ) {
var $elem = $ ( this ) ;
var $tabContent = $elem . children ( '[data-tab-content]' ) ;
if ( $tabContent . length ) {
$elem . children ( 'a' ) . off ( 'click.zf.accordion keydown.zf.accordion' ) . on ( 'click.zf.accordion' , function ( e ) {
// $(this).children('a').on('click.zf.accordion', function(e) {
e . preventDefault ( ) ;
if ( $elem . hasClass ( 'is-active' ) ) {
if ( _this . options . allowAllClosed || $elem . siblings ( ) . hasClass ( 'is-active' ) ) {
_this . up ( $tabContent ) ;
}
} else {
_this . down ( $tabContent ) ;
}
} ) . on ( 'keydown.zf.accordion' , function ( e ) {
Foundation . Keyboard . handleKey ( e , 'Accordion' , {
toggle : function ( ) {
_this . toggle ( $tabContent ) ;
} ,
next : function ( ) {
var $a = $elem . next ( ) . find ( 'a' ) . focus ( ) ;
if ( ! _this . options . multiExpand ) {
$a . trigger ( 'click.zf.accordion' ) ;
}
} ,
previous : function ( ) {
var $a = $elem . prev ( ) . find ( 'a' ) . focus ( ) ;
if ( ! _this . options . multiExpand ) {
$a . trigger ( 'click.zf.accordion' ) ;
}
} ,
handled : function ( ) {
e . preventDefault ( ) ;
e . stopPropagation ( ) ;
}
} ) ;
} ) ;
}
} ) ;
}
/ * *
* Toggles the selected content pane ' s open / close state .
* @ param { jQuery } $target - jQuery object of the pane to toggle .
* @ function
* /
} , {
key : 'toggle' ,
value : function toggle ( $target ) {
if ( $target . parent ( ) . hasClass ( 'is-active' ) ) {
if ( this . options . allowAllClosed || $target . parent ( ) . siblings ( ) . hasClass ( 'is-active' ) ) {
this . up ( $target ) ;
} else {
return ;
}
} else {
this . down ( $target ) ;
}
}
/ * *
* Opens the accordion tab defined by ` $ target ` .
* @ param { jQuery } $target - Accordion pane to open .
* @ param { Boolean } firstTime - flag to determine if reflow should happen .
* @ fires Accordion # down
* @ function
* /
} , {
key : 'down' ,
value : function down ( $target , firstTime ) {
var _this2 = this ;
if ( ! this . options . multiExpand && ! firstTime ) {
var $currentActive = this . $element . children ( '.is-active' ) . children ( '[data-tab-content]' ) ;
if ( $currentActive . length ) {
this . up ( $currentActive ) ;
}
}
$target . attr ( 'aria-hidden' , false ) . parent ( '[data-tab-content]' ) . addBack ( ) . parent ( ) . addClass ( 'is-active' ) ;
$target . slideDown ( this . options . slideSpeed , function ( ) {
/ * *
* Fires when the tab is done opening .
* @ event Accordion # down
* /
_this2 . $element . trigger ( 'down.zf.accordion' , [ $target ] ) ;
} ) ;
$ ( '#' + $target . attr ( 'aria-labelledby' ) ) . attr ( {
'aria-expanded' : true ,
'aria-selected' : true
} ) ;
}
/ * *
* Closes the tab defined by ` $ target ` .
* @ param { jQuery } $target - Accordion tab to close .
* @ fires Accordion # up
* @ function
* /
} , {
key : 'up' ,
value : function up ( $target ) {
var $aunts = $target . parent ( ) . siblings ( ) ,
_this = this ;
var canClose = this . options . multiExpand ? $aunts . hasClass ( 'is-active' ) : $target . parent ( ) . hasClass ( 'is-active' ) ;
if ( ! this . options . allowAllClosed && ! canClose ) {
return ;
}
// Foundation.Move(this.options.slideSpeed, $target, function(){
$target . slideUp ( _this . options . slideSpeed , function ( ) {
/ * *
* Fires when the tab is done collapsing up .
* @ event Accordion # up
* /
_this . $element . trigger ( 'up.zf.accordion' , [ $target ] ) ;
} ) ;
// });
$target . attr ( 'aria-hidden' , true ) . parent ( ) . removeClass ( 'is-active' ) ;
$ ( '#' + $target . attr ( 'aria-labelledby' ) ) . attr ( {
'aria-expanded' : false ,
'aria-selected' : false
} ) ;
}
/ * *
* Destroys an instance of an accordion .
* @ fires Accordion # destroyed
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . find ( '[data-tab-content]' ) . stop ( true ) . slideUp ( 0 ) . css ( 'display' , '' ) ;
this . $element . find ( 'a' ) . off ( '.zf.accordion' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Accordion ;
} ( ) ;
Accordion . defaults = {
/ * *
* Amount of time to animate the opening of an accordion pane .
* @ option
* @ example 250
* /
slideSpeed : 250 ,
/ * *
* Allow the accordion to have multiple open panes .
* @ option
* @ example false
* /
multiExpand : false ,
/ * *
* Allow the accordion to close all panes .
* @ option
* @ example false
* /
allowAllClosed : false
} ;
// Window exports
Foundation . plugin ( Accordion , 'Accordion' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* AccordionMenu module .
* @ module foundation . accordionMenu
* @ requires foundation . util . keyboard
* @ requires foundation . util . motion
* @ requires foundation . util . nest
* /
var AccordionMenu = function ( ) {
/ * *
* Creates a new instance of an accordion menu .
* @ class
* @ fires AccordionMenu # init
* @ param { jQuery } element - jQuery object to make into an accordion menu .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function AccordionMenu ( element , options ) {
_classCallCheck ( this , AccordionMenu ) ;
this . $element = element ;
this . options = $ . extend ( { } , AccordionMenu . defaults , this . $element . data ( ) , options ) ;
Foundation . Nest . Feather ( this . $element , 'accordion' ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'AccordionMenu' ) ;
Foundation . Keyboard . register ( 'AccordionMenu' , {
'ENTER' : 'toggle' ,
'SPACE' : 'toggle' ,
'ARROW_RIGHT' : 'open' ,
'ARROW_UP' : 'up' ,
'ARROW_DOWN' : 'down' ,
'ARROW_LEFT' : 'close' ,
'ESCAPE' : 'closeAll' ,
'TAB' : 'down' ,
'SHIFT_TAB' : 'up'
} ) ;
}
/ * *
* Initializes the accordion menu by hiding all nested menus .
* @ private
* /
_createClass ( AccordionMenu , [ {
key : '_init' ,
value : function _init ( ) {
this . $element . find ( '[data-submenu]' ) . not ( '.is-active' ) . slideUp ( 0 ) ; //.find('a').css('padding-left', '1rem');
this . $element . attr ( {
'role' : 'tablist' ,
'aria-multiselectable' : this . options . multiOpen
} ) ;
this . $menuLinks = this . $element . find ( '.is-accordion-submenu-parent' ) ;
this . $menuLinks . each ( function ( ) {
var linkId = this . id || Foundation . GetYoDigits ( 6 , 'acc-menu-link' ) ,
$elem = $ ( this ) ,
$sub = $elem . children ( '[data-submenu]' ) ,
subId = $sub [ 0 ] . id || Foundation . GetYoDigits ( 6 , 'acc-menu' ) ,
isActive = $sub . hasClass ( 'is-active' ) ;
$elem . attr ( {
'aria-controls' : subId ,
'aria-expanded' : isActive ,
'role' : 'tab' ,
'id' : linkId
} ) ;
$sub . attr ( {
'aria-labelledby' : linkId ,
'aria-hidden' : ! isActive ,
'role' : 'tabpanel' ,
'id' : subId
} ) ;
} ) ;
var initPanes = this . $element . find ( '.is-active' ) ;
if ( initPanes . length ) {
var _this = this ;
initPanes . each ( function ( ) {
_this . down ( $ ( this ) ) ;
} ) ;
}
this . _events ( ) ;
}
/ * *
* Adds event handlers for items within the menu .
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ;
this . $element . find ( 'li' ) . each ( function ( ) {
var $submenu = $ ( this ) . children ( '[data-submenu]' ) ;
if ( $submenu . length ) {
$ ( this ) . children ( 'a' ) . off ( 'click.zf.accordionMenu' ) . on ( 'click.zf.accordionMenu' , function ( e ) {
e . preventDefault ( ) ;
_this . toggle ( $submenu ) ;
} ) ;
}
} ) . on ( 'keydown.zf.accordionmenu' , function ( e ) {
var $element = $ ( this ) ,
$elements = $element . parent ( 'ul' ) . children ( 'li' ) ,
$prevElement ,
$nextElement ,
$target = $element . children ( '[data-submenu]' ) ;
$elements . each ( function ( i ) {
if ( $ ( this ) . is ( $element ) ) {
$prevElement = $elements . eq ( Math . max ( 0 , i - 1 ) ) . find ( 'a' ) . first ( ) ;
$nextElement = $elements . eq ( Math . min ( i + 1 , $elements . length - 1 ) ) . find ( 'a' ) . first ( ) ;
if ( $ ( this ) . children ( '[data-submenu]:visible' ) . length ) {
// has open sub menu
$nextElement = $element . find ( 'li:first-child' ) . find ( 'a' ) . first ( ) ;
}
if ( $ ( this ) . is ( ':first-child' ) ) {
// is first element of sub menu
$prevElement = $element . parents ( 'li' ) . first ( ) . find ( 'a' ) . first ( ) ;
} else if ( $prevElement . children ( '[data-submenu]:visible' ) . length ) {
// if previous element has open sub menu
$prevElement = $prevElement . find ( 'li:last-child' ) . find ( 'a' ) . first ( ) ;
}
if ( $ ( this ) . is ( ':last-child' ) ) {
// is last element of sub menu
$nextElement = $element . parents ( 'li' ) . first ( ) . next ( 'li' ) . find ( 'a' ) . first ( ) ;
}
return ;
}
} ) ;
Foundation . Keyboard . handleKey ( e , 'AccordionMenu' , {
open : function ( ) {
if ( $target . is ( ':hidden' ) ) {
_this . down ( $target ) ;
$target . find ( 'li' ) . first ( ) . find ( 'a' ) . first ( ) . focus ( ) ;
}
} ,
close : function ( ) {
if ( $target . length && ! $target . is ( ':hidden' ) ) {
// close active sub of this item
_this . up ( $target ) ;
} else if ( $element . parent ( '[data-submenu]' ) . length ) {
// close currently open sub
_this . up ( $element . parent ( '[data-submenu]' ) ) ;
$element . parents ( 'li' ) . first ( ) . find ( 'a' ) . first ( ) . focus ( ) ;
}
} ,
up : function ( ) {
$prevElement . attr ( 'tabindex' , - 1 ) . focus ( ) ;
return true ;
} ,
down : function ( ) {
$nextElement . attr ( 'tabindex' , - 1 ) . focus ( ) ;
return true ;
} ,
toggle : function ( ) {
if ( $element . children ( '[data-submenu]' ) . length ) {
_this . toggle ( $element . children ( '[data-submenu]' ) ) ;
}
} ,
closeAll : function ( ) {
_this . hideAll ( ) ;
} ,
handled : function ( preventDefault ) {
if ( preventDefault ) {
e . preventDefault ( ) ;
}
e . stopImmediatePropagation ( ) ;
}
} ) ;
} ) ; //.attr('tabindex', 0);
}
/ * *
* Closes all panes of the menu .
* @ function
* /
} , {
key : 'hideAll' ,
value : function hideAll ( ) {
this . $element . find ( '[data-submenu]' ) . slideUp ( this . options . slideSpeed ) ;
}
/ * *
* Toggles the open / close state of a submenu .
* @ function
* @ param { jQuery } $target - the submenu to toggle
* /
} , {
key : 'toggle' ,
value : function toggle ( $target ) {
if ( ! $target . is ( ':animated' ) ) {
if ( ! $target . is ( ':hidden' ) ) {
this . up ( $target ) ;
} else {
this . down ( $target ) ;
}
}
}
/ * *
* Opens the sub - menu defined by ` $ target ` .
* @ param { jQuery } $target - Sub - menu to open .
* @ fires AccordionMenu # down
* /
} , {
key : 'down' ,
value : function down ( $target ) {
var _this = this ;
if ( ! this . options . multiOpen ) {
this . up ( this . $element . find ( '.is-active' ) . not ( $target . parentsUntil ( this . $element ) . add ( $target ) ) ) ;
}
$target . addClass ( 'is-active' ) . attr ( { 'aria-hidden' : false } ) . parent ( '.is-accordion-submenu-parent' ) . attr ( { 'aria-expanded' : true } ) ;
//Foundation.Move(this.options.slideSpeed, $target, function() {
$target . slideDown ( _this . options . slideSpeed , function ( ) {
/ * *
* Fires when the menu is done opening .
* @ event AccordionMenu # down
* /
_this . $element . trigger ( 'down.zf.accordionMenu' , [ $target ] ) ;
} ) ;
//});
}
/ * *
* Closes the sub - menu defined by ` $ target ` . All sub - menus inside the target will be closed as well .
* @ param { jQuery } $target - Sub - menu to close .
* @ fires AccordionMenu # up
* /
} , {
key : 'up' ,
value : function up ( $target ) {
var _this = this ;
//Foundation.Move(this.options.slideSpeed, $target, function(){
$target . slideUp ( _this . options . slideSpeed , function ( ) {
/ * *
* Fires when the menu is done collapsing up .
* @ event AccordionMenu # up
* /
_this . $element . trigger ( 'up.zf.accordionMenu' , [ $target ] ) ;
} ) ;
//});
var $menus = $target . find ( '[data-submenu]' ) . slideUp ( 0 ) . addBack ( ) . attr ( 'aria-hidden' , true ) ;
$menus . parent ( '.is-accordion-submenu-parent' ) . attr ( 'aria-expanded' , false ) ;
}
/ * *
* Destroys an instance of accordion menu .
* @ fires AccordionMenu # destroyed
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . find ( '[data-submenu]' ) . slideDown ( 0 ) . css ( 'display' , '' ) ;
this . $element . find ( 'a' ) . off ( 'click.zf.accordionMenu' ) ;
Foundation . Nest . Burn ( this . $element , 'accordion' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return AccordionMenu ;
} ( ) ;
AccordionMenu . defaults = {
/ * *
* Amount of time to animate the opening of a submenu in ms .
* @ option
* @ example 250
* /
slideSpeed : 250 ,
/ * *
* Allow the menu to have multiple open panes .
* @ option
* @ example true
* /
multiOpen : true
} ;
// Window exports
Foundation . plugin ( AccordionMenu , 'AccordionMenu' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Drilldown module .
* @ module foundation . drilldown
* @ requires foundation . util . keyboard
* @ requires foundation . util . motion
* @ requires foundation . util . nest
* /
var Drilldown = function ( ) {
/ * *
* Creates a new instance of a drilldown menu .
* @ class
* @ param { jQuery } element - jQuery object to make into an accordion menu .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Drilldown ( element , options ) {
_classCallCheck ( this , Drilldown ) ;
this . $element = element ;
this . options = $ . extend ( { } , Drilldown . defaults , this . $element . data ( ) , options ) ;
Foundation . Nest . Feather ( this . $element , 'drilldown' ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Drilldown' ) ;
Foundation . Keyboard . register ( 'Drilldown' , {
'ENTER' : 'open' ,
'SPACE' : 'open' ,
'ARROW_RIGHT' : 'next' ,
'ARROW_UP' : 'up' ,
'ARROW_DOWN' : 'down' ,
'ARROW_LEFT' : 'previous' ,
'ESCAPE' : 'close' ,
'TAB' : 'down' ,
'SHIFT_TAB' : 'up'
} ) ;
}
/ * *
* Initializes the drilldown by creating jQuery collections of elements
* @ private
* /
_createClass ( Drilldown , [ {
key : '_init' ,
value : function _init ( ) {
this . $submenuAnchors = this . $element . find ( 'li.is-drilldown-submenu-parent' ) . children ( 'a' ) ;
this . $submenus = this . $submenuAnchors . parent ( 'li' ) . children ( '[data-submenu]' ) ;
this . $menuItems = this . $element . find ( 'li' ) . not ( '.js-drilldown-back' ) . attr ( 'role' , 'menuitem' ) . find ( 'a' ) ;
this . _prepareMenu ( ) ;
this . _keyboardEvents ( ) ;
}
/ * *
* prepares drilldown menu by setting attributes to links and elements
* sets a min height to prevent content jumping
* wraps the element if not already wrapped
* @ private
* @ function
* /
} , {
key : '_prepareMenu' ,
value : function _prepareMenu ( ) {
var _this = this ;
// if(!this.options.holdOpen){
// this._menuLinkEvents();
// }
this . $submenuAnchors . each ( function ( ) {
var $link = $ ( this ) ;
var $sub = $link . parent ( ) ;
if ( _this . options . parentLink ) {
$link . clone ( ) . prependTo ( $sub . children ( '[data-submenu]' ) ) . wrap ( '<li class="is-submenu-parent-item is-submenu-item is-drilldown-submenu-item" role="menu-item"></li>' ) ;
}
$link . data ( 'savedHref' , $link . attr ( 'href' ) ) . removeAttr ( 'href' ) ;
$link . children ( '[data-submenu]' ) . attr ( {
'aria-hidden' : true ,
'tabindex' : 0 ,
'role' : 'menu'
} ) ;
_this . _events ( $link ) ;
} ) ;
this . $submenus . each ( function ( ) {
var $menu = $ ( this ) ,
$back = $menu . find ( '.js-drilldown-back' ) ;
if ( ! $back . length ) {
$menu . prepend ( _this . options . backButton ) ;
}
_this . _back ( $menu ) ;
} ) ;
if ( ! this . $element . parent ( ) . hasClass ( 'is-drilldown' ) ) {
this . $wrapper = $ ( this . options . wrapper ) . addClass ( 'is-drilldown' ) ;
this . $wrapper = this . $element . wrap ( this . $wrapper ) . parent ( ) . css ( this . _getMaxDims ( ) ) ;
}
}
/ * *
* Adds event handlers to elements in the menu .
* @ function
* @ private
* @ param { jQuery } $elem - the current menu item to add handlers to .
* /
} , {
key : '_events' ,
value : function _events ( $elem ) {
var _this = this ;
$elem . off ( 'click.zf.drilldown' ) . on ( 'click.zf.drilldown' , function ( e ) {
if ( $ ( e . target ) . parentsUntil ( 'ul' , 'li' ) . hasClass ( 'is-drilldown-submenu-parent' ) ) {
e . stopImmediatePropagation ( ) ;
e . preventDefault ( ) ;
}
// if(e.target !== e.currentTarget.firstElementChild){
// return false;
// }
_this . _show ( $elem . parent ( 'li' ) ) ;
if ( _this . options . closeOnClick ) {
var $body = $ ( 'body' ) ;
$body . off ( '.zf.drilldown' ) . on ( 'click.zf.drilldown' , function ( e ) {
if ( e . target === _this . $element [ 0 ] || $ . contains ( _this . $element [ 0 ] , e . target ) ) {
return ;
}
e . preventDefault ( ) ;
_this . _hideAll ( ) ;
$body . off ( '.zf.drilldown' ) ;
} ) ;
}
} ) ;
}
/ * *
* Adds keydown event listener to ` li ` ' s in the menu .
* @ private
* /
} , {
key : '_keyboardEvents' ,
value : function _keyboardEvents ( ) {
var _this = this ;
this . $menuItems . add ( this . $element . find ( '.js-drilldown-back > a' ) ) . on ( 'keydown.zf.drilldown' , function ( e ) {
var $element = $ ( this ) ,
$elements = $element . parent ( 'li' ) . parent ( 'ul' ) . children ( 'li' ) . children ( 'a' ) ,
$prevElement ,
$nextElement ;
$elements . each ( function ( i ) {
if ( $ ( this ) . is ( $element ) ) {
$prevElement = $elements . eq ( Math . max ( 0 , i - 1 ) ) ;
$nextElement = $elements . eq ( Math . min ( i + 1 , $elements . length - 1 ) ) ;
return ;
}
} ) ;
Foundation . Keyboard . handleKey ( e , 'Drilldown' , {
next : function ( ) {
if ( $element . is ( _this . $submenuAnchors ) ) {
_this . _show ( $element . parent ( 'li' ) ) ;
$element . parent ( 'li' ) . one ( Foundation . transitionend ( $element ) , function ( ) {
$element . parent ( 'li' ) . find ( 'ul li a' ) . filter ( _this . $menuItems ) . first ( ) . focus ( ) ;
} ) ;
return true ;
}
} ,
previous : function ( ) {
_this . _hide ( $element . parent ( 'li' ) . parent ( 'ul' ) ) ;
$element . parent ( 'li' ) . parent ( 'ul' ) . one ( Foundation . transitionend ( $element ) , function ( ) {
setTimeout ( function ( ) {
$element . parent ( 'li' ) . parent ( 'ul' ) . parent ( 'li' ) . children ( 'a' ) . first ( ) . focus ( ) ;
} , 1 ) ;
} ) ;
return true ;
} ,
up : function ( ) {
$prevElement . focus ( ) ;
return true ;
} ,
down : function ( ) {
$nextElement . focus ( ) ;
return true ;
} ,
close : function ( ) {
_this . _back ( ) ;
//_this.$menuItems.first().focus(); // focus to first element
} ,
open : function ( ) {
if ( ! $element . is ( _this . $menuItems ) ) {
// not menu item means back button
_this . _hide ( $element . parent ( 'li' ) . parent ( 'ul' ) ) ;
$element . parent ( 'li' ) . parent ( 'ul' ) . one ( Foundation . transitionend ( $element ) , function ( ) {
setTimeout ( function ( ) {
$element . parent ( 'li' ) . parent ( 'ul' ) . parent ( 'li' ) . children ( 'a' ) . first ( ) . focus ( ) ;
} , 1 ) ;
} ) ;
} else if ( $element . is ( _this . $submenuAnchors ) ) {
_this . _show ( $element . parent ( 'li' ) ) ;
$element . parent ( 'li' ) . one ( Foundation . transitionend ( $element ) , function ( ) {
$element . parent ( 'li' ) . find ( 'ul li a' ) . filter ( _this . $menuItems ) . first ( ) . focus ( ) ;
} ) ;
}
return true ;
} ,
handled : function ( preventDefault ) {
if ( preventDefault ) {
e . preventDefault ( ) ;
}
e . stopImmediatePropagation ( ) ;
}
} ) ;
} ) ; // end keyboardAccess
}
/ * *
* Closes all open elements , and returns to root menu .
* @ function
* @ fires Drilldown # closed
* /
} , {
key : '_hideAll' ,
value : function _hideAll ( ) {
var $elem = this . $element . find ( '.is-drilldown-submenu.is-active' ) . addClass ( 'is-closing' ) ;
$elem . one ( Foundation . transitionend ( $elem ) , function ( e ) {
$elem . removeClass ( 'is-active is-closing' ) ;
} ) ;
/ * *
* Fires when the menu is fully closed .
* @ event Drilldown # closed
* /
this . $element . trigger ( 'closed.zf.drilldown' ) ;
}
/ * *
* Adds event listener for each ` back ` button , and closes open menus .
* @ function
* @ fires Drilldown # back
* @ param { jQuery } $elem - the current sub - menu to add ` back ` event .
* /
} , {
key : '_back' ,
value : function _back ( $elem ) {
var _this = this ;
$elem . off ( 'click.zf.drilldown' ) ;
$elem . children ( '.js-drilldown-back' ) . on ( 'click.zf.drilldown' , function ( e ) {
e . stopImmediatePropagation ( ) ;
// console.log('mouseup on back');
_this . _hide ( $elem ) ;
} ) ;
}
/ * *
* Adds event listener to menu items w / o submenus to close open menus on click .
* @ function
* @ private
* /
} , {
key : '_menuLinkEvents' ,
value : function _menuLinkEvents ( ) {
var _this = this ;
this . $menuItems . not ( '.is-drilldown-submenu-parent' ) . off ( 'click.zf.drilldown' ) . on ( 'click.zf.drilldown' , function ( e ) {
// e.stopImmediatePropagation();
setTimeout ( function ( ) {
_this . _hideAll ( ) ;
} , 0 ) ;
} ) ;
}
/ * *
* Opens a submenu .
* @ function
* @ fires Drilldown # open
* @ param { jQuery } $elem - the current element with a submenu to open , i . e . the ` li ` tag .
* /
} , {
key : '_show' ,
value : function _show ( $elem ) {
$elem . children ( '[data-submenu]' ) . addClass ( 'is-active' ) ;
/ * *
* Fires when the submenu has opened .
* @ event Drilldown # open
* /
this . $element . trigger ( 'open.zf.drilldown' , [ $elem ] ) ;
}
} , {
key : '_hide' ,
/ * *
* Hides a submenu
* @ function
* @ fires Drilldown # hide
* @ param { jQuery } $elem - the current sub - menu to hide , i . e . the ` ul ` tag .
* /
value : function _hide ( $elem ) {
var _this = this ;
$elem . addClass ( 'is-closing' ) . one ( Foundation . transitionend ( $elem ) , function ( ) {
$elem . removeClass ( 'is-active is-closing' ) ;
$elem . blur ( ) ;
} ) ;
/ * *
* Fires when the submenu has closed .
* @ event Drilldown # hide
* /
$elem . trigger ( 'hide.zf.drilldown' , [ $elem ] ) ;
}
/ * *
* Iterates through the nested menus to calculate the min - height , and max - width for the menu .
* Prevents content jumping .
* @ function
* @ private
* /
} , {
key : '_getMaxDims' ,
value : function _getMaxDims ( ) {
var max = 0 ,
result = { } ;
this . $submenus . add ( this . $element ) . each ( function ( ) {
var numOfElems = $ ( this ) . children ( 'li' ) . length ;
max = numOfElems > max ? numOfElems : max ;
} ) ;
result [ 'min-height' ] = max * this . $menuItems [ 0 ] . getBoundingClientRect ( ) . height + 'px' ;
result [ 'max-width' ] = this . $element [ 0 ] . getBoundingClientRect ( ) . width + 'px' ;
return result ;
}
/ * *
* Destroys the Drilldown Menu
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . _hideAll ( ) ;
Foundation . Nest . Burn ( this . $element , 'drilldown' ) ;
this . $element . unwrap ( ) . find ( '.js-drilldown-back, .is-submenu-parent-item' ) . remove ( ) . end ( ) . find ( '.is-active, .is-closing, .is-drilldown-submenu' ) . removeClass ( 'is-active is-closing is-drilldown-submenu' ) . end ( ) . find ( '[data-submenu]' ) . removeAttr ( 'aria-hidden tabindex role' ) ;
this . $submenuAnchors . each ( function ( ) {
$ ( this ) . off ( '.zf.drilldown' ) ;
} ) ;
this . $element . find ( 'a' ) . each ( function ( ) {
var $link = $ ( this ) ;
if ( $link . data ( 'savedHref' ) ) {
$link . attr ( 'href' , $link . data ( 'savedHref' ) ) . removeData ( 'savedHref' ) ;
} else {
return ;
}
} ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Drilldown ;
} ( ) ;
Drilldown . defaults = {
/ * *
* Markup used for JS generated back button . Prepended to submenu lists and deleted on ` destroy ` method , 'js-drilldown-back' class required . Remove the backslash ( ` \` ) if copy and pasting.
* @ option
* @ example '<\li><\a>Back<\/a><\/li>'
* /
backButton : '<li class="js-drilldown-back"><a tabindex="0">Back</a></li>' ,
/ * *
* Markup used to wrap drilldown menu . Use a class name for independent styling ; the JS applied class : ` is-drilldown ` is required . Remove the backslash ( ` \` ) if copy and pasting.
* @ option
* @ example '<\div class="is-drilldown"><\/div>'
* /
wrapper : '<div></div>' ,
/ * *
* Adds the parent link to the submenu .
* @ option
* @ example false
* /
parentLink : false ,
/ * *
* Allow the menu to return to root list on body click .
* @ option
* @ example false
* /
closeOnClick : false
// holdOpen: false
} ;
// Window exports
Foundation . plugin ( Drilldown , 'Drilldown' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Dropdown module .
* @ module foundation . dropdown
* @ requires foundation . util . keyboard
* @ requires foundation . util . box
* @ requires foundation . util . triggers
* /
var Dropdown = function ( ) {
/ * *
* Creates a new instance of a dropdown .
* @ class
* @ param { jQuery } element - jQuery object to make into a dropdown .
* Object should be of the dropdown panel , rather than its anchor .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Dropdown ( element , options ) {
_classCallCheck ( this , Dropdown ) ;
this . $element = element ;
this . options = $ . extend ( { } , Dropdown . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Dropdown' ) ;
Foundation . Keyboard . register ( 'Dropdown' , {
'ENTER' : 'open' ,
'SPACE' : 'open' ,
'ESCAPE' : 'close' ,
'TAB' : 'tab_forward' ,
'SHIFT_TAB' : 'tab_backward'
} ) ;
}
/ * *
* Initializes the plugin by setting / checking options and attributes , adding helper variables , and saving the anchor .
* @ function
* @ private
* /
_createClass ( Dropdown , [ {
key : '_init' ,
value : function _init ( ) {
var $id = this . $element . attr ( 'id' ) ;
this . $anchor = $ ( '[data-toggle="' + $id + '"]' ) || $ ( '[data-open="' + $id + '"]' ) ;
this . $anchor . attr ( {
'aria-controls' : $id ,
'data-is-focus' : false ,
'data-yeti-box' : $id ,
'aria-haspopup' : true ,
'aria-expanded' : false
} ) ;
this . options . positionClass = this . getPositionClass ( ) ;
this . counter = 4 ;
this . usedPositions = [ ] ;
this . $element . attr ( {
'aria-hidden' : 'true' ,
'data-yeti-box' : $id ,
'data-resize' : $id ,
'aria-labelledby' : this . $anchor [ 0 ] . id || Foundation . GetYoDigits ( 6 , 'dd-anchor' )
} ) ;
this . _events ( ) ;
}
/ * *
* Helper function to determine current orientation of dropdown pane .
* @ function
* @ returns { String } position - string value of a position class .
* /
} , {
key : 'getPositionClass' ,
value : function getPositionClass ( ) {
var verticalPosition = this . $element [ 0 ] . className . match ( /(top|left|right|bottom)/g ) ;
verticalPosition = verticalPosition ? verticalPosition [ 0 ] : '' ;
var horizontalPosition = /float-(\S+)\s/ . exec ( this . $anchor [ 0 ] . className ) ;
horizontalPosition = horizontalPosition ? horizontalPosition [ 1 ] : '' ;
var position = horizontalPosition ? horizontalPosition + ' ' + verticalPosition : verticalPosition ;
return position ;
}
/ * *
* Adjusts the dropdown panes orientation by adding / removing positioning classes .
* @ function
* @ private
* @ param { String } position - position class to remove .
* /
} , {
key : '_reposition' ,
value : function _reposition ( position ) {
this . usedPositions . push ( position ? position : 'bottom' ) ;
//default, try switching to opposite side
if ( ! position && this . usedPositions . indexOf ( 'top' ) < 0 ) {
this . $element . addClass ( 'top' ) ;
} else if ( position === 'top' && this . usedPositions . indexOf ( 'bottom' ) < 0 ) {
this . $element . removeClass ( position ) ;
} else if ( position === 'left' && this . usedPositions . indexOf ( 'right' ) < 0 ) {
this . $element . removeClass ( position ) . addClass ( 'right' ) ;
} else if ( position === 'right' && this . usedPositions . indexOf ( 'left' ) < 0 ) {
this . $element . removeClass ( position ) . addClass ( 'left' ) ;
}
//if default change didn't work, try bottom or left first
else if ( ! position && this . usedPositions . indexOf ( 'top' ) > - 1 && this . usedPositions . indexOf ( 'left' ) < 0 ) {
this . $element . addClass ( 'left' ) ;
} else if ( position === 'top' && this . usedPositions . indexOf ( 'bottom' ) > - 1 && this . usedPositions . indexOf ( 'left' ) < 0 ) {
this . $element . removeClass ( position ) . addClass ( 'left' ) ;
} else if ( position === 'left' && this . usedPositions . indexOf ( 'right' ) > - 1 && this . usedPositions . indexOf ( 'bottom' ) < 0 ) {
this . $element . removeClass ( position ) ;
} else if ( position === 'right' && this . usedPositions . indexOf ( 'left' ) > - 1 && this . usedPositions . indexOf ( 'bottom' ) < 0 ) {
this . $element . removeClass ( position ) ;
}
//if nothing cleared, set to bottom
else {
this . $element . removeClass ( position ) ;
}
this . classChanged = true ;
this . counter -- ;
}
/ * *
* Sets the position and orientation of the dropdown pane , checks for collisions .
* Recursively calls itself if a collision is detected , with a new position class .
* @ function
* @ private
* /
} , {
key : '_setPosition' ,
value : function _setPosition ( ) {
if ( this . $anchor . attr ( 'aria-expanded' ) === 'false' ) {
return false ;
}
var position = this . getPositionClass ( ) ,
$eleDims = Foundation . Box . GetDimensions ( this . $element ) ,
$anchorDims = Foundation . Box . GetDimensions ( this . $anchor ) ,
_this = this ,
direction = position === 'left' ? 'left' : position === 'right' ? 'left' : 'top' ,
param = direction === 'top' ? 'height' : 'width' ,
offset = param === 'height' ? this . options . vOffset : this . options . hOffset ;
if ( $eleDims . width >= $eleDims . windowDims . width || ! this . counter && ! Foundation . Box . ImNotTouchingYou ( this . $element ) ) {
this . $element . offset ( Foundation . Box . GetOffsets ( this . $element , this . $anchor , 'center bottom' , this . options . vOffset , this . options . hOffset , true ) ) . css ( {
'width' : $eleDims . windowDims . width - this . options . hOffset * 2 ,
'height' : 'auto'
} ) ;
this . classChanged = true ;
return false ;
}
this . $element . offset ( Foundation . Box . GetOffsets ( this . $element , this . $anchor , position , this . options . vOffset , this . options . hOffset ) ) ;
while ( ! Foundation . Box . ImNotTouchingYou ( this . $element , false , true ) && this . counter ) {
this . _reposition ( position ) ;
this . _setPosition ( ) ;
}
}
/ * *
* Adds event listeners to the element utilizing the triggers utility library .
* @ function
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ;
this . $element . on ( {
'open.zf.trigger' : this . open . bind ( this ) ,
'close.zf.trigger' : this . close . bind ( this ) ,
'toggle.zf.trigger' : this . toggle . bind ( this ) ,
'resizeme.zf.trigger' : this . _setPosition . bind ( this )
} ) ;
if ( this . options . hover ) {
this . $anchor . off ( 'mouseenter.zf.dropdown mouseleave.zf.dropdown' ) . on ( 'mouseenter.zf.dropdown' , function ( ) {
clearTimeout ( _this . timeout ) ;
_this . timeout = setTimeout ( function ( ) {
_this . open ( ) ;
_this . $anchor . data ( 'hover' , true ) ;
} , _this . options . hoverDelay ) ;
} ) . on ( 'mouseleave.zf.dropdown' , function ( ) {
clearTimeout ( _this . timeout ) ;
_this . timeout = setTimeout ( function ( ) {
_this . close ( ) ;
_this . $anchor . data ( 'hover' , false ) ;
} , _this . options . hoverDelay ) ;
} ) ;
if ( this . options . hoverPane ) {
this . $element . off ( 'mouseenter.zf.dropdown mouseleave.zf.dropdown' ) . on ( 'mouseenter.zf.dropdown' , function ( ) {
clearTimeout ( _this . timeout ) ;
} ) . on ( 'mouseleave.zf.dropdown' , function ( ) {
clearTimeout ( _this . timeout ) ;
_this . timeout = setTimeout ( function ( ) {
_this . close ( ) ;
_this . $anchor . data ( 'hover' , false ) ;
} , _this . options . hoverDelay ) ;
} ) ;
}
}
this . $anchor . add ( this . $element ) . on ( 'keydown.zf.dropdown' , function ( e ) {
var $target = $ ( this ) ,
visibleFocusableElements = Foundation . Keyboard . findFocusable ( _this . $element ) ;
Foundation . Keyboard . handleKey ( e , 'Dropdown' , {
tab _forward : function ( ) {
if ( _this . $element . find ( ':focus' ) . is ( visibleFocusableElements . eq ( - 1 ) ) ) {
// left modal downwards, setting focus to first element
if ( _this . options . trapFocus ) {
// if focus shall be trapped
visibleFocusableElements . eq ( 0 ) . focus ( ) ;
e . preventDefault ( ) ;
} else {
// if focus is not trapped, close dropdown on focus out
_this . close ( ) ;
}
}
} ,
tab _backward : function ( ) {
if ( _this . $element . find ( ':focus' ) . is ( visibleFocusableElements . eq ( 0 ) ) || _this . $element . is ( ':focus' ) ) {
// left modal upwards, setting focus to last element
if ( _this . options . trapFocus ) {
// if focus shall be trapped
visibleFocusableElements . eq ( - 1 ) . focus ( ) ;
e . preventDefault ( ) ;
} else {
// if focus is not trapped, close dropdown on focus out
_this . close ( ) ;
}
}
} ,
open : function ( ) {
if ( $target . is ( _this . $anchor ) ) {
_this . open ( ) ;
_this . $element . attr ( 'tabindex' , - 1 ) . focus ( ) ;
e . preventDefault ( ) ;
}
} ,
close : function ( ) {
_this . close ( ) ;
_this . $anchor . focus ( ) ;
}
} ) ;
} ) ;
}
/ * *
* Adds an event handler to the body to close any dropdowns on a click .
* @ function
* @ private
* /
} , {
key : '_addBodyHandler' ,
value : function _addBodyHandler ( ) {
var $body = $ ( document . body ) . not ( this . $element ) ,
_this = this ;
$body . off ( 'click.zf.dropdown' ) . on ( 'click.zf.dropdown' , function ( e ) {
if ( _this . $anchor . is ( e . target ) || _this . $anchor . find ( e . target ) . length ) {
return ;
}
if ( _this . $element . find ( e . target ) . length ) {
return ;
}
_this . close ( ) ;
$body . off ( 'click.zf.dropdown' ) ;
} ) ;
}
/ * *
* Opens the dropdown pane , and fires a bubbling event to close other dropdowns .
* @ function
* @ fires Dropdown # closeme
* @ fires Dropdown # show
* /
} , {
key : 'open' ,
value : function open ( ) {
// var _this = this;
/ * *
* Fires to close other open dropdowns
* @ event Dropdown # closeme
* /
this . $element . trigger ( 'closeme.zf.dropdown' , this . $element . attr ( 'id' ) ) ;
this . $anchor . addClass ( 'hover' ) . attr ( { 'aria-expanded' : true } ) ;
// this.$element/*.show()*/;
this . _setPosition ( ) ;
this . $element . addClass ( 'is-open' ) . attr ( { 'aria-hidden' : false } ) ;
if ( this . options . autoFocus ) {
var $focusable = Foundation . Keyboard . findFocusable ( this . $element ) ;
if ( $focusable . length ) {
$focusable . eq ( 0 ) . focus ( ) ;
}
}
if ( this . options . closeOnClick ) {
this . _addBodyHandler ( ) ;
}
/ * *
* Fires once the dropdown is visible .
* @ event Dropdown # show
* /
this . $element . trigger ( 'show.zf.dropdown' , [ this . $element ] ) ;
}
/ * *
* Closes the open dropdown pane .
* @ function
* @ fires Dropdown # hide
* /
} , {
key : 'close' ,
value : function close ( ) {
if ( ! this . $element . hasClass ( 'is-open' ) ) {
return false ;
}
this . $element . removeClass ( 'is-open' ) . attr ( { 'aria-hidden' : true } ) ;
this . $anchor . removeClass ( 'hover' ) . attr ( 'aria-expanded' , false ) ;
if ( this . classChanged ) {
var curPositionClass = this . getPositionClass ( ) ;
if ( curPositionClass ) {
this . $element . removeClass ( curPositionClass ) ;
}
this . $element . addClass ( this . options . positionClass )
/*.hide()*/ . css ( { height : '' , width : '' } ) ;
this . classChanged = false ;
this . counter = 4 ;
this . usedPositions . length = 0 ;
}
this . $element . trigger ( 'hide.zf.dropdown' , [ this . $element ] ) ;
}
/ * *
* Toggles the dropdown pane ' s visibility .
* @ function
* /
} , {
key : 'toggle' ,
value : function toggle ( ) {
if ( this . $element . hasClass ( 'is-open' ) ) {
if ( this . $anchor . data ( 'hover' ) ) return ;
this . close ( ) ;
} else {
this . open ( ) ;
}
}
/ * *
* Destroys the dropdown .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . off ( '.zf.trigger' ) . hide ( ) ;
this . $anchor . off ( '.zf.dropdown' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Dropdown ;
} ( ) ;
Dropdown . defaults = {
/ * *
* Amount of time to delay opening a submenu on hover event .
* @ option
* @ example 250
* /
hoverDelay : 250 ,
/ * *
* Allow submenus to open on hover events
* @ option
* @ example false
* /
hover : false ,
/ * *
* Don ' t close dropdown when hovering over dropdown pane
* @ option
* @ example true
* /
hoverPane : false ,
/ * *
* Number of pixels between the dropdown pane and the triggering element on open .
* @ option
* @ example 1
* /
vOffset : 1 ,
/ * *
* Number of pixels between the dropdown pane and the triggering element on open .
* @ option
* @ example 1
* /
hOffset : 1 ,
/ * *
* Class applied to adjust open position . JS will test and fill this in .
* @ option
* @ example 'top'
* /
positionClass : '' ,
/ * *
* Allow the plugin to trap focus to the dropdown pane if opened with keyboard commands .
* @ option
* @ example false
* /
trapFocus : false ,
/ * *
* Allow the plugin to set focus to the first focusable element within the pane , regardless of method of opening .
* @ option
* @ example true
* /
autoFocus : false ,
/ * *
* Allows a click on the body to close the dropdown .
* @ option
* @ example false
* /
closeOnClick : false
} ;
// Window exports
Foundation . plugin ( Dropdown , 'Dropdown' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* DropdownMenu module .
* @ module foundation . dropdown - menu
* @ requires foundation . util . keyboard
* @ requires foundation . util . box
* @ requires foundation . util . nest
* /
var DropdownMenu = function ( ) {
/ * *
* Creates a new instance of DropdownMenu .
* @ class
* @ fires DropdownMenu # init
* @ param { jQuery } element - jQuery object to make into a dropdown menu .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function DropdownMenu ( element , options ) {
_classCallCheck ( this , DropdownMenu ) ;
this . $element = element ;
this . options = $ . extend ( { } , DropdownMenu . defaults , this . $element . data ( ) , options ) ;
Foundation . Nest . Feather ( this . $element , 'dropdown' ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'DropdownMenu' ) ;
Foundation . Keyboard . register ( 'DropdownMenu' , {
'ENTER' : 'open' ,
'SPACE' : 'open' ,
'ARROW_RIGHT' : 'next' ,
'ARROW_UP' : 'up' ,
'ARROW_DOWN' : 'down' ,
'ARROW_LEFT' : 'previous' ,
'ESCAPE' : 'close'
} ) ;
}
/ * *
* Initializes the plugin , and calls _prepareMenu
* @ private
* @ function
* /
_createClass ( DropdownMenu , [ {
key : '_init' ,
value : function _init ( ) {
var subs = this . $element . find ( 'li.is-dropdown-submenu-parent' ) ;
this . $element . children ( '.is-dropdown-submenu-parent' ) . children ( '.is-dropdown-submenu' ) . addClass ( 'first-sub' ) ;
this . $menuItems = this . $element . find ( '[role="menuitem"]' ) ;
this . $tabs = this . $element . children ( '[role="menuitem"]' ) ;
this . $tabs . find ( 'ul.is-dropdown-submenu' ) . addClass ( this . options . verticalClass ) ;
if ( this . $element . hasClass ( this . options . rightClass ) || this . options . alignment === 'right' || Foundation . rtl ( ) || this . $element . parents ( '.top-bar-right' ) . is ( '*' ) ) {
this . options . alignment = 'right' ;
subs . addClass ( 'opens-left' ) ;
} else {
subs . addClass ( 'opens-right' ) ;
}
this . changed = false ;
this . _events ( ) ;
}
} , {
key : '_events' ,
/ * *
* Adds event listeners to elements within the menu
* @ private
* @ function
* /
value : function _events ( ) {
var _this = this ,
hasTouch = 'ontouchstart' in window || typeof window . ontouchstart !== 'undefined' ,
parClass = 'is-dropdown-submenu-parent' ;
// used for onClick and in the keyboard handlers
var handleClickFn = function ( e ) {
var $elem = $ ( e . target ) . parentsUntil ( 'ul' , '.' + parClass ) ,
hasSub = $elem . hasClass ( parClass ) ,
hasClicked = $elem . attr ( 'data-is-click' ) === 'true' ,
$sub = $elem . children ( '.is-dropdown-submenu' ) ;
if ( hasSub ) {
if ( hasClicked ) {
if ( ! _this . options . closeOnClick || ! _this . options . clickOpen && ! hasTouch || _this . options . forceFollow && hasTouch ) {
return ;
} else {
e . stopImmediatePropagation ( ) ;
e . preventDefault ( ) ;
_this . _hide ( $elem ) ;
}
} else {
e . preventDefault ( ) ;
e . stopImmediatePropagation ( ) ;
_this . _show ( $elem . children ( '.is-dropdown-submenu' ) ) ;
$elem . add ( $elem . parentsUntil ( _this . $element , '.' + parClass ) ) . attr ( 'data-is-click' , true ) ;
}
} else {
return ;
}
} ;
if ( this . options . clickOpen || hasTouch ) {
this . $menuItems . on ( 'click.zf.dropdownmenu touchstart.zf.dropdownmenu' , handleClickFn ) ;
}
if ( ! this . options . disableHover ) {
this . $menuItems . on ( 'mouseenter.zf.dropdownmenu' , function ( e ) {
var $elem = $ ( this ) ,
hasSub = $elem . hasClass ( parClass ) ;
if ( hasSub ) {
clearTimeout ( _this . delay ) ;
_this . delay = setTimeout ( function ( ) {
_this . _show ( $elem . children ( '.is-dropdown-submenu' ) ) ;
} , _this . options . hoverDelay ) ;
}
} ) . on ( 'mouseleave.zf.dropdownmenu' , function ( e ) {
var $elem = $ ( this ) ,
hasSub = $elem . hasClass ( parClass ) ;
if ( hasSub && _this . options . autoclose ) {
if ( $elem . attr ( 'data-is-click' ) === 'true' && _this . options . clickOpen ) {
return false ;
}
clearTimeout ( _this . delay ) ;
_this . delay = setTimeout ( function ( ) {
_this . _hide ( $elem ) ;
} , _this . options . closingTime ) ;
}
} ) ;
}
this . $menuItems . on ( 'keydown.zf.dropdownmenu' , function ( e ) {
var $element = $ ( e . target ) . parentsUntil ( 'ul' , '[role="menuitem"]' ) ,
isTab = _this . $tabs . index ( $element ) > - 1 ,
$elements = isTab ? _this . $tabs : $element . siblings ( 'li' ) . add ( $element ) ,
$prevElement ,
$nextElement ;
$elements . each ( function ( i ) {
if ( $ ( this ) . is ( $element ) ) {
$prevElement = $elements . eq ( i - 1 ) ;
$nextElement = $elements . eq ( i + 1 ) ;
return ;
}
} ) ;
var nextSibling = function ( ) {
if ( ! $element . is ( ':last-child' ) ) {
$nextElement . children ( 'a:first' ) . focus ( ) ;
e . preventDefault ( ) ;
}
} ,
prevSibling = function ( ) {
$prevElement . children ( 'a:first' ) . focus ( ) ;
e . preventDefault ( ) ;
} ,
openSub = function ( ) {
var $sub = $element . children ( 'ul.is-dropdown-submenu' ) ;
if ( $sub . length ) {
_this . _show ( $sub ) ;
$element . find ( 'li > a:first' ) . focus ( ) ;
e . preventDefault ( ) ;
} else {
return ;
}
} ,
closeSub = function ( ) {
//if ($element.is(':first-child')) {
var close = $element . parent ( 'ul' ) . parent ( 'li' ) ;
close . children ( 'a:first' ) . focus ( ) ;
_this . _hide ( close ) ;
e . preventDefault ( ) ;
//}
} ;
var functions = {
open : openSub ,
close : function ( ) {
_this . _hide ( _this . $element ) ;
_this . $menuItems . find ( 'a:first' ) . focus ( ) ; // focus to first element
e . preventDefault ( ) ;
} ,
handled : function ( ) {
e . stopImmediatePropagation ( ) ;
}
} ;
if ( isTab ) {
if ( _this . $element . hasClass ( _this . options . verticalClass ) ) {
// vertical menu
if ( _this . options . alignment === 'left' ) {
// left aligned
$ . extend ( functions , {
down : nextSibling ,
up : prevSibling ,
next : openSub ,
previous : closeSub
} ) ;
} else {
// right aligned
$ . extend ( functions , {
down : nextSibling ,
up : prevSibling ,
next : closeSub ,
previous : openSub
} ) ;
}
} else {
// horizontal menu
$ . extend ( functions , {
next : nextSibling ,
previous : prevSibling ,
down : openSub ,
up : closeSub
} ) ;
}
} else {
// not tabs -> one sub
if ( _this . options . alignment === 'left' ) {
// left aligned
$ . extend ( functions , {
next : openSub ,
previous : closeSub ,
down : nextSibling ,
up : prevSibling
} ) ;
} else {
// right aligned
$ . extend ( functions , {
next : closeSub ,
previous : openSub ,
down : nextSibling ,
up : prevSibling
} ) ;
}
}
Foundation . Keyboard . handleKey ( e , 'DropdownMenu' , functions ) ;
} ) ;
}
/ * *
* Adds an event handler to the body to close any dropdowns on a click .
* @ function
* @ private
* /
} , {
key : '_addBodyHandler' ,
value : function _addBodyHandler ( ) {
var $body = $ ( document . body ) ,
_this = this ;
$body . off ( 'mouseup.zf.dropdownmenu touchend.zf.dropdownmenu' ) . on ( 'mouseup.zf.dropdownmenu touchend.zf.dropdownmenu' , function ( e ) {
var $link = _this . $element . find ( e . target ) ;
if ( $link . length ) {
return ;
}
_this . _hide ( ) ;
$body . off ( 'mouseup.zf.dropdownmenu touchend.zf.dropdownmenu' ) ;
} ) ;
}
/ * *
* Opens a dropdown pane , and checks for collisions first .
* @ param { jQuery } $sub - ul element that is a submenu to show
* @ function
* @ private
* @ fires DropdownMenu # show
* /
} , {
key : '_show' ,
value : function _show ( $sub ) {
var idx = this . $tabs . index ( this . $tabs . filter ( function ( i , el ) {
return $ ( el ) . find ( $sub ) . length > 0 ;
} ) ) ;
var $sibs = $sub . parent ( 'li.is-dropdown-submenu-parent' ) . siblings ( 'li.is-dropdown-submenu-parent' ) ;
this . _hide ( $sibs , idx ) ;
$sub . css ( 'visibility' , 'hidden' ) . addClass ( 'js-dropdown-active' ) . attr ( { 'aria-hidden' : false } ) . parent ( 'li.is-dropdown-submenu-parent' ) . addClass ( 'is-active' ) . attr ( { 'aria-expanded' : true } ) ;
var clear = Foundation . Box . ImNotTouchingYou ( $sub , null , true ) ;
if ( ! clear ) {
var oldClass = this . options . alignment === 'left' ? '-right' : '-left' ,
$parentLi = $sub . parent ( '.is-dropdown-submenu-parent' ) ;
$parentLi . removeClass ( 'opens' + oldClass ) . addClass ( 'opens-' + this . options . alignment ) ;
clear = Foundation . Box . ImNotTouchingYou ( $sub , null , true ) ;
if ( ! clear ) {
$parentLi . removeClass ( 'opens-' + this . options . alignment ) . addClass ( 'opens-inner' ) ;
}
this . changed = true ;
}
$sub . css ( 'visibility' , '' ) ;
if ( this . options . closeOnClick ) {
this . _addBodyHandler ( ) ;
}
/ * *
* Fires when the new dropdown pane is visible .
* @ event DropdownMenu # show
* /
this . $element . trigger ( 'show.zf.dropdownmenu' , [ $sub ] ) ;
}
/ * *
* Hides a single , currently open dropdown pane , if passed a parameter , otherwise , hides everything .
* @ function
* @ param { jQuery } $elem - element with a submenu to hide
* @ param { Number } idx - index of the $tabs collection to hide
* @ private
* /
} , {
key : '_hide' ,
value : function _hide ( $elem , idx ) {
var $toClose ;
if ( $elem && $elem . length ) {
$toClose = $elem ;
} else if ( idx !== undefined ) {
$toClose = this . $tabs . not ( function ( i , el ) {
return i === idx ;
} ) ;
} else {
$toClose = this . $element ;
}
var somethingToClose = $toClose . hasClass ( 'is-active' ) || $toClose . find ( '.is-active' ) . length > 0 ;
if ( somethingToClose ) {
$toClose . find ( 'li.is-active' ) . add ( $toClose ) . attr ( {
'aria-expanded' : false ,
'data-is-click' : false
} ) . removeClass ( 'is-active' ) ;
$toClose . find ( 'ul.js-dropdown-active' ) . attr ( {
'aria-hidden' : true
} ) . removeClass ( 'js-dropdown-active' ) ;
if ( this . changed || $toClose . find ( 'opens-inner' ) . length ) {
var oldClass = this . options . alignment === 'left' ? 'right' : 'left' ;
$toClose . find ( 'li.is-dropdown-submenu-parent' ) . add ( $toClose ) . removeClass ( 'opens-inner opens-' + this . options . alignment ) . addClass ( 'opens-' + oldClass ) ;
this . changed = false ;
}
/ * *
* Fires when the open menus are closed .
* @ event DropdownMenu # hide
* /
this . $element . trigger ( 'hide.zf.dropdownmenu' , [ $toClose ] ) ;
}
}
/ * *
* Destroys the plugin .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $menuItems . off ( '.zf.dropdownmenu' ) . removeAttr ( 'data-is-click' ) . removeClass ( 'is-right-arrow is-left-arrow is-down-arrow opens-right opens-left opens-inner' ) ;
$ ( document . body ) . off ( '.zf.dropdownmenu' ) ;
Foundation . Nest . Burn ( this . $element , 'dropdown' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return DropdownMenu ;
} ( ) ;
/ * *
* Default settings for plugin
* /
DropdownMenu . defaults = {
/ * *
* Disallows hover events from opening submenus
* @ option
* @ example false
* /
disableHover : false ,
/ * *
* Allow a submenu to automatically close on a mouseleave event , if not clicked open .
* @ option
* @ example true
* /
autoclose : true ,
/ * *
* Amount of time to delay opening a submenu on hover event .
* @ option
* @ example 50
* /
hoverDelay : 50 ,
/ * *
* Allow a submenu to open / remain open on parent click event . Allows cursor to move away from menu .
* @ option
* @ example true
* /
clickOpen : false ,
/ * *
* Amount of time to delay closing a submenu on a mouseleave event .
* @ option
* @ example 500
* /
closingTime : 500 ,
/ * *
* Position of the menu relative to what direction the submenus should open . Handled by JS .
* @ option
* @ example 'left'
* /
alignment : 'left' ,
/ * *
* Allow clicks on the body to close any open submenus .
* @ option
* @ example true
* /
closeOnClick : true ,
/ * *
* Class applied to vertical oriented menus , Foundation default is ` vertical ` . Update this if using your own class .
* @ option
* @ example 'vertical'
* /
verticalClass : 'vertical' ,
/ * *
* Class applied to right - side oriented menus , Foundation default is ` align-right ` . Update this if using your own class .
* @ option
* @ example 'align-right'
* /
rightClass : 'align-right' ,
/ * *
* Boolean to force overide the clicking of links to perform default action , on second touch event for mobile .
* @ option
* @ example false
* /
forceFollow : true
} ;
// Window exports
Foundation . plugin ( DropdownMenu , 'DropdownMenu' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Equalizer module .
* @ module foundation . equalizer
* /
var Equalizer = function ( ) {
/ * *
* Creates a new instance of Equalizer .
* @ class
* @ fires Equalizer # init
* @ param { Object } element - jQuery object to add the trigger to .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Equalizer ( element , options ) {
_classCallCheck ( this , Equalizer ) ;
this . $element = element ;
this . options = $ . extend ( { } , Equalizer . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Equalizer' ) ;
}
/ * *
* Initializes the Equalizer plugin and calls functions to get equalizer functioning on load .
* @ private
* /
_createClass ( Equalizer , [ {
key : '_init' ,
value : function _init ( ) {
var eqId = this . $element . attr ( 'data-equalizer' ) || '' ;
var $watched = this . $element . find ( '[data-equalizer-watch="' + eqId + '"]' ) ;
this . $watched = $watched . length ? $watched : this . $element . find ( '[data-equalizer-watch]' ) ;
this . $element . attr ( 'data-resize' , eqId || Foundation . GetYoDigits ( 6 , 'eq' ) ) ;
this . hasNested = this . $element . find ( '[data-equalizer]' ) . length > 0 ;
this . isNested = this . $element . parentsUntil ( document . body , '[data-equalizer]' ) . length > 0 ;
this . isOn = false ;
this . _bindHandler = {
onResizeMeBound : this . _onResizeMe . bind ( this ) ,
onPostEqualizedBound : this . _onPostEqualized . bind ( this )
} ;
var imgs = this . $element . find ( 'img' ) ;
var tooSmall ;
if ( this . options . equalizeOn ) {
tooSmall = this . _checkMQ ( ) ;
$ ( window ) . on ( 'changed.zf.mediaquery' , this . _checkMQ . bind ( this ) ) ;
} else {
this . _events ( ) ;
}
if ( tooSmall !== undefined && tooSmall === false || tooSmall === undefined ) {
if ( imgs . length ) {
Foundation . onImagesLoaded ( imgs , this . _reflow . bind ( this ) ) ;
} else {
this . _reflow ( ) ;
}
}
}
/ * *
* Removes event listeners if the breakpoint is too small .
* @ private
* /
} , {
key : '_pauseEvents' ,
value : function _pauseEvents ( ) {
this . isOn = false ;
this . $element . off ( {
'.zf.equalizer' : this . _bindHandler . onPostEqualizedBound ,
'resizeme.zf.trigger' : this . _bindHandler . onResizeMeBound
} ) ;
}
/ * *
* function to handle $elements resizeme . zf . trigger , with bound this on _bindHandler . onResizeMeBound
* @ private
* /
} , {
key : '_onResizeMe' ,
value : function _onResizeMe ( e ) {
this . _reflow ( ) ;
}
/ * *
* function to handle $elements postequalized . zf . equalizer , with bound this on _bindHandler . onPostEqualizedBound
* @ private
* /
} , {
key : '_onPostEqualized' ,
value : function _onPostEqualized ( e ) {
if ( e . target !== this . $element [ 0 ] ) {
this . _reflow ( ) ;
}
}
/ * *
* Initializes events for Equalizer .
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ;
this . _pauseEvents ( ) ;
if ( this . hasNested ) {
this . $element . on ( 'postequalized.zf.equalizer' , this . _bindHandler . onPostEqualizedBound ) ;
} else {
this . $element . on ( 'resizeme.zf.trigger' , this . _bindHandler . onResizeMeBound ) ;
}
this . isOn = true ;
}
/ * *
* Checks the current breakpoint to the minimum required size .
* @ private
* /
} , {
key : '_checkMQ' ,
value : function _checkMQ ( ) {
var tooSmall = ! Foundation . MediaQuery . atLeast ( this . options . equalizeOn ) ;
if ( tooSmall ) {
if ( this . isOn ) {
this . _pauseEvents ( ) ;
this . $watched . css ( 'height' , 'auto' ) ;
}
} else {
if ( ! this . isOn ) {
this . _events ( ) ;
}
}
return tooSmall ;
}
/ * *
* A noop version for the plugin
* @ private
* /
} , {
key : '_killswitch' ,
value : function _killswitch ( ) {
return ;
}
/ * *
* Calls necessary functions to update Equalizer upon DOM change
* @ private
* /
} , {
key : '_reflow' ,
value : function _reflow ( ) {
if ( ! this . options . equalizeOnStack ) {
if ( this . _isStacked ( ) ) {
this . $watched . css ( 'height' , 'auto' ) ;
return false ;
}
}
if ( this . options . equalizeByRow ) {
this . getHeightsByRow ( this . applyHeightByRow . bind ( this ) ) ;
} else {
this . getHeights ( this . applyHeight . bind ( this ) ) ;
}
}
/ * *
* Manually determines if the first 2 elements are * NOT * stacked .
* @ private
* /
} , {
key : '_isStacked' ,
value : function _isStacked ( ) {
return this . $watched [ 0 ] . getBoundingClientRect ( ) . top !== this . $watched [ 1 ] . getBoundingClientRect ( ) . top ;
}
/ * *
* Finds the outer heights of children contained within an Equalizer parent and returns them in an array
* @ param { Function } cb - A non - optional callback to return the heights array to .
* @ returns { Array } heights - An array of heights of children within Equalizer container
* /
} , {
key : 'getHeights' ,
value : function getHeights ( cb ) {
var heights = [ ] ;
for ( var i = 0 , len = this . $watched . length ; i < len ; i ++ ) {
this . $watched [ i ] . style . height = 'auto' ;
heights . push ( this . $watched [ i ] . offsetHeight ) ;
}
cb ( heights ) ;
}
/ * *
* Finds the outer heights of children contained within an Equalizer parent and returns them in an array
* @ param { Function } cb - A non - optional callback to return the heights array to .
* @ returns { Array } groups - An array of heights of children within Equalizer container grouped by row with element , height and max as last child
* /
} , {
key : 'getHeightsByRow' ,
value : function getHeightsByRow ( cb ) {
var lastElTopOffset = this . $watched . length ? this . $watched . first ( ) . offset ( ) . top : 0 ,
groups = [ ] ,
group = 0 ;
//group by Row
groups [ group ] = [ ] ;
for ( var i = 0 , len = this . $watched . length ; i < len ; i ++ ) {
this . $watched [ i ] . style . height = 'auto' ;
//maybe could use this.$watched[i].offsetTop
var elOffsetTop = $ ( this . $watched [ i ] ) . offset ( ) . top ;
if ( elOffsetTop != lastElTopOffset ) {
group ++ ;
groups [ group ] = [ ] ;
lastElTopOffset = elOffsetTop ;
}
groups [ group ] . push ( [ this . $watched [ i ] , this . $watched [ i ] . offsetHeight ] ) ;
}
for ( var j = 0 , ln = groups . length ; j < ln ; j ++ ) {
var heights = $ ( groups [ j ] ) . map ( function ( ) {
return this [ 1 ] ;
} ) . get ( ) ;
var max = Math . max . apply ( null , heights ) ;
groups [ j ] . push ( max ) ;
}
cb ( groups ) ;
}
/ * *
* Changes the CSS height property of each child in an Equalizer parent to match the tallest
* @ param { array } heights - An array of heights of children within Equalizer container
* @ fires Equalizer # preequalized
* @ fires Equalizer # postequalized
* /
} , {
key : 'applyHeight' ,
value : function applyHeight ( heights ) {
var max = Math . max . apply ( null , heights ) ;
/ * *
* Fires before the heights are applied
* @ event Equalizer # preequalized
* /
this . $element . trigger ( 'preequalized.zf.equalizer' ) ;
this . $watched . css ( 'height' , max ) ;
/ * *
* Fires when the heights have been applied
* @ event Equalizer # postequalized
* /
this . $element . trigger ( 'postequalized.zf.equalizer' ) ;
}
/ * *
* Changes the CSS height property of each child in an Equalizer parent to match the tallest by row
* @ param { array } groups - An array of heights of children within Equalizer container grouped by row with element , height and max as last child
* @ fires Equalizer # preequalized
* @ fires Equalizer # preequalizedRow
* @ fires Equalizer # postequalizedRow
* @ fires Equalizer # postequalized
* /
} , {
key : 'applyHeightByRow' ,
value : function applyHeightByRow ( groups ) {
/ * *
* Fires before the heights are applied
* /
this . $element . trigger ( 'preequalized.zf.equalizer' ) ;
for ( var i = 0 , len = groups . length ; i < len ; i ++ ) {
var groupsILength = groups [ i ] . length ,
max = groups [ i ] [ groupsILength - 1 ] ;
if ( groupsILength <= 2 ) {
$ ( groups [ i ] [ 0 ] [ 0 ] ) . css ( { 'height' : 'auto' } ) ;
continue ;
}
/ * *
* Fires before the heights per row are applied
* @ event Equalizer # preequalizedRow
* /
this . $element . trigger ( 'preequalizedrow.zf.equalizer' ) ;
for ( var j = 0 , lenJ = groupsILength - 1 ; j < lenJ ; j ++ ) {
$ ( groups [ i ] [ j ] [ 0 ] ) . css ( { 'height' : max } ) ;
}
/ * *
* Fires when the heights per row have been applied
* @ event Equalizer # postequalizedRow
* /
this . $element . trigger ( 'postequalizedrow.zf.equalizer' ) ;
}
/ * *
* Fires when the heights have been applied
* /
this . $element . trigger ( 'postequalized.zf.equalizer' ) ;
}
/ * *
* Destroys an instance of Equalizer .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . _pauseEvents ( ) ;
this . $watched . css ( 'height' , 'auto' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Equalizer ;
} ( ) ;
/ * *
* Default settings for plugin
* /
Equalizer . defaults = {
/ * *
* Enable height equalization when stacked on smaller screens .
* @ option
* @ example true
* /
equalizeOnStack : true ,
/ * *
* Enable height equalization row by row .
* @ option
* @ example false
* /
equalizeByRow : false ,
/ * *
* String representing the minimum breakpoint size the plugin should equalize heights on .
* @ option
* @ example 'medium'
* /
equalizeOn : ''
} ;
// Window exports
Foundation . plugin ( Equalizer , 'Equalizer' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Interchange module .
* @ module foundation . interchange
* @ requires foundation . util . mediaQuery
* @ requires foundation . util . timerAndImageLoader
* /
var Interchange = function ( ) {
/ * *
* Creates a new instance of Interchange .
* @ class
* @ fires Interchange # init
* @ param { Object } element - jQuery object to add the trigger to .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Interchange ( element , options ) {
_classCallCheck ( this , Interchange ) ;
this . $element = element ;
this . options = $ . extend ( { } , Interchange . defaults , options ) ;
this . rules = [ ] ;
this . currentPath = '' ;
this . _init ( ) ;
this . _events ( ) ;
Foundation . registerPlugin ( this , 'Interchange' ) ;
}
/ * *
* Initializes the Interchange plugin and calls functions to get interchange functioning on load .
* @ function
* @ private
* /
_createClass ( Interchange , [ {
key : '_init' ,
value : function _init ( ) {
this . _addBreakpoints ( ) ;
this . _generateRules ( ) ;
this . _reflow ( ) ;
}
/ * *
* Initializes events for Interchange .
* @ function
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
$ ( window ) . on ( 'resize.zf.interchange' , Foundation . util . throttle ( this . _reflow . bind ( this ) , 50 ) ) ;
}
/ * *
* Calls necessary functions to update Interchange upon DOM change
* @ function
* @ private
* /
} , {
key : '_reflow' ,
value : function _reflow ( ) {
var match ;
// Iterate through each rule, but only save the last match
for ( var i in this . rules ) {
if ( this . rules . hasOwnProperty ( i ) ) {
var rule = this . rules [ i ] ;
if ( window . matchMedia ( rule . query ) . matches ) {
match = rule ;
}
}
}
if ( match ) {
this . replace ( match . path ) ;
}
}
/ * *
* Gets the Foundation breakpoints and adds them to the Interchange . SPECIAL _QUERIES object .
* @ function
* @ private
* /
} , {
key : '_addBreakpoints' ,
value : function _addBreakpoints ( ) {
for ( var i in Foundation . MediaQuery . queries ) {
if ( Foundation . MediaQuery . queries . hasOwnProperty ( i ) ) {
var query = Foundation . MediaQuery . queries [ i ] ;
Interchange . SPECIAL _QUERIES [ query . name ] = query . value ;
}
}
}
/ * *
* Checks the Interchange element for the provided media query + content pairings
* @ function
* @ private
* @ param { Object } element - jQuery object that is an Interchange instance
* @ returns { Array } scenarios - Array of objects that have 'mq' and 'path' keys with corresponding keys
* /
} , {
key : '_generateRules' ,
value : function _generateRules ( element ) {
var rulesList = [ ] ;
var rules ;
if ( this . options . rules ) {
rules = this . options . rules ;
} else {
rules = this . $element . data ( 'interchange' ) . match ( /\[.*?\]/g ) ;
}
for ( var i in rules ) {
if ( rules . hasOwnProperty ( i ) ) {
var rule = rules [ i ] . slice ( 1 , - 1 ) . split ( ', ' ) ;
var path = rule . slice ( 0 , - 1 ) . join ( '' ) ;
var query = rule [ rule . length - 1 ] ;
if ( Interchange . SPECIAL _QUERIES [ query ] ) {
query = Interchange . SPECIAL _QUERIES [ query ] ;
}
rulesList . push ( {
path : path ,
query : query
} ) ;
}
}
this . rules = rulesList ;
}
/ * *
* Update the ` src ` property of an image , or change the HTML of a container , to the specified path .
* @ function
* @ param { String } path - Path to the image or HTML partial .
* @ fires Interchange # replaced
* /
} , {
key : 'replace' ,
value : function replace ( path ) {
if ( this . currentPath === path ) return ;
var _this = this ,
trigger = 'replaced.zf.interchange' ;
// Replacing images
if ( this . $element [ 0 ] . nodeName === 'IMG' ) {
2016-09-08 07:52:22 +00:00
this . $element . attr ( 'src' , path ) . on ( 'load' , function ( ) {
2016-09-07 10:58:25 +00:00
_this . currentPath = path ;
} ) . trigger ( trigger ) ;
}
// Replacing background images
else if ( path . match ( /\.(gif|jpg|jpeg|png|svg|tiff)([?#].*)?/i ) ) {
this . $element . css ( { 'background-image' : 'url(' + path + ')' } ) . trigger ( trigger ) ;
}
// Replacing HTML
else {
$ . get ( path , function ( response ) {
_this . $element . html ( response ) . trigger ( trigger ) ;
$ ( response ) . foundation ( ) ;
_this . currentPath = path ;
} ) ;
}
/ * *
* Fires when content in an Interchange element is done being loaded .
* @ event Interchange # replaced
* /
// this.$element.trigger('replaced.zf.interchange');
}
/ * *
* Destroys an instance of interchange .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
//TODO this.
}
} ] ) ;
return Interchange ;
} ( ) ;
/ * *
* Default settings for plugin
* /
Interchange . defaults = {
/ * *
* Rules to be applied to Interchange elements . Set with the ` data-interchange ` array notation .
* @ option
* /
rules : null
} ;
Interchange . SPECIAL _QUERIES = {
'landscape' : 'screen and (orientation: landscape)' ,
'portrait' : 'screen and (orientation: portrait)' ,
'retina' : 'only screen and (-webkit-min-device-pixel-ratio: 2), only screen and (min--moz-device-pixel-ratio: 2), only screen and (-o-min-device-pixel-ratio: 2/1), only screen and (min-device-pixel-ratio: 2), only screen and (min-resolution: 192dpi), only screen and (min-resolution: 2dppx)'
} ;
// Window exports
Foundation . plugin ( Interchange , 'Interchange' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Magellan module .
* @ module foundation . magellan
* /
var Magellan = function ( ) {
/ * *
* Creates a new instance of Magellan .
* @ class
* @ fires Magellan # init
* @ param { Object } element - jQuery object to add the trigger to .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Magellan ( element , options ) {
_classCallCheck ( this , Magellan ) ;
this . $element = element ;
this . options = $ . extend ( { } , Magellan . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Magellan' ) ;
}
/ * *
* Initializes the Magellan plugin and calls functions to get equalizer functioning on load .
* @ private
* /
_createClass ( Magellan , [ {
key : '_init' ,
value : function _init ( ) {
var id = this . $element [ 0 ] . id || Foundation . GetYoDigits ( 6 , 'magellan' ) ;
var _this = this ;
this . $targets = $ ( '[data-magellan-target]' ) ;
this . $links = this . $element . find ( 'a' ) ;
this . $element . attr ( {
'data-resize' : id ,
'data-scroll' : id ,
'id' : id
} ) ;
this . $active = $ ( ) ;
this . scrollPos = parseInt ( window . pageYOffset , 10 ) ;
this . _events ( ) ;
}
/ * *
* Calculates an array of pixel values that are the demarcation lines between locations on the page .
* Can be invoked if new elements are added or the size of a location changes .
* @ function
* /
} , {
key : 'calcPoints' ,
value : function calcPoints ( ) {
var _this = this ,
body = document . body ,
html = document . documentElement ;
this . points = [ ] ;
this . winHeight = Math . round ( Math . max ( window . innerHeight , html . clientHeight ) ) ;
this . docHeight = Math . round ( Math . max ( body . scrollHeight , body . offsetHeight , html . clientHeight , html . scrollHeight , html . offsetHeight ) ) ;
this . $targets . each ( function ( ) {
var $tar = $ ( this ) ,
pt = Math . round ( $tar . offset ( ) . top - _this . options . threshold ) ;
$tar . targetPoint = pt ;
_this . points . push ( pt ) ;
} ) ;
}
/ * *
* Initializes events for Magellan .
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ,
$body = $ ( 'html, body' ) ,
opts = {
duration : _this . options . animationDuration ,
easing : _this . options . animationEasing
} ;
$ ( window ) . one ( 'load' , function ( ) {
if ( _this . options . deepLinking ) {
if ( location . hash ) {
_this . scrollToLoc ( location . hash ) ;
}
}
_this . calcPoints ( ) ;
_this . _updateActive ( ) ;
} ) ;
this . $element . on ( {
'resizeme.zf.trigger' : this . reflow . bind ( this ) ,
'scrollme.zf.trigger' : this . _updateActive . bind ( this )
} ) . on ( 'click.zf.magellan' , 'a[href^="#"]' , function ( e ) {
e . preventDefault ( ) ;
var arrival = this . getAttribute ( 'href' ) ;
_this . scrollToLoc ( arrival ) ;
} ) ;
}
/ * *
* Function to scroll to a given location on the page .
* @ param { String } loc - a properly formatted jQuery id selector . Example : '#foo'
* @ function
* /
} , {
key : 'scrollToLoc' ,
value : function scrollToLoc ( loc ) {
var scrollPos = Math . round ( $ ( loc ) . offset ( ) . top - this . options . threshold / 2 - this . options . barOffset ) ;
$ ( 'html, body' ) . stop ( true ) . animate ( { scrollTop : scrollPos } , this . options . animationDuration , this . options . animationEasing ) ;
}
/ * *
* Calls necessary functions to update Magellan upon DOM change
* @ function
* /
} , {
key : 'reflow' ,
value : function reflow ( ) {
this . calcPoints ( ) ;
this . _updateActive ( ) ;
}
/ * *
* Updates the visibility of an active location link , and updates the url hash for the page , if deepLinking enabled .
* @ private
* @ function
* @ fires Magellan # update
* /
} , {
key : '_updateActive' ,
value : function _updateActive ( ) /*evt, elem, scrollPos*/ {
var winPos = /*scrollPos ||*/ parseInt ( window . pageYOffset , 10 ) ,
curIdx ;
if ( winPos + this . winHeight === this . docHeight ) {
curIdx = this . points . length - 1 ;
} else if ( winPos < this . points [ 0 ] ) {
curIdx = 0 ;
} else {
var isDown = this . scrollPos < winPos ,
_this = this ,
curVisible = this . points . filter ( function ( p , i ) {
return isDown ? p - _this . options . barOffset <= winPos : p - _this . options . barOffset - _this . options . threshold <= winPos ;
} ) ;
curIdx = curVisible . length ? curVisible . length - 1 : 0 ;
}
this . $active . removeClass ( this . options . activeClass ) ;
this . $active = this . $links . eq ( curIdx ) . addClass ( this . options . activeClass ) ;
if ( this . options . deepLinking ) {
var hash = this . $active [ 0 ] . getAttribute ( 'href' ) ;
if ( window . history . pushState ) {
window . history . pushState ( null , null , hash ) ;
} else {
window . location . hash = hash ;
}
}
this . scrollPos = winPos ;
/ * *
* Fires when magellan is finished updating to the new active element .
* @ event Magellan # update
* /
this . $element . trigger ( 'update.zf.magellan' , [ this . $active ] ) ;
}
/ * *
* Destroys an instance of Magellan and resets the url of the window .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . off ( '.zf.trigger .zf.magellan' ) . find ( '.' + this . options . activeClass ) . removeClass ( this . options . activeClass ) ;
if ( this . options . deepLinking ) {
var hash = this . $active [ 0 ] . getAttribute ( 'href' ) ;
window . location . hash . replace ( hash , '' ) ;
}
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Magellan ;
} ( ) ;
/ * *
* Default settings for plugin
* /
Magellan . defaults = {
/ * *
* Amount of time , in ms , the animated scrolling should take between locations .
* @ option
* @ example 500
* /
animationDuration : 500 ,
/ * *
* Animation style to use when scrolling between locations .
* @ option
* @ example 'ease-in-out'
* /
animationEasing : 'linear' ,
/ * *
* Number of pixels to use as a marker for location changes .
* @ option
* @ example 50
* /
threshold : 50 ,
/ * *
* Class applied to the active locations link on the magellan container .
* @ option
* @ example 'active'
* /
activeClass : 'active' ,
/ * *
* Allows the script to manipulate the url of the current page , and if supported , alter the history .
* @ option
* @ example true
* /
deepLinking : false ,
/ * *
* Number of pixels to offset the scroll of the page on item click if using a sticky nav bar .
* @ option
* @ example 25
* /
barOffset : 0
} ;
// Window exports
Foundation . plugin ( Magellan , 'Magellan' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* OffCanvas module .
* @ module foundation . offcanvas
* @ requires foundation . util . mediaQuery
* @ requires foundation . util . triggers
* @ requires foundation . util . motion
* /
var OffCanvas = function ( ) {
/ * *
* Creates a new instance of an off - canvas wrapper .
* @ class
* @ fires OffCanvas # init
* @ param { Object } element - jQuery object to initialize .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function OffCanvas ( element , options ) {
_classCallCheck ( this , OffCanvas ) ;
this . $element = element ;
this . options = $ . extend ( { } , OffCanvas . defaults , this . $element . data ( ) , options ) ;
this . $lastTrigger = $ ( ) ;
this . $triggers = $ ( ) ;
this . _init ( ) ;
this . _events ( ) ;
Foundation . registerPlugin ( this , 'OffCanvas' ) ;
}
/ * *
* Initializes the off - canvas wrapper by adding the exit overlay ( if needed ) .
* @ function
* @ private
* /
_createClass ( OffCanvas , [ {
key : '_init' ,
value : function _init ( ) {
var id = this . $element . attr ( 'id' ) ;
this . $element . attr ( 'aria-hidden' , 'true' ) ;
// Find triggers that affect this element and add aria-expanded to them
this . $triggers = $ ( document ) . find ( '[data-open="' + id + '"], [data-close="' + id + '"], [data-toggle="' + id + '"]' ) . attr ( 'aria-expanded' , 'false' ) . attr ( 'aria-controls' , id ) ;
// Add a close trigger over the body if necessary
if ( this . options . closeOnClick ) {
if ( $ ( '.js-off-canvas-exit' ) . length ) {
this . $exiter = $ ( '.js-off-canvas-exit' ) ;
} else {
var exiter = document . createElement ( 'div' ) ;
exiter . setAttribute ( 'class' , 'js-off-canvas-exit' ) ;
$ ( '[data-off-canvas-content]' ) . append ( exiter ) ;
this . $exiter = $ ( exiter ) ;
}
}
this . options . isRevealed = this . options . isRevealed || new RegExp ( this . options . revealClass , 'g' ) . test ( this . $element [ 0 ] . className ) ;
if ( this . options . isRevealed ) {
this . options . revealOn = this . options . revealOn || this . $element [ 0 ] . className . match ( /(reveal-for-medium|reveal-for-large)/g ) [ 0 ] . split ( '-' ) [ 2 ] ;
this . _setMQChecker ( ) ;
}
if ( ! this . options . transitionTime ) {
this . options . transitionTime = parseFloat ( window . getComputedStyle ( $ ( '[data-off-canvas-wrapper]' ) [ 0 ] ) . transitionDuration ) * 1000 ;
}
}
/ * *
* Adds event handlers to the off - canvas wrapper and the exit overlay .
* @ function
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
this . $element . off ( '.zf.trigger .zf.offcanvas' ) . on ( {
'open.zf.trigger' : this . open . bind ( this ) ,
'close.zf.trigger' : this . close . bind ( this ) ,
'toggle.zf.trigger' : this . toggle . bind ( this ) ,
'keydown.zf.offcanvas' : this . _handleKeyboard . bind ( this )
} ) ;
if ( this . options . closeOnClick && this . $exiter . length ) {
this . $exiter . on ( { 'click.zf.offcanvas' : this . close . bind ( this ) } ) ;
}
}
/ * *
* Applies event listener for elements that will reveal at certain breakpoints .
* @ private
* /
} , {
key : '_setMQChecker' ,
value : function _setMQChecker ( ) {
var _this = this ;
$ ( window ) . on ( 'changed.zf.mediaquery' , function ( ) {
if ( Foundation . MediaQuery . atLeast ( _this . options . revealOn ) ) {
_this . reveal ( true ) ;
} else {
_this . reveal ( false ) ;
}
} ) . one ( 'load.zf.offcanvas' , function ( ) {
if ( Foundation . MediaQuery . atLeast ( _this . options . revealOn ) ) {
_this . reveal ( true ) ;
}
} ) ;
}
/ * *
* Handles the revealing / hiding the off - canvas at breakpoints , not the same as open .
* @ param { Boolean } isRevealed - true if element should be revealed .
* @ function
* /
} , {
key : 'reveal' ,
value : function reveal ( isRevealed ) {
var $closer = this . $element . find ( '[data-close]' ) ;
if ( isRevealed ) {
this . close ( ) ;
this . isRevealed = true ;
// if (!this.options.forceTop) {
// var scrollPos = parseInt(window.pageYOffset);
// this.$element[0].style.transform = 'translate(0,' + scrollPos + 'px)';
// }
// if (this.options.isSticky) { this._stick(); }
this . $element . off ( 'open.zf.trigger toggle.zf.trigger' ) ;
if ( $closer . length ) {
$closer . hide ( ) ;
}
} else {
this . isRevealed = false ;
// if (this.options.isSticky || !this.options.forceTop) {
// this.$element[0].style.transform = '';
// $(window).off('scroll.zf.offcanvas');
// }
this . $element . on ( {
'open.zf.trigger' : this . open . bind ( this ) ,
'toggle.zf.trigger' : this . toggle . bind ( this )
} ) ;
if ( $closer . length ) {
$closer . show ( ) ;
}
}
}
/ * *
* Opens the off - canvas menu .
* @ function
* @ param { Object } event - Event object passed from listener .
* @ param { jQuery } trigger - element that triggered the off - canvas to open .
* @ fires OffCanvas # opened
* /
} , {
key : 'open' ,
value : function open ( event , trigger ) {
if ( this . $element . hasClass ( 'is-open' ) || this . isRevealed ) {
return ;
}
var _this = this ,
$body = $ ( document . body ) ;
if ( this . options . forceTop ) {
$ ( 'body' ) . scrollTop ( 0 ) ;
}
// window.pageYOffset = 0;
// if (!this.options.forceTop) {
// var scrollPos = parseInt(window.pageYOffset);
// this.$element[0].style.transform = 'translate(0,' + scrollPos + 'px)';
// if (this.$exiter.length) {
// this.$exiter[0].style.transform = 'translate(0,' + scrollPos + 'px)';
// }
// }
/ * *
* Fires when the off - canvas menu opens .
* @ event OffCanvas # opened
* /
Foundation . Move ( this . options . transitionTime , this . $element , function ( ) {
$ ( '[data-off-canvas-wrapper]' ) . addClass ( 'is-off-canvas-open is-open-' + _this . options . position ) ;
_this . $element . addClass ( 'is-open' ) ;
// if (_this.options.isSticky) {
// _this._stick();
// }
} ) ;
this . $triggers . attr ( 'aria-expanded' , 'true' ) ;
this . $element . attr ( 'aria-hidden' , 'false' ) . trigger ( 'opened.zf.offcanvas' ) ;
if ( this . options . closeOnClick ) {
this . $exiter . addClass ( 'is-visible' ) ;
}
if ( trigger ) {
this . $lastTrigger = trigger ;
}
if ( this . options . autoFocus ) {
this . $element . one ( Foundation . transitionend ( this . $element ) , function ( ) {
_this . $element . find ( 'a, button' ) . eq ( 0 ) . focus ( ) ;
} ) ;
}
if ( this . options . trapFocus ) {
$ ( '[data-off-canvas-content]' ) . attr ( 'tabindex' , '-1' ) ;
this . _trapFocus ( ) ;
}
}
/ * *
* Traps focus within the offcanvas on open .
* @ private
* /
} , {
key : '_trapFocus' ,
value : function _trapFocus ( ) {
var focusable = Foundation . Keyboard . findFocusable ( this . $element ) ,
first = focusable . eq ( 0 ) ,
last = focusable . eq ( - 1 ) ;
focusable . off ( '.zf.offcanvas' ) . on ( 'keydown.zf.offcanvas' , function ( e ) {
if ( e . which === 9 || e . keycode === 9 ) {
if ( e . target === last [ 0 ] && ! e . shiftKey ) {
e . preventDefault ( ) ;
first . focus ( ) ;
}
if ( e . target === first [ 0 ] && e . shiftKey ) {
e . preventDefault ( ) ;
last . focus ( ) ;
}
}
} ) ;
}
/ * *
* Allows the offcanvas to appear sticky utilizing translate properties .
* @ private
* /
// OffCanvas.prototype._stick = function() {
// var elStyle = this.$element[0].style;
//
// if (this.options.closeOnClick) {
// var exitStyle = this.$exiter[0].style;
// }
//
// $(window).on('scroll.zf.offcanvas', function(e) {
// console.log(e);
// var pageY = window.pageYOffset;
// elStyle.transform = 'translate(0,' + pageY + 'px)';
// if (exitStyle !== undefined) { exitStyle.transform = 'translate(0,' + pageY + 'px)'; }
// });
// // this.$element.trigger('stuck.zf.offcanvas');
// };
/ * *
* Closes the off - canvas menu .
* @ function
* @ param { Function } cb - optional cb to fire after closure .
* @ fires OffCanvas # closed
* /
} , {
key : 'close' ,
value : function close ( cb ) {
if ( ! this . $element . hasClass ( 'is-open' ) || this . isRevealed ) {
return ;
}
var _this = this ;
// Foundation.Move(this.options.transitionTime, this.$element, function() {
$ ( '[data-off-canvas-wrapper]' ) . removeClass ( 'is-off-canvas-open is-open-' + _this . options . position ) ;
_this . $element . removeClass ( 'is-open' ) ;
// Foundation._reflow();
// });
this . $element . attr ( 'aria-hidden' , 'true' )
/ * *
* Fires when the off - canvas menu opens .
* @ event OffCanvas # closed
* /
. trigger ( 'closed.zf.offcanvas' ) ;
// if (_this.options.isSticky || !_this.options.forceTop) {
// setTimeout(function() {
// _this.$element[0].style.transform = '';
// $(window).off('scroll.zf.offcanvas');
// }, this.options.transitionTime);
// }
if ( this . options . closeOnClick ) {
this . $exiter . removeClass ( 'is-visible' ) ;
}
this . $triggers . attr ( 'aria-expanded' , 'false' ) ;
if ( this . options . trapFocus ) {
$ ( '[data-off-canvas-content]' ) . removeAttr ( 'tabindex' ) ;
}
}
/ * *
* Toggles the off - canvas menu open or closed .
* @ function
* @ param { Object } event - Event object passed from listener .
* @ param { jQuery } trigger - element that triggered the off - canvas to open .
* /
} , {
key : 'toggle' ,
value : function toggle ( event , trigger ) {
if ( this . $element . hasClass ( 'is-open' ) ) {
this . close ( event , trigger ) ;
} else {
this . open ( event , trigger ) ;
}
}
/ * *
* Handles keyboard input when detected . When the escape key is pressed , the off - canvas menu closes , and focus is restored to the element that opened the menu .
* @ function
* @ private
* /
} , {
key : '_handleKeyboard' ,
value : function _handleKeyboard ( event ) {
if ( event . which !== 27 ) return ;
event . stopPropagation ( ) ;
event . preventDefault ( ) ;
this . close ( ) ;
this . $lastTrigger . focus ( ) ;
}
/ * *
* Destroys the offcanvas plugin .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . close ( ) ;
this . $element . off ( '.zf.trigger .zf.offcanvas' ) ;
this . $exiter . off ( '.zf.offcanvas' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return OffCanvas ;
} ( ) ;
OffCanvas . defaults = {
/ * *
* Allow the user to click outside of the menu to close it .
* @ option
* @ example true
* /
closeOnClick : true ,
/ * *
* Amount of time in ms the open and close transition requires . If none selected , pulls from body style .
* @ option
* @ example 500
* /
transitionTime : 0 ,
/ * *
* Direction the offcanvas opens from . Determines class applied to body .
* @ option
* @ example left
* /
position : 'left' ,
/ * *
* Force the page to scroll to top on open .
* @ option
* @ example true
* /
forceTop : true ,
/ * *
* Allow the offcanvas to remain open for certain breakpoints .
* @ option
* @ example false
* /
isRevealed : false ,
/ * *
* Breakpoint at which to reveal . JS will use a RegExp to target standard classes , if changing classnames , pass your class with the ` revealClass ` option .
* @ option
* @ example reveal - for - large
* /
revealOn : null ,
/ * *
* Force focus to the offcanvas on open . If true , will focus the opening trigger on close .
* @ option
* @ example true
* /
autoFocus : true ,
/ * *
* Class used to force an offcanvas to remain open . Foundation defaults for this are ` reveal-for-large ` & ` reveal-for-medium ` .
* @ option
* TODO improve the regex testing for this .
* @ example reveal - for - large
* /
revealClass : 'reveal-for-' ,
/ * *
* Triggers optional focus trapping when opening an offcanvas . Sets tabindex of [ data - off - canvas - content ] to - 1 for accessibility purposes .
* @ option
* @ example true
* /
trapFocus : false
} ;
// Window exports
Foundation . plugin ( OffCanvas , 'OffCanvas' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Orbit module .
* @ module foundation . orbit
* @ requires foundation . util . keyboard
* @ requires foundation . util . motion
* @ requires foundation . util . timerAndImageLoader
* @ requires foundation . util . touch
* /
var Orbit = function ( ) {
/ * *
* Creates a new instance of an orbit carousel .
* @ class
* @ param { jQuery } element - jQuery object to make into an Orbit Carousel .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Orbit ( element , options ) {
_classCallCheck ( this , Orbit ) ;
this . $element = element ;
this . options = $ . extend ( { } , Orbit . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Orbit' ) ;
Foundation . Keyboard . register ( 'Orbit' , {
'ltr' : {
'ARROW_RIGHT' : 'next' ,
'ARROW_LEFT' : 'previous'
} ,
'rtl' : {
'ARROW_LEFT' : 'next' ,
'ARROW_RIGHT' : 'previous'
}
} ) ;
}
/ * *
* Initializes the plugin by creating jQuery collections , setting attributes , and starting the animation .
* @ function
* @ private
* /
_createClass ( Orbit , [ {
key : '_init' ,
value : function _init ( ) {
this . $wrapper = this . $element . find ( '.' + this . options . containerClass ) ;
this . $slides = this . $element . find ( '.' + this . options . slideClass ) ;
var $images = this . $element . find ( 'img' ) ,
initActive = this . $slides . filter ( '.is-active' ) ;
if ( ! initActive . length ) {
this . $slides . eq ( 0 ) . addClass ( 'is-active' ) ;
}
if ( ! this . options . useMUI ) {
this . $slides . addClass ( 'no-motionui' ) ;
}
if ( $images . length ) {
Foundation . onImagesLoaded ( $images , this . _prepareForOrbit . bind ( this ) ) ;
} else {
this . _prepareForOrbit ( ) ; //hehe
}
if ( this . options . bullets ) {
this . _loadBullets ( ) ;
}
this . _events ( ) ;
if ( this . options . autoPlay && this . $slides . length > 1 ) {
this . geoSync ( ) ;
}
if ( this . options . accessible ) {
// allow wrapper to be focusable to enable arrow navigation
this . $wrapper . attr ( 'tabindex' , 0 ) ;
}
}
/ * *
* Creates a jQuery collection of bullets , if they are being used .
* @ function
* @ private
* /
} , {
key : '_loadBullets' ,
value : function _loadBullets ( ) {
this . $bullets = this . $element . find ( '.' + this . options . boxOfBullets ) . find ( 'button' ) ;
}
/ * *
* Sets a ` timer ` object on the orbit , and starts the counter for the next slide .
* @ function
* /
} , {
key : 'geoSync' ,
value : function geoSync ( ) {
var _this = this ;
this . timer = new Foundation . Timer ( this . $element , {
duration : this . options . timerDelay ,
infinite : false
} , function ( ) {
_this . changeSlide ( true ) ;
} ) ;
this . timer . start ( ) ;
}
/ * *
* Sets wrapper and slide heights for the orbit .
* @ function
* @ private
* /
} , {
key : '_prepareForOrbit' ,
value : function _prepareForOrbit ( ) {
var _this = this ;
this . _setWrapperHeight ( function ( max ) {
_this . _setSlideHeight ( max ) ;
} ) ;
}
/ * *
* Calulates the height of each slide in the collection , and uses the tallest one for the wrapper height .
* @ function
* @ private
* @ param { Function } cb - a callback function to fire when complete .
* /
} , {
key : '_setWrapperHeight' ,
value : function _setWrapperHeight ( cb ) {
//rewrite this to `for` loop
var max = 0 ,
temp ,
counter = 0 ;
this . $slides . each ( function ( ) {
temp = this . getBoundingClientRect ( ) . height ;
$ ( this ) . attr ( 'data-slide' , counter ) ;
if ( counter ) {
//if not the first slide, set css position and display property
$ ( this ) . css ( { 'position' : 'relative' , 'display' : 'none' } ) ;
}
max = temp > max ? temp : max ;
counter ++ ;
} ) ;
if ( counter === this . $slides . length ) {
this . $wrapper . css ( { 'height' : max } ) ; //only change the wrapper height property once.
cb ( max ) ; //fire callback with max height dimension.
}
}
/ * *
* Sets the max - height of each slide .
* @ function
* @ private
* /
} , {
key : '_setSlideHeight' ,
value : function _setSlideHeight ( height ) {
this . $slides . each ( function ( ) {
$ ( this ) . css ( 'max-height' , height ) ;
} ) ;
}
/ * *
* Adds event listeners to basically everything within the element .
* @ function
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ;
//***************************************
//**Now using custom event - thanks to:**
//** Yohai Ararat of Toronto **
//***************************************
if ( this . $slides . length > 1 ) {
if ( this . options . swipe ) {
this . $slides . off ( 'swipeleft.zf.orbit swiperight.zf.orbit' ) . on ( 'swipeleft.zf.orbit' , function ( e ) {
e . preventDefault ( ) ;
_this . changeSlide ( true ) ;
} ) . on ( 'swiperight.zf.orbit' , function ( e ) {
e . preventDefault ( ) ;
_this . changeSlide ( false ) ;
} ) ;
}
//***************************************
if ( this . options . autoPlay ) {
this . $slides . on ( 'click.zf.orbit' , function ( ) {
_this . $element . data ( 'clickedOn' , _this . $element . data ( 'clickedOn' ) ? false : true ) ;
_this . timer [ _this . $element . data ( 'clickedOn' ) ? 'pause' : 'start' ] ( ) ;
} ) ;
if ( this . options . pauseOnHover ) {
this . $element . on ( 'mouseenter.zf.orbit' , function ( ) {
_this . timer . pause ( ) ;
} ) . on ( 'mouseleave.zf.orbit' , function ( ) {
if ( ! _this . $element . data ( 'clickedOn' ) ) {
_this . timer . start ( ) ;
}
} ) ;
}
}
if ( this . options . navButtons ) {
var $controls = this . $element . find ( '.' + this . options . nextClass + ', .' + this . options . prevClass ) ;
$controls . attr ( 'tabindex' , 0 )
//also need to handle enter/return and spacebar key presses
. on ( 'click.zf.orbit touchend.zf.orbit' , function ( e ) {
e . preventDefault ( ) ;
_this . changeSlide ( $ ( this ) . hasClass ( _this . options . nextClass ) ) ;
} ) ;
}
if ( this . options . bullets ) {
this . $bullets . on ( 'click.zf.orbit touchend.zf.orbit' , function ( ) {
if ( /is-active/g . test ( this . className ) ) {
return false ;
} //if this is active, kick out of function.
var idx = $ ( this ) . data ( 'slide' ) ,
ltr = idx > _this . $slides . filter ( '.is-active' ) . data ( 'slide' ) ,
$slide = _this . $slides . eq ( idx ) ;
_this . changeSlide ( ltr , $slide , idx ) ;
} ) ;
}
this . $wrapper . add ( this . $bullets ) . on ( 'keydown.zf.orbit' , function ( e ) {
// handle keyboard event with keyboard util
Foundation . Keyboard . handleKey ( e , 'Orbit' , {
next : function ( ) {
_this . changeSlide ( true ) ;
} ,
previous : function ( ) {
_this . changeSlide ( false ) ;
} ,
handled : function ( ) {
// if bullet is focused, make sure focus moves
if ( $ ( e . target ) . is ( _this . $bullets ) ) {
_this . $bullets . filter ( '.is-active' ) . focus ( ) ;
}
}
} ) ;
} ) ;
}
}
/ * *
* Changes the current slide to a new one .
* @ function
* @ param { Boolean } isLTR - flag if the slide should move left to right .
* @ param { jQuery } chosenSlide - the jQuery element of the slide to show next , if one is selected .
* @ param { Number } idx - the index of the new slide in its collection , if one chosen .
* @ fires Orbit # slidechange
* /
} , {
key : 'changeSlide' ,
value : function changeSlide ( isLTR , chosenSlide , idx ) {
var $curSlide = this . $slides . filter ( '.is-active' ) . eq ( 0 ) ;
if ( /mui/g . test ( $curSlide [ 0 ] . className ) ) {
return false ;
} //if the slide is currently animating, kick out of the function
var $firstSlide = this . $slides . first ( ) ,
$lastSlide = this . $slides . last ( ) ,
dirIn = isLTR ? 'Right' : 'Left' ,
dirOut = isLTR ? 'Left' : 'Right' ,
_this = this ,
$newSlide ;
if ( ! chosenSlide ) {
//most of the time, this will be auto played or clicked from the navButtons.
$newSlide = isLTR ? //if wrapping enabled, check to see if there is a `next` or `prev` sibling, if not, select the first or last slide to fill in. if wrapping not enabled, attempt to select `next` or `prev`, if there's nothing there, the function will kick out on next step. CRAZY NESTED TERNARIES!!!!!
this . options . infiniteWrap ? $curSlide . next ( '.' + this . options . slideClass ) . length ? $curSlide . next ( '.' + this . options . slideClass ) : $firstSlide : $curSlide . next ( '.' + this . options . slideClass ) : //pick next slide if moving left to right
this . options . infiniteWrap ? $curSlide . prev ( '.' + this . options . slideClass ) . length ? $curSlide . prev ( '.' + this . options . slideClass ) : $lastSlide : $curSlide . prev ( '.' + this . options . slideClass ) ; //pick prev slide if moving right to left
} else {
$newSlide = chosenSlide ;
}
if ( $newSlide . length ) {
if ( this . options . bullets ) {
idx = idx || this . $slides . index ( $newSlide ) ; //grab index to update bullets
this . _updateBullets ( idx ) ;
}
if ( this . options . useMUI ) {
Foundation . Motion . animateIn ( $newSlide . addClass ( 'is-active' ) . css ( { 'position' : 'absolute' , 'top' : 0 } ) , this . options [ 'animInFrom' + dirIn ] , function ( ) {
$newSlide . css ( { 'position' : 'relative' , 'display' : 'block' } ) . attr ( 'aria-live' , 'polite' ) ;
} ) ;
Foundation . Motion . animateOut ( $curSlide . removeClass ( 'is-active' ) , this . options [ 'animOutTo' + dirOut ] , function ( ) {
$curSlide . removeAttr ( 'aria-live' ) ;
if ( _this . options . autoPlay && ! _this . timer . isPaused ) {
_this . timer . restart ( ) ;
}
//do stuff?
} ) ;
} else {
$curSlide . removeClass ( 'is-active is-in' ) . removeAttr ( 'aria-live' ) . hide ( ) ;
$newSlide . addClass ( 'is-active is-in' ) . attr ( 'aria-live' , 'polite' ) . show ( ) ;
if ( this . options . autoPlay && ! this . timer . isPaused ) {
this . timer . restart ( ) ;
}
}
/ * *
* Triggers when the slide has finished animating in .
* @ event Orbit # slidechange
* /
this . $element . trigger ( 'slidechange.zf.orbit' , [ $newSlide ] ) ;
}
}
/ * *
* Updates the active state of the bullets , if displayed .
* @ function
* @ private
* @ param { Number } idx - the index of the current slide .
* /
} , {
key : '_updateBullets' ,
value : function _updateBullets ( idx ) {
var $oldBullet = this . $element . find ( '.' + this . options . boxOfBullets ) . find ( '.is-active' ) . removeClass ( 'is-active' ) . blur ( ) ,
span = $oldBullet . find ( 'span:last' ) . detach ( ) ,
$newBullet = this . $bullets . eq ( idx ) . addClass ( 'is-active' ) . append ( span ) ;
}
/ * *
* Destroys the carousel and hides the element .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . off ( '.zf.orbit' ) . find ( '*' ) . off ( '.zf.orbit' ) . end ( ) . hide ( ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Orbit ;
} ( ) ;
Orbit . defaults = {
/ * *
* Tells the JS to look for and loadBullets .
* @ option
* @ example true
* /
bullets : true ,
/ * *
* Tells the JS to apply event listeners to nav buttons
* @ option
* @ example true
* /
navButtons : true ,
/ * *
* motion - ui animation class to apply
* @ option
* @ example 'slide-in-right'
* /
animInFromRight : 'slide-in-right' ,
/ * *
* motion - ui animation class to apply
* @ option
* @ example 'slide-out-right'
* /
animOutToRight : 'slide-out-right' ,
/ * *
* motion - ui animation class to apply
* @ option
* @ example 'slide-in-left'
*
* /
animInFromLeft : 'slide-in-left' ,
/ * *
* motion - ui animation class to apply
* @ option
* @ example 'slide-out-left'
* /
animOutToLeft : 'slide-out-left' ,
/ * *
* Allows Orbit to automatically animate on page load .
* @ option
* @ example true
* /
autoPlay : true ,
/ * *
* Amount of time , in ms , between slide transitions
* @ option
* @ example 5000
* /
timerDelay : 5000 ,
/ * *
* Allows Orbit to infinitely loop through the slides
* @ option
* @ example true
* /
infiniteWrap : true ,
/ * *
* Allows the Orbit slides to bind to swipe events for mobile , requires an additional util library
* @ option
* @ example true
* /
swipe : true ,
/ * *
* Allows the timing function to pause animation on hover .
* @ option
* @ example true
* /
pauseOnHover : true ,
/ * *
* Allows Orbit to bind keyboard events to the slider , to animate frames with arrow keys
* @ option
* @ example true
* /
accessible : true ,
/ * *
* Class applied to the container of Orbit
* @ option
* @ example 'orbit-container'
* /
containerClass : 'orbit-container' ,
/ * *
* Class applied to individual slides .
* @ option
* @ example 'orbit-slide'
* /
slideClass : 'orbit-slide' ,
/ * *
* Class applied to the bullet container . You ' re welcome .
* @ option
* @ example 'orbit-bullets'
* /
boxOfBullets : 'orbit-bullets' ,
/ * *
* Class applied to the ` next ` navigation button .
* @ option
* @ example 'orbit-next'
* /
nextClass : 'orbit-next' ,
/ * *
* Class applied to the ` previous ` navigation button .
* @ option
* @ example 'orbit-previous'
* /
prevClass : 'orbit-previous' ,
/ * *
* Boolean to flag the js to use motion ui classes or not . Default to true for backwards compatability .
* @ option
* @ example true
* /
useMUI : true
} ;
// Window exports
Foundation . plugin ( Orbit , 'Orbit' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* ResponsiveMenu module .
* @ module foundation . responsiveMenu
* @ requires foundation . util . triggers
* @ requires foundation . util . mediaQuery
* @ requires foundation . util . accordionMenu
* @ requires foundation . util . drilldown
* @ requires foundation . util . dropdown - menu
* /
var ResponsiveMenu = function ( ) {
/ * *
* Creates a new instance of a responsive menu .
* @ class
* @ fires ResponsiveMenu # init
* @ param { jQuery } element - jQuery object to make into a dropdown menu .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function ResponsiveMenu ( element , options ) {
_classCallCheck ( this , ResponsiveMenu ) ;
this . $element = $ ( element ) ;
this . rules = this . $element . data ( 'responsive-menu' ) ;
this . currentMq = null ;
this . currentPlugin = null ;
this . _init ( ) ;
this . _events ( ) ;
Foundation . registerPlugin ( this , 'ResponsiveMenu' ) ;
}
/ * *
* Initializes the Menu by parsing the classes from the 'data-ResponsiveMenu' attribute on the element .
* @ function
* @ private
* /
_createClass ( ResponsiveMenu , [ {
key : '_init' ,
value : function _init ( ) {
// The first time an Interchange plugin is initialized, this.rules is converted from a string of "classes" to an object of rules
if ( typeof this . rules === 'string' ) {
var rulesTree = { } ;
// Parse rules from "classes" pulled from data attribute
var rules = this . rules . split ( ' ' ) ;
// Iterate through every rule found
for ( var i = 0 ; i < rules . length ; i ++ ) {
var rule = rules [ i ] . split ( '-' ) ;
var ruleSize = rule . length > 1 ? rule [ 0 ] : 'small' ;
var rulePlugin = rule . length > 1 ? rule [ 1 ] : rule [ 0 ] ;
if ( MenuPlugins [ rulePlugin ] !== null ) {
rulesTree [ ruleSize ] = MenuPlugins [ rulePlugin ] ;
}
}
this . rules = rulesTree ;
}
if ( ! $ . isEmptyObject ( this . rules ) ) {
this . _checkMediaQueries ( ) ;
}
}
/ * *
* Initializes events for the Menu .
* @ function
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ;
$ ( window ) . on ( 'changed.zf.mediaquery' , function ( ) {
_this . _checkMediaQueries ( ) ;
} ) ;
// $(window).on('resize.zf.ResponsiveMenu', function() {
// _this._checkMediaQueries();
// });
}
/ * *
* Checks the current screen width against available media queries . If the media query has changed , and the plugin needed has changed , the plugins will swap out .
* @ function
* @ private
* /
} , {
key : '_checkMediaQueries' ,
value : function _checkMediaQueries ( ) {
var matchedMq ,
_this = this ;
// Iterate through each rule and find the last matching rule
$ . each ( this . rules , function ( key ) {
if ( Foundation . MediaQuery . atLeast ( key ) ) {
matchedMq = key ;
}
} ) ;
// No match? No dice
if ( ! matchedMq ) return ;
// Plugin already initialized? We good
if ( this . currentPlugin instanceof this . rules [ matchedMq ] . plugin ) return ;
// Remove existing plugin-specific CSS classes
$ . each ( MenuPlugins , function ( key , value ) {
_this . $element . removeClass ( value . cssClass ) ;
} ) ;
// Add the CSS class for the new plugin
this . $element . addClass ( this . rules [ matchedMq ] . cssClass ) ;
// Create an instance of the new plugin
if ( this . currentPlugin ) this . currentPlugin . destroy ( ) ;
this . currentPlugin = new this . rules [ matchedMq ] . plugin ( this . $element , { } ) ;
}
/ * *
* Destroys the instance of the current plugin on this element , as well as the window resize handler that switches the plugins out .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . currentPlugin . destroy ( ) ;
$ ( window ) . off ( '.zf.ResponsiveMenu' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return ResponsiveMenu ;
} ( ) ;
ResponsiveMenu . defaults = { } ;
// The plugin matches the plugin classes with these plugin instances.
var MenuPlugins = {
dropdown : {
cssClass : 'dropdown' ,
plugin : Foundation . _plugins [ 'dropdown-menu' ] || null
} ,
drilldown : {
cssClass : 'drilldown' ,
plugin : Foundation . _plugins [ 'drilldown' ] || null
} ,
accordion : {
cssClass : 'accordion-menu' ,
plugin : Foundation . _plugins [ 'accordion-menu' ] || null
}
} ;
// Window exports
Foundation . plugin ( ResponsiveMenu , 'ResponsiveMenu' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* ResponsiveToggle module .
* @ module foundation . responsiveToggle
* @ requires foundation . util . mediaQuery
* /
var ResponsiveToggle = function ( ) {
/ * *
* Creates a new instance of Tab Bar .
* @ class
* @ fires ResponsiveToggle # init
* @ param { jQuery } element - jQuery object to attach tab bar functionality to .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function ResponsiveToggle ( element , options ) {
_classCallCheck ( this , ResponsiveToggle ) ;
this . $element = $ ( element ) ;
this . options = $ . extend ( { } , ResponsiveToggle . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
this . _events ( ) ;
Foundation . registerPlugin ( this , 'ResponsiveToggle' ) ;
}
/ * *
* Initializes the tab bar by finding the target element , toggling element , and running update ( ) .
* @ function
* @ private
* /
_createClass ( ResponsiveToggle , [ {
key : '_init' ,
value : function _init ( ) {
var targetID = this . $element . data ( 'responsive-toggle' ) ;
if ( ! targetID ) {
console . error ( 'Your tab bar needs an ID of a Menu as the value of data-tab-bar.' ) ;
}
this . $targetMenu = $ ( '#' + targetID ) ;
this . $toggler = this . $element . find ( '[data-toggle]' ) ;
this . _update ( ) ;
}
/ * *
* Adds necessary event handlers for the tab bar to work .
* @ function
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ;
this . _updateMqHandler = this . _update . bind ( this ) ;
$ ( window ) . on ( 'changed.zf.mediaquery' , this . _updateMqHandler ) ;
this . $toggler . on ( 'click.zf.responsiveToggle' , this . toggleMenu . bind ( this ) ) ;
}
/ * *
* Checks the current media query to determine if the tab bar should be visible or hidden .
* @ function
* @ private
* /
} , {
key : '_update' ,
value : function _update ( ) {
// Mobile
if ( ! Foundation . MediaQuery . atLeast ( this . options . hideFor ) ) {
this . $element . show ( ) ;
this . $targetMenu . hide ( ) ;
}
// Desktop
else {
this . $element . hide ( ) ;
this . $targetMenu . show ( ) ;
}
}
/ * *
* Toggles the element attached to the tab bar . The toggle only happens if the screen is small enough to allow it .
* @ function
* @ fires ResponsiveToggle # toggled
* /
} , {
key : 'toggleMenu' ,
value : function toggleMenu ( ) {
if ( ! Foundation . MediaQuery . atLeast ( this . options . hideFor ) ) {
this . $targetMenu . toggle ( 0 ) ;
/ * *
* Fires when the element attached to the tab bar toggles .
* @ event ResponsiveToggle # toggled
* /
this . $element . trigger ( 'toggled.zf.responsiveToggle' ) ;
}
}
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . off ( '.zf.responsiveToggle' ) ;
this . $toggler . off ( '.zf.responsiveToggle' ) ;
$ ( window ) . off ( 'changed.zf.mediaquery' , this . _updateMqHandler ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return ResponsiveToggle ;
} ( ) ;
ResponsiveToggle . defaults = {
/ * *
* The breakpoint after which the menu is always shown , and the tab bar is hidden .
* @ option
* @ example 'medium'
* /
hideFor : 'medium'
} ;
// Window exports
Foundation . plugin ( ResponsiveToggle , 'ResponsiveToggle' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Reveal module .
* @ module foundation . reveal
* @ requires foundation . util . keyboard
* @ requires foundation . util . box
* @ requires foundation . util . triggers
* @ requires foundation . util . mediaQuery
* @ requires foundation . util . motion if using animations
* /
var Reveal = function ( ) {
/ * *
* Creates a new instance of Reveal .
* @ class
* @ param { jQuery } element - jQuery object to use for the modal .
* @ param { Object } options - optional parameters .
* /
function Reveal ( element , options ) {
_classCallCheck ( this , Reveal ) ;
this . $element = element ;
this . options = $ . extend ( { } , Reveal . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Reveal' ) ;
Foundation . Keyboard . register ( 'Reveal' , {
'ENTER' : 'open' ,
'SPACE' : 'open' ,
'ESCAPE' : 'close' ,
'TAB' : 'tab_forward' ,
'SHIFT_TAB' : 'tab_backward'
} ) ;
}
/ * *
* Initializes the modal by adding the overlay and close buttons , ( if selected ) .
* @ private
* /
_createClass ( Reveal , [ {
key : '_init' ,
value : function _init ( ) {
this . id = this . $element . attr ( 'id' ) ;
this . isActive = false ;
this . cached = { mq : Foundation . MediaQuery . current } ;
this . isMobile = mobileSniff ( ) ;
this . $anchor = $ ( '[data-open="' + this . id + '"]' ) . length ? $ ( '[data-open="' + this . id + '"]' ) : $ ( '[data-toggle="' + this . id + '"]' ) ;
this . $anchor . attr ( {
'aria-controls' : this . id ,
'aria-haspopup' : true ,
'tabindex' : 0
} ) ;
if ( this . options . fullScreen || this . $element . hasClass ( 'full' ) ) {
this . options . fullScreen = true ;
this . options . overlay = false ;
}
if ( this . options . overlay && ! this . $overlay ) {
this . $overlay = this . _makeOverlay ( this . id ) ;
}
this . $element . attr ( {
'role' : 'dialog' ,
'aria-hidden' : true ,
'data-yeti-box' : this . id ,
'data-resize' : this . id
} ) ;
if ( this . $overlay ) {
this . $element . detach ( ) . appendTo ( this . $overlay ) ;
} else {
this . $element . detach ( ) . appendTo ( $ ( 'body' ) ) ;
this . $element . addClass ( 'without-overlay' ) ;
}
this . _events ( ) ;
if ( this . options . deepLink && window . location . hash === '#' + this . id ) {
$ ( window ) . one ( 'load.zf.reveal' , this . open . bind ( this ) ) ;
}
}
/ * *
* Creates an overlay div to display behind the modal .
* @ private
* /
} , {
key : '_makeOverlay' ,
value : function _makeOverlay ( id ) {
var $overlay = $ ( '<div></div>' ) . addClass ( 'reveal-overlay' ) . appendTo ( 'body' ) ;
return $overlay ;
}
/ * *
* Updates position of modal
* TODO : Figure out if we actually need to cache these values or if it doesn ' t matter
* @ private
* /
} , {
key : '_updatePosition' ,
value : function _updatePosition ( ) {
var width = this . $element . outerWidth ( ) ;
var outerWidth = $ ( window ) . width ( ) ;
var height = this . $element . outerHeight ( ) ;
var outerHeight = $ ( window ) . height ( ) ;
var left , top ;
if ( this . options . hOffset === 'auto' ) {
left = parseInt ( ( outerWidth - width ) / 2 , 10 ) ;
} else {
left = parseInt ( this . options . hOffset , 10 ) ;
}
if ( this . options . vOffset === 'auto' ) {
if ( height > outerHeight ) {
top = parseInt ( Math . min ( 100 , outerHeight / 10 ) , 10 ) ;
} else {
top = parseInt ( ( outerHeight - height ) / 4 , 10 ) ;
}
} else {
top = parseInt ( this . options . vOffset , 10 ) ;
}
this . $element . css ( { top : top + 'px' } ) ;
// only worry about left if we don't have an overlay or we havea horizontal offset,
// otherwise we're perfectly in the middle
if ( ! this . $overlay || this . options . hOffset !== 'auto' ) {
this . $element . css ( { left : left + 'px' } ) ;
this . $element . css ( { margin : '0px' } ) ;
}
}
/ * *
* Adds event handlers for the modal .
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this2 = this ;
var _this = this ;
this . $element . on ( {
'open.zf.trigger' : this . open . bind ( this ) ,
'close.zf.trigger' : function ( event , $element ) {
if ( event . target === _this . $element [ 0 ] || $ ( event . target ) . parents ( '[data-closable]' ) [ 0 ] === $element ) {
// only close reveal when it's explicitly called
return _this2 . close . apply ( _this2 ) ;
}
} ,
'toggle.zf.trigger' : this . toggle . bind ( this ) ,
'resizeme.zf.trigger' : function ( ) {
_this . _updatePosition ( ) ;
}
} ) ;
if ( this . $anchor . length ) {
this . $anchor . on ( 'keydown.zf.reveal' , function ( e ) {
if ( e . which === 13 || e . which === 32 ) {
e . stopPropagation ( ) ;
e . preventDefault ( ) ;
_this . open ( ) ;
}
} ) ;
}
if ( this . options . closeOnClick && this . options . overlay ) {
this . $overlay . off ( '.zf.reveal' ) . on ( 'click.zf.reveal' , function ( e ) {
if ( e . target === _this . $element [ 0 ] || $ . contains ( _this . $element [ 0 ] , e . target ) ) {
return ;
}
_this . close ( ) ;
} ) ;
}
if ( this . options . deepLink ) {
$ ( window ) . on ( 'popstate.zf.reveal:' + this . id , this . _handleState . bind ( this ) ) ;
}
}
/ * *
* Handles modal methods on back / forward button clicks or any other event that triggers popstate .
* @ private
* /
} , {
key : '_handleState' ,
value : function _handleState ( e ) {
if ( window . location . hash === '#' + this . id && ! this . isActive ) {
this . open ( ) ;
} else {
this . close ( ) ;
}
}
/ * *
* Opens the modal controlled by ` this. $ anchor ` , and closes all others by default .
* @ function
* @ fires Reveal # closeme
* @ fires Reveal # open
* /
} , {
key : 'open' ,
value : function open ( ) {
var _this3 = this ;
if ( this . options . deepLink ) {
var hash = '#' + this . id ;
if ( window . history . pushState ) {
window . history . pushState ( null , null , hash ) ;
} else {
window . location . hash = hash ;
}
}
this . isActive = true ;
// Make elements invisible, but remove display: none so we can get size and positioning
this . $element . css ( { 'visibility' : 'hidden' } ) . show ( ) . scrollTop ( 0 ) ;
if ( this . options . overlay ) {
this . $overlay . css ( { 'visibility' : 'hidden' } ) . show ( ) ;
}
this . _updatePosition ( ) ;
this . $element . hide ( ) . css ( { 'visibility' : '' } ) ;
if ( this . $overlay ) {
this . $overlay . css ( { 'visibility' : '' } ) . hide ( ) ;
if ( this . $element . hasClass ( 'fast' ) ) {
this . $overlay . addClass ( 'fast' ) ;
} else if ( this . $element . hasClass ( 'slow' ) ) {
this . $overlay . addClass ( 'slow' ) ;
}
}
if ( ! this . options . multipleOpened ) {
/ * *
* Fires immediately before the modal opens .
* Closes any other modals that are currently open
* @ event Reveal # closeme
* /
this . $element . trigger ( 'closeme.zf.reveal' , this . id ) ;
}
// Motion UI method of reveal
if ( this . options . animationIn ) {
var _this ;
( function ( ) {
var afterAnimationFocus = function ( ) {
_this . $element . attr ( {
'aria-hidden' : false ,
'tabindex' : - 1
} ) . focus ( ) ;
console . log ( 'focus' ) ;
} ;
_this = _this3 ;
if ( _this3 . options . overlay ) {
Foundation . Motion . animateIn ( _this3 . $overlay , 'fade-in' ) ;
}
Foundation . Motion . animateIn ( _this3 . $element , _this3 . options . animationIn , function ( ) {
_this3 . focusableElements = Foundation . Keyboard . findFocusable ( _this3 . $element ) ;
afterAnimationFocus ( ) ;
} ) ;
} ) ( ) ;
}
// jQuery method of reveal
else {
if ( this . options . overlay ) {
this . $overlay . show ( 0 ) ;
}
this . $element . show ( this . options . showDelay ) ;
}
// handle accessibility
this . $element . attr ( {
'aria-hidden' : false ,
'tabindex' : - 1
} ) . focus ( ) ;
/ * *
* Fires when the modal has successfully opened .
* @ event Reveal # open
* /
this . $element . trigger ( 'open.zf.reveal' ) ;
if ( this . isMobile ) {
this . originalScrollPos = window . pageYOffset ;
$ ( 'html, body' ) . addClass ( 'is-reveal-open' ) ;
} else {
$ ( 'body' ) . addClass ( 'is-reveal-open' ) ;
}
setTimeout ( function ( ) {
_this3 . _extraHandlers ( ) ;
} , 0 ) ;
}
/ * *
* Adds extra event handlers for the body and window if necessary .
* @ private
* /
} , {
key : '_extraHandlers' ,
value : function _extraHandlers ( ) {
var _this = this ;
this . focusableElements = Foundation . Keyboard . findFocusable ( this . $element ) ;
if ( ! this . options . overlay && this . options . closeOnClick && ! this . options . fullScreen ) {
$ ( 'body' ) . on ( 'click.zf.reveal' , function ( e ) {
if ( e . target === _this . $element [ 0 ] || $ . contains ( _this . $element [ 0 ] , e . target ) ) {
return ;
}
_this . close ( ) ;
} ) ;
}
if ( this . options . closeOnEsc ) {
$ ( window ) . on ( 'keydown.zf.reveal' , function ( e ) {
Foundation . Keyboard . handleKey ( e , 'Reveal' , {
close : function ( ) {
if ( _this . options . closeOnEsc ) {
_this . close ( ) ;
_this . $anchor . focus ( ) ;
}
}
} ) ;
} ) ;
}
// lock focus within modal while tabbing
this . $element . on ( 'keydown.zf.reveal' , function ( e ) {
var $target = $ ( this ) ;
// handle keyboard event with keyboard util
Foundation . Keyboard . handleKey ( e , 'Reveal' , {
tab _forward : function ( ) {
if ( _this . $element . find ( ':focus' ) . is ( _this . focusableElements . eq ( - 1 ) ) ) {
// left modal downwards, setting focus to first element
_this . focusableElements . eq ( 0 ) . focus ( ) ;
return true ;
}
if ( _this . focusableElements . length === 0 ) {
// no focusable elements inside the modal at all, prevent tabbing in general
return true ;
}
} ,
tab _backward : function ( ) {
if ( _this . $element . find ( ':focus' ) . is ( _this . focusableElements . eq ( 0 ) ) || _this . $element . is ( ':focus' ) ) {
// left modal upwards, setting focus to last element
_this . focusableElements . eq ( - 1 ) . focus ( ) ;
return true ;
}
if ( _this . focusableElements . length === 0 ) {
// no focusable elements inside the modal at all, prevent tabbing in general
return true ;
}
} ,
open : function ( ) {
if ( _this . $element . find ( ':focus' ) . is ( _this . $element . find ( '[data-close]' ) ) ) {
setTimeout ( function ( ) {
// set focus back to anchor if close button has been activated
_this . $anchor . focus ( ) ;
} , 1 ) ;
} else if ( $target . is ( _this . focusableElements ) ) {
// dont't trigger if acual element has focus (i.e. inputs, links, ...)
_this . open ( ) ;
}
} ,
close : function ( ) {
if ( _this . options . closeOnEsc ) {
_this . close ( ) ;
_this . $anchor . focus ( ) ;
}
} ,
handled : function ( preventDefault ) {
if ( preventDefault ) {
e . preventDefault ( ) ;
}
}
} ) ;
} ) ;
}
/ * *
* Closes the modal .
* @ function
* @ fires Reveal # closed
* /
} , {
key : 'close' ,
value : function close ( ) {
if ( ! this . isActive || ! this . $element . is ( ':visible' ) ) {
return false ;
}
var _this = this ;
// Motion UI method of hiding
if ( this . options . animationOut ) {
if ( this . options . overlay ) {
Foundation . Motion . animateOut ( this . $overlay , 'fade-out' , finishUp ) ;
} else {
finishUp ( ) ;
}
Foundation . Motion . animateOut ( this . $element , this . options . animationOut ) ;
}
// jQuery method of hiding
else {
if ( this . options . overlay ) {
this . $overlay . hide ( 0 , finishUp ) ;
} else {
finishUp ( ) ;
}
this . $element . hide ( this . options . hideDelay ) ;
}
// Conditionals to remove extra event listeners added on open
if ( this . options . closeOnEsc ) {
$ ( window ) . off ( 'keydown.zf.reveal' ) ;
}
if ( ! this . options . overlay && this . options . closeOnClick ) {
$ ( 'body' ) . off ( 'click.zf.reveal' ) ;
}
this . $element . off ( 'keydown.zf.reveal' ) ;
function finishUp ( ) {
if ( _this . isMobile ) {
$ ( 'html, body' ) . removeClass ( 'is-reveal-open' ) ;
if ( _this . originalScrollPos ) {
$ ( 'body' ) . scrollTop ( _this . originalScrollPos ) ;
_this . originalScrollPos = null ;
}
} else {
$ ( 'body' ) . removeClass ( 'is-reveal-open' ) ;
}
_this . $element . attr ( 'aria-hidden' , true ) ;
/ * *
* Fires when the modal is done closing .
* @ event Reveal # closed
* /
_this . $element . trigger ( 'closed.zf.reveal' ) ;
}
/ * *
* Resets the modal content
* This prevents a running video to keep going in the background
* /
if ( this . options . resetOnClose ) {
this . $element . html ( this . $element . html ( ) ) ;
}
this . isActive = false ;
if ( _this . options . deepLink ) {
if ( window . history . replaceState ) {
window . history . replaceState ( "" , document . title , window . location . pathname ) ;
} else {
window . location . hash = '' ;
}
}
}
/ * *
* Toggles the open / closed state of a modal .
* @ function
* /
} , {
key : 'toggle' ,
value : function toggle ( ) {
if ( this . isActive ) {
this . close ( ) ;
} else {
this . open ( ) ;
}
}
} , {
key : 'destroy' ,
/ * *
* Destroys an instance of a modal .
* @ function
* /
value : function destroy ( ) {
if ( this . options . overlay ) {
this . $element . appendTo ( $ ( 'body' ) ) ; // move $element outside of $overlay to prevent error unregisterPlugin()
this . $overlay . hide ( ) . off ( ) . remove ( ) ;
}
this . $element . hide ( ) . off ( ) ;
this . $anchor . off ( '.zf' ) ;
$ ( window ) . off ( '.zf.reveal:' + this . id ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Reveal ;
} ( ) ;
Reveal . defaults = {
/ * *
* Motion - UI class to use for animated elements . If none used , defaults to simple show / hide .
* @ option
* @ example 'slide-in-left'
* /
animationIn : '' ,
/ * *
* Motion - UI class to use for animated elements . If none used , defaults to simple show / hide .
* @ option
* @ example 'slide-out-right'
* /
animationOut : '' ,
/ * *
* Time , in ms , to delay the opening of a modal after a click if no animation used .
* @ option
* @ example 10
* /
showDelay : 0 ,
/ * *
* Time , in ms , to delay the closing of a modal after a click if no animation used .
* @ option
* @ example 10
* /
hideDelay : 0 ,
/ * *
* Allows a click on the body / overlay to close the modal .
* @ option
* @ example true
* /
closeOnClick : true ,
/ * *
* Allows the modal to close if the user presses the ` ESCAPE ` key .
* @ option
* @ example true
* /
closeOnEsc : true ,
/ * *
* If true , allows multiple modals to be displayed at once .
* @ option
* @ example false
* /
multipleOpened : false ,
/ * *
* Distance , in pixels , the modal should push down from the top of the screen .
* @ option
* @ example auto
* /
vOffset : 'auto' ,
/ * *
* Distance , in pixels , the modal should push in from the side of the screen .
* @ option
* @ example auto
* /
hOffset : 'auto' ,
/ * *
* Allows the modal to be fullscreen , completely blocking out the rest of the view . JS checks for this as well .
* @ option
* @ example false
* /
fullScreen : false ,
/ * *
* Percentage of screen height the modal should push up from the bottom of the view .
* @ option
* @ example 10
* /
btmOffsetPct : 10 ,
/ * *
* Allows the modal to generate an overlay div , which will cover the view when modal opens .
* @ option
* @ example true
* /
overlay : true ,
/ * *
* Allows the modal to remove and reinject markup on close . Should be true if using video elements w / o using provider ' s api , otherwise , videos will continue to play in the background .
* @ option
* @ example false
* /
resetOnClose : false ,
/ * *
* Allows the modal to alter the url on open / close , and allows the use of the ` back ` button to close modals . ALSO , allows a modal to auto - maniacally open on page load IF the hash === the modal ' s user - set id .
* @ option
* @ example false
* /
deepLink : false
} ;
// Window exports
Foundation . plugin ( Reveal , 'Reveal' ) ;
function iPhoneSniff ( ) {
return ( /iP(ad|hone|od).*OS/ . test ( window . navigator . userAgent )
) ;
}
function androidSniff ( ) {
return ( /Android/ . test ( window . navigator . userAgent )
) ;
}
function mobileSniff ( ) {
return iPhoneSniff ( ) || androidSniff ( ) ;
}
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Slider module .
* @ module foundation . slider
* @ requires foundation . util . motion
* @ requires foundation . util . triggers
* @ requires foundation . util . keyboard
* @ requires foundation . util . touch
* /
var Slider = function ( ) {
/ * *
* Creates a new instance of a drilldown menu .
* @ class
* @ param { jQuery } element - jQuery object to make into an accordion menu .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Slider ( element , options ) {
_classCallCheck ( this , Slider ) ;
this . $element = element ;
this . options = $ . extend ( { } , Slider . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Slider' ) ;
Foundation . Keyboard . register ( 'Slider' , {
'ltr' : {
'ARROW_RIGHT' : 'increase' ,
'ARROW_UP' : 'increase' ,
'ARROW_DOWN' : 'decrease' ,
'ARROW_LEFT' : 'decrease' ,
'SHIFT_ARROW_RIGHT' : 'increase_fast' ,
'SHIFT_ARROW_UP' : 'increase_fast' ,
'SHIFT_ARROW_DOWN' : 'decrease_fast' ,
'SHIFT_ARROW_LEFT' : 'decrease_fast'
} ,
'rtl' : {
'ARROW_LEFT' : 'increase' ,
'ARROW_RIGHT' : 'decrease' ,
'SHIFT_ARROW_LEFT' : 'increase_fast' ,
'SHIFT_ARROW_RIGHT' : 'decrease_fast'
}
} ) ;
}
/ * *
* Initilizes the plugin by reading / setting attributes , creating collections and setting the initial position of the handle ( s ) .
* @ function
* @ private
* /
_createClass ( Slider , [ {
key : '_init' ,
value : function _init ( ) {
this . inputs = this . $element . find ( 'input' ) ;
this . handles = this . $element . find ( '[data-slider-handle]' ) ;
this . $handle = this . handles . eq ( 0 ) ;
this . $input = this . inputs . length ? this . inputs . eq ( 0 ) : $ ( '#' + this . $handle . attr ( 'aria-controls' ) ) ;
this . $fill = this . $element . find ( '[data-slider-fill]' ) . css ( this . options . vertical ? 'height' : 'width' , 0 ) ;
var isDbl = false ,
_this = this ;
if ( this . options . disabled || this . $element . hasClass ( this . options . disabledClass ) ) {
this . options . disabled = true ;
this . $element . addClass ( this . options . disabledClass ) ;
}
if ( ! this . inputs . length ) {
this . inputs = $ ( ) . add ( this . $input ) ;
this . options . binding = true ;
}
this . _setInitAttr ( 0 ) ;
this . _events ( this . $handle ) ;
if ( this . handles [ 1 ] ) {
this . options . doubleSided = true ;
this . $handle2 = this . handles . eq ( 1 ) ;
this . $input2 = this . inputs . length > 1 ? this . inputs . eq ( 1 ) : $ ( '#' + this . $handle2 . attr ( 'aria-controls' ) ) ;
if ( ! this . inputs [ 1 ] ) {
this . inputs = this . inputs . add ( this . $input2 ) ;
}
isDbl = true ;
this . _setHandlePos ( this . $handle , this . options . initialStart , true , function ( ) {
_this . _setHandlePos ( _this . $handle2 , _this . options . initialEnd , true ) ;
} ) ;
// this.$handle.triggerHandler('click.zf.slider');
this . _setInitAttr ( 1 ) ;
this . _events ( this . $handle2 ) ;
}
if ( ! isDbl ) {
this . _setHandlePos ( this . $handle , this . options . initialStart , true ) ;
}
}
/ * *
* Sets the position of the selected handle and fill bar .
* @ function
* @ private
* @ param { jQuery } $hndl - the selected handle to move .
* @ param { Number } location - floating point between the start and end values of the slider bar .
* @ param { Function } cb - callback function to fire on completion .
* @ fires Slider # moved
* @ fires Slider # changed
* /
} , {
key : '_setHandlePos' ,
value : function _setHandlePos ( $hndl , location , noInvert , cb ) {
// don't move if the slider has been disabled since its initialization
if ( this . $element . hasClass ( this . options . disabledClass ) ) {
return ;
}
//might need to alter that slightly for bars that will have odd number selections.
location = parseFloat ( location ) ; //on input change events, convert string to number...grumble.
// prevent slider from running out of bounds, if value exceeds the limits set through options, override the value to min/max
if ( location < this . options . start ) {
location = this . options . start ;
} else if ( location > this . options . end ) {
location = this . options . end ;
}
var isDbl = this . options . doubleSided ;
if ( isDbl ) {
//this block is to prevent 2 handles from crossing eachother. Could/should be improved.
if ( this . handles . index ( $hndl ) === 0 ) {
var h2Val = parseFloat ( this . $handle2 . attr ( 'aria-valuenow' ) ) ;
location = location >= h2Val ? h2Val - this . options . step : location ;
} else {
var h1Val = parseFloat ( this . $handle . attr ( 'aria-valuenow' ) ) ;
location = location <= h1Val ? h1Val + this . options . step : location ;
}
}
//this is for single-handled vertical sliders, it adjusts the value to account for the slider being "upside-down"
//for click and drag events, it's weird due to the scale(-1, 1) css property
if ( this . options . vertical && ! noInvert ) {
location = this . options . end - location ;
}
var _this = this ,
vert = this . options . vertical ,
hOrW = vert ? 'height' : 'width' ,
lOrT = vert ? 'top' : 'left' ,
handleDim = $hndl [ 0 ] . getBoundingClientRect ( ) [ hOrW ] ,
elemDim = this . $element [ 0 ] . getBoundingClientRect ( ) [ hOrW ] ,
//percentage of bar min/max value based on click or drag point
pctOfBar = percent ( location - this . options . start , this . options . end - this . options . start ) . toFixed ( 2 ) ,
//number of actual pixels to shift the handle, based on the percentage obtained above
pxToMove = ( elemDim - handleDim ) * pctOfBar ,
//percentage of bar to shift the handle
movement = ( percent ( pxToMove , elemDim ) * 100 ) . toFixed ( this . options . decimal ) ;
//fixing the decimal value for the location number, is passed to other methods as a fixed floating-point value
location = parseFloat ( location . toFixed ( this . options . decimal ) ) ;
// declare empty object for css adjustments, only used with 2 handled-sliders
var css = { } ;
this . _setValues ( $hndl , location ) ;
// TODO update to calculate based on values set to respective inputs??
if ( isDbl ) {
var isLeftHndl = this . handles . index ( $hndl ) === 0 ,
//empty variable, will be used for min-height/width for fill bar
dim ,
//percentage w/h of the handle compared to the slider bar
handlePct = ~ ~ ( percent ( handleDim , elemDim ) * 100 ) ;
//if left handle, the math is slightly different than if it's the right handle, and the left/top property needs to be changed for the fill bar
if ( isLeftHndl ) {
//left or top percentage value to apply to the fill bar.
css [ lOrT ] = movement + '%' ;
//calculate the new min-height/width for the fill bar.
dim = parseFloat ( this . $handle2 [ 0 ] . style [ lOrT ] ) - movement + handlePct ;
//this callback is necessary to prevent errors and allow the proper placement and initialization of a 2-handled slider
//plus, it means we don't care if 'dim' isNaN on init, it won't be in the future.
if ( cb && typeof cb === 'function' ) {
cb ( ) ;
} //this is only needed for the initialization of 2 handled sliders
} else {
//just caching the value of the left/bottom handle's left/top property
var handlePos = parseFloat ( this . $handle [ 0 ] . style [ lOrT ] ) ;
//calculate the new min-height/width for the fill bar. Use isNaN to prevent false positives for numbers <= 0
//based on the percentage of movement of the handle being manipulated, less the opposing handle's left/top position, plus the percentage w/h of the handle itself
dim = movement - ( isNaN ( handlePos ) ? this . options . initialStart / ( ( this . options . end - this . options . start ) / 100 ) : handlePos ) + handlePct ;
}
// assign the min-height/width to our css object
css [ 'min-' + hOrW ] = dim + '%' ;
}
this . $element . one ( 'finished.zf.animate' , function ( ) {
/ * *
* Fires when the handle is done moving .
* @ event Slider # moved
* /
_this . $element . trigger ( 'moved.zf.slider' , [ $hndl ] ) ;
} ) ;
//because we don't know exactly how the handle will be moved, check the amount of time it should take to move.
var moveTime = this . $element . data ( 'dragging' ) ? 1000 / 60 : this . options . moveTime ;
Foundation . Move ( moveTime , $hndl , function ( ) {
//adjusting the left/top property of the handle, based on the percentage calculated above
$hndl . css ( lOrT , movement + '%' ) ;
if ( ! _this . options . doubleSided ) {
//if single-handled, a simple method to expand the fill bar
_this . $fill . css ( hOrW , pctOfBar * 100 + '%' ) ;
} else {
//otherwise, use the css object we created above
_this . $fill . css ( css ) ;
}
} ) ;
/ * *
* Fires when the value has not been change for a given time .
* @ event Slider # changed
* /
clearTimeout ( _this . timeout ) ;
_this . timeout = setTimeout ( function ( ) {
_this . $element . trigger ( 'changed.zf.slider' , [ $hndl ] ) ;
} , _this . options . changedDelay ) ;
}
/ * *
* Sets the initial attribute for the slider element .
* @ function
* @ private
* @ param { Number } idx - index of the current handle / input to use .
* /
} , {
key : '_setInitAttr' ,
value : function _setInitAttr ( idx ) {
var id = this . inputs . eq ( idx ) . attr ( 'id' ) || Foundation . GetYoDigits ( 6 , 'slider' ) ;
this . inputs . eq ( idx ) . attr ( {
'id' : id ,
'max' : this . options . end ,
'min' : this . options . start ,
'step' : this . options . step
} ) ;
this . handles . eq ( idx ) . attr ( {
'role' : 'slider' ,
'aria-controls' : id ,
'aria-valuemax' : this . options . end ,
'aria-valuemin' : this . options . start ,
'aria-valuenow' : idx === 0 ? this . options . initialStart : this . options . initialEnd ,
'aria-orientation' : this . options . vertical ? 'vertical' : 'horizontal' ,
'tabindex' : 0
} ) ;
}
/ * *
* Sets the input and ` aria-valuenow ` values for the slider element .
* @ function
* @ private
* @ param { jQuery } $handle - the currently selected handle .
* @ param { Number } val - floating point of the new value .
* /
} , {
key : '_setValues' ,
value : function _setValues ( $handle , val ) {
var idx = this . options . doubleSided ? this . handles . index ( $handle ) : 0 ;
this . inputs . eq ( idx ) . val ( val ) ;
$handle . attr ( 'aria-valuenow' , val ) ;
}
/ * *
* Handles events on the slider element .
* Calculates the new location of the current handle .
* If there are two handles and the bar was clicked , it determines which handle to move .
* @ function
* @ private
* @ param { Object } e - the ` event ` object passed from the listener .
* @ param { jQuery } $handle - the current handle to calculate for , if selected .
* @ param { Number } val - floating point number for the new value of the slider .
* TODO clean this up , there ' s a lot of repeated code between this and the _setHandlePos fn .
* /
} , {
key : '_handleEvent' ,
value : function _handleEvent ( e , $handle , val ) {
var value , hasVal ;
if ( ! val ) {
//click or drag events
e . preventDefault ( ) ;
var _this = this ,
vertical = this . options . vertical ,
param = vertical ? 'height' : 'width' ,
direction = vertical ? 'top' : 'left' ,
eventOffset = vertical ? e . pageY : e . pageX ,
halfOfHandle = this . $handle [ 0 ] . getBoundingClientRect ( ) [ param ] / 2 ,
barDim = this . $element [ 0 ] . getBoundingClientRect ( ) [ param ] ,
windowScroll = vertical ? $ ( window ) . scrollTop ( ) : $ ( window ) . scrollLeft ( ) ;
var elemOffset = this . $element . offset ( ) [ direction ] ;
// touch events emulated by the touch util give position relative to screen, add window.scroll to event coordinates...
// best way to guess this is simulated is if clientY == pageY
if ( e . clientY === e . pageY ) {
eventOffset = eventOffset + windowScroll ;
}
var eventFromBar = eventOffset - elemOffset ;
var barXY ;
if ( eventFromBar < 0 ) {
barXY = 0 ;
} else if ( eventFromBar > barDim ) {
barXY = barDim ;
} else {
barXY = eventFromBar ;
}
offsetPct = percent ( barXY , barDim ) ;
value = ( this . options . end - this . options . start ) * offsetPct + this . options . start ;
// turn everything around for RTL, yay math!
if ( Foundation . rtl ( ) && ! this . options . vertical ) {
value = this . options . end - value ;
}
value = _this . _adjustValue ( null , value ) ;
//boolean flag for the setHandlePos fn, specifically for vertical sliders
hasVal = false ;
if ( ! $handle ) {
//figure out which handle it is, pass it to the next function.
var firstHndlPos = absPosition ( this . $handle , direction , barXY , param ) ,
secndHndlPos = absPosition ( this . $handle2 , direction , barXY , param ) ;
$handle = firstHndlPos <= secndHndlPos ? this . $handle : this . $handle2 ;
}
} else {
//change event on input
value = this . _adjustValue ( null , val ) ;
hasVal = true ;
}
this . _setHandlePos ( $handle , value , hasVal ) ;
}
/ * *
* Adjustes value for handle in regard to step value . returns adjusted value
* @ function
* @ private
* @ param { jQuery } $handle - the selected handle .
* @ param { Number } value - value to adjust . used if $handle is falsy
* /
} , {
key : '_adjustValue' ,
value : function _adjustValue ( $handle , value ) {
var val ,
step = this . options . step ,
div = parseFloat ( step / 2 ) ,
left ,
prev _val ,
next _val ;
if ( ! ! $handle ) {
val = parseFloat ( $handle . attr ( 'aria-valuenow' ) ) ;
} else {
val = value ;
}
left = val % step ;
prev _val = val - left ;
next _val = prev _val + step ;
if ( left === 0 ) {
return val ;
}
val = val >= prev _val + div ? next _val : prev _val ;
return val ;
}
/ * *
* Adds event listeners to the slider elements .
* @ function
* @ private
* @ param { jQuery } $handle - the current handle to apply listeners to .
* /
} , {
key : '_events' ,
value : function _events ( $handle ) {
var _this = this ,
curHandle ,
timer ;
this . inputs . off ( 'change.zf.slider' ) . on ( 'change.zf.slider' , function ( e ) {
var idx = _this . inputs . index ( $ ( this ) ) ;
_this . _handleEvent ( e , _this . handles . eq ( idx ) , $ ( this ) . val ( ) ) ;
} ) ;
if ( this . options . clickSelect ) {
this . $element . off ( 'click.zf.slider' ) . on ( 'click.zf.slider' , function ( e ) {
if ( _this . $element . data ( 'dragging' ) ) {
return false ;
}
if ( ! $ ( e . target ) . is ( '[data-slider-handle]' ) ) {
if ( _this . options . doubleSided ) {
_this . _handleEvent ( e ) ;
} else {
_this . _handleEvent ( e , _this . $handle ) ;
}
}
} ) ;
}
if ( this . options . draggable ) {
this . handles . addTouch ( ) ;
var $body = $ ( 'body' ) ;
$handle . off ( 'mousedown.zf.slider' ) . on ( 'mousedown.zf.slider' , function ( e ) {
$handle . addClass ( 'is-dragging' ) ;
_this . $fill . addClass ( 'is-dragging' ) ; //
_this . $element . data ( 'dragging' , true ) ;
curHandle = $ ( e . currentTarget ) ;
$body . on ( 'mousemove.zf.slider' , function ( e ) {
e . preventDefault ( ) ;
_this . _handleEvent ( e , curHandle ) ;
} ) . on ( 'mouseup.zf.slider' , function ( e ) {
_this . _handleEvent ( e , curHandle ) ;
$handle . removeClass ( 'is-dragging' ) ;
_this . $fill . removeClass ( 'is-dragging' ) ;
_this . $element . data ( 'dragging' , false ) ;
$body . off ( 'mousemove.zf.slider mouseup.zf.slider' ) ;
} ) ;
} )
// prevent events triggered by touch
. on ( 'selectstart.zf.slider touchmove.zf.slider' , function ( e ) {
e . preventDefault ( ) ;
} ) ;
}
$handle . off ( 'keydown.zf.slider' ) . on ( 'keydown.zf.slider' , function ( e ) {
var _$handle = $ ( this ) ,
idx = _this . options . doubleSided ? _this . handles . index ( _$handle ) : 0 ,
oldValue = parseFloat ( _this . inputs . eq ( idx ) . val ( ) ) ,
newValue ;
// handle keyboard event with keyboard util
Foundation . Keyboard . handleKey ( e , 'Slider' , {
decrease : function ( ) {
newValue = oldValue - _this . options . step ;
} ,
increase : function ( ) {
newValue = oldValue + _this . options . step ;
} ,
decrease _fast : function ( ) {
newValue = oldValue - _this . options . step * 10 ;
} ,
increase _fast : function ( ) {
newValue = oldValue + _this . options . step * 10 ;
} ,
handled : function ( ) {
// only set handle pos when event was handled specially
e . preventDefault ( ) ;
_this . _setHandlePos ( _$handle , newValue , true ) ;
}
} ) ;
/*if (newValue) { / / if pressed key has special function , update value
e . preventDefault ( ) ;
_this . _setHandlePos ( _$handle , newValue ) ;
} * /
} ) ;
}
/ * *
* Destroys the slider plugin .
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . handles . off ( '.zf.slider' ) ;
this . inputs . off ( '.zf.slider' ) ;
this . $element . off ( '.zf.slider' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Slider ;
} ( ) ;
Slider . defaults = {
/ * *
* Minimum value for the slider scale .
* @ option
* @ example 0
* /
start : 0 ,
/ * *
* Maximum value for the slider scale .
* @ option
* @ example 100
* /
end : 100 ,
/ * *
* Minimum value change per change event .
* @ option
* @ example 1
* /
step : 1 ,
/ * *
* Value at which the handle / input * ( left handle / first input ) * should be set to on initialization .
* @ option
* @ example 0
* /
initialStart : 0 ,
/ * *
* Value at which the right handle / second input should be set to on initialization .
* @ option
* @ example 100
* /
initialEnd : 100 ,
/ * *
* Allows the input to be located outside the container and visible . Set to by the JS
* @ option
* @ example false
* /
binding : false ,
/ * *
* Allows the user to click / tap on the slider bar to select a value .
* @ option
* @ example true
* /
clickSelect : true ,
/ * *
* Set to true and use the ` vertical ` class to change alignment to vertical .
* @ option
* @ example false
* /
vertical : false ,
/ * *
* Allows the user to drag the slider handle ( s ) to select a value .
* @ option
* @ example true
* /
draggable : true ,
/ * *
* Disables the slider and prevents event listeners from being applied . Double checked by JS with ` disabledClass ` .
* @ option
* @ example false
* /
disabled : false ,
/ * *
* Allows the use of two handles . Double checked by the JS . Changes some logic handling .
* @ option
* @ example false
* /
doubleSided : false ,
/ * *
* Potential future feature .
* /
// steps: 100,
/ * *
* Number of decimal places the plugin should go to for floating point precision .
* @ option
* @ example 2
* /
decimal : 2 ,
/ * *
* Time delay for dragged elements .
* /
// dragDelay: 0,
/ * *
* Time , in ms , to animate the movement of a slider handle if user clicks / taps on the bar . Needs to be manually set if updating the transition time in the Sass settings .
* @ option
* @ example 200
* /
moveTime : 200 , //update this if changing the transition time in the sass
/ * *
* Class applied to disabled sliders .
* @ option
* @ example 'disabled'
* /
disabledClass : 'disabled' ,
/ * *
* Will invert the default layout for a vertical < span data - tooltip title = "who would do this???" > < / s p a n > s l i d e r .
* @ option
* @ example false
* /
invertVertical : false ,
/ * *
* Milliseconds before the ` changed.zf-slider ` event is triggered after value change .
* @ option
* @ example 500
* /
changedDelay : 500
} ;
function percent ( frac , num ) {
return frac / num ;
}
function absPosition ( $handle , dir , clickPos , param ) {
return Math . abs ( $handle . position ( ) [ dir ] + $handle [ param ] ( ) / 2 - clickPos ) ;
}
// Window exports
Foundation . plugin ( Slider , 'Slider' ) ;
} ( jQuery ) ;
//*********this is in case we go to static, absolute positions instead of dynamic positioning********
// this.setSteps(function() {
// _this._events();
// var initStart = _this.options.positions[_this.options.initialStart - 1] || null;
// var initEnd = _this.options.initialEnd ? _this.options.position[_this.options.initialEnd - 1] : null;
// if (initStart || initEnd) {
// _this._handleEvent(initStart, initEnd);
// }
// });
//***********the other part of absolute positions*************
// Slider.prototype.setSteps = function(cb) {
// var posChange = this.$element.outerWidth() / this.options.steps;
// var counter = 0
// while(counter < this.options.steps) {
// if (counter) {
// this.options.positions.push(this.options.positions[counter - 1] + posChange);
// } else {
// this.options.positions.push(posChange);
// }
// counter++;
// }
// cb();
// };
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Sticky module .
* @ module foundation . sticky
* @ requires foundation . util . triggers
* @ requires foundation . util . mediaQuery
* /
var Sticky = function ( ) {
/ * *
* Creates a new instance of a sticky thing .
* @ class
* @ param { jQuery } element - jQuery object to make sticky .
* @ param { Object } options - options object passed when creating the element programmatically .
* /
function Sticky ( element , options ) {
_classCallCheck ( this , Sticky ) ;
this . $element = element ;
this . options = $ . extend ( { } , Sticky . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Sticky' ) ;
}
/ * *
* Initializes the sticky element by adding classes , getting / setting dimensions , breakpoints and attributes
* @ function
* @ private
* /
_createClass ( Sticky , [ {
key : '_init' ,
value : function _init ( ) {
var $parent = this . $element . parent ( '[data-sticky-container]' ) ,
id = this . $element [ 0 ] . id || Foundation . GetYoDigits ( 6 , 'sticky' ) ,
_this = this ;
if ( ! $parent . length ) {
this . wasWrapped = true ;
}
this . $container = $parent . length ? $parent : $ ( this . options . container ) . wrapInner ( this . $element ) ;
this . $container . addClass ( this . options . containerClass ) ;
this . $element . addClass ( this . options . stickyClass ) . attr ( { 'data-resize' : id } ) ;
this . scrollCount = this . options . checkEvery ;
this . isStuck = false ;
$ ( window ) . one ( 'load.zf.sticky' , function ( ) {
if ( _this . options . anchor !== '' ) {
_this . $anchor = $ ( '#' + _this . options . anchor ) ;
} else {
_this . _parsePoints ( ) ;
}
_this . _setSizes ( function ( ) {
_this . _calc ( false ) ;
} ) ;
_this . _events ( id . split ( '-' ) . reverse ( ) . join ( '-' ) ) ;
} ) ;
}
/ * *
* If using multiple elements as anchors , calculates the top and bottom pixel values the sticky thing should stick and unstick on .
* @ function
* @ private
* /
} , {
key : '_parsePoints' ,
value : function _parsePoints ( ) {
var top = this . options . topAnchor == "" ? 1 : this . options . topAnchor ,
btm = this . options . btmAnchor == "" ? document . documentElement . scrollHeight : this . options . btmAnchor ,
pts = [ top , btm ] ,
breaks = { } ;
for ( var i = 0 , len = pts . length ; i < len && pts [ i ] ; i ++ ) {
var pt ;
if ( typeof pts [ i ] === 'number' ) {
pt = pts [ i ] ;
} else {
var place = pts [ i ] . split ( ':' ) ,
anchor = $ ( '#' + place [ 0 ] ) ;
pt = anchor . offset ( ) . top ;
if ( place [ 1 ] && place [ 1 ] . toLowerCase ( ) === 'bottom' ) {
pt += anchor [ 0 ] . getBoundingClientRect ( ) . height ;
}
}
breaks [ i ] = pt ;
}
this . points = breaks ;
return ;
}
/ * *
* Adds event handlers for the scrolling element .
* @ private
* @ param { String } id - psuedo - random id for unique scroll event listener .
* /
} , {
key : '_events' ,
value : function _events ( id ) {
var _this = this ,
scrollListener = this . scrollListener = 'scroll.zf.' + id ;
if ( this . isOn ) {
return ;
}
if ( this . canStick ) {
this . isOn = true ;
$ ( window ) . off ( scrollListener ) . on ( scrollListener , function ( e ) {
if ( _this . scrollCount === 0 ) {
_this . scrollCount = _this . options . checkEvery ;
_this . _setSizes ( function ( ) {
_this . _calc ( false , window . pageYOffset ) ;
} ) ;
} else {
_this . scrollCount -- ;
_this . _calc ( false , window . pageYOffset ) ;
}
} ) ;
}
this . $element . off ( 'resizeme.zf.trigger' ) . on ( 'resizeme.zf.trigger' , function ( e , el ) {
_this . _setSizes ( function ( ) {
_this . _calc ( false ) ;
if ( _this . canStick ) {
if ( ! _this . isOn ) {
_this . _events ( id ) ;
}
} else if ( _this . isOn ) {
_this . _pauseListeners ( scrollListener ) ;
}
} ) ;
} ) ;
}
/ * *
* Removes event handlers for scroll and change events on anchor .
* @ fires Sticky # pause
* @ param { String } scrollListener - unique , namespaced scroll listener attached to ` window `
* /
} , {
key : '_pauseListeners' ,
value : function _pauseListeners ( scrollListener ) {
this . isOn = false ;
$ ( window ) . off ( scrollListener ) ;
/ * *
* Fires when the plugin is paused due to resize event shrinking the view .
* @ event Sticky # pause
* @ private
* /
this . $element . trigger ( 'pause.zf.sticky' ) ;
}
/ * *
* Called on every ` scroll ` event and on ` _init `
* fires functions based on booleans and cached values
* @ param { Boolean } checkSizes - true if plugin should recalculate sizes and breakpoints .
* @ param { Number } scroll - current scroll position passed from scroll event cb function . If not passed , defaults to ` window.pageYOffset ` .
* /
} , {
key : '_calc' ,
value : function _calc ( checkSizes , scroll ) {
if ( checkSizes ) {
this . _setSizes ( ) ;
}
if ( ! this . canStick ) {
if ( this . isStuck ) {
this . _removeSticky ( true ) ;
}
return false ;
}
if ( ! scroll ) {
scroll = window . pageYOffset ;
}
if ( scroll >= this . topPoint ) {
if ( scroll <= this . bottomPoint ) {
if ( ! this . isStuck ) {
this . _setSticky ( ) ;
}
} else {
if ( this . isStuck ) {
this . _removeSticky ( false ) ;
}
}
} else {
if ( this . isStuck ) {
this . _removeSticky ( true ) ;
}
}
}
/ * *
* Causes the $element to become stuck .
* Adds ` position: fixed; ` , and helper classes .
* @ fires Sticky # stuckto
* @ function
* @ private
* /
} , {
key : '_setSticky' ,
value : function _setSticky ( ) {
var _this = this ,
stickTo = this . options . stickTo ,
mrgn = stickTo === 'top' ? 'marginTop' : 'marginBottom' ,
notStuckTo = stickTo === 'top' ? 'bottom' : 'top' ,
css = { } ;
css [ mrgn ] = this . options [ mrgn ] + 'em' ;
css [ stickTo ] = 0 ;
css [ notStuckTo ] = 'auto' ;
css [ 'left' ] = this . $container . offset ( ) . left + parseInt ( window . getComputedStyle ( this . $container [ 0 ] ) [ "padding-left" ] , 10 ) ;
this . isStuck = true ;
this . $element . removeClass ( 'is-anchored is-at-' + notStuckTo ) . addClass ( 'is-stuck is-at-' + stickTo ) . css ( css )
/ * *
* Fires when the $element has become ` position: fixed; `
* Namespaced to ` top ` or ` bottom ` , e . g . ` sticky.zf.stuckto:top `
* @ event Sticky # stuckto
* /
. trigger ( 'sticky.zf.stuckto:' + stickTo ) ;
this . $element . on ( "transitionend webkitTransitionEnd oTransitionEnd otransitionend MSTransitionEnd" , function ( ) {
_this . _setSizes ( ) ;
} ) ;
}
/ * *
* Causes the $element to become unstuck .
* Removes ` position: fixed; ` , and helper classes .
* Adds other helper classes .
* @ param { Boolean } isTop - tells the function if the $element should anchor to the top or bottom of its $anchor element .
* @ fires Sticky # unstuckfrom
* @ private
* /
} , {
key : '_removeSticky' ,
value : function _removeSticky ( isTop ) {
var stickTo = this . options . stickTo ,
stickToTop = stickTo === 'top' ,
css = { } ,
anchorPt = ( this . points ? this . points [ 1 ] - this . points [ 0 ] : this . anchorHeight ) - this . elemHeight ,
mrgn = stickToTop ? 'marginTop' : 'marginBottom' ,
notStuckTo = stickToTop ? 'bottom' : 'top' ,
topOrBottom = isTop ? 'top' : 'bottom' ;
css [ mrgn ] = 0 ;
css [ 'bottom' ] = 'auto' ;
if ( isTop ) {
css [ 'top' ] = 0 ;
} else {
css [ 'top' ] = anchorPt ;
}
css [ 'left' ] = '' ;
this . isStuck = false ;
this . $element . removeClass ( 'is-stuck is-at-' + stickTo ) . addClass ( 'is-anchored is-at-' + topOrBottom ) . css ( css )
/ * *
* Fires when the $element has become anchored .
* Namespaced to ` top ` or ` bottom ` , e . g . ` sticky.zf.unstuckfrom:bottom `
* @ event Sticky # unstuckfrom
* /
. trigger ( 'sticky.zf.unstuckfrom:' + topOrBottom ) ;
}
/ * *
* Sets the $element and $container sizes for plugin .
* Calls ` _setBreakPoints ` .
* @ param { Function } cb - optional callback function to fire on completion of ` _setBreakPoints ` .
* @ private
* /
} , {
key : '_setSizes' ,
value : function _setSizes ( cb ) {
this . canStick = Foundation . MediaQuery . atLeast ( this . options . stickyOn ) ;
if ( ! this . canStick ) {
cb ( ) ;
}
var _this = this ,
newElemWidth = this . $container [ 0 ] . getBoundingClientRect ( ) . width ,
comp = window . getComputedStyle ( this . $container [ 0 ] ) ,
pdng = parseInt ( comp [ 'padding-right' ] , 10 ) ;
if ( this . $anchor && this . $anchor . length ) {
this . anchorHeight = this . $anchor [ 0 ] . getBoundingClientRect ( ) . height ;
} else {
this . _parsePoints ( ) ;
}
this . $element . css ( {
'max-width' : newElemWidth - pdng + 'px'
} ) ;
var newContainerHeight = this . $element [ 0 ] . getBoundingClientRect ( ) . height || this . containerHeight ;
if ( this . $element . css ( "display" ) == "none" ) {
newContainerHeight = 0 ;
}
this . containerHeight = newContainerHeight ;
this . $container . css ( {
height : newContainerHeight
} ) ;
this . elemHeight = newContainerHeight ;
if ( this . isStuck ) {
this . $element . css ( { "left" : this . $container . offset ( ) . left + parseInt ( comp [ 'padding-left' ] , 10 ) } ) ;
}
this . _setBreakPoints ( newContainerHeight , function ( ) {
if ( cb ) {
cb ( ) ;
}
} ) ;
}
/ * *
* Sets the upper and lower breakpoints for the element to become sticky / unsticky .
* @ param { Number } elemHeight - px value for sticky . $element height , calculated by ` _setSizes ` .
* @ param { Function } cb - optional callback function to be called on completion .
* @ private
* /
} , {
key : '_setBreakPoints' ,
value : function _setBreakPoints ( elemHeight , cb ) {
if ( ! this . canStick ) {
if ( cb ) {
cb ( ) ;
} else {
return false ;
}
}
var mTop = emCalc ( this . options . marginTop ) ,
mBtm = emCalc ( this . options . marginBottom ) ,
topPoint = this . points ? this . points [ 0 ] : this . $anchor . offset ( ) . top ,
bottomPoint = this . points ? this . points [ 1 ] : topPoint + this . anchorHeight ,
// topPoint = this.$anchor.offset().top || this.points[0],
// bottomPoint = topPoint + this.anchorHeight || this.points[1],
winHeight = window . innerHeight ;
if ( this . options . stickTo === 'top' ) {
topPoint -= mTop ;
bottomPoint -= elemHeight + mTop ;
} else if ( this . options . stickTo === 'bottom' ) {
topPoint -= winHeight - ( elemHeight + mBtm ) ;
bottomPoint -= winHeight - mBtm ;
} else {
//this would be the stickTo: both option... tricky
}
this . topPoint = topPoint ;
this . bottomPoint = bottomPoint ;
if ( cb ) {
cb ( ) ;
}
}
/ * *
* Destroys the current sticky element .
* Resets the element to the top position first .
* Removes event listeners , JS - added css properties and classes , and unwraps the $element if the JS added the $container .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . _removeSticky ( true ) ;
this . $element . removeClass ( this . options . stickyClass + ' is-anchored is-at-top' ) . css ( {
height : '' ,
top : '' ,
bottom : '' ,
'max-width' : ''
} ) . off ( 'resizeme.zf.trigger' ) ;
if ( this . $anchor && this . $anchor . length ) {
this . $anchor . off ( 'change.zf.sticky' ) ;
}
$ ( window ) . off ( this . scrollListener ) ;
if ( this . wasWrapped ) {
this . $element . unwrap ( ) ;
} else {
this . $container . removeClass ( this . options . containerClass ) . css ( {
height : ''
} ) ;
}
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Sticky ;
} ( ) ;
Sticky . defaults = {
/ * *
* Customizable container template . Add your own classes for styling and sizing .
* @ option
* @ example '<div data-sticky-container class="small-6 columns"></div>'
* /
container : '<div data-sticky-container></div>' ,
/ * *
* Location in the view the element sticks to .
* @ option
* @ example 'top'
* /
stickTo : 'top' ,
/ * *
* If anchored to a single element , the id of that element .
* @ option
* @ example 'exampleId'
* /
anchor : '' ,
/ * *
* If using more than one element as anchor points , the id of the top anchor .
* @ option
* @ example 'exampleId:top'
* /
topAnchor : '' ,
/ * *
* If using more than one element as anchor points , the id of the bottom anchor .
* @ option
* @ example 'exampleId:bottom'
* /
btmAnchor : '' ,
/ * *
* Margin , in ` em ` ' s to apply to the top of the element when it becomes sticky .
* @ option
* @ example 1
* /
marginTop : 1 ,
/ * *
* Margin , in ` em ` ' s to apply to the bottom of the element when it becomes sticky .
* @ option
* @ example 1
* /
marginBottom : 1 ,
/ * *
* Breakpoint string that is the minimum screen size an element should become sticky .
* @ option
* @ example 'medium'
* /
stickyOn : 'medium' ,
/ * *
* Class applied to sticky element , and removed on destruction . Foundation defaults to ` sticky ` .
* @ option
* @ example 'sticky'
* /
stickyClass : 'sticky' ,
/ * *
* Class applied to sticky container . Foundation defaults to ` sticky-container ` .
* @ option
* @ example 'sticky-container'
* /
containerClass : 'sticky-container' ,
/ * *
* Number of scroll events between the plugin ' s recalculating sticky points . Setting it to ` 0 ` will cause it to recalc every scroll event , setting it to ` -1 ` will prevent recalc on scroll .
* @ option
* @ example 50
* /
checkEvery : - 1
} ;
/ * *
* Helper function to calculate em values
* @ param Number { em } - number of em ' s to calculate into pixels
* /
function emCalc ( em ) {
return parseInt ( window . getComputedStyle ( document . body , null ) . fontSize , 10 ) * em ;
}
// Window exports
Foundation . plugin ( Sticky , 'Sticky' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Tabs module .
* @ module foundation . tabs
* @ requires foundation . util . keyboard
* @ requires foundation . util . timerAndImageLoader if tabs contain images
* /
var Tabs = function ( ) {
/ * *
* Creates a new instance of tabs .
* @ class
* @ fires Tabs # init
* @ param { jQuery } element - jQuery object to make into tabs .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Tabs ( element , options ) {
_classCallCheck ( this , Tabs ) ;
this . $element = element ;
this . options = $ . extend ( { } , Tabs . defaults , this . $element . data ( ) , options ) ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Tabs' ) ;
Foundation . Keyboard . register ( 'Tabs' , {
'ENTER' : 'open' ,
'SPACE' : 'open' ,
'ARROW_RIGHT' : 'next' ,
'ARROW_UP' : 'previous' ,
'ARROW_DOWN' : 'next' ,
'ARROW_LEFT' : 'previous'
// 'TAB': 'next',
// 'SHIFT_TAB': 'previous'
} ) ;
}
/ * *
* Initializes the tabs by showing and focusing ( if autoFocus = true ) the preset active tab .
* @ private
* /
_createClass ( Tabs , [ {
key : '_init' ,
value : function _init ( ) {
var _this = this ;
this . $tabTitles = this . $element . find ( '.' + this . options . linkClass ) ;
this . $tabContent = $ ( '[data-tabs-content="' + this . $element [ 0 ] . id + '"]' ) ;
this . $tabTitles . each ( function ( ) {
var $elem = $ ( this ) ,
$link = $elem . find ( 'a' ) ,
isActive = $elem . hasClass ( 'is-active' ) ,
hash = $link [ 0 ] . hash . slice ( 1 ) ,
linkId = $link [ 0 ] . id ? $link [ 0 ] . id : hash + '-label' ,
$tabContent = $ ( '#' + hash ) ;
$elem . attr ( { 'role' : 'presentation' } ) ;
$link . attr ( {
'role' : 'tab' ,
'aria-controls' : hash ,
'aria-selected' : isActive ,
'id' : linkId
} ) ;
$tabContent . attr ( {
'role' : 'tabpanel' ,
'aria-hidden' : ! isActive ,
'aria-labelledby' : linkId
} ) ;
if ( isActive && _this . options . autoFocus ) {
$link . focus ( ) ;
}
} ) ;
if ( this . options . matchHeight ) {
var $images = this . $tabContent . find ( 'img' ) ;
if ( $images . length ) {
Foundation . onImagesLoaded ( $images , this . _setHeight . bind ( this ) ) ;
} else {
this . _setHeight ( ) ;
}
}
this . _events ( ) ;
}
/ * *
* Adds event handlers for items within the tabs .
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
this . _addKeyHandler ( ) ;
this . _addClickHandler ( ) ;
this . _setHeightMqHandler = null ;
if ( this . options . matchHeight ) {
this . _setHeightMqHandler = this . _setHeight . bind ( this ) ;
$ ( window ) . on ( 'changed.zf.mediaquery' , this . _setHeightMqHandler ) ;
}
}
/ * *
* Adds click handlers for items within the tabs .
* @ private
* /
} , {
key : '_addClickHandler' ,
value : function _addClickHandler ( ) {
var _this = this ;
this . $element . off ( 'click.zf.tabs' ) . on ( 'click.zf.tabs' , '.' + this . options . linkClass , function ( e ) {
e . preventDefault ( ) ;
e . stopPropagation ( ) ;
if ( $ ( this ) . hasClass ( 'is-active' ) ) {
return ;
}
_this . _handleTabChange ( $ ( this ) ) ;
} ) ;
}
/ * *
* Adds keyboard event handlers for items within the tabs .
* @ private
* /
} , {
key : '_addKeyHandler' ,
value : function _addKeyHandler ( ) {
var _this = this ;
var $firstTab = _this . $element . find ( 'li:first-of-type' ) ;
var $lastTab = _this . $element . find ( 'li:last-of-type' ) ;
this . $tabTitles . off ( 'keydown.zf.tabs' ) . on ( 'keydown.zf.tabs' , function ( e ) {
if ( e . which === 9 ) return ;
var $element = $ ( this ) ,
$elements = $element . parent ( 'ul' ) . children ( 'li' ) ,
$prevElement ,
$nextElement ;
$elements . each ( function ( i ) {
if ( $ ( this ) . is ( $element ) ) {
if ( _this . options . wrapOnKeys ) {
$prevElement = i === 0 ? $elements . last ( ) : $elements . eq ( i - 1 ) ;
$nextElement = i === $elements . length - 1 ? $elements . first ( ) : $elements . eq ( i + 1 ) ;
} else {
$prevElement = $elements . eq ( Math . max ( 0 , i - 1 ) ) ;
$nextElement = $elements . eq ( Math . min ( i + 1 , $elements . length - 1 ) ) ;
}
return ;
}
} ) ;
// handle keyboard event with keyboard util
Foundation . Keyboard . handleKey ( e , 'Tabs' , {
open : function ( ) {
$element . find ( '[role="tab"]' ) . focus ( ) ;
_this . _handleTabChange ( $element ) ;
} ,
previous : function ( ) {
$prevElement . find ( '[role="tab"]' ) . focus ( ) ;
_this . _handleTabChange ( $prevElement ) ;
} ,
next : function ( ) {
$nextElement . find ( '[role="tab"]' ) . focus ( ) ;
_this . _handleTabChange ( $nextElement ) ;
} ,
handled : function ( ) {
e . stopPropagation ( ) ;
e . preventDefault ( ) ;
}
} ) ;
} ) ;
}
/ * *
* Opens the tab ` $ targetContent ` defined by ` $ target ` .
* @ param { jQuery } $target - Tab to open .
* @ fires Tabs # change
* @ function
* /
} , {
key : '_handleTabChange' ,
value : function _handleTabChange ( $target ) {
var $tabLink = $target . find ( '[role="tab"]' ) ,
hash = $tabLink [ 0 ] . hash ,
$targetContent = this . $tabContent . find ( hash ) ,
$oldTab = this . $element . find ( '.' + this . options . linkClass + '.is-active' ) . removeClass ( 'is-active' ) . find ( '[role="tab"]' ) . attr ( { 'aria-selected' : 'false' } ) ;
$ ( '#' + $oldTab . attr ( 'aria-controls' ) ) . removeClass ( 'is-active' ) . attr ( { 'aria-hidden' : 'true' } ) ;
$target . addClass ( 'is-active' ) ;
$tabLink . attr ( { 'aria-selected' : 'true' } ) ;
$targetContent . addClass ( 'is-active' ) . attr ( { 'aria-hidden' : 'false' } ) ;
/ * *
* Fires when the plugin has successfully changed tabs .
* @ event Tabs # change
* /
this . $element . trigger ( 'change.zf.tabs' , [ $target ] ) ;
}
/ * *
* Public method for selecting a content pane to display .
* @ param { jQuery | String } elem - jQuery object or string of the id of the pane to display .
* @ function
* /
} , {
key : 'selectTab' ,
value : function selectTab ( elem ) {
var idStr ;
if ( typeof elem === 'object' ) {
idStr = elem [ 0 ] . id ;
} else {
idStr = elem ;
}
if ( idStr . indexOf ( '#' ) < 0 ) {
idStr = '#' + idStr ;
}
var $target = this . $tabTitles . find ( '[href="' + idStr + '"]' ) . parent ( '.' + this . options . linkClass ) ;
this . _handleTabChange ( $target ) ;
}
} , {
key : '_setHeight' ,
/ * *
* Sets the height of each panel to the height of the tallest panel .
* If enabled in options , gets called on media query change .
* If loading content via external source , can be called directly or with _reflow .
* @ function
* @ private
* /
value : function _setHeight ( ) {
var max = 0 ;
this . $tabContent . find ( '.' + this . options . panelClass ) . css ( 'height' , '' ) . each ( function ( ) {
var panel = $ ( this ) ,
isActive = panel . hasClass ( 'is-active' ) ;
if ( ! isActive ) {
panel . css ( { 'visibility' : 'hidden' , 'display' : 'block' } ) ;
}
var temp = this . getBoundingClientRect ( ) . height ;
if ( ! isActive ) {
panel . css ( {
'visibility' : '' ,
'display' : ''
} ) ;
}
max = temp > max ? temp : max ;
} ) . css ( 'height' , max + 'px' ) ;
}
/ * *
* Destroys an instance of an tabs .
* @ fires Tabs # destroyed
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . find ( '.' + this . options . linkClass ) . off ( '.zf.tabs' ) . hide ( ) . end ( ) . find ( '.' + this . options . panelClass ) . hide ( ) ;
if ( this . options . matchHeight ) {
if ( this . _setHeightMqHandler != null ) {
$ ( window ) . off ( 'changed.zf.mediaquery' , this . _setHeightMqHandler ) ;
}
}
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Tabs ;
} ( ) ;
Tabs . defaults = {
/ * *
* Allows the window to scroll to content of active pane on load if set to true .
* @ option
* @ example false
* /
autoFocus : false ,
/ * *
* Allows keyboard input to 'wrap' around the tab links .
* @ option
* @ example true
* /
wrapOnKeys : true ,
/ * *
* Allows the tab content panes to match heights if set to true .
* @ option
* @ example false
* /
matchHeight : false ,
/ * *
* Class applied to ` li ` ' s in tab link list .
* @ option
* @ example 'tabs-title'
* /
linkClass : 'tabs-title' ,
/ * *
* Class applied to the content containers .
* @ option
* @ example 'tabs-panel'
* /
panelClass : 'tabs-panel'
} ;
function checkClass ( $elem ) {
return $elem . hasClass ( 'is-active' ) ;
}
// Window exports
Foundation . plugin ( Tabs , 'Tabs' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Toggler module .
* @ module foundation . toggler
* @ requires foundation . util . motion
* @ requires foundation . util . triggers
* /
var Toggler = function ( ) {
/ * *
* Creates a new instance of Toggler .
* @ class
* @ fires Toggler # init
* @ param { Object } element - jQuery object to add the trigger to .
* @ param { Object } options - Overrides to the default plugin settings .
* /
function Toggler ( element , options ) {
_classCallCheck ( this , Toggler ) ;
this . $element = element ;
this . options = $ . extend ( { } , Toggler . defaults , element . data ( ) , options ) ;
this . className = '' ;
this . _init ( ) ;
this . _events ( ) ;
Foundation . registerPlugin ( this , 'Toggler' ) ;
}
/ * *
* Initializes the Toggler plugin by parsing the toggle class from data - toggler , or animation classes from data - animate .
* @ function
* @ private
* /
_createClass ( Toggler , [ {
key : '_init' ,
value : function _init ( ) {
var input ;
// Parse animation classes if they were set
if ( this . options . animate ) {
input = this . options . animate . split ( ' ' ) ;
this . animationIn = input [ 0 ] ;
this . animationOut = input [ 1 ] || null ;
}
// Otherwise, parse toggle class
else {
input = this . $element . data ( 'toggler' ) ;
// Allow for a . at the beginning of the string
this . className = input [ 0 ] === '.' ? input . slice ( 1 ) : input ;
}
// Add ARIA attributes to triggers
var id = this . $element [ 0 ] . id ;
$ ( '[data-open="' + id + '"], [data-close="' + id + '"], [data-toggle="' + id + '"]' ) . attr ( 'aria-controls' , id ) ;
// If the target is hidden, add aria-hidden
this . $element . attr ( 'aria-expanded' , this . $element . is ( ':hidden' ) ? false : true ) ;
}
/ * *
* Initializes events for the toggle trigger .
* @ function
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
this . $element . off ( 'toggle.zf.trigger' ) . on ( 'toggle.zf.trigger' , this . toggle . bind ( this ) ) ;
}
/ * *
* Toggles the target class on the target element . An event is fired from the original trigger depending on if the resultant state was "on" or "off" .
* @ function
* @ fires Toggler # on
* @ fires Toggler # off
* /
} , {
key : 'toggle' ,
value : function toggle ( ) {
this [ this . options . animate ? '_toggleAnimate' : '_toggleClass' ] ( ) ;
}
} , {
key : '_toggleClass' ,
value : function _toggleClass ( ) {
this . $element . toggleClass ( this . className ) ;
var isOn = this . $element . hasClass ( this . className ) ;
if ( isOn ) {
/ * *
* Fires if the target element has the class after a toggle .
* @ event Toggler # on
* /
this . $element . trigger ( 'on.zf.toggler' ) ;
} else {
/ * *
* Fires if the target element does not have the class after a toggle .
* @ event Toggler # off
* /
this . $element . trigger ( 'off.zf.toggler' ) ;
}
this . _updateARIA ( isOn ) ;
}
} , {
key : '_toggleAnimate' ,
value : function _toggleAnimate ( ) {
var _this = this ;
if ( this . $element . is ( ':hidden' ) ) {
Foundation . Motion . animateIn ( this . $element , this . animationIn , function ( ) {
_this . _updateARIA ( true ) ;
this . trigger ( 'on.zf.toggler' ) ;
} ) ;
} else {
Foundation . Motion . animateOut ( this . $element , this . animationOut , function ( ) {
_this . _updateARIA ( false ) ;
this . trigger ( 'off.zf.toggler' ) ;
} ) ;
}
}
} , {
key : '_updateARIA' ,
value : function _updateARIA ( isOn ) {
this . $element . attr ( 'aria-expanded' , isOn ? true : false ) ;
}
/ * *
* Destroys the instance of Toggler on the element .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . off ( '.zf.toggler' ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Toggler ;
} ( ) ;
Toggler . defaults = {
/ * *
* Tells the plugin if the element should animated when toggled .
* @ option
* @ example false
* /
animate : false
} ;
// Window exports
Foundation . plugin ( Toggler , 'Toggler' ) ;
} ( jQuery ) ;
'use strict' ;
var _createClass = function ( ) { function defineProperties ( target , props ) { for ( var i = 0 ; i < props . length ; i ++ ) { var descriptor = props [ i ] ; descriptor . enumerable = descriptor . enumerable || false ; descriptor . configurable = true ; if ( "value" in descriptor ) descriptor . writable = true ; Object . defineProperty ( target , descriptor . key , descriptor ) ; } } return function ( Constructor , protoProps , staticProps ) { if ( protoProps ) defineProperties ( Constructor . prototype , protoProps ) ; if ( staticProps ) defineProperties ( Constructor , staticProps ) ; return Constructor ; } ; } ( ) ;
function _classCallCheck ( instance , Constructor ) { if ( ! ( instance instanceof Constructor ) ) { throw new TypeError ( "Cannot call a class as a function" ) ; } }
! function ( $ ) {
/ * *
* Tooltip module .
* @ module foundation . tooltip
* @ requires foundation . util . box
* @ requires foundation . util . triggers
* /
var Tooltip = function ( ) {
/ * *
* Creates a new instance of a Tooltip .
* @ class
* @ fires Tooltip # init
* @ param { jQuery } element - jQuery object to attach a tooltip to .
* @ param { Object } options - object to extend the default configuration .
* /
function Tooltip ( element , options ) {
_classCallCheck ( this , Tooltip ) ;
this . $element = element ;
this . options = $ . extend ( { } , Tooltip . defaults , this . $element . data ( ) , options ) ;
this . isActive = false ;
this . isClick = false ;
this . _init ( ) ;
Foundation . registerPlugin ( this , 'Tooltip' ) ;
}
/ * *
* Initializes the tooltip by setting the creating the tip element , adding it ' s text , setting private variables and setting attributes on the anchor .
* @ private
* /
_createClass ( Tooltip , [ {
key : '_init' ,
value : function _init ( ) {
var elemId = this . $element . attr ( 'aria-describedby' ) || Foundation . GetYoDigits ( 6 , 'tooltip' ) ;
this . options . positionClass = this . options . positionClass || this . _getPositionClass ( this . $element ) ;
this . options . tipText = this . options . tipText || this . $element . attr ( 'title' ) ;
this . template = this . options . template ? $ ( this . options . template ) : this . _buildTemplate ( elemId ) ;
this . template . appendTo ( document . body ) . text ( this . options . tipText ) . hide ( ) ;
this . $element . attr ( {
'title' : '' ,
'aria-describedby' : elemId ,
'data-yeti-box' : elemId ,
'data-toggle' : elemId ,
'data-resize' : elemId
} ) . addClass ( this . triggerClass ) ;
//helper variables to track movement on collisions
this . usedPositions = [ ] ;
this . counter = 4 ;
this . classChanged = false ;
this . _events ( ) ;
}
/ * *
* Grabs the current positioning class , if present , and returns the value or an empty string .
* @ private
* /
} , {
key : '_getPositionClass' ,
value : function _getPositionClass ( element ) {
if ( ! element ) {
return '' ;
}
// var position = element.attr('class').match(/top|left|right/g);
var position = element [ 0 ] . className . match ( /\b(top|left|right)\b/g ) ;
position = position ? position [ 0 ] : '' ;
return position ;
}
} , {
key : '_buildTemplate' ,
/ * *
* builds the tooltip element , adds attributes , and returns the template .
* @ private
* /
value : function _buildTemplate ( id ) {
var templateClasses = ( this . options . tooltipClass + ' ' + this . options . positionClass + ' ' + this . options . templateClasses ) . trim ( ) ;
var $template = $ ( '<div></div>' ) . addClass ( templateClasses ) . attr ( {
'role' : 'tooltip' ,
'aria-hidden' : true ,
'data-is-active' : false ,
'data-is-focus' : false ,
'id' : id
} ) ;
return $template ;
}
/ * *
* Function that gets called if a collision event is detected .
* @ param { String } position - positioning class to try
* @ private
* /
} , {
key : '_reposition' ,
value : function _reposition ( position ) {
this . usedPositions . push ( position ? position : 'bottom' ) ;
//default, try switching to opposite side
if ( ! position && this . usedPositions . indexOf ( 'top' ) < 0 ) {
this . template . addClass ( 'top' ) ;
} else if ( position === 'top' && this . usedPositions . indexOf ( 'bottom' ) < 0 ) {
this . template . removeClass ( position ) ;
} else if ( position === 'left' && this . usedPositions . indexOf ( 'right' ) < 0 ) {
this . template . removeClass ( position ) . addClass ( 'right' ) ;
} else if ( position === 'right' && this . usedPositions . indexOf ( 'left' ) < 0 ) {
this . template . removeClass ( position ) . addClass ( 'left' ) ;
}
//if default change didn't work, try bottom or left first
else if ( ! position && this . usedPositions . indexOf ( 'top' ) > - 1 && this . usedPositions . indexOf ( 'left' ) < 0 ) {
this . template . addClass ( 'left' ) ;
} else if ( position === 'top' && this . usedPositions . indexOf ( 'bottom' ) > - 1 && this . usedPositions . indexOf ( 'left' ) < 0 ) {
this . template . removeClass ( position ) . addClass ( 'left' ) ;
} else if ( position === 'left' && this . usedPositions . indexOf ( 'right' ) > - 1 && this . usedPositions . indexOf ( 'bottom' ) < 0 ) {
this . template . removeClass ( position ) ;
} else if ( position === 'right' && this . usedPositions . indexOf ( 'left' ) > - 1 && this . usedPositions . indexOf ( 'bottom' ) < 0 ) {
this . template . removeClass ( position ) ;
}
//if nothing cleared, set to bottom
else {
this . template . removeClass ( position ) ;
}
this . classChanged = true ;
this . counter -- ;
}
/ * *
* sets the position class of an element and recursively calls itself until there are no more possible positions to attempt , or the tooltip element is no longer colliding .
* if the tooltip is larger than the screen width , default to full width - any user selected margin
* @ private
* /
} , {
key : '_setPosition' ,
value : function _setPosition ( ) {
var position = this . _getPositionClass ( this . template ) ,
$tipDims = Foundation . Box . GetDimensions ( this . template ) ,
$anchorDims = Foundation . Box . GetDimensions ( this . $element ) ,
direction = position === 'left' ? 'left' : position === 'right' ? 'left' : 'top' ,
param = direction === 'top' ? 'height' : 'width' ,
offset = param === 'height' ? this . options . vOffset : this . options . hOffset ,
_this = this ;
if ( $tipDims . width >= $tipDims . windowDims . width || ! this . counter && ! Foundation . Box . ImNotTouchingYou ( this . template ) ) {
this . template . offset ( Foundation . Box . GetOffsets ( this . template , this . $element , 'center bottom' , this . options . vOffset , this . options . hOffset , true ) ) . css ( {
// this.$element.offset(Foundation.GetOffsets(this.template, this.$element, 'center bottom', this.options.vOffset, this.options.hOffset, true)).css({
'width' : $anchorDims . windowDims . width - this . options . hOffset * 2 ,
'height' : 'auto'
} ) ;
return false ;
}
this . template . offset ( Foundation . Box . GetOffsets ( this . template , this . $element , 'center ' + ( position || 'bottom' ) , this . options . vOffset , this . options . hOffset ) ) ;
while ( ! Foundation . Box . ImNotTouchingYou ( this . template ) && this . counter ) {
this . _reposition ( position ) ;
this . _setPosition ( ) ;
}
}
/ * *
* reveals the tooltip , and fires an event to close any other open tooltips on the page
* @ fires Tooltip # closeme
* @ fires Tooltip # show
* @ function
* /
} , {
key : 'show' ,
value : function show ( ) {
if ( this . options . showOn !== 'all' && ! Foundation . MediaQuery . atLeast ( this . options . showOn ) ) {
// console.error('The screen is too small to display this tooltip');
return false ;
}
var _this = this ;
this . template . css ( 'visibility' , 'hidden' ) . show ( ) ;
this . _setPosition ( ) ;
/ * *
* Fires to close all other open tooltips on the page
* @ event Closeme # tooltip
* /
this . $element . trigger ( 'closeme.zf.tooltip' , this . template . attr ( 'id' ) ) ;
this . template . attr ( {
'data-is-active' : true ,
'aria-hidden' : false
} ) ;
_this . isActive = true ;
// console.log(this.template);
this . template . stop ( ) . hide ( ) . css ( 'visibility' , '' ) . fadeIn ( this . options . fadeInDuration , function ( ) {
//maybe do stuff?
} ) ;
/ * *
* Fires when the tooltip is shown
* @ event Tooltip # show
* /
this . $element . trigger ( 'show.zf.tooltip' ) ;
}
/ * *
* Hides the current tooltip , and resets the positioning class if it was changed due to collision
* @ fires Tooltip # hide
* @ function
* /
} , {
key : 'hide' ,
value : function hide ( ) {
// console.log('hiding', this.$element.data('yeti-box'));
var _this = this ;
this . template . stop ( ) . attr ( {
'aria-hidden' : true ,
'data-is-active' : false
} ) . fadeOut ( this . options . fadeOutDuration , function ( ) {
_this . isActive = false ;
_this . isClick = false ;
if ( _this . classChanged ) {
_this . template . removeClass ( _this . _getPositionClass ( _this . template ) ) . addClass ( _this . options . positionClass ) ;
_this . usedPositions = [ ] ;
_this . counter = 4 ;
_this . classChanged = false ;
}
} ) ;
/ * *
* fires when the tooltip is hidden
* @ event Tooltip # hide
* /
this . $element . trigger ( 'hide.zf.tooltip' ) ;
}
/ * *
* adds event listeners for the tooltip and its anchor
* TODO combine some of the listeners like focus and mouseenter , etc .
* @ private
* /
} , {
key : '_events' ,
value : function _events ( ) {
var _this = this ;
var $template = this . template ;
var isFocus = false ;
if ( ! this . options . disableHover ) {
this . $element . on ( 'mouseenter.zf.tooltip' , function ( e ) {
if ( ! _this . isActive ) {
_this . timeout = setTimeout ( function ( ) {
_this . show ( ) ;
} , _this . options . hoverDelay ) ;
}
} ) . on ( 'mouseleave.zf.tooltip' , function ( e ) {
clearTimeout ( _this . timeout ) ;
if ( ! isFocus || _this . isClick && ! _this . options . clickOpen ) {
_this . hide ( ) ;
}
} ) ;
}
if ( this . options . clickOpen ) {
this . $element . on ( 'mousedown.zf.tooltip' , function ( e ) {
e . stopImmediatePropagation ( ) ;
if ( _this . isClick ) {
//_this.hide();
// _this.isClick = false;
} else {
_this . isClick = true ;
if ( ( _this . options . disableHover || ! _this . $element . attr ( 'tabindex' ) ) && ! _this . isActive ) {
_this . show ( ) ;
}
}
} ) ;
} else {
this . $element . on ( 'mousedown.zf.tooltip' , function ( e ) {
e . stopImmediatePropagation ( ) ;
_this . isClick = true ;
} ) ;
}
if ( ! this . options . disableForTouch ) {
this . $element . on ( 'tap.zf.tooltip touchend.zf.tooltip' , function ( e ) {
_this . isActive ? _this . hide ( ) : _this . show ( ) ;
} ) ;
}
this . $element . on ( {
// 'toggle.zf.trigger': this.toggle.bind(this),
// 'close.zf.trigger': this.hide.bind(this)
'close.zf.trigger' : this . hide . bind ( this )
} ) ;
this . $element . on ( 'focus.zf.tooltip' , function ( e ) {
isFocus = true ;
if ( _this . isClick ) {
// If we're not showing open on clicks, we need to pretend a click-launched focus isn't
// a real focus, otherwise on hover and come back we get bad behavior
if ( ! _this . options . clickOpen ) {
isFocus = false ;
}
return false ;
} else {
_this . show ( ) ;
}
} ) . on ( 'focusout.zf.tooltip' , function ( e ) {
isFocus = false ;
_this . isClick = false ;
_this . hide ( ) ;
} ) . on ( 'resizeme.zf.trigger' , function ( ) {
if ( _this . isActive ) {
_this . _setPosition ( ) ;
}
} ) ;
}
/ * *
* adds a toggle method , in addition to the static show ( ) & hide ( ) functions
* @ function
* /
} , {
key : 'toggle' ,
value : function toggle ( ) {
if ( this . isActive ) {
this . hide ( ) ;
} else {
this . show ( ) ;
}
}
/ * *
* Destroys an instance of tooltip , removes template element from the view .
* @ function
* /
} , {
key : 'destroy' ,
value : function destroy ( ) {
this . $element . attr ( 'title' , this . template . text ( ) ) . off ( '.zf.trigger .zf.tootip' )
// .removeClass('has-tip')
. removeAttr ( 'aria-describedby' ) . removeAttr ( 'data-yeti-box' ) . removeAttr ( 'data-toggle' ) . removeAttr ( 'data-resize' ) ;
this . template . remove ( ) ;
Foundation . unregisterPlugin ( this ) ;
}
} ] ) ;
return Tooltip ;
} ( ) ;
Tooltip . defaults = {
disableForTouch : false ,
/ * *
* Time , in ms , before a tooltip should open on hover .
* @ option
* @ example 200
* /
hoverDelay : 200 ,
/ * *
* Time , in ms , a tooltip should take to fade into view .
* @ option
* @ example 150
* /
fadeInDuration : 150 ,
/ * *
* Time , in ms , a tooltip should take to fade out of view .
* @ option
* @ example 150
* /
fadeOutDuration : 150 ,
/ * *
* Disables hover events from opening the tooltip if set to true
* @ option
* @ example false
* /
disableHover : false ,
/ * *
* Optional addtional classes to apply to the tooltip template on init .
* @ option
* @ example 'my-cool-tip-class'
* /
templateClasses : '' ,
/ * *
* Non - optional class added to tooltip templates . Foundation default is 'tooltip' .
* @ option
* @ example 'tooltip'
* /
tooltipClass : 'tooltip' ,
/ * *
* Class applied to the tooltip anchor element .
* @ option
* @ example 'has-tip'
* /
triggerClass : 'has-tip' ,
/ * *
* Minimum breakpoint size at which to open the tooltip .
* @ option
* @ example 'small'
* /
showOn : 'small' ,
/ * *
* Custom template to be used to generate markup for tooltip .
* @ option
* @ example '<div class="tooltip"></div>'
* /
template : '' ,
/ * *
* Text displayed in the tooltip template on open .
* @ option
* @ example 'Some cool space fact here.'
* /
tipText : '' ,
touchCloseText : 'Tap to close.' ,
/ * *
* Allows the tooltip to remain open if triggered with a click or touch event .
* @ option
* @ example true
* /
clickOpen : true ,
/ * *
* Additional positioning classes , set by the JS
* @ option
* @ example 'top'
* /
positionClass : '' ,
/ * *
* Distance , in pixels , the template should push away from the anchor on the Y axis .
* @ option
* @ example 10
* /
vOffset : 10 ,
/ * *
* Distance , in pixels , the template should push away from the anchor on the X axis , if aligned to a side .
* @ option
* @ example 12
* /
hOffset : 12
} ;
/ * *
* TODO utilize resize event trigger
* /
// Window exports
Foundation . plugin ( Tooltip , 'Tooltip' ) ;
} ( jQuery ) ;