Wondering if someone could assist me with this.
I am generating menu options for both an ELEVAT (elevated) and AUTHOR (authorised basic user) using a PHP loop which accesses an XML file set so that secure = 0 or 1 as follows:
<menuitem>
<itemname>Edit Event</itemname>
<itemfilename>editevent.php</itemfilename>
<itemfilepath>scripts</itemfilepath>
<secure>0</secure>
</menuitem>
<menuitem>
<itemname>Archive</itemname>
<itemfilename>eventsarchive.php</itemfilename>
<itemfilepath>scripts</itemfilepath>
<secure>1</secure>
</menuitem>
0 = authorised basic user and 1 = elevated user
Considering that I have so many menu links now I have 2 rows for the elevated user, I am trying to output to the browser so that the last menu item of the first row of page links does not print a pipe.
So far I have managed to get the basic user login to generate without a pipe after the last link however I cannot for the life of me figure out how to remove the | from the last link of the first row of links for the elevated user login.
Here is my PHP function:
function pagemenu($pageFile)
{
# Open the DB connection
$sql = dbconnect();
$linkPath = getlinkpath($pageFile);
# The $pageFile value is the file name of the calling page
# Set the path to the menu source file
$xmlsrc = $linkPath . 'xml/menulist.xml';
# Load the menu source file into a SimpleXML object
if (!$menulist = simplexml_load_file($xmlsrc)) {
# Print an error message if the source file does not load
print 'Unable to load the XML source file';
} # Process the menulist.xml file
else {
# Set a counter for the menu items
$itemCount = 1;
# Find the folder path of the calling page
foreach ($menulist as $menu) {
if ($menu->itemfilename == $pageFile) {
$linkPath = $menu->itemfilepath;
} else {
$linkPath = '';
}
}
# Scroll through all the menu items and build the menu
print '<div class="menubar">' . PHP_EOL;
foreach ($menulist as $menu) {
# If the menu item is the current page don't display a link
if ($menu->itemfilename == $pageFile) {
# Don't print a pipe before the first menu item
if ($itemCount != 1) {
print ' | ';
}
print $menu->itemname;
} # Display a link for all the other menu items
else {
# Construct the link path to the menu item file
# A link to the index file
if ($menu->itemfilepath == 'root') {
$thisLink = '../' . $menu->itemfilename;
} # A link to a file in the same folder
elseif ($menu->itemfilepath == $linkPath) {
$thisLink = $menu->itemfilename;
} elseif ($pageFile == 'index.php' and $menu->itemfilepath != $linkPath) {
$thisLink = $menu->itemfilepath . '/' . $menu->itemfilename;
} # A link to a file in a different folder
elseif ($menu->itemfilepath != $linkPath) {
$thisLink = '../' . $menu->itemfilepath . '/' . $menu->itemfilename;
}
# Create the connection to the mysql database and handle error if there is one
$query = mysqli_query(
$sql, "SELECT user_type_id FROM user_details WHERE user_id = '$_SESSION[validUser]'"
);
$usertype = mysqli_fetch_assoc($query);
# Don't print a pipe before the first menu item
if ($usertype['user_type_id'] == "ELEVAT") {
if ($itemCount != 1) {
# Tried the following added to the above line without success
# && ($itemCount !=11))
print ' | ';
}
} else {
if (($itemCount != 1) && ($itemCount != 5) && ($itemCount != 6) && ($itemCount != 7)
&& ($itemCount != 8)
&& ($itemCount != 9)
&& ($itemCount != 10)
&& ($itemCount != 11)
&& ($itemCount != 12)
&& ($itemCount != 13)
&& ($itemCount != 14)
&& ($itemCount != 15)
&& ($itemCount != 16)
&& ($itemCount != 17)
) {
print ' | ';
}
}
# Display the menu item as a link
if ($menu->secure == 1) {
if ($usertype['user_type_id'] == "ELEVAT") {
print '<a href="' . $thisLink . '">' . $menu->itemname . '</a>';
}
} else {
print '<a href="' . $thisLink . '">' . $menu->itemname . '</a>';
}
}
# Increment the menu item counter
$itemCount++;
}
}
print '</div>' . PHP_EOL;
return;
# Close the DB connection
mysqli_close($sql);
}
so that the last menu item of the first row of page links does not print a pipe.
This is a common problem. You need to know when the last element is there or not. You can do this by caching so that you know if an element is the last element or not (compare with CachingIterator::hasNext()
, or count()
if you're working with arrays).
In your case it is perhaps most easy to create an xpath
expression that fetches all those entries from the menu that you're interested in.
That is first for the current page and second for the user-group you have there (secure 0/1).
http://php.net/simplexml.examples-basic covers how to do that.
Once done, the SimpleXMLElement::xpath()
method will give you an array you can iterate over to output your menu. You can then use a condition based on count()
or do array-iteration and cache it to use the CachingIterator::hasNext()
method to find out wheter you're on the last row or not.
$entries = $xml->xpath($query);
$entries = new CachingIterator(new ArrayIterator($entries));
foreach ($entries as $entry)
{
$menutItem = menu_item_create_from_xml($entry);
menu_item_output($menutItem, $entries->hasNext());
# ^^^ tell the menu output function whether or
# not this is the last element of the menu
}