search ]

Archives: Snippets | Page 14

Change the WordPress Search URL Query String

By default WordPress uses the "s" parameter as the query string to perform a site search. In some cases you may want to change this parameter to a different string. You can do this easily with the following function:

function change_search_url_rewrite() {
    if ( is_search() && ! empty( $_GET['s'] ) ) {
        wp_redirect( home_url( "/search/" ) . urlencode( get_query_var( 's' ) ) );
        exit();
    }
}
add_action( 'template_redirect', 'change_search_url_rewrite' );

After adding this function, the search URL will be search/test instead of ?s=test

Show Product Categories in WooCommerce Breadcrumbs

To display the product category in WooCommerce breadcrumbs, add the following code to your child theme’s functions.php file:

/**
 * Show product categories in WooCommerce breadcrumbs
 */
// Get breadcrumbs on product pages that read: Home > Shop > Product category > Product Name
add_filter( 'woo_breadcrumbs_trail', 'woo_custom_breadcrumbs_trail_add_product_categories', 20 );

function woo_custom_breadcrumbs_trail_add_product_categories ( $trail ) {
  if ( ( get_post_type() == 'product' ) && is_singular() ) {
		global $post;

		$taxonomy = 'product_cat';

		$terms = get_the_terms( $post->ID, $taxonomy );
		$links = array();

		if ( $terms && ! is_wp_error( $terms ) ) {
		$count = 0;
			foreach ( $terms as $c ) {
				$count++;
				if ( $count > 1 ) { continue; }
				$parents = woo_get_term_parents( $c->term_id, $taxonomy, true, ', ', $c->name, array() );

				if ( $parents != '' && ! is_wp_error( $parents ) ) {
					$parents_arr = explode( ', ', $parents );

					foreach ( $parents_arr as $p ) {
						if ( $p != '' ) { $links[] = $p; }
					}
				}
			}

			// Add the trail back on to the end.
			// $links[] = $trail['trail_end'];
			$trail_end = get_the_title($post->ID);

			// Add the new links, and the original trail's end, back into the trail.
			array_splice( $trail, 2, count( $trail ) - 1, $links );

			$trail['trail_end'] = $trail_end;
		}
	}

	return $trail;
}

/**
 * Retrieve term parents with separator.
 *
 * @param int $id Term ID.
 * @param string $taxonomy.
 * @param bool $link Optional, default is false. Whether to format with link.
 * @param string $separator Optional, default is '/'. How to separate terms.
 * @param bool $nicename Optional, default is false. Whether to use nice name for display.
 * @param array $visited Optional. Already linked to terms to prevent duplicates.
 * @return string
 */

if ( ! function_exists( 'woo_get_term_parents' ) ) {
function woo_get_term_parents( $id, $taxonomy, $link = false, $separator = '/', $nicename = false, $visited = array() ) {
	$chain = '';
	$parent = &get_term( $id, $taxonomy );
	if ( is_wp_error( $parent ) )
		return $parent;

	if ( $nicename ) {
		$name = $parent->slug;
	} else {
		$name = $parent->name;
	}

	if ( $parent->parent && ( $parent->parent != $parent->term_id ) && !in_array( $parent->parent, $visited ) ) {
		$visited[] = $parent->parent;
		$chain .= woo_get_term_parents( $parent->parent, $taxonomy, $link, $separator, $nicename, $visited );
	}

	if ( $link ) {
		$chain .= '<a href="' . get_term_link( $parent, $taxonomy ) . '" title="' . esc_attr( sprintf( __( "View all posts in %s" ), $parent->name ) ) . '">'.$parent->name.'</a>' . $separator;
	} else {
		$chain .= $name.$separator;
	}
	return $chain;
	}
}

For more on breadcrumbs, see Adding Breadcrumbs to WordPress.

Display My Account Link in WooCommerce Templates

The following code displays the link to the “My Account” page on WooCommerce sites. If the user is not logged in, the link will show the text “Login / Register”, otherwise it will show “My Account”.

<?php if ( is_user_logged_in() ) { ?>
	<a href="<?php echo get_permalink( get_option('woocommerce_myaccount_page_id') ); ?>" title="<?php _e('My Account','woothemes'); ?>"><?php _e('My Account','woothemes'); ?></a>
<?php } 
else { ?>
	<a href="<?php echo get_permalink( get_option('woocommerce_myaccount_page_id') ); ?>" title="<?php _e('Login / Register','woothemes'); ?>"><?php _e('Login / Register','woothemes'); ?></a>
<?php } ?>

More information about the My Account page in the post Customizing the My Account page in WooCommerce.

Basic WooCommerce Products Loop

This is a simple example of a basic WooCommerce products loop. If you want to learn more, here is a post about the right way to retrieve WooCommerce products in your theme.

<ul class="products">
	<?php
		$args = array(
			'post_type' => 'product',
			'posts_per_page' => 12
			);
		$loop = new WP_Query( $args );
		if ( $loop->have_posts() ) {
			while ( $loop->have_posts() ) : $loop->the_post();
				wc_get_template_part( 'content', 'product' );
			endwhile;
		} else {
			echo __( 'No products found' );
		}
		wp_reset_postdata();
	?>
</ul><!--/.products-->

Customize WooCommerce Breadcrumbs

Here are several examples that let you change the breadcrumbs of WooCommerce. Add the snippets in this post to your child theme’s functions.php file.

Note that some of the snippets in this post will not work with the Storefront theme.

a. Changing the “Home” text

/**
 * Rename "home" in breadcrumb
 */
add_filter( 'woocommerce_breadcrumb_defaults', 'wcc_change_breadcrumb_home_text' );
function wcc_change_breadcrumb_home_text( $defaults ) {
    // Change the breadcrumb home text from 'Home' to 'Apartment'
	$defaults['home'] = 'Apartment';
	return $defaults;
}

b. Changing the separator

/**
 * Change the breadcrumb separator
 */
add_filter( 'woocommerce_breadcrumb_defaults', 'wcc_change_breadcrumb_delimiter' );
function wcc_change_breadcrumb_delimiter( $defaults ) {
	// Change the breadcrumb delimeter from '/' to '>'
	$defaults['delimiter'] = ' > ';
	return $defaults;
}

c. Changing several default parameters at once

/**
 * Change several of the breadcrumb defaults
 */
add_filter( 'woocommerce_breadcrumb_defaults', 'jk_woocommerce_breadcrumbs' );
function jk_woocommerce_breadcrumbs() {
    return array(
            'delimiter'   => ' &#47; ',
            'wrap_before' => '<nav class="woocommerce-breadcrumb" itemprop="breadcrumb">',
            'wrap_after'  => '</nav>',
            'before'      => '',
            'after'       => '',
            'home'        => _x( 'Home', 'breadcrumb', 'woocommerce' ),
        );
}

d. Changing the Home link URL

/**
 * Replace the home link URL
 */
add_filter( 'woocommerce_breadcrumb_home_url', 'woo_custom_breadrumb_home_url' );
function woo_custom_breadrumb_home_url() {
    return 'http://woocommerce.com';
}

e. Complete removal of breadcrumbs

Useful when you add breadcrumbs differently on your site….

/**
 * Remove the breadcrumbs 
 */
add_action( 'init', 'woo_remove_wc_breadcrumbs' );
function woo_remove_wc_breadcrumbs() {
    remove_action( 'woocommerce_before_main_content', 'woocommerce_breadcrumb', 20, 0 );
}

You can also remove WooCommerce breadcrumbs on specific pages only.

Remove Product Content by Category in WooCommerce

The following code for example removes product images on the WooCommerce single product page only for products in the “Cookware” category. You can of course remove any content you want by using the WooCommerce hooks available to you.

/**
 * Remove product content based on category
 */
function remove_product_content() {
	// If a product in the 'Cookware' category is being viewed...
	if ( is_product() && has_term( 'Cookware', 'product_cat' ) ) {
		//... Remove the images
		remove_action( 'woocommerce_before_single_product_summary', 'woocommerce_show_product_images', 20 );
		// For a full list of what can be removed please see woocommerce-hooks.php
	}
}
add_action( 'wp', 'remove_product_content' );

Add Random Sorting to WooCommerce Catalog

The following code is an example of how to add a random sorting option on the WooCommerce product catalog page. In the same way you can add any sorting option you want according to the options available for the orderby parameter of WP_Query. Take a look at the WordPress Codex for more information about the orderby parameter.

This code should be in your functions.php file:

/**
 * Add custom sorting options (asc/desc)
 */
add_filter( 'woocommerce_get_catalog_ordering_args', 'custom_woocommerce_get_catalog_ordering_args' );
function custom_woocommerce_get_catalog_ordering_args( $args ) {
  $orderby_value = isset( $_GET['orderby'] ) ? wc_clean( $_GET['orderby'] ) : apply_filters( 'woocommerce_default_catalog_orderby', get_option( 'woocommerce_default_catalog_orderby' ) );
	if ( 'random_list' == $orderby_value ) {
		$args['orderby'] = 'rand';
		$args['order'] = '';
		$args['meta_key'] = '';
	}
	return $args;
}
add_filter( 'woocommerce_default_catalog_orderby_options', 'custom_woocommerce_catalog_orderby' );
add_filter( 'woocommerce_catalog_orderby', 'custom_woocommerce_catalog_orderby' );
function custom_woocommerce_catalog_orderby( $sortby ) {
	$sortby['random_list'] = 'Random';
	return $sortby;
}

For more on WooCommerce product queries, see Properly Retrieve WooCommerce Products.

Allow HTML in Category and Tag Descriptions

By default WordPress removes HTML from the description of tags and categories. Add this code to your functions.php file to allow HTML in the description of these terms.

/**
 * Allow HTML in term (category, tag) descriptions
 */
foreach ( array( 'pre_term_description' ) as $filter ) {
	remove_filter( $filter, 'wp_filter_kses' );
	if ( ! current_user_can( 'unfiltered_html' ) ) {
		add_filter( $filter, 'wp_filter_post_kses' );
	}
}
 
foreach ( array( 'term_description' ) as $filter ) {
	remove_filter( $filter, 'wp_kses_data' );
}

This removes a WordPress filter. Learn more in WordPress Hooks Explained.

Auto Display First Post Image or Default Fallback Image

Say you want to use the featured image (post thumbnail) that WordPress provides, but you have an archive with many posts and it would take a long time to add that featured image to each of them.

For new posts you can use the featured image in the standard way, but for old posts you want to use the first image in the post content as the featured image, or a default image if there are no images in that specific post. Add the following code to functions.php:

function catch_that_image() {
  global $post, $posts;
  $first_img = '';
  ob_start();
  ob_end_clean();
  $output = preg_match_all('/<img.+?src=['"]([^'"]+)['"].*?>/i', $post->post_content, $matches);
  $first_img = $matches[1][0];

  if(empty($first_img)) {
    $first_img = "/path/to/default.png";
  }
  return $first_img;
}

And to use this inside the WordPress loop:

if ( get_the_post_thumbnail($post_id) != '' ) {

  echo '<a href="'; the_permalink(); echo '" class="thumbnail-wrapper">';
   the_post_thumbnail();
  echo '</a>';

} else {

 echo '<a href="'; the_permalink(); echo '" class="thumbnail-wrapper">';
 echo '<img src="';
 echo catch_that_image();
 echo '" alt="" />';
 echo '</a>';

}

For more on WordPress image handling, see Image Sizes in WordPress.

Add Category Name to body_class in WordPress

The body_class function helps add classes to the body tag, which usually contains information about what type of page is currently displayed, and allows you to style specific elements on that page by that specific class.

For some reason WordPress does not add a class describing which category (or categories) you are in on a single post page (e.g. single.php). To add the category name to that body tag, use the following code:

function sv_add_category_to_single($classes) {
    if (is_single() ) {
        global $post;
        foreach((get_the_category($post->ID)) as $category) {
            // add category slug to the $classes array
            $classes[] = $category->category_nicename;
        }
    }
    // return the $classes array
    return $classes;
}
add_filter('body_class','sv_add_category_to_single');

This uses the body_class filter. Learn more in WordPress Hooks Explained.

Savvy WordPress Development official logo