I have an array of images.
In the array, for each image, I have whether the image is tall or wide.
I need to loop through all of the images, and pair a tall with wide into a div, then move to the next until they are all done.
I have something that sort of works using a foreach loop, but the problem is that some images get skipped … the loop stops when each image has gone through the loop, which is standard behavior for a “foreach” loop, from what I have read…
So now I am wondering if there is a different loop I should use, or should I put my foreach loop inside another loop so that it repeats until the images are used up?
Here is my loop so far, that does what I want, but leaves out several images:
$num_of_images = count($images);
$notins = array();
$order = 1;
$i = 0;
//start my loop
foreach ($images as $image) {
$id = $image->ID;
//check if image is in the notins array..skips if it is
if (!in_array($id, $notins)){
//find out if the image is tall or wide
$attach = wp_get_attachment_image_src( $id, 'full');
$height = $attach['2'];
$width = $attach['1'];
if ($height < $width) { $size = "wide" ;} else { $size = "tall" ;}
//get the link to the sized image
$preview_array = image_downsize( $image->ID, $size );
$img_preview = $preview_array[0]; // thumbnail or medium image to use for preview.
if( $order == 3 ){ //if previous slide was tall, get a wide slide
if($size == "wide") { $order = 1; array_push($notins, $id); $i++; ?>
<!-- - - - - - - - - - - Image - - - - - - - - - - - - - -->
<div class="image <?php echo $size; ?>" style="background: url(<?php echo $img_preview; ?>) no-repeat center !important; background-size: cover !important; max-width: 100%; ">
</div>
<!-- - - - - - - - - - - end Image - - - - - - - - - - - - - -->
</li><!--.slide --><?php
}
}
if( $order == 2 ){ //if previous slide was wide, get a tall slide
if($size == "tall" ) { $order = 1; array_push($notins, $id); $i++; ?>
<!-- - - - - - - - - - - Image - - - - - - - - - - - - - -->
<div class="image <?php echo $size; ?>" style="background: url(<?php echo $img_preview; ?>) no-repeat center !important; background-size: cover !important; max-width: 100%; ">
</div>
<!-- - - - - - - - - - - end Image - - - - - - - - - - - - - -->
</li><!--.slide --><?php
}
}
if( $order == 1) { //if this is the first slide in the div
if( !in_array($id, $notins) ) { $i++; array_push($notins, $id); ?>
<li class="the-slide gallery">
<!-- - - - - - - - - - - Image - - - - - - - - - - - - - -->
<div class="image <?php echo $size; ?>" style="background: url(<?php echo $img_preview; ?>) no-repeat center !important; background-size: cover !important; max-width: 100%; ">
</div>
<!-- - - - - - - - - - - end Image - - - - - - - - - - - - - --><?php
if( $i == 17 ){ ?> </div><!--.slide --> <?php }
if($size == "wide"){ $order = 2; } if($size == "tall"){ $order = 3; } } }
}
}
}
These answers are provided by our Community. If you find them useful, show some love by clicking the heart. If you run into issues leave a comment, or add your own answer to help others.
This question was answered by @sierracircle:
Okay, using @ryanpq idea of putting everything into two arrays has worked. I can reverse the order of using the larger or smaller of the two arrays, depending on if I want images to show up that do not have a partner image.
Here are my loops (tested and works):
if ($images) { $tall = array(); $wide = array(); foreach ($images as $image) { $id = $image->ID; $attach = wp_get_attachment_image_src( $id, 'full'); $height = $attach['2']; $width = $attach['1']; if ($height < $width) { $size = "wide" ;} else { $size = "tall" ; } if( $size == 'tall') { array_push($tall, $id); } if( $size == 'wide') { array_push($wide, $id); } } //get everything into two arrays //get the larger and smaller of the two arrays if(count($tall) > count($wide)){ $large = $tall; $small = $wide; $size = "tall"; $sm_size = "wide"; } else { $large = $wide; $small = $tall; $size = "wide"; $sm_size = "tall";} //now loop through the smaller array $i = 0; foreach($large as $image) { $id = $image; $previews = image_downsize( $id, $size ); $img = $previews[0]; $sm_id = $small[$i]; $sm_previews = image_downsize( $sm_id, $sm_size ); $sm_img = $sm_previews[0]; ?> <li class="the-slide gallery"> <!-- - - - - - - - - - - Image - - - - - - - - - - - - - --> <div class="image <?php echo $size; ?>" style="background: url(<?php echo $img; ?>) no-repeat center !important; background-size: cover !important; max-width: 100%; "> </div> <!-- - - - - - - - - - - end Image - - - - - - - - - - - - - --> <!-- - - - - - - - - - - Image - - - - - - - - - - - - - --> <div class="image <?php echo $sm_size; ?>" style="background: url(<?php echo $sm_img; ?>) no-repeat center !important; background-size: cover !important; max-width: 100%; "> </div> <!-- - - - - - - - - - - end Image - - - - - - - - - - - - - --> <?php $i++; } } //if images
…
Okay, using @ryanpq idea of putting everything into two arrays has worked. I can reverse the order of using the larger or smaller of the two arrays, depending on if I want images to show up that do not have a partner image.
Here are my loops (tested and works):
…
Thanks for the idea @ryanpq
If you want to pair one tall with one wide for each div maybe you should use your first foreach to push the elements into two arrays $tall and $wide and then loop through the larger of these two arrays grabbing one element from each array for each loop. You may have to do a bit more if one array ends up larger than the other but that would depend on how you want things to display in the end if the arrays have a non-equal number of items.