First of all, I know this is simple but I'm not a PHP developer by trade so I apologize if this is dumb for everyone. That being said, I've spent the last 3 hrs searching and can't find a way to do this without re-inventing my wheel so to speak. I use a simple command to mark the navigation on websites when the page is "current".
<li><a <?php if (strpos($_SERVER['PHP_SELF'], 'page')) echo 'class="current"';?> href="page.php" class="tp">Page</a></li>
Works great in most cases. However in this case, I need to concatenate the class string, not overwrite it with current. I've tried
...echo'class=" "."current".'
and several variations and can't get it to simply add the class not overwrite it. Thank you
Is the <li> not in a loop?
Ideally your menu would come from a table array through which you would loop. If that is the case; try this:
foreach(..){
$class = strpos($_SERVER['PHP_SELF'], 'page') ? " current" : "";
echo "<li>Page</li>";
}
Overall, for readability, I would recommend to not put if statements inline in the HTML.
But based on your code:
<?php
$class = strpos($_SERVER['PHP_SELF'], 'page') ? " current" : "";
?>
<li>Page</li>
What about something like this :
<li>
<a href="page.php"
class="<?php if (strpos($_SERVER['PHP_SELF'], 'page')) {echo 'current ';} ?>tp">
Page
</a>
</li>
This way, you'll always have at least class="tp", and, if the condition is met, a 'current ' (note the space at the end of this string : it's important and required so the two classes are separated by a space and not considered as one) will be inserted just before the 'tp', inside the class="..."
I have a small php website that has a menu that is included via include_once. I need an HTML class added to the current menu item for each page.
So if a user clicks on a link and goes to that page the new page will load with the new menu item with class="current". How can I go about doing this?
Let's say you write your menu like this:
<ul>
<li> Link1 </li>
<li> Link2 </li>
<li> Link3 </li>
</ul>
Here is a good old php4 style solution :-p
<?php
//you get which link was clicked
if(isset($_GET['menu']) $menu = $_GET['menu'];
else $menu = 1;
$1 = $2 = $3 = ""; //you create 3 empty strings
switch($menu){ //you assign the correct string with your css class name
case "1": $1 = 'class="current"';break;
case "2": $2 = 'class="current"';break;
case "3": $3 = 'class="current"';break;
}
?>
//echo the variables into the menu anchors ( <?=$1?> is equivalent to <? echo $1; ?> )
<ul>
<li><a href="link1.com?menu=1" <?=$1?> >Link1</a></li>
<li><a href="link2.com?menu=2" <?=$2?> >Link2</a></li>
<li><a href="link3.com?menu=3" <?=$3?> >Link3</a></li>
</ul>
You can also place the <?=$1?> into the <li> or anywhere else wanted...
If you're using javascript in your project, you could also give an id to your anchors (like Link1), get the menu value like above with $_GET, and then use javascript to add the class to the desired link.
I gave you this answer because from what you're writing I guess you're not using any PHP framework but coding you app the old way... there's plenty of nice PHP framework around here that will have pre-made solution for this... might be hard at the beginning but it's worth it...
Good luck!
Hi
I am going to highlight a menu item according to the page that is reading currently, when user click on different page through the menu, that menu item will be highlighted, example is http://templates.joomlart.com/ja_pyrite/index.php?option=com_content&view=article&id=44&Itemid=53.
If I use PHP/jQuery to check the url and highlight the menu, it will be good if the url look like "http://example.com/contact", but the example above is bad.
If I don't going to check the url and highlight the menu item, could someone give me a idea/method that can be done with the same effect?
Thank you
I found this on 960 Development, been googling for a while for this, so happy when I finally found it!
<ul class="sub-nav" >
<?php
$full_name = $_SERVER['PHP_SELF'];
$name_array = explode('/',$full_name);
$count = count($name_array);
$page_name = $name_array[$count-1];
?>
<li><a class="<?php echo ($page_name=='where-to-buy.php')?'active':'';?>" href="where-to-buy.php">WHERE TO BUY</a></li>
<li><a class="<?php echo ($page_name=='about.php')?'active':'';?>" href="about.php">ABOUT US</a></li>
<li><a class="<?php echo ($page_name=='contact.php')?'active':'';?>" href="contact.php">CONTACT US</a></li>
It is working fully for me, get the pages I need to be "active" to be active and dosent active any of thoes who got the class when I'm in another page!
Take a look at it!
Edit:
Even if you got a (in this example) contact.php?person=John, it will "active" the contact.php link!
do something like this
<div id="nav_menu">
<?php
$currentFile = $_SERVER['REQUEST_URI'];
$pages = array(
array("file" => "/index.php", "title" => "Home"),
array("file" => "/about.php", "title" => "About Us"),
array("file" => "/schedule.php", "title" => "Schedule")
);
$menuOutput = "<ul>";
foreach ($pages as $page) {
$activeAppend = ($page["file"] == $currentFile) ? " id='active' " : "class='nav_button'";
$currentAppend = ($page["file"] == $currentFile) ? " id='current' " : "class='nav_button'";
$menuOutput .= "<li " . $currentAppend . ">"
. "<a href='" . $page["file"] . "' id='".$page["id"]."'>" . $page["title"] ."</a>"
. "</li>";
}
$menuOutput .= "</ul>";
echo $menuOutput;
?>
</div>
i hope you get the idea, i had this on stackoverflow a while ago but i forgot what was the question
edit:
here i finnally found the original question
In the HTML code you use to generate your navigation, add some PHP logic that will add a selected class to the button of the page that you are currently on. Then just add some CSS for the selected class.
Can you do something like this? It should select any link that points at the current page - so you can apply whatever you like to highlight it.
$('a[href="'+window.location+'"]').addClass('menu-highlight');
A good technique is to add a specific class or id attribute to body element and then style it in CSS. It requires minimum of server side programming and keeps all the presentation logic in CSS as it should be done.
<style>
.contact #contact { background:#000; }
...
</style>
<body class="contact">
<ul>
<li id="homepage">Homepage</li>
...
<li id="contact">Contact</li>
</ul>
...
I would like to have a vertical navigation menu compatibbel with jQuery UI ThemeRoller.
How can I define the styles for my menu?
I just build menus dynamically and php code is following:
$menu = '<ul>';
foreach ($items as $val) {
if ( 'sep' == $val['link'] )
$menu.=$val['label'].'<br>';
else {
// echo $_SERVER['SCRIPT_FILENAME']."<br>".DEF_PATH.$val['link'];
if ($_SERVER['SCRIPT_FILENAME'] == DEF_PATH.$val['link']) {
$menu .= '<li class="current"><a href="'.$val['link'].'"';
$menu .= ' class="current"';
}else
$menu .= '<li><a href="'.$val['link'].'"';
$menu .= ' target="'.$val['target'].'" '.'>'.$val['label']."</a></li>\n";
}
}
$menu.="</ul>\n";
$main_menu.=$menu;
thanks Arman.
jQuery UI Uses "CSS Framework", you can read about it here. Basically it uses a well defined set of classes for specific things, just use the appropriate classes include the theme/CSS you want to use and you're done :)
For a menu you probably want to start with the Interaction States classes section. For example instead of this:
<li class="current">
You would probably want ui-state-active or ui-state-highlight either replacing or in addition to current (in addition if .current has additional style rules you want), like this:
<li class="current ui-state-active">
Try adding display:block to them (UI might have made them inline):
$menu .= '<li style="display:block;"><a href="'.$val['link'].'"';
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 9 years ago.
Improve this question
What's the most elegant templating (preferably in pure PHP!) solution you've seen?
Specifically i'm interested in handling:
Detecting in a repeating block whether it's the first or last element
Easy handling of odd/even cases, like a zebra striped table, or similar
Other modulos logic, where you'd do something every n'th time.
I'm looking for something that makes this less of a pain:
<?php
$persons = array('John', 'Jack', 'Jill', 'Jason');
?>
<?php $i = 0; ?>
<?php if (isset($persons)): ?>
<ul>
<?php foreach ($persons as $name): ?>
<li class="<?= ($i++ % 2 === 0) ? 'odd' : 'even' ?>"><?= $name ?></li>
<?php endforeach ?>
</ul>
<?php endif ?>
Does it really take the mess above to create something like this below?
<ul>
<li class="odd">John</li>
<li class="even">Jack</li>
<li class="odd">Jill</li>
<li class="even">Jason</li>
</ul>
Is it only me that find the above near hideous?
All those starting and closing of php-tags makes me cringe.
You don't need to open the tags more than once. You can also make a function out of it if you do the same thing multiple times:
<?php
function makeul($items, $classes) {
$c = count($classes);
$out = "";
if (isset($items) && count($items) > 0) {
$out = "<ul>\n";
foreach ($items as $item) {
$out .= "\t<li class=\"" . $classes[$i++%$c] . "\">$item</li>\n";
}
$out .= "</ul>\n";
}
return $out;
}
?>
other page content
<?php
$persons = array('John', 'Jack', 'Jill', 'Jason');
$classes = array('odd', 'even');
print makeul($persons, $classes);
?>
Also, if you don't mind using Javascript, Jquery makes things done mod 2 pretty easy (e.g., for zebra striping a table):
$("tr:odd").addClass("odd");
$("tr:even").addClass("even");
Tiny But Strong
www.tinybutstrong.com
It doesn't make the smarty mistake of embedding another macro language in the page, but does allow you to handle every practical web display issue I've ever thrown at it. In particular the above odd/even constructs are a doddle. For something like your code selecting from a database table
In the PHP file
$TBS->MergeBlock('blk1',$sqlconnect, "SELECT name from people ");
And in the HTML file
<ul>
<li class="odd">[blk.name;block=ul]</li>
<li class="even">[blk.name;block=ul]</li>
</ul>
And that's it. Notice that the HTML is completely Dreamweaver compatible. Furthermore if I wanted to make that alternate over three line styles all I'd need to do is add the extra line, maybe with different classes, so
<ul>
<li class="linestyle1">[blk.name;block=ul]</li>
<li class="linestyle2">[blk.name;block=ul]</li>
<li class="linestyle3">[blk.name;block=ul]</li>
</ul>
A small help on the looping:
<? $b=false; foreach($MyList as $name) { ?>
<li class="row<?= $b=!$b ?>"><?= htmlspecialchars($name); ?></li>
<? } ?>
By saying $b=!$b, it automatically alternates between true and false. Since false prints as "", and true prints as "1", then by defining css classes row and row1, you can get your altering rows without any trouble.
consider using :first-child css to style the first one differently.
It ain't pure PHP (the templating syntax then), but it works realy nice; Smarty.
For loops you can do:
<ul>
{foreach from=$var name=loop item=test}
{if $smarty.foreach.loop.first}<li>This is the first item</li>{/if}
<li class="{cycle values="odd,even"}">{$var.name}</li>
{if $smarty.foreach.loop.last}<li>This was the last item</li>{/if}
{/foreach}
</ul>
have you considered phptal?. one main benefit of it (or something similar) is that you get templates which can pass validation. most php template engines seem to ignore this.
I use PHPTAL for templating because it is written in 100% actual HTML with placeholder data, so it even works in a WYSIWYG editor for a web designer. That and it's just way easy to understand.
Here's what it would look like for me. Please forgive the markup, I'm new here and the four spaces block wasn't working right for me (the list was a list, not the markup).
PHP Code:
$tal = new PHPTAL;
$tal->setTemplate('people.htm')
->set('people', array('John', 'Jack', 'Jill', 'Jason'));
echo $tal->execute();
Template:
<ul>
<li tal:repeat="person people" tal:content="person">John Doe</li>
</ul>
Output:
JohnJackJillJason
Now obviously I wouldn't make a template for this little, but I could use a macro for it or build a whole page and include that variable. But you get the idea. Using PHPTAL has just about tripled my speed at templating and programming, just by the simplicity (no new syntax to learn like smarty).
How's about XSLT? The only template system that has a standards body behind it. Works the same across programming languages. Learn it once, use it everywhere!
Symfony Components: Templating
(source: symfony-project.org)
Symfony intends on moving to a new templating system based on the lightweight PHP templating system twig.
The lead developer Fabien Potencier, explains the decision here: http://fabien.potencier.org/article/35/templating-engines-in-php-follow-up
Symfony can usually be replied upon to make very informed decisions on such matters, so this framework should be something to look into.
The component is here: http://components.symfony-project.org/templating/
I've used Smarty Template Engine in the past. It's Pretty solid. And as you can probably tell from the website; it has quite the large user-base and is updated regularly.
It's in pure PHP as well.
Savant is a lightweight, pure PHP templating engine. Version 2 has a cycle plugin similar to the Smarty one mentioned earlier. I haven't been able to find a reference to the same plugin in version 3, but I'm sure you could write it fairly easily.
If is just to apply a CSS style, why don't you use the :nth-of-type(odd) selector.
For example:
li:nth-of-type(odd) {
background: #f2f6f8;
background: linear-gradient(top, #f2f6f8 0%, #e0eff9 100%);
}
http://jsfiddle.net/melonangie/nU7qK/enter code here
I use Modulo like you did in your example all the time.
If what cringes you is the opening and closing tags, write a function that creates the html string and then have it return it. At least it will save you some tags.
I have been a fan of HAML for quite a while, it looks like PHP folk have HAML now: see http://phphaml.sourceforge.net/
<?= ($i++ % 2 === 0) ? 'odd' : 'even' ?>
You're doing it the other way around. Your first item is now called even instead of odd. Use ++$i.
I'm having the same problem. But I think your original solution is the neatest. So I'll go with that.
I created a simple templating system in PHP to solve this problem a while ago:
http://code.google.com/p/templatephp/
It takes a multidimensional array, and requires the addition of some extra tags to the HMTL to create the combined template.
It's not as complicated (albeit powerful) as Smarty and some other solutons, but wins out in simplicity a lot of the time. A demo of the menu creation:
<p>Main Menu</p>
<ul>
{block:menu_items}
<li>{var:name}</li>
{/block:menu_items}
</ul>
Merged with...
array (
'menu_items' => array (
array (
'link' => 'home.htm',
'name' => 'Home'
),
array (
'link' => 'about.htm',
'name' => 'About Us'
),
array (
'link' => 'portfolio.htm',
'name' => 'Portfolio'
),
array (
'link' => 'contact.htm',
'name' => 'Contact Us'
)
)
);
Will create the menu...
<p>Main Menu</p>
<ul>
<li>Home</li>
<li>About Us</li>
<li>Portfolio</li>
<li>Contact Us</li>
</ul>
<?php
define ('CRLF', "\r\n");
$persons = array('John', 'Jack', 'Jill', 'Jason');
$color = 'white'; // Init $color for striped list
$ho = '<UL>' . CRLF; // Start HTML Output variable
foreach ($persons as $name)
{
$ho .= ' <li class="' . $color . '">' . $name . '</li>' . CRLF;
$color = ($color == 'white') ? 'grey' : 'white'; // if white, make it grey else white
}
$ho .= '</ul>' . CRLF;
echo $ho;
?>