Dynamically Add Alternate Language to Existing WordPress Menus

October 13, 2015
Posted in: Code Snippets, Web Development, WordPress

Managing a bilingual WordPress website is a bit more work than a single-language site. There are page and post translations, string translations, and menu translations. Depending on your site’s design, you may want to add a link to the alternate language in an existing menu instead of adding WPML‘s language switcher menu.

Creating a link to the alternate language’s homepage would mean simply adding it to the WordPress menu, but creating a dynamic link to the current page/post in the alternate language means we need a page-specific URL generated by WPML.

There are many approaches to add the link, but in this post, we’ll explore two quick options.

Option 1: Automatically add a language switcher link to a menu based on theme postition

This option will automatically add an item to the end of an existing menu, and will do it outside of WordPress, meaning it can’t be managed in the administration console.

Add this code to your theme’s functions.php file:


add_filter('wp_nav_menu_items', 'add_lang_menu_item', 10, 2);

function add_lang_menu_item($items, $args) {
	if (function_exists('icl_get_languages') && $args->theme_location == 'primary') {
		$languages = icl_get_languages('skip_missing=0');

		if(!empty($languages)){

			foreach($languages as $l){
				if(!$l['active']){
					$items = $items . '<li class="menu-item"><a href="' . $l['url'] . '">' . $l['native_name'] . '</a></li>';
					break;
				}
			}
		}
	}
	return $items;
}

Change the theme_location == 'primary' to reflect the theme_location your desired menu is using, and you’ll see an additional nav item when you refresh.

Option 2: Replace a custom menu item with a dynamic URL

If you’d prefer to have a bit more control as to where the menu item appears, and the exact text displayed, you can add a custom menu item and replace its URL when the page is loaded.

We’ll need to detect the custom menu item, so let’s set its URL to point to something recognizable.  Assuming you have French as your alternate language, you might have something like this:

Machine-WordPress-Custom-WPML-Menu-Item

We’ll be looking for #lang as the menu item’s URL, and will display Français in the menu.

Add this code to your theme’s functions.php file to perform the automatic URL replacement:


add_filter( 'nav_menu_link_attributes', 'replace_lang_menu_item', 10, 3 );

function replace_lang_menu_item( $atts, $item, $args ) {
	if( $atts['href'] && $atts['href'] == '#lang' ) {
		if (function_exists('icl_get_languages')){
			$languages = icl_get_languages('skip_missing=0&orderby=code');
			if(!empty($languages)){
				foreach($languages as $l){
					if(!$l['active']) {
						$atts['href'] = $l['url'];
						break;
					}
				}
			}
		}
	}
	return $atts;
}

The URL will be replaced with the link to the page/post in the alternate language, and you can manage the menu item’s text and position in any menu on the site (even more than one at a time).

Scott Buckingham

President / Owner
613-801-1350 x101
[email protected]
Scott is a WordPress expert who has worked on hundreds of web design and development projects. He excels at finding creative ways to solve technical problems. View full profile