'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 ($) {
/**
* ResponsiveAccordionTabs module.
* @module foundation.responsiveAccordionTabs
* @requires foundation.util.keyboard
* @requires foundation.util.timerAndImageLoader
* @requires foundation.util.motion
* @requires foundation.accordion
* @requires foundation.tabs
*/
var ResponsiveAccordionTabs = function () {
/**
* Creates a new instance of a responsive accordion tabs.
* @class
* @fires ResponsiveAccordionTabs#init
* @param {jQuery} element - jQuery object to make into a dropdown menu.
* @param {Object} options - Overrides to the default plugin settings.
*/
function ResponsiveAccordionTabs(element, options) {
_classCallCheck(this, ResponsiveAccordionTabs);
this.$element = $(element);
this.options = $.extend({}, this.$element.data(), options);
this.rules = this.$element.data('responsive-accordion-tabs');
this.currentMq = null;
this.currentPlugin = null;
if (!this.$element.attr('id')) {
this.$element.attr('id', Foundation.GetYoDigits(6, 'responsiveaccordiontabs'));
};
this._init();
this._events();
Foundation.registerPlugin(this, 'ResponsiveAccordionTabs');
}
/**
* Initializes the Menu by parsing the classes from the 'data-responsive-accordion-tabs' attribute on the element.
* @function
* @private
*/
_createClass(ResponsiveAccordionTabs, [{
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;
}
this._getAllOptions();
if (!$.isEmptyObject(this.rules)) {
this._checkMediaQueries();
}
}
}, {
key: '_getAllOptions',
value: function _getAllOptions() {
//get all defaults and options
var _this = this;
_this.allOptions = {};
for (var key in MenuPlugins) {
if (MenuPlugins.hasOwnProperty(key)) {
var obj = MenuPlugins[key];
try {
var dummyPlugin = $('<ul></ul>');
var tmpPlugin = new obj.plugin(dummyPlugin, _this.options);
for (var keyKey in tmpPlugin.options) {
if (tmpPlugin.options.hasOwnProperty(keyKey) && keyKey !== 'zfPlugin') {
var objObj = tmpPlugin.options[keyKey];
_this.allOptions[keyKey] = objObj;
}
}
tmpPlugin.destroy();
} catch (e) {}
}
}
}
/**
* Initializes events for the Menu.
* @function
* @private
*/
}, {
key: '_events',
value: function _events() {
var _this = this;
$(window).on('changed.zf.mediaquery', 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) {
//don't know why but on nested elements data zfPlugin get's lost
if (!this.currentPlugin.$element.data('zfPlugin') && this.storezfData) this.currentPlugin.$element.data('zfPlugin', this.storezfData);
this.currentPlugin.destroy();
}
this._handleMarkup(this.rules[matchedMq].cssClass);
this.currentPlugin = new this.rules[matchedMq].plugin(this.$element, {});
this.storezfData = this.currentPlugin.$element.data('zfPlugin');
}
}, {
key: '_handleMarkup',
value: function _handleMarkup(toSet) {
var _this = this,
fromString = 'accordion';
var $panels = $('[data-tabs-content=' + this.$element.attr('id') + ']');
if ($panels.length) fromString = 'tabs';
if (fromString === toSet) {
return;
};
var tabsTitle = _this.allOptions.linkClass ? _this.allOptions.linkClass : 'tabs-title';
var tabsPanel = _this.allOptions.panelClass ? _this.allOptions.panelClass : 'tabs-panel';
this.$element.removeAttr('role');
var $liHeads = this.$element.children('.' + tabsTitle + ',[data-accordion-item]').removeClass(tabsTitle).removeClass('accordion-item').removeAttr('data-accordion-item');
var $liHeadsA = $liHeads.children('a').removeClass('accordion-title');
if (fromString === 'tabs') {
$panels = $panels.children('.' + tabsPanel).removeClass(tabsPanel).removeAttr('role').removeAttr('aria-hidden').removeAttr('aria-labelledby');
$panels.children('a').removeAttr('role').removeAttr('aria-controls').removeAttr('aria-selected');
} else {
$panels = $liHeads.children('[data-tab-content]').removeClass('accordion-content');
};
$panels.css({ display: '', visibility: '' });
$liHeads.css({ display: '', visibility: '' });
if (toSet === 'accordion') {
$panels.each(function (key, value) {
$(value).appendTo($liHeads.get(key)).addClass('accordion-content').attr('data-tab-content', '').removeClass('is-active').css({ height: '' });
$('[data-tabs-content=' + _this.$element.attr('id') + ']').after('<div id="tabs-placeholder-' + _this.$element.attr('id') + '"></div>').remove();
$liHeads.addClass('accordion-item').attr('data-accordion-item', '');
$liHeadsA.addClass('accordion-title');
});
} else if (toSet === 'tabs') {
var $tabsContent = $('[data-tabs-content=' + _this.$element.attr('id') + ']');
var $placeholder = $('#tabs-placeholder-' + _this.$element.attr('id'));
if ($placeholder.length) {
$tabsContent = $('<div class="tabs-content"></div>').insertAfter($placeholder).attr('data-tabs-content', _this.$element.attr('id'));
$placeholder.remove();
} else {
$tabsContent = $('<div class="tabs-content"></div>').insertAfter(_this.$element).attr('data-tabs-content', _this.$element.attr('id'));
};
$panels.each(function (key, value) {
var tempValue = $(value).appendTo($tabsContent).addClass(tabsPanel);
var hash = $liHeadsA.get(key).hash.slice(1);
var id = $(value).attr('id') || Foundation.GetYoDigits(6, 'accordion');
if (hash !== id) {
if (hash !== '') {
$(value).attr('id', hash);
} else {
hash = id;
$(value).attr('id', hash);
$($liHeadsA.get(key)).attr('href', $($liHeadsA.get(key)).attr('href').replace('#', '') + '#' + hash);
};
};
var isActive = $($liHeads.get(key)).hasClass('is-active');
if (isActive) {
tempValue.addClass('is-active');
};
});
$liHeads.addClass(tabsTitle);
};
}
/**
* 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() {
if (this.currentPlugin) this.currentPlugin.destroy();
$(window).off('.zf.ResponsiveAccordionTabs');
Foundation.unregisterPlugin(this);
}
}]);
return ResponsiveAccordionTabs;
}();
ResponsiveAccordionTabs.defaults = {};
// The plugin matches the plugin classes with these plugin instances.
var MenuPlugins = {
tabs: {
cssClass: 'tabs',
plugin: Foundation._plugins.tabs || null
},
accordion: {
cssClass: 'accordion',
plugin: Foundation._plugins.accordion || null
}
};
// Window exports
Foundation.plugin(ResponsiveAccordionTabs, 'ResponsiveAccordionTabs');
}(jQuery);
|