diff --git a/CHANGELOG.md b/CHANGELOG.md index 35ae5be1..7fb2d5be 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +### HEAD +* Add module for a cleaner navigation walker ([#73](https://github.com/roots/soil/issues/72)) +* Use short array syntax ([#72](https://github.com/roots/soil/issues/72)) + ### 3.2.0: April 12th, 2015 * Add module for loading jQuery from Google's CDN with a local fallback ([#64](https://github.com/roots/soil/issues/64)) * Add note about activating the plugin ([#62](https://github.com/roots/soil/issues/62)) diff --git a/README.md b/README.md index c415ab00..28afc881 100644 --- a/README.md +++ b/README.md @@ -42,6 +42,9 @@ wp plugin activate soil * **Cleaner WordPress markup**
`add_theme_support('soil-clean-up');` +* **Cleaner walker for navigation menus**
+ `add_theme_support('soil-nav-walker');` + * **Root relative URLs**
`add_theme_support('soil-relative-urls');` diff --git a/lib/utils.php b/lib/utils.php new file mode 100644 index 00000000..c5f4fec7 --- /dev/null +++ b/lib/utils.php @@ -0,0 +1,38 @@ +Home + *
  • Sample PageHome
  • + * + * + * You can enable/disable this feature in functions.php (or lib/config.php if you're using Sage): + * add_theme_support('soil-nav-walker'); + */ +class NavWalker extends \Walker_Nav_Menu { + private $cpt; // Boolean, is current post a custom post type + private $archive; // Stores the archive page for current URL + + public function __construct() { + add_filter('nav_menu_css_class', array($this, 'cssClasses'), 10, 2); + add_filter('nav_menu_item_id', '__return_null'); + $cpt = get_post_type(); + $this->cpt = in_array($cpt, get_post_types(array('_builtin' => false))); + $this->archive = get_post_type_archive_link($cpt); + } + + public function checkCurrent($classes) { + return preg_match('/(current[-_])|active/', $classes); + } + + // @codingStandardsIgnoreStart + function display_element($element, &$children_elements, $max_depth, $depth = 0, $args, &$output) { + $element->is_subitem = ((!empty($children_elements[$element->ID]) && (($depth + 1) < $max_depth || ($max_depth === 0)))); + + if ($element->is_subitem) { + foreach ($children_elements[$element->ID] as $child) { + if ($child->current_item_parent || Utils\url_compare($this->archive, $child->url)) { + $element->classes[] = 'active'; + } + } + } + + $element->is_active = strpos($this->archive, $element->url); + + if ($element->is_active) { + $element->classes[] = 'active'; + } + + parent::display_element($element, $children_elements, $max_depth, $depth, $args, $output); + } + // @codingStandardsIgnoreEnd + + public function cssClasses($classes, $item) { + $slug = sanitize_title($item->title); + + if ($this->cpt) { + $classes = str_replace('current_page_parent', '', $classes); + + if (Utils\url_compare($this->archive, $item->url)) { + $classes[] = 'active'; + } + } + + $classes = preg_replace('/(current(-menu-|[-_]page[-_])(item|parent|ancestor))/', 'active', $classes); + $classes = preg_replace('/^((menu|page)[-_\w+]+)+/', '', $classes); + + $classes[] = 'menu-' . $slug; + + $classes = array_unique($classes); + + return array_filter($classes, 'Roots\\Soil\\Utils\\is_element_empty'); + } +} + +/** + * Clean up wp_nav_menu_args + * + * Remove the container + * Remove the id="" on nav menu items + */ +function nav_menu_args($args = '') { + $nav_menu_args = []; + $nav_menu_args['container'] = false; + + if (!$args['items_wrap']) { + $nav_menu_args['items_wrap'] = ''; + } + + if (!$args['walker']) { + $nav_menu_args['walker'] = new \Roots\Soil\Nav\NavWalker(); + } + + return array_merge($args, $nav_menu_args); +} +add_filter('wp_nav_menu_args', __NAMESPACE__ . '\\nav_menu_args'); +add_filter('nav_menu_item_id', '__return_null'); diff --git a/modules/relative-urls.php b/modules/relative-urls.php index de623ca0..5d54e60e 100644 --- a/modules/relative-urls.php +++ b/modules/relative-urls.php @@ -11,18 +11,6 @@ * You can enable/disable this feature in functions.php (or lib/config.php if you're using Sage): * add_theme_support('soil-relative-urls'); */ -function root_relative_url($input) { - preg_match('|(?:https?:)?//([^/]+)(/.*)|i', $input, $matches); - - if (!isset($matches[1]) || !isset($matches[2])) { - return $input; - } elseif (($matches[1] === $_SERVER['SERVER_NAME']) || $matches[1] === $_SERVER['SERVER_NAME'] . ':' . $_SERVER['SERVER_PORT']) { - return wp_make_link_relative($input); - } else { - return $input; - } -} - function enable_root_relative_urls() { return !(is_admin() || preg_match('/sitemap(_index)?\.xml/', $_SERVER['REQUEST_URI']) || in_array($GLOBALS['pagenow'], ['wp-login.php', 'wp-register.php'])); } @@ -47,7 +35,7 @@ function enable_root_relative_urls() { 'style_loader_src' ]; - add_filters($root_rel_filters, __NAMESPACE__ . '\\root_relative_url'); + add_filters($root_rel_filters, 'Roots\\Soil\\Utils\\root_relative_url'); } function add_filters($tags, $function) { diff --git a/soil.php b/soil.php index a4b95555..40a0f6a8 100644 --- a/soil.php +++ b/soil.php @@ -50,6 +50,8 @@ public function set($options) { } } +require_once(plugin_dir_path(__FILE__) . 'lib/utils.php'); + function load_modules() { global $_wp_theme_features; foreach (glob(__DIR__ . '/modules/*.php') as $file) {