I have a set of 12 circles, some will be blank, some will have an icons (this is driven by Wordpress whether they have an icon or not).
I then have a standard Wordpress loop looking for icons, if an icon is present then it will output. It also iterates the $counter variable starting at 1.
How can I take the count of that - then create a new loop to create blank circles?
So for instance, if 5 circles have icons then I would need 7 blank circles.
This is my attempt, at the moment it's creating an infinite loop. So from the example this needs to output 7, with the class name outputting the numbers 7, 8, 9 etc up to 12 to fill in the blanks.
Where am I going wrong?
<?php $final = 12 - $counter;
for($count = 1; $count <= $final; $count++) { ?>
<a class="research-circle blank-circle rs-<?php echo $final; ?>" href="#"></a>
<?php $final++; } ?>
It's infinite because you're increasing both values simultaneously.
Try this:
for($count = 1; $count <= $final; $count++) { ?>
<a class="research-circle blank-circle rs-<?php echo ($final + $count); ?>" href="#">
</a>
<?php }
?>
Look inside your loop condition: You tell PHP to loop until $count is greater than $final.
But in your loop, you increase both $count and $final value. $count will never be greater than $final.
Related
I have a working php code which made a numerical loop counting up from 1.
<?php
$i = 0; // define number
while (have_rows('the_rows')) : row(); // begin while loop
$i++; // increase increment with each loop ?>
<div>
<?php echo $i; // outputting the number ?>
</div>
<?php
endwhile; // end while loop
?>
This code will loop through all available entries and stop after there are no more entries. It will count up for each $i output.
For example, it might look like this:
<div>1</div>
<div>2</div>
<div>3</div>
<div>4</div>
<div>5</div>
<div>6</div>
<div>7</div>
There is no pre-set number. It could be any number including 1, 5, 74, or 938 entries. The loop will continue to all entries and stops after all entries are finished.
This works fine if I start at one. But since the number is not fixed, looping backwards is a tad more difficult.
How can I reverse this loop so that first of all, it counts the numbers backwards (e.g. if there are 7 rows, it counts backwards from 7), and also to reverse the loop starting with the last row?
e.g.
<div>7</div>
<div>6</div>
<div>5</div>
<div>4</div>
<div>3</div>
<div>2</div>
<div>1</div>
If you don't know the length of the data, get the length of the data and then print it out, in reverse.
<?php
$i = 0;
while(has_rows('the_rows')):
row();
$i++;
endwhile;
while($i > 0):
?>
<div><?php echo $i--; ?></div>
<?php endwhile; ?>
Without knowing the number of rows in advance and without looping twice, you have several options.
One is to build an array and reverse it:
<?php
$i = 0;
while (have_rows('the_rows')) : row();
$i++;
$html[] = "
<div>
$i
</div>";
endwhile;
echo implode(array_reverse($html));
Or prepend each one onto an array:
<?php
$i = 0;
while (have_rows('the_rows')) : row();
$i++;
$html = "
<div>
$i
</div>";
array_unshift($data, $html);
endwhile;
echo implode($data);
Or prepend the new string to the existing one:
<?php
$i = 0;
$html = "";
while (have_rows('the_rows')) : row();
$i++;
$html = "
<div>
$i
</div>$html";
endwhile;
echo $html;
However this looks like WordPress or something, so I would think there would be a way to get the number of rows before the loop.
I'm pretty new to PHP but I have built some fairly simple WordPress themes in my time. I'm trying to make something unique and I'm not sure how to accomplish it (or if it's even possible).
My goal is to create a loop that will dynamically close rows when it reaches the column "12" count for bootstrap (IE: col-md-3 + col-md-3 + col-md-6 = 12). The look I'm ultimately trying to achieve and how I currently have my static file set up => https://jsfiddle.net/y2mLr3hd/7/embedded/result/. I'm only using "display: flex;" for right now to just demonstrate what I'm trying to achieve. I'd like it be just rows rather than a single row.
I'm use to the standard loop for WordPress using ULs and LIs but I have no idea on how to go about what I'm trying to do. I'd like the loop to figure a random number for the column size consisting of the column sizes "3, 4, 6, 8" and create rows with columns sizes equaling "12" like I stated before. THAT or find a way on how to make it work with the way I currently have it set up.
This is the closest thing to what I'm looking for but really isn't even that close =>https://stackoverflow.com/questions/16427962/twitter-bootstrap-spans-in-dynamic-websites#=. Here's the code from that link for quick reference:
$i=0;
foreach ($posts as $post):
if ($i%2==0) echo '<div class="row-fluid">';
echo '<div class="span6">'. $post->content .'</div>';
if ($i%2==1) echo '</div>';
$i++;
endforeach;
Any help on how I might be able to go about this would be GREATLY appreciated!
There are two parts to your question:
How to divide 12 in random parts using 3, 4, 6, and 8
Given an array of numbers that add up to 12, how to generate a row with posts?
The first one is more a mathematics question. Note that you can only combine 3s and 6s, or 4s and 8s. You cannot combine 3 and 4, and still get 12.
We'll devise a simple algorithm with this in mind:
function getRandomNumbers()
{
// We start with an empty array and add numbers until we hit 12.
$result = array();
// We choose either 3 or 4 as basic number.
$x = mt_rand(3, 4);
// Now, as long as we don't hit 12, we iterate through a loop,
// adding either the basic number, or 2 times the basic number:
while (array_sum($result) < 12) {
// Randomly decide
if (mt_rand(0, 1) > 0) {
$newElement = 2 * $x; // This is either 6 or 8
// However, always make sure not to exceed 12:
if (array_sum($result) + $newElement > 12) {
$newElement = $x;
}
} else {
$newElement = $x; // This is either 3 or 4
}
// Add the new number to the array:
$result[] = $newElement;
}
// Return the resulting array
return $result;
}
Now we need to use these arrays to create rows. We start by generating an array with random numbers with the function we wrote.
We'll simply iterate through the posts, use the numbers in the array until there's none left. We'll generate a new array with random numbers whenever we need a new one. Since that means we have added 12 width-worth of columns, that's the point where we need to start a new row as well.
// Get the initial array with random numbers
$randomArray = getRandomNumbers();
// Open the initial row.
echo '<div>';
foreach ($posts as $post):
if (count($randomArray) < 1) {
// Close the row and start a new one:
echo '</div><div>';
// Get a fresh array with random numbers:
$randomArray = getRandomNumbers();
}
$nextRandomNumber = array_pop($randomArray); // This takes the next number.
echo '<div class="col-md-' . $nextRandomNumber . '">'. $post->content .'</div>';
endforeach;
echo '</div>'; // Close the final row.
Newb question: I'm using a foreach loop to get items from an array.
I need to start looping at an offset number- (I'm using a $i variable to do this, no problem).
But when my foreach reaches the end of the array I want it to start going through the array again until it reaches the offset number.
I need to do this so I can have a user open any image in an artist's portfolio and have this image used as the first image presented in a grid of thumbnail icons , with all the other images subsequently populating the rest of the grid.
Any ideas?
Please bear in mind I'm new to PHP! :)
See below for an example of my current code...
$i=0;
$limit=50;// install this in the if conditional with the offset in it (below) to limit the number of thumbnails added to the page.
$offset=$any_arbitrary_link_dependant_integer;
foreach($portfolio_image_array as $k=>$image_obj){//$k = an integer counter, $image_obj = one of the many stored imageObject arrays.
$i++;
if ($i > $offset && $i < $limit) {// ignore all portfolio_array items below the offset number.
if ($img_obj->boolean_test_thing===true) {// OK as a way to test equivalency?
// do something
} else if ($img_obj->boolean_test_thing===false) { // Now add all the non-see_more small thumbnails:
// do something else
} else {
// error handler will go here.
}
} // end of offset conditional
}// end of add boolean_test_thing thumbnails foreach loop.
};// end of add thumbnails loop.
$i = 0;
$limit = 50;
$offset = $any_arbitrary_link_dependant_integer;
$count = count($portfolio_image_array);
foreach($portfolio_image_array as $k=>$image_obj){//$k = an integer counter, $image_obj = one of the many stored imageObject arrays.
$i++;
if ($i > $offset && $i < $limit && $i < ($count - $offset)) {// ignore all portfolio_array items below the offset number.
if ($img_obj->boolean_test_thing===true) {// OK as a way to test equivalency?
// do something
} else if ($img_obj->boolean_test_thing===false) { // Now add all the non-see_more small thumbnails:
// do something else
} else {
// error handler will go here.
}
} // end of offset conditional
}// end of add boolean_test_thing thumbnails foreach loop.
};
Only thing I added was a $count variable.
Edit: If your array starts at 0 I would suggest you put the $i++; at the end of your foreach loop.
A simple method is to use two separate numeric for loops, the first going from offset to end, and the second going from beginning to offset.
<?php
// Create an example array - ignore this line
$example = array(1,2,3,4,5,6);
$offset = 3;
// Standard loop stuff
$count = count($example);
for($i = $offset; $i < $count; $i++)
{
echo $example[$i]."<br />";
}
for($i = 0; $i < $offset; $i++)
{
echo $example[$i]."<br />";
}
?>
This is also almost certainly cheaper than doing multiple checks on every single element in the array, and it expresses exactly what you are trying to do to other programmers who look at this code - including yourself in 2 weeks time.
Edit: depending on the nature of the array, in order to use numeric keys you may first need to do $example = array_values($portfolio_image_array);.
Using Answer Question to force StackOverflow to let me post a decent length of text!
OK #Mark Walet et al, not sure how to post correctly on this forum yet but here goes. I got the issue sorted as follows:
$i=0;
$offset=$image_to_display_number;
$array_length = count($portfolio_image_array);
// FIRST HALF LOOP:
foreach($portfolio_image_array as $k=>$img_obj){// go through array from offset (chosen image) to end.
if ($i >= $offset && $i <= $array_length) {
echo write_thumbnails_fun($type_of_thumbnail, $image_path, $k, $i, $portfolio_image_array, $title, $image_original);
$t_total++;// update thumbnail total count.
}
$i++;
}// end of foreach loop 1.
$looped=true;// Just FYI.
$i=0;// Reset.
// SECOND HALF LOOP:
foreach($portfolio_image_array as $k=>$img_obj){// go through array from beginning to offset.
if ($i < $offset) {
echo write_thumbnails_fun($type_of_thumbnail, $image_path, $k, $i, $portfolio_image_array, $title, $image_original);
}
$i++;
}// end of foreach loop 2.
Thankyou so much for all the help!
:)
as #arkascha suggested use modulo operator
<?php
$example = array(1,2,3,4,5,6);
$count = count($example);
$offset = 3;
for($i = 0; $i < $count; $i++) {
$idx = ($offset + $i) % count
echo $example[$idx]."<br />";
}
?>
I dont know if this is possible, but im trying to get pagination from a get_pages() function of Wordpress since i need those pages being echo with different classes or inside some div so I can manage them with Javascript later to match the desire template.
So far I have this to echo the content:
$pages = get_pages('child_of='.$post->ID.'&sort_column=post_date&sort_order=desc');
$i =0;
foreach($pages as $page)
{
$content = $page->post_content;
if(!$content)
continue;
$i++;
$content = apply_filters('the_content', $content);
$doc = new DOMDocument();
$doc->loadHTML($content);
$xpath = new DOMXPath($doc);
$imagesrc = $xpath->evaluate("string(//img/#src)");
$imagehref = $xpath->evaluate("string(//a/#href)");
for($i = 0; $i < count($content); $i+=5) {
echo "<li><a id='item-$i' href='$imagehref'><img src='$imagesrc'/></a></li>\n";
for($i = 5; $i < count($content); $i+=18) {
echo "more";
}
}
So right now i do get all items no matter if there is 10 or 50, but what i want it is to put them in blocks of 8, is that possible to do inside a for each? or there is another way to do it?
Note I need to plit large set of posts into blocks of 8
any help will be really appreciated
thanks :)
An alternative to #aelfric5578's answer is to use array_chunk to break the array into the pieces you need. You could break the original $pages array or generate an array in the foreach and break that, whichever works best for you but I'd probably break the $pages array. Here is an example using the original $pages.
$blocks = array_chunk($pages, 8);
The benefit is going to be readability and maintainability. Since you already have an iterator-- and maybe should have maybe two, you seem to be using the same variable name twice-- it could get confusing to add more counters.
You need a separate counter. Since you already have $i you can use a conditional and the modulo operator. $i % 8 returns zero if $i is divisible by 8 and the remainder of that division otherwise.
So, if $i % 8 == 0, start your grouping. Assuming you plan on grouping things with a <div> or something like that. You can close your grouping after $i % 8 == 7 at the end of your for loop.
However, it seems you're setting $i twice. Is there a reason for this? For my solution to work, you would need to use a different variable for the inner for loop.
I am facing an problem. I have built a foreach loop in PHP:
<?php $show = false; ?>
<?php foreach ($this->items as $item) : ?>
But I want to echo the first 20 items and continue with the following 16 items.
I have managed to make it to do a break after 20 items but I am not getting the following 16 items ( starting from nr 21 ).
This is what I have so far:
<?php $show = false; ?>
<?php $i = $item->id = 1; ?>
<?php foreach ($this->items as $item) : ?>
<?php if(++$i > 20) break; ?>
If I set $i to '21' it still echos item 1 and so on.
Solution ## Thanks to #dhavald
<?php $show = false; ?>
<?php foreach (array_slice ($this->items, 0, 20) as $item) : ?>
By placing an array_slice in the foreach you can control the items you want show.
So on the next div i want to show item 21 to 36, the only thing i had to change was the 0 and 20 into , 20, 36
To clarify what I am looking for, I have three divs where I want to echo some items onto it. If an user collapse a div on the first there will appear the first 20 items and if a user clicks div2 the next 16 items will appear.
How can I correct this code to make that happen?
As i forgotten to mention, the solutions you bring on helped me really to understand the process but as i used a component generator for Joomla 3.1 there is one row of code that make it a little bit more complex to call the first 20 and second 16 items.
Directly after the foreach loop there is this line of code
if($item->state == 1 || ($item->state == 0 && JFactory::getUser()>authorise('core.edit.own',' com_ncitycatemus.vraagantwoordtoevoegen.'.$item->id))):
$show = true;
How can i manage it than with the loop ? Or do you suggest another way?
Thanks in advance! Really helped me to understand the loop!!
break breaks out of and stops a loop. continue skips the rest of the code in the loop, and jumps to the next iteration.
Using break and continue is in my opinion the wrong approach here. I'd simply use two for loops:
$keys = array_keys($this->items);
$keysLength = count($keys);
echo '<div id="div1">';
for ($i = 0; $i < min($keysLength, 20); $i++) {
echo $this->items[$keys[$i]];
}
echo '</div>';
if ($keysLength >= 20) {
echo '<div id="div2">';
for ($i = 20; $i < min($keysLength, 36); $i++) { //36 being 20 + 16
echo $this->items[$keys[$i]];
}
echo '</div>';
}
Note: This will work with any amount of items in $this->items. If it's under 20, it'll simply skip the next 16, and if it's above 36, it'll simply ignore the rest.
you can use array_slice to get a part of $this->items array and assign it into 3 different variables and loop over them separately.
$itemsDiv1 = array_slice($this->items, 0, 20); // gives first 20 items
$itemsDiv2 = array_slice($this->items, 20, 16); // gives next 16 items
and so on..
Don't use break; use continue;
<?php $i = 0; ?>
<!-- first group -->
<div>
<?php foreach ($this->items as $item) : ?>
<?php
/**
* Check if count divided by 20 has no remainder
*/
if ( (++$i % 20) == 0 ): ?>
</div>
<!-- start new group -->
<div>
<?php endif ?>
<?php endforeach ?>
<!-- end last group -->
</div>
$stockNotNull = StockDetail::where('sku', 10101001)
->where('stock_quantity', '>', 0)->get('stock_id', 'stock_quantity');
$toSell = 14;
// decrements just once for each $stockNotNull
foreach ($stockNotNull as $product) {
if ($toSell < 1) {
return;
}
$product->decrement('stock_quantity');
// $product->stock_quantity--; returns with a null
// dump($product->stock_quantity);
$product->save();
$toSell--;
// dump($toSell);
if($product->stock_quantity === 0) {
continue;
}
}
This is what I got so far, decrementing in the usual manner i.e $variable-- gives me a null value, $product->decrement('stock_quantity') subtracts 1 on each run, even if the stock_quantity field is far greater than the $toSell variable. The logic is there in my head, I'm just having trouble taking the quantity from the current item and moving on to the next only when the stock_quantity is 0.