How to stop a foreach() loop while reading from a textfile? - php

I'm making a website for my clan.
I'd like to have a dynamic table of contents on the left.
E.G. If you click on the link "games" it should stop and print the other list. A list in a list.
I know, that sounds pretty strange, I think it'd be the best if I'll show you my code.
Here it is:
<div class="links">
<?php
$zeilen = file ('../inhaltsverzeichnis.txt');
foreach ($zeilen as $zeile)
{
if($zeile == 3)
{
$games = file ('games_inhaltsverzeichnis.txt');
foreach ($games as $game)
{
echo $game;
}
}
else
{
echo $zeile;
}
}
?>
I hope you know what I mean.

The break statement allows you to escape from the "nearest enclosing loop". If you add an argument (e.g. break 2;), you escape "the nearest two loops". Not absolutely sure how your code relates to the description of the problem (the title of the question), or where you would want the break statement - but that's what you need.

Related

get all categories listing from database

Main purpose is to get all categories listing from database by passing variables to url and show it to the main page.here i have omitted some code bt i tried to clarify.
1.can I exclude encodeHtml() method, too difficult for me to understand
2.i am not getting specially this part of code and having my head for 4 days
foreach($cats as $cat) {
echo "<li><a href=\"/?page=catalogue&category=".$cat['id']."\"";//here id is 'category id' from database. this full line will echo what?
echo Helper::getActive(array('category' => $cat['id']));//it will output what ?
echo ">";
echo Helper::encodeHtml($cat['name']);//as from ur answer can we omit encodeHTML() method and use htmlspecialchars($cat['name']); instead ?
echo "</a>
3.any easier solution will be more appreciated
in our database we have 'id' and 'name' of catagory listing
please check below for reference
/*below is the code in header section of template */
<?php
$objCatalogue = new Catalogue();// creating object of Catalogue class
$cats = $objCatalogue->getCategories(); // this gets all categories from database
<h2>Categories</h2>
<?php
foreach($cats as $cat) {
echo "<li><a href=\"/?page=catalogue&category=".$cat['id']."\"";
echo Helper::getActive(array('category' => $cat['id']));
echo ">";
echo Helper::encodeHtml($cat['name']);
echo "</a></li>";
}
?>
/*below is the helper class which is Helper.php */
public static function getActive($page = null) {
if(!empty($page)) {
if(is_array($page)) {
$error = array();
foreach($page as $key => $value) {
if(Url::getParam($key) != $value) //getParam takes name of the parameter and returns us the value by $_GET
{
array_push($error, $key);
}
}
return empty($error) ? " class=\"act\"" : null;
}
}
//CHECK THIS LINE BROTHER
return $page == Url::currentPage() ? " class=\"act\"" : null;// url::currentPage returns the current page but what is 'class =act ' :(
}
public static function encodeHTML($string, $case = 2) {
switch($case) {
case 1:
return htmlentities($string, ENT_NOQUOTES, 'UTF-8', false);
break;
case 2:
$pattern = '<([a-zA-Z0-9\.\, "\'_\/\-\+~=;:\(\)?&#%![\]#]+)>';
// put text only, devided with html tags into array
$textMatches = preg_split('/' . $pattern . '/', $string);
// array for sanitised output
$textSanitised = array();
foreach($textMatches as $key => $value) {
$textSanitised[$key] = htmlentities(html_entity_decode($value, ENT_QUOTES, 'UTF-8'), ENT_QUOTES, 'UTF-8');
}
foreach($textMatches as $key => $value) {
$string = str_replace($value, $textSanitised[$key], $string);
}
return $string;
break;
}
}
Firstly, in your URL (/?page=catalogue&category=) you don't need to put &, as this is an HTML entity for actually displaying an ampersand in a web page. Just use /?page=catalogue&category=.
Secondly, you can use urlencode() to prepare strings for sending in the URL, and urldecode() on the other end.
In answer to your first point you just need to make sure that ANYTHING from the user (whether via $_POST or $_GET) is sanitized, prior to being used in code, output to a web page, or used in database queries. Use htmlspecialchars() for cleaning before outputting to a web page, and prepared statements prior to entering user input into a query.
In answer to your second point please read the documentation in the links I have provided above. Just reading the documentation on htmlspecialchars() will help you a lot.
Hope this helps.
Alright then.
<?php
foreach($cats as $cat) {
echo "<li><a href=\"/?page=catalogue&category=".$cat['id']."\"";
echo Helper::getActive(array('category' => $cat['id']));
echo ">";
echo Helper::encodeHtml($cat['name']);
echo "</a></li>";
}
?>
Im just going to kindof skim through it, because honestly if you really want to learn all this you should probably google the shit out of every piece of code you don't understand, it's the way we all learn things.
< ?php announces some php script to follow. And as you can see, there does follow some php code after.
foreach is a way of getting each element from an array or list and doing something to that element.
echo sends whatever string comes after it to the page, or whatever is listening to its output. In this case, it looks like the echo's are printing some <li> list item with an <a> anchor in it.
Helper::getActive(): Helper is some class that is defined somewhere, :: is syntax for calling a static function that belongs to the class (Helper in this case). getActive is the function name.
array('category' => $cat['id'] is a piece of code that creates an array with 1 element in it, being one with key 'category' and a value of whatever is in $cat['id'].
By looking at getActive: it looks like it's a function that checks the url for some value so it can determine which page to display. It also checks if the url contains errors.
By lookingat encodeHtml(): it looks like it's a function that makes sure that whatever text you're trying to put on the screen, isn't something that could cause harm. In some situations, people will try to make your server print javascript that could harm the user (by sending personal data to somewhere). The encodeHtml() will ensure that no such thing can be done by stripping certain characters from the text you're about to send to the page.
USE GOOGLE.

Splitting an external array to give different titles

I've been trying to figure out how to split the array and add different titles for each of the separate titles on the page, for each of the different things that this displays. However the most I can manage to do is add a comma between the numbers and words.
I would like to add selling"1st variable price"second variable" etc however I don't quite know how to do anything other than to turn this very confusing looking bunch of letters:
user name and notes 01001000013972583957ecCCany amount-w378- v west
into anything other than this:
0,100,10000,1397258395,7ec,CC,any amount-w378- v west
Also, this is what it looks like in its JSON form:
{"selling":"0","quantity":"100","price":"10000","date":"1397258395","rs_name":"7ec","contact":"CC","notes":"any amount-w378- v west"}
I just want all the information that is in there to displayed like that however I'm not quite sure how to add the titles that is in the JSON data. I also don't have access to the external site to change anything.
A little background: what I am trying to achieve is a price look-up for a game on my website from an external site. I tried to use an iframe but it was terrible; I would rather just manually display it rather than showing their site from mine - their style and my style clash terribly.
$json = file_get_contents('http://forums.zybez.net/runescape-2007-prices/api/rune+axe');
$obj = json_decode($json,true);
$blah1 = implode( $obj[0]["offers"][1]);
print_r($blah1);
If you know where it is, you should be able to just grab it and show it out?
You can use a failsafe to check if it is present with is_array() and isset() functions - see php.net docs on them.
Your print_r should give you good valid info -- try to wrap it around <pre></pre> tags before for better readability or view the source - it will be easier!
<pre><?php print_r($obj) ?></pre>
This should be your starting point, and from here you will either take the first one of your items or loop through all with
foreach ($obj as $o) { //should be $objects, not $obj
//do whatever with $o, like echo $o['price']
}
Each offers row is a table with each field separated by row:
$item = json_decode(file_get_contents('http://forums.zybez.net/runescape-2007-prices/api/rune+axe'));
while ($offer = array_shift($item[0]->offers)) {
echo "<table>" . PHP_EOL;
foreach ($offer as $field => $value) {
echo "<tr><th>$field</th><td>$value</td></tr>" . PHP_EOL;
}
echo "</table>" . PHP_EOL;
}
http://codepad.org/C3PQJHqL
Tables in HTML:
http://jsfiddle.net/G5QqZ/

I need help sorting out an if statement in a simplexml statement

Some basic background ...
I have a form that enters data to an xml file and another page that displays the data from teh xml depending that it meets the requirements . All of this I have managed to get done and thanks to a member on here I got it to show only the data as long as it has todays date and status is out . But I am left with the problem of trying to sort an if statement which needs to show data if it has it or show another div if not .
My Code ...
$lib = simplexml_load_file("sample.xml");
$today = date("m/d/y");
$query = $lib->xpath("//entry[.//date[contains(., '$today')]] | //entry[.//status[contains(., 'out')]]");
foreach($query as $node){
echo "<div id='one'>$node->name</div>
<div id='two'>$node->notes</div>
<div id='three'><div class='front'>$node->comments</div></div>";
}
So to reiterate if query returns matched data do the foreach else show another div
I only wish to know the right code for the if else statement if soneone could help with this I would be very grateful and will up vote any answer as soon as I have the reputation in place . I also apologise in advance if the question has been asked before or if it is too vague thanks again .
If xpath fails to resolve the path, it will return false (see here). Wrap the foreach loop in a simple check:
if( $query ) {
foreach($query as $node){
...
}
}
else {
// Echo the special div.
}
Since PHP is loose typed, if xpath happens to return an empty array, this check will also handle that case. Be aware that if the xpath call does return false, there may be a separate error at play that may require additional or alternative handling.

How can i change an image with a if statement in a foreach loop PHP?

I'm using CMS ProscessWire.
I've a working foreach loop that shows child's title and 5 links. The links are shown as images. This works flawless. But then I want for an empty link a black and white image to show there's no link. So i made a if statement. But when i put the if statement inside the loop the only child that is shown is the one with an empty link.
Does anyone know how tot resolve this? I think it's a simple thing, but can't figure it out.
PHP-Code:
$rdio='rdio.png';
$itunes='itunes.png';
$xbox='xbox.png';
$googleplay='googleplay.png';
$spotify='spotify.png';
$deezer='deezer.png';
foreach($page->children as $child)
if(!$child->Rdio) {
$rdio='rdiog.png';
}
else
{
$rdio='rdio.png';
}
echo "<ul style='background-color:#CCC;'>"."<li><h1>{$child->title}</h1></li>".<li><a class='rdio' href='{$child->Rdio}'><img src='../site/templates/img/$rdio' alt='rdio'/></a></li>"."<li><a class='itunes' href='{$child->iTunes}'><img src='../site/templates/img/$itunes' alt='itunes'/></a></li>"."<li><a class='xbox' href='{$child->Xbox}'><img src='../site/templates/img/$xbox' alt='xbox'/></a></li>"."<li><a class='googleplay' href='{$child->GooglePlay}'><img src='../site/templates/img/$googleplay' alt='googleplay'/></li>"."<li><a class='spotify' href='{$child->Spotify}'><img src='../site/templates/img/$spotify' alt='spotify'/></a></li>"."<li><a class='deezer' href='{$child->Deezer}'><img src='../site/templates/img/$deezer' alt='deezer'/></a></li>"."</ul><br/>";
You are missing some brackets around foreach which only executes the following IF statement and continues to print out a single element on your page. To correct this, just add brackets around the foreach loop like this:
$rdio='rdio.png';
$itunes='itunes.png';
$xbox='xbox.png';
$googleplay='googleplay.png';
$spotify='spotify.png';
$deezer='deezer.png';
foreach($page->children as $child) {
if(!$child->Rdio) {
$rdio='rdiog.png';
}
else
{
$rdio='rdio.png';
}
echo "<ul style='background-color:#CCC;'>"."<li><h1>{$child->title}</h1></li>".<li><a class='rdio' href='{$child->Rdio}'><img src='../site/templates/img/$rdio' alt='rdio'/></a></li>"."<li><a class='itunes' href='{$child->iTunes}'><img src='../site/templates/img/$itunes' alt='itunes'/></a></li>"."<li><a class='xbox' href='{$child->Xbox}'><img src='../site/templates/img/$xbox' alt='xbox'/></a></li>"."<li><a class='googleplay' href='{$child->GooglePlay}'><img src='../site/templates/img/$googleplay' alt='googleplay'/></li>"."<li><a class='spotify' href='{$child->Spotify}'><img src='../site/templates/img/$spotify' alt='spotify'/></a></li>"."<li><a class='deezer' href='{$child->Deezer}'><img src='../site/templates/img/$deezer' alt='deezer'/></a></li>"."</ul><br/>";
Try using empty method:
$rdio='rdio.png';
$itunes='itunes.png';
$xbox='xbox.png';
$googleplay='googleplay.png';
$spotify='spotify.png';
$deezer='deezer.png';
foreach($page->children as $child) {
if(empty($child->Rdio)) {
$rdio='rdiog.png';
}
else
{
$rdio='rdio.png';
}
echo "<ul style='background-color:#CCC;'>"."<li><h1>{$child->title}</h1></li>".<li><a class='rdio' href='{$child->Rdio}'><img src='../site/templates/img/$rdio' alt='rdio'/></a></li>"."<li><a class='itunes' href='{$child->iTunes}'><img src='../site/templates/img/$itunes' alt='itunes'/></a></li>"."<li><a class='xbox' href='{$child->Xbox}'><img src='../site/templates/img/$xbox' alt='xbox'/></a></li>"."<li><a class='googleplay' href='{$child->GooglePlay}'><img src='../site/templates/img/$googleplay' alt='googleplay'/></li>"."<li><a class='spotify' href='{$child->Spotify}'><img src='../site/templates/img/$spotify' alt='spotify'/></a></li>"."<li><a class='deezer' href='{$child->Deezer}'><img src='../site/templates/img/$deezer' alt='deezer'/></a></li>"."</ul><br/>";

PHP, XML, Accessing Attributes

I'm having a some trouble accessing attributes in my XML. My code is below. Initially I had two loops and this was working with no problems.
I would first get the image names and then use the second loop to get the story heading and story details. Then insert everything into the database. I want to tidy up the code and use only one loop. My image name is store in the Href attribute. ()
Sample XML layout (http://pastie.org/1850682). The XML layout is a bit messy so that was the reason for using two loops.
$xml = new SimpleXMLElement('entertainment/Showbiz.xml', null, true);
// Get story images
//$i=0;
//$image = $xml->xpath('NewsItem/NewsComponent/NewsComponent/NewsComponent/NewsComponent/NewsComponent/ContentItem');
// foreach($image as $imageNode){
// $attributeArray = $imageNode->attributes();
// if ($attributeArray != ""){
// $imageArray[$i] = $attributeArray;
// $i++;
// }
//}
// Get story header & detail
$i=0;
$story = $xml->xpath('NewsItem/NewsComponent/NewsComponent/NewsComponent');
foreach($story as $contentItem){
//$dbImage = $imageArray[$i]['Href'];
foreach($contentItem->xpath('ContentItem/DataContent/nitf/body/body.head/hedline/hl1') as $headline){
$strDetail = "";
foreach($contentItem->xpath('ContentItem/DataContent/nitf/body/body.content/p') as $detail){
$strDetail .= '<p>'.$detail.'</p>';
foreach($contentItem->xpath('NewsComponent/NewsComponent/ContentItem') as $imageNode){
$dbImage = $imageNode->attributes();
}
}
$link = getUnique($headline);
$sql = "INSERT INTO tablename (headline, detail, image, link) VALUES ('".mysql_real_escape_string($headline)."', '".mysql_real_escape_string($strDetail)."', '".mysql_real_escape_string($dbImage)."', '".$link."')";
if (mysql_query($sql, $db) or die(mysql_error())){
echo "Loaded ";
}else{
echo "Not Loaded ";
}
}
$i++;
}
I think I'm close to getting it. I tried putting a few echo statements in the fourth nested foreach loop, but nothing was out. So its not executing that loop. I've been at this for a few hours and googled as well, just can't manage to get it.
If all else fails, I'll just go back to using two loops.
Regards,
Stephen
This was pretty difficult to follow. I've simplified the structure so we can see the parts of the hierarchy we care about.
It appears that the NewsComponent that has a Duid attribute is what defines/contains one complete news piece. Of its two children, the first child NewsComponent contains the summary and text, while the second child NewsComponent contains the image.
Your initial XPath query is for 'NewsItem/NewsComponent/NewsComponent/NewsComponent', which is the first NewsComponent child (the one with the body text). You can't find the image from that point because the image isn't within that NewsComponent; you've gone one level too deep. (I was tipped off by the fact I got a PHP Notice: Undefined variable: dbImage.) Thus, drop your initial XPath query back a level, and add that extra level to your subsequent XPath queries where needed.
From this:
$story = $xml->xpath('NewsItem/NewsComponent/NewsComponent/NewsComponent');
foreach($story as $contentItem){
foreach($contentItem->xpath('ContentItem/DataContent/nitf/body/body.head/hedline/hl1') as $headline){
foreach($contentItem->xpath('ContentItem/DataContent/nitf/body/body.content/p') as $detail){
foreach($contentItem->xpath('NewsComponent/NewsComponent/ContentItem') as $imageNode){ /* ... */ }}}}
to this:
$story = $xml->xpath('NewsItem/NewsComponent/NewsComponent');
foreach($story as $contentItem){
foreach($contentItem->xpath('NewsComponent/ContentItem/DataContent/nitf/body/body.head/hedline/hl1') as $headline){
foreach($contentItem->xpath('NewsComponent/ContentItem/DataContent/nitf/body/body.content/p') as $detail){
foreach($contentItem->xpath('NewsComponent/NewsComponent/NewsComponent/ContentItem') as $imageNode){ /* ... */ }}}}
However, the image still doesn't work after that. Because you're using loops (sometimes unnecessarily), $dbImage gets reassigned to an empty string. The first ContentItem has the Href attribute, which gets assigned to $dbImage. But then it loops to the next ContentItem, which has no attributes and therefore overwrites $dbImage with an empty value. I'd recommend modifying that XPath query to find only ContentItems that have an Href attribute, like this:
->xpath('NewsComponent/NewsComponent/NewsComponent/ContentItem[#Href]')
That should do it.
Other thoughts
Refactor to clean up this code, if/where possible.
As I mentioned, sometimes you are looping and nesting when you don't need to, and it just ends up being harder to follow and potentially introducing logical bugs (like the image one). It seems that the structure of this file will always be consistent. If so, you can forgo some looping and go straight for the pieces of data you're looking for. You could do something like this:
// Get story header & detail
$stories = $xml->xpath('/NewsML/NewsItem/NewsComponent/NewsComponent');
foreach ($stories as $story) {
$headlineItem = $story->xpath('NewsComponent/ContentItem/DataContent/nitf/body/body.head/hedline/hl1');
$headline = $headlineItem[0];
$detailItems = $story->xpath('NewsComponent/ContentItem/DataContent/nitf/body/body.content/p');
$strDetail = '<p>' . implode('</p><p>', $detailItems) . '</p>';
$imageItem = $story->xpath('NewsComponent/NewsComponent/NewsComponent/ContentItem[#Href]');
$imageAtts = $imageItem[0]->attributes();
$dbImage = $imageAtts['Href'];
$link = getUnique($headline);
$sql = "INSERT INTO tablename (headline, detail, image, link) VALUES ('".mysql_real_escape_string($headline)."', '".mysql_real_escape_string($strDetail)."', '".mysql_real_escape_string($dbImage)."', '".$link."')";
if (mysql_query($sql, $db) or die(mysql_error())) {
echo "Loaded ";
} else {
echo "Not Loaded ";
}
}

Categories