Skip to content

Instantly share code, notes, and snippets.

@wpsmith
Last active January 16, 2021 19:34
Show Gist options
  • Save wpsmith/ebb01847c3d1af847cbcbb8fcf21542f to your computer and use it in GitHub Desktop.
Save wpsmith/ebb01847c3d1af847cbcbb8fcf21542f to your computer and use it in GitHub Desktop.

Revisions

  1. wpsmith revised this gist Jan 16, 2021. 1 changed file with 87 additions and 5 deletions.
    92 changes: 87 additions & 5 deletions ResponsiveMenus.php
    Original file line number Diff line number Diff line change
    @@ -6,9 +6,39 @@
    * Class ResponsiveMenus
    */
    class ResponsiveMenus {
    /**
    * Keeps whether the menu toggle button has been hooked already or not.
    *
    * @var bool
    */
    private $combined_menu_toggle_hooked = false;

    /**
    * Contains a raw copy of the menu settings.
    *
    * @var array
    */
    protected $menu_settings;

    /**
    * Contains a list of all the menus that are combined.
    *
    * @var string[]
    */
    protected $combined_menus;

    /**
    * Contains a list of all the menus.
    *
    * @var string[]
    */
    protected $all_menus;

    /**
    * Min-width media query string.
    *
    * @var string
    */
    protected $min_width;

    /**
    @@ -29,7 +59,8 @@ public function __construct( $menu_settings = array(), $min_width = '960px' ) {
    }

    add_action( 'init', array( $this, 'cls_style' ) );
    add_action( 'after_setup_theme', array( $this, 'filter_nav_menus' ) );
    add_action( 'after_setup_theme', array( $this, 'maybe_add_nav_menus_output_filter' ) );
    add_action( 'wp_nav_menu_args', array( $this, 'maybe_add_nav_menus_attributes_filter' ) );
    }

    /**
    @@ -51,12 +82,36 @@ protected function set_menu_settings( $menu_settings ) {
    );

    if ( isset( $settings['menuClasses'] ) && isset( $settings['menuClasses']['combine'] ) ) {
    $this->combined_menus = array_map( function ( $v ) {
    return str_replace( '.nav-', '', $v );
    }, $settings['menuClasses']['combine'] );
    $this->combined_menus = array_map( array(
    __CLASS__,
    'get_nav_handle_from_nav_class'
    ), $settings['menuClasses']['combine'] );
    }

    $this->all_menus = $this->combined_menus;
    foreach ( $settings['menuClasses'] as $k => $classes ) {
    if ( 'combine' === $k ) {
    continue;
    }
    $this->all_menus = array_merge( $this->all_menus, array_map( array(
    __CLASS__,
    'get_nav_handle_from_nav_class'
    ), $classes ) );
    }

    $this->menu_settings = $settings;
    $this->all_menus = array_unique($this->all_menus);
    }

    /**
    * Removes the `.nav-` prefix from class selector.
    *
    * @param string $class Nav class name.
    *
    * @return string|string[]
    */
    public static function get_nav_handle_from_nav_class( $class ) {
    return str_replace( '.nav-', '', $class );
    }

    /**
    @@ -93,7 +148,7 @@ protected function get_filter_nav_menu_location( $menu_location ) {
    /**
    * Adds filters to the appropriate nav menus.
    */
    public function filter_nav_menus() {
    public function maybe_add_nav_menus_output_filter() {
    $menus = get_theme_support( 'genesis-menus' );

    foreach ( (array) $menus[0] as $menu => $menu_name ) {
    @@ -111,6 +166,33 @@ public function filter_nav_menus() {
    }
    }

    /**
    * @param $args
    *
    * @return mixed
    */
    public function maybe_add_nav_menus_attributes_filter( $args ) {
    if ( ! in_array( $args['theme_location'], $this->all_menus, true ) ) {
    return $args;
    }

    add_filter( "genesis_attr_nav-{$args['theme_location']}", array( $this, 'genesis_attr_nav' ), PHP_INT_MAX );
    return $args;
    }

    /**
    * Add attributes for primary navigation element.
    *
    * @since 2.6.0
    *
    * @param array $attributes Existing attributes for primary navigation element.
    * @return array Amended attributes for primary navigation element.
    */
    public function genesis_attr_nav( $attributes ) {
    $attributes['class'] .= ' genesis-responsive-menu';
    return $attributes;
    }

    /**
    * Adds a filter to the theme menu output.
    *
  2. wpsmith revised this gist Jan 16, 2021. 2 changed files with 2 additions and 2 deletions.
    2 changes: 1 addition & 1 deletion responsive-menus.js
    Original file line number Diff line number Diff line change
    @@ -7,7 +7,7 @@
    * @author StudioPress
    * @author Travis Smith
    * @link https://github.com/copyblogger/responsive-menus/
    * @link https://gist.github.com
    * @link https://gist.github.com/wpsmith/ebb01847c3d1af847cbcbb8fcf21542f
    * @license GPL-2.0-or-later
    */

    2 changes: 1 addition & 1 deletion gistfile1.txt → responsive-menus.min.js
    Original file line number Diff line number Diff line change
    @@ -7,7 +7,7 @@
    * @author StudioPress
    * @author Travis Smith
    * @link https://github.com/copyblogger/responsive-menus/
    * @link https://gist.github.com
    * @link https://gist.github.com/wpsmith/ebb01847c3d1af847cbcbb8fcf21542f
    * @license GPL-2.0-or-later
    */
    !function(n,o){"use strict";var t="undefined"==typeof genesis_responsive_menu?"":genesis_responsive_menu,e=t.menuClasses,i={},u=[],r=t.combineMethod||"append";o.each(e,function(a){i[a]=[],o.each(this,function(e,n){var s=n,n=o(n);1<n.length?o.each(n,function(e,n){e=s+"-"+e;o(this).addClass(e.replace(".","")),i[a].push(e),"combine"===a&&u.push(e)}):1==n.length&&(i[a].push(s),"combine"===a&&u.push(s))})}),void 0===i.others&&(i.others=[]),1==u.length&&(i.others.push(u[0]),i.combine=null,u=null);var s={},l="menu-toggle",d="sub-menu-toggle",c="genesis-responsive-menu";function p(){var e,n,i,s,a,t=o('button[id^="genesis-mobile-"]').attr("id");void 0!==t&&("none"===g(t)&&(o("."+l+", ."+c+" .sub-menu-toggle").removeClass("activated").attr("aria-expanded",!1).attr("aria-pressed",!1),o("."+c+", ."+c+" .sub-menu").attr("style","")),e=t,n=o("."+c+" .js-superfish"),s="destroy","function"==typeof n.superfish&&("none"===g(e)&&(s={delay:100,animation:{opacity:"show",height:"show"},dropShadows:!1,speed:"fast"}),n.superfish(s)),i=t,s=b(),0<!o(s).length||o.each(s,function(e,n){var s=n.replace(".",""),a="genesis-"+s,t="genesis-mobile-"+s;"none"==g(i)&&(a="genesis-mobile-"+s,t="genesis-"+s);s=o('.genesis-skip-link a[href="#'+a+'"]');null!==u&&n!==u[0]&&s.toggleClass("skip-link-hidden"),0<s.length&&(n=(n=s.attr("href")).replace(a,t),s.attr("href",n))}),s=t,null!=u&&(a=u[0],t=o(u).filter(function(e){if(0<e)return e}),"none"!==g(s)?(o.each(t,function(e,n){"prepend"===r?o(n).find(".menu > li").addClass("moved-item-"+n.replace(".","")).prependTo(a+" ul.genesis-nav-menu"):o(n).find(".menu > li").addClass("moved-item-"+n.replace(".","")).appendTo(a+" ul.genesis-nav-menu")}),o(v(t)).hide()):(o(v(t)).show(),o.each(t,function(e,n){o(".moved-item-"+n.replace(".","")).appendTo(n+" ul.genesis-nav-menu").removeClass("moved-item-"+n.replace(".",""))}))))}function h(){var e=o(this),n=e.next("nav");e.attr("id","genesis-mobile-"+o(n).attr("class").match(/nav-\w*\b/))}function m(){var e=o(this);a(e,"aria-pressed"),a(e,"aria-expanded"),e.toggleClass("activated"),e.next("nav").slideToggle("fast")}function f(){var e=o(this),n=e.closest(".menu-item").siblings();a(e,"aria-pressed"),a(e,"aria-expanded"),e.toggleClass("activated"),e.next(".sub-menu").slideToggle("fast"),n.find("."+d).removeClass("activated").attr("aria-pressed","false"),n.find(".sub-menu").slideUp("fast")}function g(e){e=n.getElementById(e);return window.getComputedStyle(e).getPropertyValue("display")}function a(e,n){e.attr(n,function(e,n){return"false"===n})}function v(e){return o.map(e,function(e,n){return e}).join(",")}function b(){var s=[];return null!==u&&o.each(u,function(e,n){s.push(n.valueOf())}),o.each(i.others,function(e,n){s.push(n.valueOf())}),0<s.length?s:null}s.init=function(){var e,n,s,a;0!=o(b()).length&&(e=void 0!==t.menuIconClass?t.menuIconClass:"dashicons-before dashicons-menu",n=void 0!==t.subMenuIconClass?t.subMenuIconClass:"dashicons-before dashicons-arrow-down-alt2",a={menu:o("<button />",{class:l,"aria-expanded":!1,"aria-pressed":!1}).append(t.mainMenu),submenu:o("<button />",{class:d,"aria-expanded":!1,"aria-pressed":!1}).append(o("<span />",{class:"screen-reader-text",text:t.subMenu}))},o(v(i)).addClass(c),s=a,o(v(i)).find(".sub-menu").before(s.submenu),null!==u?(a=i.others.concat(u[0]),o("."+l)||o(v(a)).before(s.menu)):o(v(i.others)).before(s.menu),o("."+l).addClass(e),o("."+d).addClass(n),o("."+l).on("click.genesisMenu-mainbutton",m).each(h),o("."+d).on("click.genesisMenu-subbutton",f),o(window).on("resize.genesisMenu",p).triggerHandler("resize.genesisMenu"))},o(n).ready(function(){null!==b()&&s.init()})}(document,jQuery);
  3. wpsmith created this gist Jan 16, 2021.
    186 changes: 186 additions & 0 deletions ResponsiveMenus.php
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,186 @@
    <?php

    namespace WPS\WP\Themes\Genesis\Menus;

    /**
    * Class ResponsiveMenus
    */
    class ResponsiveMenus {
    private $combined_menu_toggle_hooked = false;
    protected $menu_settings;
    protected $combined_menus;
    protected $min_width;

    /**
    * ResponsiveMenus constructor.
    *
    * @param array $menu_settings Responsive Menus JS settings.
    * @param string $min_width Min width to hide menu button.
    */
    public function __construct( $menu_settings = array(), $min_width = '960px' ) {
    $this->set_menu_settings( $menu_settings );
    $this->min_width = $min_width;

    add_action( 'body_class', array( __CLASS__, 'add_body_class' ) );
    if ( function_exists( 'wp_body_open' ) ) {
    add_action( 'wp_body_open', array( __CLASS__, 'do_no_js' ), 0 );
    } else {
    add_action( 'genesis_before', array( __CLASS__, 'do_no_js' ), 0 );
    }

    add_action( 'init', array( $this, 'cls_style' ) );
    add_action( 'after_setup_theme', array( $this, 'filter_nav_menus' ) );
    }

    /**
    * Sets the class paramters based on responsive menus js.
    *
    * @param array $menu_settings Associative array for responsive menus js.
    */
    protected function set_menu_settings( $menu_settings ) {
    $settings = ! empty( $menu_settings ) ? $menu_settings : array(
    'mainMenu' => __( 'Menu' ),
    'menuIconClass' => 'dashicons-before dashicons-menu',
    'subMenu' => __( 'Submenu' ),
    'subMenuIconsClass' => 'dashicons-before dashicons-arrow-down-alt2',
    'menuClasses' => array(
    'combine' => array(),
    'others' => array(),
    ),
    'addMenuButtons' => false,
    );

    if ( isset( $settings['menuClasses'] ) && isset( $settings['menuClasses']['combine'] ) ) {
    $this->combined_menus = array_map( function ( $v ) {
    return str_replace( '.nav-', '', $v );
    }, $settings['menuClasses']['combine'] );
    }

    $this->menu_settings = $settings;
    }

    /**
    * Adds .no-js class body class.
    *
    * @param array $classes Current classes.
    *
    * @return array The new classes.
    *
    */
    public static function add_body_class( $classes ) {
    $classes[] = 'no-js';

    return array_unique( $classes );
    }

    /**
    * Gets the Genesis filter name for a specific menu location.
    *
    * @param string $menu_location Menu location.
    *
    * @return string
    */
    protected function get_filter_nav_menu_location( $menu_location ) {
    if ( 'primary' === $menu_location ) {
    return 'genesis_do_nav';
    } elseif ( 'secondary' === $menu_location ) {
    return 'genesis_do_subnav';
    }

    return "genesis_{$menu_location}_nav";
    }

    /**
    * Adds filters to the appropriate nav menus.
    */
    public function filter_nav_menus() {
    $menus = get_theme_support( 'genesis-menus' );

    foreach ( (array) $menus[0] as $menu => $menu_name ) {
    // Make sure a menu exists.
    if ( has_nav_menu( $menu ) ) {
    // For combined menus, only add the hook to the first menu that appears.
    if ( in_array( $menu, $this->combined_menus, true ) && ! $this->combined_menu_toggle_hooked ) {
    $this->add_hook( $menu );
    $this->combined_menu_toggle_hooked = true;
    } elseif ( ! in_array( $menu, $this->combined_menus, true ) ) {
    // For non-combined menus, go ahead and add a hook.
    $this->add_hook( $menu );
    }
    }
    }
    }

    /**
    * Adds a filter to the theme menu output.
    *
    * @param string $menu Theme menu location.
    */
    protected function add_hook( $menu ) {
    add_filter( $this->get_filter_nav_menu_location( $menu ), array(
    __CLASS__,
    'add_menu_toggle_button'
    ), PHP_INT_MAX, 3 );
    }

    /**
    * Output JS to remove .no-js if JS is enabled.
    * Connects to the genesis theme handle.
    */
    public function cls_style() {
    wp_add_inline_style( genesis_get_theme_handle(), "/*CLS Fix*/@media only screen and (min-width: $this->min_width) {.no-js button.menu-toggle {display: none;}}" );
    }

    /**
    * Outputs script tag to remove the .no-js class from the body tag.
    */
    public static function do_no_js() {
    echo '<script>(function() {document.body.className = document.body.className.replace("no-js","");})();</script>';
    }

    /**
    * Adds menu toggle button.
    *
    * @param string $nav_output Opening container markup, nav, closing container markup.
    * @param string $nav Navigation list (`<ul>`).
    * @param array $args {
    * Arguments for `wp_nav_menu()`.
    *
    * @type string $theme_location Menu location ID.
    * @type string $container Container markup.
    * @type string $menu_class Class(es) applied to the `<ul>`.
    * @type bool $echo 0 to indicate `wp_nav_menu()` should return not echo.
    * }
    *
    * @return string Modified menu output.
    */
    public static function add_menu_toggle_button( $nav_output, $nav, $args ) {
    return self::get_menu_toggle( $args['theme_location'] ) . $nav_output;
    }

    /**
    * Outputs the menu toggle button.
    *
    * @param string $menu Navigation menu slug.
    */
    public static function do_menu_toggle( $menu = 'primary' ) {
    echo self::get_menu_toggle( $menu );
    }

    /**
    * Gets the menu toggle button output.
    *
    * @param string $menu Navigation menu slug.
    *
    * @return string Menu toggle button output.
    */
    public static function get_menu_toggle( $menu = 'primary' ) {
    $menu = '' === $menu ? 'primary' : $menu;

    return sprintf(
    '<button class="menu-toggle dashicons-before dashicons-menu" aria-expanded="false" aria-pressed="false" id="genesis-mobile-nav-%s">%s</button>',
    $menu,
    __( 'Menu', 'farmhouse' )
    );
    }
    }
    23 changes: 23 additions & 0 deletions functions.php
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,23 @@
    <?php

    // Adds responsive menus support for CLS.
    require_once CHILD_DIR . '/lib/responsive-menus.php';
    new WPS\WP\Themes\Genesis\Menus\ResponsiveMenus( array(
    'mainMenu' => __( 'Menu', 'theme-domain' ),
    'menuIconClass' => 'dashicons-before dashicons-menu',
    'subMenu' => __( 'Submenu', 'theme-domain' ),
    'subMenuIconsClass' => 'dashicons-before dashicons-arrow-down-alt2',
    'menuClasses' => array(
    'combine' => array(
    '.nav-primary',
    '.nav-header',
    '.nav-header-left',
    '.nav-header-right',
    '.nav-secondary',
    ),
    'others' => array(
    '.nav-footer',
    ),
    ),
    'addMenuButtons' => false,
    ) );
    13 changes: 13 additions & 0 deletions gistfile1.txt
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,13 @@
    /**
    * Add the accessible responsive menu.
    *
    * @version 1.1.5
    *
    * @package Farmhouse Theme\JS
    * @author StudioPress
    * @author Travis Smith
    * @link https://github.com/copyblogger/responsive-menus/
    * @link https://gist.github.com
    * @license GPL-2.0-or-later
    */
    !function(n,o){"use strict";var t="undefined"==typeof genesis_responsive_menu?"":genesis_responsive_menu,e=t.menuClasses,i={},u=[],r=t.combineMethod||"append";o.each(e,function(a){i[a]=[],o.each(this,function(e,n){var s=n,n=o(n);1<n.length?o.each(n,function(e,n){e=s+"-"+e;o(this).addClass(e.replace(".","")),i[a].push(e),"combine"===a&&u.push(e)}):1==n.length&&(i[a].push(s),"combine"===a&&u.push(s))})}),void 0===i.others&&(i.others=[]),1==u.length&&(i.others.push(u[0]),i.combine=null,u=null);var s={},l="menu-toggle",d="sub-menu-toggle",c="genesis-responsive-menu";function p(){var e,n,i,s,a,t=o('button[id^="genesis-mobile-"]').attr("id");void 0!==t&&("none"===g(t)&&(o("."+l+", ."+c+" .sub-menu-toggle").removeClass("activated").attr("aria-expanded",!1).attr("aria-pressed",!1),o("."+c+", ."+c+" .sub-menu").attr("style","")),e=t,n=o("."+c+" .js-superfish"),s="destroy","function"==typeof n.superfish&&("none"===g(e)&&(s={delay:100,animation:{opacity:"show",height:"show"},dropShadows:!1,speed:"fast"}),n.superfish(s)),i=t,s=b(),0<!o(s).length||o.each(s,function(e,n){var s=n.replace(".",""),a="genesis-"+s,t="genesis-mobile-"+s;"none"==g(i)&&(a="genesis-mobile-"+s,t="genesis-"+s);s=o('.genesis-skip-link a[href="#'+a+'"]');null!==u&&n!==u[0]&&s.toggleClass("skip-link-hidden"),0<s.length&&(n=(n=s.attr("href")).replace(a,t),s.attr("href",n))}),s=t,null!=u&&(a=u[0],t=o(u).filter(function(e){if(0<e)return e}),"none"!==g(s)?(o.each(t,function(e,n){"prepend"===r?o(n).find(".menu > li").addClass("moved-item-"+n.replace(".","")).prependTo(a+" ul.genesis-nav-menu"):o(n).find(".menu > li").addClass("moved-item-"+n.replace(".","")).appendTo(a+" ul.genesis-nav-menu")}),o(v(t)).hide()):(o(v(t)).show(),o.each(t,function(e,n){o(".moved-item-"+n.replace(".","")).appendTo(n+" ul.genesis-nav-menu").removeClass("moved-item-"+n.replace(".",""))}))))}function h(){var e=o(this),n=e.next("nav");e.attr("id","genesis-mobile-"+o(n).attr("class").match(/nav-\w*\b/))}function m(){var e=o(this);a(e,"aria-pressed"),a(e,"aria-expanded"),e.toggleClass("activated"),e.next("nav").slideToggle("fast")}function f(){var e=o(this),n=e.closest(".menu-item").siblings();a(e,"aria-pressed"),a(e,"aria-expanded"),e.toggleClass("activated"),e.next(".sub-menu").slideToggle("fast"),n.find("."+d).removeClass("activated").attr("aria-pressed","false"),n.find(".sub-menu").slideUp("fast")}function g(e){e=n.getElementById(e);return window.getComputedStyle(e).getPropertyValue("display")}function a(e,n){e.attr(n,function(e,n){return"false"===n})}function v(e){return o.map(e,function(e,n){return e}).join(",")}function b(){var s=[];return null!==u&&o.each(u,function(e,n){s.push(n.valueOf())}),o.each(i.others,function(e,n){s.push(n.valueOf())}),0<s.length?s:null}s.init=function(){var e,n,s,a;0!=o(b()).length&&(e=void 0!==t.menuIconClass?t.menuIconClass:"dashicons-before dashicons-menu",n=void 0!==t.subMenuIconClass?t.subMenuIconClass:"dashicons-before dashicons-arrow-down-alt2",a={menu:o("<button />",{class:l,"aria-expanded":!1,"aria-pressed":!1}).append(t.mainMenu),submenu:o("<button />",{class:d,"aria-expanded":!1,"aria-pressed":!1}).append(o("<span />",{class:"screen-reader-text",text:t.subMenu}))},o(v(i)).addClass(c),s=a,o(v(i)).find(".sub-menu").before(s.submenu),null!==u?(a=i.others.concat(u[0]),o("."+l)||o(v(a)).before(s.menu)):o(v(i.others)).before(s.menu),o("."+l).addClass(e),o("."+d).addClass(n),o("."+l).on("click.genesisMenu-mainbutton",m).each(h),o("."+d).on("click.genesisMenu-subbutton",f),o(window).on("resize.genesisMenu",p).triggerHandler("resize.genesisMenu"))},o(n).ready(function(){null!==b()&&s.init()})}(document,jQuery);
    485 changes: 485 additions & 0 deletions responsive-menus.js
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,485 @@
    /**
    * Add the accessible responsive menu.
    *
    * @version 1.1.5
    *
    * @package Farmhouse Theme\JS
    * @author StudioPress
    * @author Travis Smith
    * @link https://github.com/copyblogger/responsive-menus/
    * @link https://gist.github.com
    * @license GPL-2.0-or-later
    */

    (function (document, $, undefined) {

    'use strict';

    var defaultOptions = {
    addMenuButtons: true
    },
    genesisMenuParams = typeof genesis_responsive_menu === 'undefined' ? '' : genesis_responsive_menu,
    genesisMenusUnchecked = genesisMenuParams.menuClasses,
    genesisMenus = {},
    menusToCombine = [],
    combineMethod = genesisMenuParams.combineMethod || 'append';

    // Merge options to genesisMenuParams
    $.each(defaultOptions, function(k,v){
    if (genesis_responsive_menu.hasOwnProperty(k)) {
    genesisMenuParams[k] = (genesis_responsive_menu.addMenuButtons === 'true' || genesis_responsive_menu.addMenuButtons === '1');
    } else {
    genesisMenuParams[k] = v;
    }
    })

    /**
    * Validate the menus passed by the theme with what's being loaded on the page,
    * and pass the new and accurate information to our new data.
    *
    * @param {genesisMenusUnchecked} Raw data from the localized script in the theme.
    * @return {array} genesisMenus array gets populated with updated data.
    * @return {array} menusToCombine array gets populated with relevant data.
    */
    $.each(
    genesisMenusUnchecked, function (group) {

    // Mirror our group object to populate.
    genesisMenus[group] = [];

    // Loop through each instance of the specified menu on the page.
    $.each(
    this, function (key, value) {

    var menuString = value,
    $menu = $(value);

    // If there is more than one instance, append the index and update array.
    if ($menu.length > 1) {

    $.each(
    $menu, function (key, value) {

    var newString = menuString + '-' + key;

    $(this).addClass(newString.replace('.', ''));

    genesisMenus[group].push(newString);

    if ('combine' === group) {
    menusToCombine.push(newString);
    }

    }
    );

    } else if ($menu.length == 1) {

    genesisMenus[group].push(menuString);

    if ('combine' === group) {
    menusToCombine.push(menuString);
    }

    }

    }
    );

    }
    );

    // Make sure there is something to use for the 'others' array.
    if (typeof genesisMenus.others == 'undefined') {
    genesisMenus.others = [];
    }

    // If there's only one menu on the page for combining, push it to the 'others' array and nullify our 'combine' variable.
    if (menusToCombine.length == 1) {
    genesisMenus.others.push(menusToCombine[0]);
    genesisMenus.combine = null;
    menusToCombine = null;
    }

    var genesisMenu = {},
    mainMenuButtonClass = 'menu-toggle',
    subMenuButtonClass = 'sub-menu-toggle',
    responsiveMenuClass = 'genesis-responsive-menu';

    // Initialize.
    genesisMenu.init = function () {

    // Exit early if there are no menus to do anything.
    if ($(_getAllMenusArray()).length == 0) {
    return;
    }

    var menuIconClass = typeof genesisMenuParams.menuIconClass !== 'undefined' ? genesisMenuParams.menuIconClass : 'dashicons-before dashicons-menu';
    var subMenuIconClass = typeof genesisMenuParams.subMenuIconClass !== 'undefined' ? genesisMenuParams.subMenuIconClass : 'dashicons-before dashicons-arrow-down-alt2';
    var existingMenu = $('button.menu-toggle');
    var toggleButtons = {
    submenu: _getSubMenuButton()
    };

    if (existingMenu) {
    toggleButtons.menu = existingMenu;
    } else {
    toggleButtons.menu = _getMenuButton();
    }

    // Add the responsive menu class to the active menus.
    _addResponsiveMenuClass();

    // Add the main nav button to the primary menu, or exit the plugin.
    if (genesisMenuParams.addMenuButtons) {
    _addMenuButtons(toggleButtons);
    }

    // Setup additional classes.
    $('.' + mainMenuButtonClass).addClass(menuIconClass);
    $('.' + subMenuButtonClass).addClass(subMenuIconClass);
    $('.' + mainMenuButtonClass).on('click.genesisMenu-mainbutton', _mainmenuToggle).each(_addClassID);
    $('.' + subMenuButtonClass).on('click.genesisMenu-subbutton', _submenuToggle);
    $(window).on('resize.genesisMenu', _doResize).triggerHandler('resize.genesisMenu');
    };

    function _getSubMenuButton() {
    return $('<button />', {
    'class': subMenuButtonClass,
    'aria-expanded': false,
    'aria-pressed': false
    }).append($('<span />', {
    'class': 'screen-reader-text',
    'text': genesisMenuParams.subMenu
    }));
    }
    function _getMenuButton() {
    return $('<button />', {
    'class': mainMenuButtonClass,
    'aria-expanded': false,
    'aria-pressed': false
    }).append(genesisMenuParams.mainMenu);
    }

    /**
    * Add menu toggle button to appropriate menus.
    *
    * @param {toggleButtons} Object of menu buttons to use for toggles.
    */
    function _addMenuButtons(toggleButtons) {

    // Apply sub menu toggle to each sub-menu found in the menuList.
    $(_getMenuSelectorString(genesisMenus)).find('.sub-menu').before(toggleButtons.submenu);

    if (menusToCombine !== null) {

    var menusToToggle = genesisMenus.others.concat(menusToCombine[0]);

    // Only add menu button the primary menu and navs NOT in the combine variable.
    $(_getMenuSelectorString(menusToToggle)).before(toggleButtons.menu);

    } else {

    // Apply the main menu toggle to all menus in the list.
    $(_getMenuSelectorString(genesisMenus.others)).before(toggleButtons.menu);

    }

    }

    /**
    * Add the responsive menu class.
    */
    function _addResponsiveMenuClass() {
    $(_getMenuSelectorString(genesisMenus)).addClass(responsiveMenuClass);
    }

    /**
    * Execute our responsive menu functions on window resizing.
    */
    function _doResize() {
    var buttons = $('button[id^="genesis-mobile-"]').attr('id');
    if (typeof buttons === 'undefined') {
    return;
    }
    _maybeClose(buttons);
    _superfishToggle(buttons);
    _changeSkipLink(buttons);
    _combineMenus(buttons);
    }

    /**
    * Add the nav- class of the related farmhouse menu as
    * an ID to associated button (helps target specific buttons outside of context).
    */
    function _addClassID() {
    var $this = $(this),
    nav = $this.next('nav'),
    id = 'class';

    if (nav) {
    $this.attr('id', 'genesis-mobile-' + $(nav).attr(id).match(/nav-\w*\b/));
    }
    }

    /**
    * Combine our menus if the mobile menu is visible.
    *
    * @params buttons
    */
    function _combineMenus(buttons) {

    // Exit early if there are no menus to combine.
    if (menusToCombine == null) {
    return;
    }

    // Split up the menus to combine based on order of appearance in the array.
    var primaryMenu = menusToCombine[0],
    combinedMenus = $(menusToCombine).filter(
    function (index) {
    if (index > 0) {
    return index;
    }
    }
    );

    // If the responsive menu is active, append items in 'combinedMenus' object to the 'primaryMenu' object.
    if ('none' !== _getDisplayValue(buttons)) {

    $.each(
    combinedMenus, function (key, value) {
    if (combineMethod === 'prepend') {
    $(value).find('.menu > li').addClass('moved-item-' + value.replace('.', '')).prependTo(primaryMenu + ' ul.genesis-nav-menu');
    } else {
    $(value).find('.menu > li').addClass('moved-item-' + value.replace('.', '')).appendTo(primaryMenu + ' ul.genesis-nav-menu');
    }
    }
    );
    $(_getMenuSelectorString(combinedMenus)).hide();

    } else {

    $(_getMenuSelectorString(combinedMenus)).show();
    $.each(
    combinedMenus, function (key, value) {
    $('.moved-item-' + value.replace('.', '')).appendTo(value + ' ul.genesis-nav-menu').removeClass('moved-item-' + value.replace('.', ''));
    }
    );

    }

    }

    /**
    * Action to happen when the main menu button is clicked.
    */
    function _mainmenuToggle() {
    var $this = $(this);
    _toggleAria($this, 'aria-pressed');
    _toggleAria($this, 'aria-expanded');
    $this.toggleClass('activated');
    $this.next('nav').slideToggle('fast');
    }

    /**
    * Action for submenu toggles.
    */
    function _submenuToggle() {

    var $this = $(this),
    others = $this.closest('.menu-item').siblings();
    _toggleAria($this, 'aria-pressed');
    _toggleAria($this, 'aria-expanded');
    $this.toggleClass('activated');
    $this.next('.sub-menu').slideToggle('fast');

    others.find('.' + subMenuButtonClass).removeClass('activated').attr('aria-pressed', 'false');
    others.find('.sub-menu').slideUp('fast');

    }

    /**
    * Activate/deactivate superfish.
    *
    * @params buttons
    */
    function _superfishToggle(buttons) {
    var _superfish = $('.' + responsiveMenuClass + ' .js-superfish'),
    $args = 'destroy';
    if (typeof _superfish.superfish !== 'function') {
    return;
    }
    if ('none' === _getDisplayValue(buttons)) {
    $args = {
    'delay': 100,
    'animation': {'opacity': 'show', 'height': 'show'},
    'dropShadows': false,
    'speed': 'fast'
    };
    }
    _superfish.superfish($args);
    }

    /**
    * Modify skip link to match mobile buttons.
    *
    * @param buttons
    */
    function _changeSkipLink(buttons) {

    // Start with an empty array.
    var menuToggleList = _getAllMenusArray();

    // Exit out if there are no menu items to update.
    if (!$(menuToggleList).length > 0) {
    return;
    }

    $.each(
    menuToggleList, function (key, value) {

    var newValue = value.replace('.', ''),
    startLink = 'genesis-' + newValue,
    endLink = 'genesis-mobile-' + newValue;

    if ('none' == _getDisplayValue(buttons)) {
    startLink = 'genesis-mobile-' + newValue;
    endLink = 'genesis-' + newValue;
    }

    var $item = $('.genesis-skip-link a[href="#' + startLink + '"]');

    if (menusToCombine !== null && value !== menusToCombine[0]) {
    $item.toggleClass('skip-link-hidden');
    }

    if ($item.length > 0) {
    var link = $item.attr('href');
    link = link.replace(startLink, endLink);

    $item.attr('href', link);
    } else {
    return;
    }

    }
    );

    }

    /**
    * Close all the menu toggles if buttons are hidden.
    *
    * @param buttons
    */
    function _maybeClose(buttons) {
    if ('none' !== _getDisplayValue(buttons)) {
    return true;
    }

    $('.' + mainMenuButtonClass + ', .' + responsiveMenuClass + ' .sub-menu-toggle')
    .removeClass('activated')
    .attr('aria-expanded', false)
    .attr('aria-pressed', false);

    $('.' + responsiveMenuClass + ', .' + responsiveMenuClass + ' .sub-menu')
    .attr('style', '');
    }

    /**
    * Generic function to get the display value of an element.
    *
    * @param {id} $id ID to check
    * @return {string} CSS value of display property
    */
    function _getDisplayValue($id) {
    var element = document.getElementById($id),
    style = window.getComputedStyle(element);
    return style.getPropertyValue('display');
    }

    /**
    * Toggle aria attributes.
    *
    * @param {button} $this passed through
    * @param {aria-xx} attribute aria attribute to toggle
    * @return {bool} from _ariaReturn
    */
    function _toggleAria($this, attribute) {
    $this.attr(
    attribute, function (index, value) {
    return 'false' === value;
    }
    );
    }

    /**
    * Helper function to return a comma separated string of menu selectors.
    *
    * @param {itemArray} Array of menu items to loop through.
    * @param {ignoreSecondary} boolean of whether to ignore the 'secondary' menu item.
    * @return {string} Comma-separated string.
    */
    function _getMenuSelectorString(itemArray) {

    var itemString = $.map(
    itemArray, function (value, key) {
    return value;
    }
    );

    return itemString.join(',');

    }

    /**
    * Helper function to return a group array of all the menus in
    * both the 'others' and 'combine' arrays.
    *
    * @return {array} Array of all menu items as class selectors.
    */
    function _getAllMenusArray() {

    // Start with an empty array.
    var menuList = [];

    // If there are menus in the 'menusToCombine' array, add them to 'menuList'.
    if (menusToCombine !== null) {

    $.each(
    menusToCombine, function (key, value) {
    menuList.push(value.valueOf());
    }
    );

    }

    // Add menus in the 'others' array to 'menuList'.
    $.each(
    genesisMenus.others, function (key, value) {
    menuList.push(value.valueOf());
    }
    );

    if (menuList.length > 0) {
    return menuList;
    } else {
    return null;
    }

    }

    $(document).ready(
    function () {

    if (_getAllMenusArray() !== null) {

    genesisMenu.init();

    }

    }
    );

    }(document, jQuery));