Ask your WordPress questions! Pay money and get answers fast! (more info)

Pulling out Posts per Taxonomy

  • SOLVED

On a theme we just bought [http://themeforest.net/item/ventura-wordpress-corporate-business-theme/full_screen_preview/378380], there's a PHP file ( taxonomy-product_cats.php) that pulls out products. In this file, there's a loop that displays all products for a particular category:


<?php
wp_reset_query();
query_posts($query_string . '&posts_per_page=15&paged=' . $paged);
if (have_posts()) :
while ( have_posts() ) : the_post();
$price = get_post_meta(get_the_ID(), 'inception_price', true);
?>

<div class="omc-product-listing">
<a href="<?php the_permalink();?>">

<?php
if(has_post_thumbnail()) {
the_post_thumbnail('product', array('class' => 'omc-product-frame'));
} else {
?>
<img src="<?php echo get_template_directory_uri() ;?>/images/no-image.png" width="170" height="170" class="omc-product-frame" alt="no photo" />
<?php } ?>
</a>

<span class="omc-listing-header"><a href="<?php the_permalink();?>"><?php the_title();?></a></span>
<span class="omc-listing-price"><?php echo($price);?></span>
<span class="omc-listing-more"><a href="<?php the_permalink();?>">&raquo;</a></span>

</div><!-- /omc-product-listing -->
<?php endwhile; ?>
<br class="clear" />
<div class="product-pagination">
<?php kriesi_pagination(); ?>
</div>
<br class="clear" />
<?php endif; wp_reset_query(); ?>


The result can be seen here, on the upper part of the picture: http://www.wikishenzhen.com/site/uploads/before-after.jpg

What I'd like to achieve is to pull out products for a given category, but display then "per subcategory". These are the current categories: http://www.wikishenzhen.com/site/uploads/categories.jpg

That's what is shown on the second half of the picture here: http://www.wikishenzhen.com/site/uploads/before-after.jpg

I think it needs a loop, but I don't know how to implement it in this case.

I asked the developer of this theme (who's very nice and fast to respond). He said that it needs to pull out the posts per taxonomy.

Thank you.
Adriano

Answers (2)

2011-10-13

Abdessamad Idrissi answers:

Did you check this solution [[LINK href="http://wpquestions.com/question/show/id/926"]]here[[/LINK]]? It is the same issue as yours.
I will adjust it to suite your case :)


Giorgio Adriano comments:

Hi Abdessamad,

It does seem to be the same issue as mine, but I'm not really sure about it. Can you help out? I'm not good with taxonomy and all that.

What do you need to make it work? Will a list of my categories/subcategories be enough? Also, will I have to edit the code whenever the categories/subcategories change?

Cheers,
Adriano


Abdessamad Idrissi comments:

Hey Giorgio,

you don't have to edit anything whenevr you add new categories.

I'm working on it.. :)


Abdessamad Idrissi comments:

All right :)

Back up your "taxonomy-product_cats.php" and replace it with

<?php
$post_type = 'product';

// Get all the taxonomies for this post type
$taxonomies = get_object_taxonomies( (object) array( 'post_type' => $post_type ) );

foreach( $taxonomies as $taxonomy ) :

// Gets every "category" (term) in this taxonomy to get the respective posts
$terms = get_terms( $taxonomy->name );

foreach( $terms as $term ) :

?>
<div class"clear"></div>

<h2><?php echo $term->name; ?></h2>

<?php
$posts = new WP_Query( "taxonomy=$taxonomy&term=$term->slug&posts_per_page=2" );

if( $posts->have_posts() ) :
while( $posts->have_posts() ) : $posts->the_post();

$price = get_post_meta(get_the_ID(), 'inception_price', true); ?>

<div class="omc-product-listing">
<a href="<?php the_permalink();?>">

<?php
if(has_post_thumbnail()) {
the_post_thumbnail('product', array('class' => 'omc-product-frame'));
} else {
?>
<img src="<?php echo get_template_directory_uri() ;?>/images/no-image.png" width="170" height="170" class="omc-product-frame" alt="no photo" />
<?php } ?>
</a>

<span class="omc-listing-header"><a href="<?php the_permalink();?>"><?php the_title();?></a></span>
<span class="omc-listing-price"><?php echo($price);?></span>
<span class="omc-listing-more"><a href="<?php the_permalink();?>">&raquo;</a></span>

</div><!-- /omc-product-listing -->


<?php

endwhile;
endif;

endforeach;

endforeach;
?>

<br class="clear" />

<div class="product-pagination">
<?php kriesi_pagination(); ?>
</div>

<br class="clear" />


Giorgio Adriano comments:

Hi Abdessamad,

I've got an error back:


Parse error: syntax error, unexpected T_ENDIF in .../taxonomy-product_cats.php on line 149


I should perhaps give you here the entire file content:

<?php

get_header();

$taxonomy_single = get_query_var( 'term' ) ;

?>

<div id="omc-header-under">

<span id="omc-header-overlay"></span>

<?php

$theme_options = get_option('option_tree');
$header_image_upload = get_option_tree( 'header_image_upload', $theme_options, false );
$header_image_select = get_option_tree( 'header_image_select', $theme_options, false );
$blog_header = get_option_tree( 'blog_page_header', $theme_options, false );
$products_upload = get_option_tree( 'products_upload', $theme_options, false );
$skin = get_option_tree( 'skin', $theme_options, false );

if ($products_upload !='') { ?>

<img width="1020" src="<?php echo($products_upload);?>" alt="header image" class="omc-header-image fix-height" />

<?php } elseif ($header_image_upload !='') { ?>

<img width="1020" src="<?php echo($header_image_upload);?>" alt="header image" class="omc-header-image fix-height" />

<?php } elseif ($header_image_select !='') { ?>

<img src="<?php echo(get_template_directory_uri());?>/images/headers/<?php echo($header_image_select);?>.jpg" alt="header image" class="omc-header-image fix-height" />

<?php } else {?>

<img height="200" width="1020" src="<?php echo(get_template_directory_uri());?>/images/skins/<?php echo($skin);?>/default_header.jpg" alt="header image" class="omc-header-image" />

<?php } ?>

<div id="omc-ribbon">

<h1><span class="omc-ribbon-left"></span><span class="omc-ribbon-middle"><?php $term = get_term_by( 'slug', get_query_var( 'term' ), get_query_var( 'taxonomy' ) ); echo $term->name; ?></span><span class="omc-ribbon-right"></span></h1>

<div id="omc-breadcrumb">

<?php if(function_exists('bcn_display')) { bcn_display();}?>

</div><!-- /omc-breadcrumb -->

</div>

</div><!-- /omc-header-under -->

<div class="omc-inner-page-content-wrapper right-sidebar">

<?php if ( is_active_sidebar( 8 ) ) { ?>

<div id="omc-sidebar" class="omc-right">

<ul class="xoxo">

<?php dynamic_sidebar( 'Products Sidebar' ); ?>
</ul>

</div>

<?php } else { get_sidebar(); } ?>

<div id="omc-main-left-column" class="omc-content">

<span class="product-margin"></span>

<?php
wp_reset_query();
query_posts($query_string . '&posts_per_page=9&paged=' . $paged);
if (have_posts()) :
while ( have_posts() ) : the_post();
$price = get_post_meta(get_the_ID(), 'inception_price', true);
?>

<div class="omc-product-listing">

<a href="<?php the_permalink();?>">

<?php
if(has_post_thumbnail()) {
the_post_thumbnail('product', array('class' => 'omc-product-frame'));
} else {
?>

<img src="<?php echo get_template_directory_uri() ;?>/images/no-image.png" width="170" height="170" class="omc-product-frame" alt="no photo" />

<?php } ?>

</a>

<span class="omc-listing-header"><a href="<?php the_permalink();?>"><?php the_title();?></a></span>
<span class="omc-listing-price"><?php echo($price);?></span>
<span class="omc-listing-more"><a href="<?php the_permalink();?>">&raquo;</a></span>

</div><!-- /omc-product-listing -->

<?php endwhile; ?>

<br class="clear" />

<div class="product-pagination">

<?php kriesi_pagination(); ?>

</div>

<br class="clear" />

<?php endif; wp_reset_query(); ?>

</div><!-- /omc-main-left-column -->

<br class="clear" />

</div><!-- /omc-inner-page-content -->

<?php get_footer(); ?>


Cheers,
Adriano


Abdessamad Idrissi comments:

All right! got it ;)


Abdessamad Idrissi comments:

Here's it

<?php

get_header();

$taxonomy_single = get_query_var( 'term' ) ;

?>


<div id="omc-header-under">

<span id="omc-header-overlay"></span>

<?php


$theme_options = get_option('option_tree');
$header_image_upload = get_option_tree( 'header_image_upload', $theme_options, false );
$header_image_select = get_option_tree( 'header_image_select', $theme_options, false );
$blog_header = get_option_tree( 'blog_page_header', $theme_options, false );
$products_upload = get_option_tree( 'products_upload', $theme_options, false );
$skin = get_option_tree( 'skin', $theme_options, false );
if ($products_upload !='') { ?>

<img width="1020" src="<?php echo($products_upload);?>" alt="header image" class="omc-header-image fix-height" />
<?php } elseif ($header_image_upload !='') { ?>

<img width="1020" src="<?php echo($header_image_upload);?>" alt="header image" class="omc-header-image fix-height" />
<?php } elseif ($header_image_select !='') { ?>

<img src="<?php echo(get_template_directory_uri());?>/images/headers/<?php echo($header_image_select);?>.jpg" alt="header image" class="omc-header-image fix-height" />
<?php } else {?>

<img height="200" width="1020" src="<?php echo(get_template_directory_uri());?>/images/skins/<?php echo($skin);?>/default_header.jpg" alt="header image" class="omc-header-image" />

<?php } ?>

<div id="omc-ribbon">

<h1><span class="omc-ribbon-left"></span><span class="omc-ribbon-middle"><?php $term = get_term_by( 'slug', get_query_var( 'term' ), get_query_var( 'taxonomy' ) ); echo $term->name; ?></span><span class="omc-ribbon-right"></span></h1>
<div id="omc-breadcrumb">


<?php if(function_exists('bcn_display')) { bcn_display();}?>

</div><!-- /omc-breadcrumb -->

</div>


</div><!-- /omc-header-under -->


<div class="omc-inner-page-content-wrapper right-sidebar">


<?php if ( is_active_sidebar( 8 ) ) { ?>

<div id="omc-sidebar" class="omc-right">

<ul class="xoxo">

<?php dynamic_sidebar( 'Products Sidebar' ); ?>
</ul>

</div>

<?php } else { get_sidebar(); } ?>

<div id="omc-main-left-column" class="omc-content">
<span class="product-margin"></span>
<?php
wp_reset_query();

$defaults = array(
'product_cats' => ''
);
$args = wp_parse_args( $query_string, $defaults );
$current_cat = get_term_by('name', $args['product_cats'], 'product_cats');

// Gets every "category" (term) in this taxonomy to get the respective posts
$terms = get_terms( 'product_cats', 'child_of='.$current_cat->term_id.'&orderby=count&hide_empty=0' );

//var_dump( $current_cat );

foreach( $terms as $term ) :
//query_posts($query_string . 'term=$term->slug');
$posts = new WP_Query( "taxonomy=product_cats&term=$term->slug" );

?>
<div class"clear"></div>
<br class="clear">

<h2><?php echo $term->name; ?></h2>

<?php
if( $posts->have_posts() ) :
while( $posts->have_posts() ) : $posts->the_post();

$price = get_post_meta(get_the_ID(), 'inception_price', true);
?>
<div class="omc-product-listing">
<a href="<?php the_permalink();?>">

<?php
if(has_post_thumbnail()) {
the_post_thumbnail('product', array('class' => 'omc-product-frame'));
} else {
?>

<img src="<?php echo get_template_directory_uri() ;?>/images/no-image.png" width="170" height="170" class="omc-product-frame" alt="no photo" />

<?php } ?>

</a>

<span class="omc-listing-header"><a href="<?php the_permalink();?>"><?php the_title();?></a></span>
<span class="omc-listing-price"><?php echo($price);?></span>
<span class="omc-listing-more"><a href="<?php the_permalink();?>">&raquo;</a></span>
</div><!-- /omc-product-listing -->
<?php

endwhile;
else:

echo 'no results';

endif; wp_reset_query();

endforeach;


?>
<br class="clear" />
<div class="product-pagination">
<?php kriesi_pagination(); ?>
</div>

</div><!-- /omc-main-left-column -->

<br class="clear" />


</div><!-- /omc-inner-page-content -->



<?php get_footer(); ?>


Giorgio Adriano comments:

Abdessamad,

This version is better, but it lists all categories and all subcategories, not matter what category is selected:

For instance, to be more specific, http://www.discoverypublisher.com/stock/china-guides/ and http://www.discoverypublisher.com/stock/chinese-language/ return the same output.

You can check out the menues from http://www.discoverypublisher.com/


Giorgio Adriano comments:

Abdessamad,

As the site is live, I'm reverting back to the old code for now. If you have a fix, please let me know.

Cheers.
Adriano


Abdessamad Idrissi comments:

Hey Adriano,

I'm working on it and will let you know as soon as I finish customizing ;)


Giorgio Adriano comments:

Sure, thanks!


Abdessamad Idrissi comments:

okay, here you are; check [[LINK href="http://pastebin.com/cb5e9egt"]]this one[[/LINK]].


Giorgio Adriano comments:

Abdessamad,

First class! It's working. Thank you so much my friend.

Cheers,
Adriano


Abdessamad Idrissi comments:

Basiclly what the actual code do is :

* Check if the requested category <strong>HAVE NO</strong> sub categories -> then show the products inside this category.

* If the requested category <strong>HAVE </strong>sub categories -> then show the products organized by sub categories.


Giorgio Adriano comments:

Working great, thank you Abdessamad.


Giorgio Adriano comments:

Abdessamad, I just have a little issue in the code. It's with pagination.

If you go to http://www.discoverypublisher.com/stock/china-guides/ you'll see at the bottom of the page, "Page 1 / 2." However, there's no page 2 there, its content is the same.

The corresponding code has been commented out:


foreach( $terms as $term ) :
//query_posts($query_string . '&posts_per_page=9&paged=' . $paged);
$posts = new WP_Query( "taxonomy=product_cats&term=$term->slug" );



Either we disable pagination, or we enable it with page limit. Either is fine him me.

Thanks.
Adriano


Giorgio Adriano comments:

Just changed "Blog pages show at most" to 30 in Settings. It's seems to be working...


Giorgio Adriano comments:

The things is after I set "Blog pages show at most" to 30, the pagination for the blog at http://www.discoverypublisher.com/category/dp/ breaks, it goes to 404.php upon hitting "Page 2."

Any idea about the cause, Abdessamad?


Abdessamad Idrissi comments:

Well, I checked and it seems working :) http://www.discoverypublisher.com/category/dp/page/3/


Giorgio Adriano comments:

Yes, I've just disabled kriesi_pagination() in taxonomy-product_cats.php and set "Blog pages show at most" back to 10. That's good for me. I don't need pagination for the products.

The blog is working OK with pagination set to 10.

Another last question, Abdessamad. To only display the last level of subcategories, and not the intermediate ones, would that take a lot of effort to implement? This is what I mean, concretely speaking:

Right now, http://www.discoverypublisher.com/stock/chinese-language/ has:

- http://www.discoverypublisher.com/stock/mandarin-english/
- http://www.discoverypublisher.com/stock/mandarin-english-mobile/
- http://www.discoverypublisher.com/stock/mandarin-english-paperback/

- http://www.discoverypublisher.com/stock/mandarin-french/
- http://www.discoverypublisher.com/stock/mandarin-french-paperback/

There's a lot of redundancy in the displayed products. Would it be possible to only display, for http://www.discoverypublisher.com/stock/chinese-language/, the last subcategory level, and not the intermediate ones, like this:

- http://www.discoverypublisher.com/stock/mandarin-english-mobile/
- http://www.discoverypublisher.com/stock/mandarin-english-paperback/
- http://www.discoverypublisher.com/stock/mandarin-french-paperback/

Thanks Abdessamad.
Adriano


Giorgio Adriano comments:

Formatting issue in my last post:

<code>

Right now, http://www.discoverypublisher.com/stock/chinese-language/ has:

> http://www.discoverypublisher.com/stock/mandarin-english/
--- http://www.discoverypublisher.com/stock/mandarin-english-mobile/
--- http://www.discoverypublisher.com/stock/mandarin-english-paperback/

> http://www.discoverypublisher.com/stock/mandarin-french/
--- http://www.discoverypublisher.com/stock/mandarin-french-paperback/

There's a lot of redundancy in the displayed products. Would it be possible to only display, for http://www.discoverypublisher.com/stock/chinese-language/, the last subcategory level, and not the intermediate ones, like this:

- http://www.discoverypublisher.com/stock/mandarin-english-mobile/
- http://www.discoverypublisher.com/stock/mandarin-english-paperback/
- http://www.discoverypublisher.com/stock/mandarin-french-paperback/
<code>


Abdessamad Idrissi comments:

I think this you can organize it in the custom menu: put only the categories you want to show.


Giorgio Adriano comments:

Abdessamad, what happens is when the loop goes through /stock/chinese-language/, it lists everything under /stock/mandarin-english/ along with its subcategories, then lists everything under each subcategories. We then end up with twice a many products that we should have:

> http://www.discoverypublisher.com/stock/mandarin-english/ => 4x
--- http://www.discoverypublisher.com/stock/mandarin-english-mobile/ => 1x
--- http://www.discoverypublisher.com/stock/mandarin-english-paperback/ => x3

Total 8 products, but there are actually 4.

Same for:

> http://www.discoverypublisher.com/stock/mandarin-french/ => 2x
--- http://www.discoverypublisher.com/stock/mandarin-french-paperback/ => x2

Total 4 products, but there are actually 2.


Abdessamad Idrissi comments:

Hey Giorgio,

I checked again your website and seems it is working without duplicate products.

The only problem I see now is if you go for example to [[LINK href="http://www.discoverypublisher.com/stock/china-guides/"]]this page[[/LINK]], at the bottom you will see that it shows 2 products in a row instead of 3 per row. To fix this you may comment out the line 20 in "js/scripts" that says
//$omc("div.omc-product-listing:nth-child(4), div.omc-product-listing:nth-child(7), div.omc-product-listing:nth-child(10), ").css("margin-right", "0px");

and in the "taxonomy-product_cats" change the code in the begining of the two loops to something like:

<h2><?php echo $term->name; ?></h2>

<?php
$i = 0;
$style = '';
if( $posts->have_posts() ) :
while( $posts->have_posts() ) : $posts->the_post();

$i++;
// fixes the margin of each 3rd product in the loop (instead of using jQuery)
if (($i % 3) == 0) $style = ' style="margin-right: 0px;" '; else $style = '';
?>
<div class="omc-product-listing" <?php echo $style; ?>>

I updated the full script at [[LINK href="http://pastebin.com/cb5e9egt"]]pastebin.com[[/LINK]]


Giorgio Adriano comments:

Hi Abdessamad, that works superbly well, thank you. I saw that issue, but I didn't want to bother you with it. So, thanks again for the extra effort.

Regarding the other issue, I'm going to reiterate it again here. However, I know that you've spent a lot of time on this question, so if you think you can change the code in order to satisfy this request, I'll post another question at USD25 for your to pick up and address. It's only fair, considering the work involved.

Firstly, all menues that have one-level children are working perfectly. There's no duplicate products under them.
I'm referring here to, for instance:
- http://www.discoverypublisher.com/international-stores/
- http://www.discoverypublisher.com/stock/china-guides/

The issue is with this menu, which has more than one levels of children:
- http://www.discoverypublisher.com/stock/chinese-language/

This category is "Chinese Language". Under it, there are 2 categories:

- Mandarin (in English)
-- Mobile Apps => 1 product
-- Paperback => 3 products
- Mandarin (in French)
-- Paperback => 2 products

"Chinese Language" has then in total 1+3 + 2, total 6 products.

What is this page at the moment, at: http://www.discoverypublisher.com/stock/chinese-language/ are 12 products instead of 6. The reason why is because the loops produces this:

- Mandarin (in English) => 4 products
-- Mobile Apps => 1 product
-- Paperback => 3 products
- Mandarin (in French) => 2 products
-- Paperback => 2 products

which the result of all categories+subcategories products (4+1+3), AND all subcategories products (1+3+2), which is 12.

What the loop should produce is:

- Mandarin (in English) => Display Nothing
-- Mobile Apps => 1 product
-- Paperback => 3 products
- Mandarin (in French) => Display Nothing
-- Paperback => 2 products

Kindly let me know if I have been clear and if you could address this new request.
Adriano


Abdessamad Idrissi comments:

All right ;)

Now It's much more clear.

I'll reproduce the same organization in my local WordPress Lab (Whoohoo! ) and be back to you with satisfying results!


Giorgio Adriano comments:

Abdessamad, I've just opened a 2nd question: http://wpquestions.com/question/show/id/3144

Cheers,
Adriano

2011-10-13

Luis Cordova answers:

so if this working http://pastebin.com/cb5e9egt ? or not?

thanks!


Giorgio Adriano comments:

Yes, it's working just fine. Go ahead!