I have a layout where we want to place the custom posts types on alternating rows and 2 & 3 columns.
so basically:
<div class="wrapper">
<div class="row">
<div>post 1</div>
<div>post 2</div>
</div>
<div class="row">
<div>post 3</div>
<div>post 4</div>
<div>post 5</div>
</div>
<!-- then 2 new row with 2 columns followed by 3 columns and so on -->
</div>
Any suggestions?
$args = array(
'posts_per_page' => -1,
'post_type' => 'post',
);
$the_query = new WP_Query($args);
if (!empty($the_query->posts)) {
$count_post_row = 0;
$rowcount = 1;
echo '<div class="wrapper">'; // start wrapper
foreach ($the_query->posts as $post) {
$count_post_row++;
if ($count_post_row == 1) {
echo '<div class="row">'; // start row
}
echo '<div>' . $post->post_title . '</div>';
if ($rowcount == 1 && $count_post_row == 2) {
$count_post_row = 0;
$rowcount = 2;
echo '</div>'; // end row if its first section and 2 post add
}
if ($rowcount == 2 && $count_post_row == 3) {
$rowcount = 1;
$count_post_row = 0;
echo '</div>'; // end row if its second section and 3 post add
}
}
echo '</div>'; // start wrapper
}
This is the code you got your results and its continue as your requirements you can check the screenshot below.. If need any more help drop the comment or message will help..
Related
I am trying to make something like the image.
I'm using WordPress and woocommerce and would like to display products like this.
This is the normal html that does the work.
I need to be able to put it into a loop:
<div class="container" style="width: 100%">
<div class="row">
<div class="col-lg-3 col-md-3 col-sm-3 col-xs-3">Span 3</div>
<div class="col-lg-3 col-md-3 col-sm-3 col-xs-3">
<div>Span 2</div>
<div>Span 2</div>
<div>Span 2</div>
</div>
</div>
</div>
I am using the bootstrap grid.css
Here is what I have done:
while ($loop->have_posts()) : $loop->the_post();
if ($product_counter < $product_counter_max) {
if ($grid_counter == 0) { ?>
<div class="col-lg-3 col-md-3 col-sm-3 col-xs-3">
<img src="<?php echo get_the_post_thumbnail_url($loop->post->ID); ?>"/>
<?php echo get_the_title();
$product = wc_get_product($loop->post->ID);
/**reviews**/
$average = $product->get_average_rating($loop->post->ID);
$review_count = $product->get_review_count($loop->post->ID);
if ($average != 0) {
for ($x = 0; $x < 5; $x++) {
if ($x < $average) {
echo '<i class="fa fa-star swatchchecked"></i>';
} else {
echo '<i class="fa fa-star"></i>';
}
}//for loop
}//end of if
else {
echo "No Rating Yet";
}//end of reviews
echo '<p>' . sprintf("%.2f", $product->get_price()) . '</p>';
?>
</div>
<?php
} else {
?>
<div style="clear: both">there</div>
<?php
}
}
$grid_counter++;
$product_counter++;
endwhile;
} else {
echo __('No products found');
}
wp_reset_postdata();
I'm not sure how to make the little items stack 3 on top of each other like the image
Please help!
So here's a way to create the grid layout you want. While the minute details aren't included in this answer, what I'm providing for you should give you enough of an idea of how to set up the inner portions to layout how you want those to layout.
If it was me... I'd set it up so that with your incremented grid, you can make different layouts for the columns 1 and 3 vs column 2 and 4. But like I said, this should point you in the right direction.
// Not sure why you are using a counter value when you can
// set the loop to return whatever you want. But you didn't show your loop
$product_counter_max = 8;
// Set grid counter at 1;
$grid_counter = 1;
$product_counter = 0;
echo '<div class="row">';
if ($loop->have_posts()){
while ($loop->have_posts()) : $loop->the_post();
// This next line could be superflous based on earlier comment
if ($product_counter < $product_counter_max) {
if ($grid_counter == 1 || $grid_counter == 5 ) {
echo '<div class="col-3">';
} else {
// Add an extra wrapper div around the second and fourth column
if ($grid_counter == 2 || $grid_counter == 6 ) echo '<div class="col-3">';
// This is an inner column
echo '<div class="col-12">';
}?>
<img src="<?php echo get_the_post_thumbnail_url($loop->post->ID); ?>"/>
<?php echo get_the_title();
$product = wc_get_product($loop->post->ID);
/**reviews**/
$average = $product->get_average_rating($loop->post->ID);
$review_count = $product->get_review_count($loop->post->ID);
if ($average != 0) {
for ($x = 0; $x < 5; $x++) {
if ($x < $average) {
echo '<i class="fa fa-star swatchchecked"></i>';
} else {
echo '<i class="fa fa-star"></i>';
}
}//for loop
}//end of if
else {
echo "No Rating Yet";
}//end of reviews
echo '<p>' . sprintf("%.2f", $product->get_price()) . '</p>';
?>
</div>
<?php
if ($grid_counter == 4 || $grid_counter == 8 ) echo '</div>';
}
$grid_counter++;
$product_counter++;
endwhile;
} else {
echo __('No products found');
}
wp_reset_postdata();
echo '</div>';
I'm using the following working code to wrap every 3 elements in a div:
$count = 1
foreach( $names as $name ):
if ($count%3 == 1) {
echo '<div class="wrap">';
}
echo $name;
if ($count%3 == 0) {
echo '</div>';
}
$count++;
endforeach;
if ($count%3 != 1) echo "</div>";
That returns:
<div class="wrap">
name
name
name
</div>
<div class="wrap">
name
name
name
</div>
<div class="wrap">
name
name
name
</div>
<div class="wrap">
name
name
name
</div>
So far so good.. but i want the second wrapped set to have 4 "name" elements like so:
<div class="wrap">
name
name
name
</div>
<div class="wrap">
name
name
name
name
</div>
<div class="wrap">
name
name
name
</div>
<div class="wrap">
name
name
name
</div>
Every 3 items should be wrapped in the div, except the second set which will have 4 items.
Or another way to explain: items 4 to 8 will be wrapped in a div while every other 3 items will be wrapped in div.
How can this be achieved?
Add special cases for the first two DIVs, and adjust the modulus for the ones after that.
$count = 1
foreach( $names as $name ):
if ($count == 1 || $count == 4 || ($count > 5 && $count % 3 == 2)) {
echo '<div class="wrap">';
}
echo $name;
if ($count == 3 || $count == 7 || ($count > 7 && $count % 3 == 1)) {
echo '</div>';
}
$count++;
endforeach;
// Finish the last block -- lots of different cases
if ($count < 4 || ($count > 4 && $count < 8) || ($count > 8 && $count % 3 != 2)) {
echo '</div>';
}
I am using ACF repeater to display images, I want to achieve layout so that 1 - 2 - 3 elements go with col-lg-4 grid and 4-5-6-7 go with col-lg-3 grid and so on, repeating that layout for all items
I've tried using but it's to get 3 elements into 1 div
mostly my layout will be
first row 3x col-lg-4
second row 4x col-lg-3
third row 3x col-lg-4
fourth row 4x col-lg-3
<?php
// check if the repeater field has rows of data
if( have_rows('gallery_repeater') ):
// loop through the rows of data
// add a counter
$count = 0;
$group = 0;
while ( have_rows('gallery_repeater') ) : the_row();
// vars
$teacher_bio = get_sub_field('image');
if ($count % 3 == 0) {
$group++;
?>
<div id="teachers-<?php echo $group; ?>" class="cf group-<?php echo $group; ?>">
<?php
}
?>
<div class="teacher">
<img src="<?php the_sub_field('image'); ?>" />
<?php echo $teacher_bio; ?>
</div><!-- .teacher -->
<?php
if ($count % 3 == 2) {
?>
</div><!-- #teachers -->
<?php
}
$count++;
endwhile;
else :
// no rows found
endif;
?>
Hi Please check below code for reference :
$gallery_repeater = get_field('gallery_repeater');
foreach (array_chunk($gallery_repeater, 7) as $key => $value) {
foreach ($value as $k => $val) {
$class = $k < 3 ? 'col-lg-3' : 'col-lg-4';
echo '<div class="'.$class.'"> <img src="'.$val['image'].'" />'.$val['teacher_bio'].'</div>';
}
}
So I have a question similar to this one but I'm applying it only in vanilla PHP and not in wordpress. After countless hours of struggle I finally got the answer but somehow if I increase the size of my grid number the items are not aligning.
I want it to look like this:
-----------
- 1 2 3 4 -
-----------
But:
As stated on my problem if I tried to increase the grid (or more precisely the item) it becomes like this:
-----------
- 1 2 3 4 -
- 5 -
-6 -
-7 -
-----------
It becomes cluttered. Below is the code that I'm trying to experiment.
<div class="container">
<?php
$i=0;
$item=0;
$html_tag = '<div class = "row"><div class="col 3">';
while($item <= 4)
{
?>
<?php if($i % 4 == 0) {
$html_tag .= 'col '.$i.'</div>';
}
else {
$html_tag .= '<div class="col"> col '.$i.'</div>';
}
?>
<?php
$i++;
$item++;
}
$html_tag .= '</div>';
?>
<?php echo $html_tag ?>
P.S. I'm using twitter bootstrap 4 for it's responsiveness.
EDIT:
Notice the screenshot below, I just realized that there is an extra text which is 'col ?3' inside the div row instead of another div column (which wasn't created).
You should inspect your code, the final structure is not correct.
This is what you got
<div class="container">
<div class="row">
<div class="col 3">col 0</div>
<div class="col"> col 1</div>
<div class="col"> col 2</div>
<div class="col"> col 3</div>
col 4
</div>
</div>
Try with this code
$html = '';
$totalItemPerLine = 3;
$totalItem = 7;
for($i = 0; $i < $totalItem; $i++)
{
if($i % $totalItemPerLine == 0)
{
$html .= '<div class="row">'; // OPEN ROW
}
$html .= '<div class="col"> col '.$i.'</div>';
if($i % $totalItemPerLine == ($totalItemPerLine-1))
{
$html .= '</div>'; // CLOSE ROW
}
}
echo $html;
NOTE: You could do exactly the same with a while, but I used a for for the readability
EDIT:
Based on your comment #DavidDiaz this is the code directly with HTML
But I recommend you to learn POO and use class to do this page
$html = '';
$totalItemPerLine = 3;
$totalItem = 7;
for($i = 0; $i < $totalItem; $i++)
{
if($i % $totalItemPerLine == 0)
{?>
<div class="row"> <!-- OPEN ROW -->
<?php } ?>
<div class="col"> col <?= $i ?> </div>
<?php if($i % $totalItemPerLine == ($totalItemPerLine-1))
{ ?>
</div> <!-- CLOSE ROW -->
<?php }
} ?>
Something wrong with the accepted answer. It doesn't close the last row. It needs another condition.
$html = '';
$totalItemPerLine = 3;
$totalItem = 7;
for($i = 0; $i < $totalItem; $i++)
{
if($i % $totalItemPerLine == 0)
{
$html .= '<div class="row">'; // OPEN ROW
}
$html .= '<div class="col"> col '.$i.'</div>';
if($i % $totalItemPerLine == ($totalItemPerLine-1) || $i == ($totalItems-1))
{
$html .= '</div>'; // CLOSE ROW
}
}
echo $html;
I have an ACF Repeater field i'd like to output as an accordion grid, like so:
<div class="intro row">
<div class="item item-1">name 1</div>
<div class="item item-2">name 2</div>
<div class="item item-3">name 3</div>
<div class="item item-4">name 4</div>
</div>
<div class="expanded row">
<div class="expand" id="item-1">expanded info 1</div>
<div class="expand" id="item-2">expanded info 2</div>
<div class="expand" id="item-3">expanded info 3</div>
<div class="expand" id="item-4">expanded info 4</div>
</div>
<div class="intro row">
<div class="item item-5">name 5</div>
<div class="item item-6">name 6</div>
<div class="item item-7">name 7</div>
<div class="item item-8">name 8</div>
</div>
<div class="expanded row">
<div class="expand" id="item-5">expanded info 5</div>
<div class="expand" id="item-6">expanded info 6</div>
<div class="expand" id="item-7">expanded info 7</div>
<div class="expand" id="item-8">expanded info 8</div>
</div>
I can group the initial row fine, it's just the second "expanded" row i'm having trouble with. How can I repeat and group the second row of 4 correctly in the same loop? My current PHP:
<?php // check if the repeater field has rows of data
if( have_rows('features') ):
// loop through the rows of data
// add a counter
$count = 0;
$group = 0;
while ( have_rows('features') ) : the_row();
$name = get_sub_field('feature_name');
$expandedInfo = get_sub_field('feature_info');
if ($count % 4 == 0) {
$group++;
?>
<div class="intro row">
<?php
}
?>
<div class="item item-<?php echo $count; ?>">
<?php echo $name ?>
</div><!-- item-->
<?php
if ($count % 4 == 3) {
?>
</div><!-- intro-->
<?php
}
$count++;
endwhile;
else :
// no rows found
endif;
?>
The second 'expanded' row can be done so that you store each count (item-1,item-2) in an array or just traverse through all the count when you close the intro row.
<?php
if ($count % 4 == 3) {
?>
</div><!-- intro-->
<div class="expanded row">
<?php
$start = $count-3;
// if $count is 4, $start will be 1, and the $i will go to 4
// if $count is 8, $start will be 5
for($i=$start;$i<=$count;$i++){
echo '<div class="expand" id="item-' . $i . '"></div>';
} ?>
</div>
<?php
}
This is just an example. I would suggest you to store each $count in an array and then use the count($array) to get the number of them. After you have traversed the array, reset it.
The Array Approach
<?php // check if the repeater field has rows of data
if( have_rows('features') ):
// loop through the rows of data
// add a counter
$count = 0;
$group = 0;
// Content Array
$content_array = array();
while ( have_rows('features') ) : the_row();
$name = get_sub_field('feature_name');
$expandedInfo = get_sub_field('feature_info');
// Adding the Expanded Info
$content_array[ 'item-' . $count ] = $expandedInfo;
if ($count % 4 == 0) {
$group++;
?>
<div class="intro row">
<?php
}
?>
<div class="item item-<?php echo $count; ?>">
<?php echo $name ?>
</div><!-- item-->
<?php
if ($count % 4 == 3) {
?>
</div><!-- intro-->
<div class="expanded row">
<?php
foreach( $content_array as $item_id => $expanded_info ) {
echo '<div class="expanded" id="' . $item_id . '">';
echo $expanded_info;
echo '</div>';
} ?>
</div>
<?php
// Resetting the Array
$content_array = array();
}
$count++;
endwhile;
else :
// no rows found
endif;
?>
okey, lets see ,
using variables to store your templates may helps a lot in this context ,
as follow :
$intro = '';
$expanded = '';
while (have_rows('features')) :
the_row();
if ($count % 4 == 0) {
$group++;
$intro .= '<div class="intro row">';
$expanded .= '<div class="expanded row">';
}
$intro .= '<div class="item item-' . $count . '"></div><!-- item-->';
$expanded .= '<div class="expand" id="item-' . $count . '"></div>';
if ($count % 4 == 3) {
$intro = '</div><!-- intro-->';
$expanded = '</div><!-- intro-->';
}
$count++;
endwhile;
I've made a quick example to explain to show you how using variables may fix your issue : https://3v4l.org/cKPP4
Can't test it right now, but I think something like that should work.
<?php // check if the repeater field has rows of data
if( have_rows('features') ):
// loop through the rows of data
// add a counter
$count = 0;
$group = 0;
$array = array();
while ( have_rows('features') ) : the_row();
$name = get_sub_field('feature_name');
$expandedInfo = get_sub_field('feature_info');
if ($count % 4 == 0) {
$group++;
?>
<div class="intro row">
<?php
}
?>
<div class="item item-<?php echo $count; ?>">
<?php echo $name ?>
</div><!-- item-->
<?php
array_push($array, $expandedInfo);
if ($count % 4 == 3) {
?>
</div><!-- intro-->
<div class="expanded row">
<?php
for ($i=0; $i < count($array); $i++) {
echo '<div class="expand" id="item-'.$i + 1.'">'.$array[$i].'</div>';
}
echo '</div>';
}
$count++;
endwhile;
else :
// no rows found
endif;
?>