16

I'm using already designed theme for wordpress, and now instead of regular blog posts I would like to display WooCommerce products (which are custom post types I persume).

This is the current query with display loop:

<?php 
                $args = array(
                    //'posts_per_page' => '2',
                    'paged' => get_query_var('paged')
                );
                $homepage_query = new WP_Query($args);
            ?>
            <?php //query_posts('posts_per_page=4&paged='.get_query_var('paged')); ?>
            <?php if ( have_posts() ) : ?>  
                <?php while ( $homepage_query->have_posts() ) : $homepage_query->the_post(); ?>
                    <?php if($style == 'blog_style') { ?>
                    <div id="blog-style" class="post-box">
                        <?php get_template_part('content', 'blog'); ?>
                    </div>
                    <?php } else { ?>
                    <div class="post-box grid_4 <?php aero_post_box_class(); ?>">
                        <?php get_template_part('content', ''); ?>
                    </div>
                    <?php } ?>
                <?php endwhile; ?>

Is there a way to add options to $args so the loop displays WooCommerce products? I'm also using pagination with this loop, which is required on this project, so that's why it's important to use this loop.

3 Answers 3

29

You should be able to access products through the loop, setting the post_type arg to product:

<?php

// Setup your custom query
$args = array( 'post_type' => 'product', ... );
$loop = new WP_Query( $args );

while ( $loop->have_posts() ) : $loop->the_post(); ?>

    <a href="<?php echo get_permalink( $loop->post->ID ) ?>">
        <?php the_title(); ?>
    </a>

<?php endwhile; wp_reset_query(); // Remember to reset ?>
Sign up to request clarification or add additional context in comments.

4 Comments

Yes it's looping now, great!
If you want to get price, etc. you may want to do: $product = get_product($loop->post); and then use it just like WC_Product is used: echo $product->get_price_html(); etc.
get_product() is depricated now, Use $product = new WC_Product($loop->post->ID);
Shouldn't use WP_Query for a WC loop should use WC_product_Query
20

This is the proper way to re-create and customize the WooCommerce product loop:

  if(!function_exists('wc_get_products')) {
    return;
  }

  $paged                   = (get_query_var('paged')) ? absint(get_query_var('paged')) : 1; // if your custom loop is on a static front page then check for the query var 'page' instead of 'paged', see https://developer.wordpress.org/reference/classes/wp_query/#pagination-parameters
  $ordering                = WC()->query->get_catalog_ordering_args();
  $ordering['orderby']     = array_shift(explode(' ', $ordering['orderby']));
  $ordering['orderby']     = stristr($ordering['orderby'], 'price') ? 'meta_value_num' : $ordering['orderby'];
  $products_per_page       = apply_filters('loop_shop_per_page', wc_get_default_products_per_row() * wc_get_default_product_rows_per_page());

  $products_ids            = wc_get_products(array(
    'status'               => 'publish',
    'limit'                => $products_per_page,
    'page'                 => $paged,
    'paginate'             => true,
    'return'               => 'ids',
    'orderby'              => $ordering['orderby'],
    'order'                => $ordering['order'],
  ));

  wc_set_loop_prop('current_page', $paged);
  wc_set_loop_prop('is_paginated', wc_string_to_bool(true));
  wc_set_loop_prop('page_template', get_page_template_slug());
  wc_set_loop_prop('per_page', $products_per_page);
  wc_set_loop_prop('total', $products_ids->total);
  wc_set_loop_prop('total_pages', $products_ids->max_num_pages);

  if($products_ids) {
    do_action('woocommerce_before_shop_loop');
    woocommerce_product_loop_start();
      foreach($products_ids->products as $featured_product) {
        $post_object = get_post($featured_product);
        setup_postdata($GLOBALS['post'] =& $post_object);
        wc_get_template_part('content', 'product');
      }
      wp_reset_postdata();
    woocommerce_product_loop_end();
    do_action('woocommerce_after_shop_loop');
  } else {
    do_action('woocommerce_no_products_found');
  }

Using the code above, you would customize the wc_get_products() arguments to get the IDs of the products you want (if you have specific criteria). Once that code is in place, all the features of a native WooCommerce loop will be available to you—pagination, ordering, etc. This method is superior to WP_Query and get_posts() because those two methods can break.

I've written a more detailed blog post about custom WooCommerce loops here: https://cfxdesign.com/create-a-custom-woocommerce-product-loop-the-right-way/

3 Comments

what if the loop is for infinite scrolling and not for pagination? There will be duplicate products to display.
If you understand what's going on here then it shouldn't be a stretch to adapt this to infinite scrolling. However, just because you can do something, doesn't mean you should!
If wc_get_products() is called with 'return' => 'ids' the loop should start as foreach($products_ids as $featured_product) { instead of foreach($products_ids->products as $featured_product) {.
-4

You can Also get Category using thi code

       $terms = get_terms('product_cat');

       foreach ($terms as $term) {
         $term_link =  get_term_link( $term, 'product_cat' );
         echo '<li><a href="' . $term_link . '">' . $term->name . '</a></li>';
       }

If You want only parent category then

wp_list_categories('taxonomy=product_cat&orderby=order&title_li=&depth=1'); 

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.