Drupal tip #6: Displaying different elements depending on the page being viewed

Someone asked me how I display different header images on urlgreyhot depending on what section (corresponding to the global nav tabs) you are viewing. My solution might not be exactly simple or the best way to go, but it works. Here are the steps:

1) I use the path_auto module to create URLs depending on either node type or vocabulary. So in my pathaoto settings I have weblog entry urls created as "weblog/[title]" and everywhere else the URL is either created manually or built based on the category (taxonomy term) so the services section urls are "services/[page title]".

2) In the PHP-Template theme, I do a regular expression check to see what the path is and assign a variable depending on what section we're in, e.g.

$dapath = $_SERVER["REQUEST_URI"];
if (eregi("/personal/services*.*",$dapath)) {
  $sect = "services";
}

3) I put that variable in the body tag:

<body id="<?php echo $sect; ?>">

4) I place an empty div in the page, which will be the placeholder for header image:

<div id="section-header"></div>

5) I put a rule in my style sheet to display the appropriate image depending on what section is being displayed:

#services #section-header {
  height: 131px;
  background: #fff url(bg-sect-about-me.jpg) top right no-repeat;
}

This is also how I display a selected tab in the global navigation. The idea there would be to make each link in the nav have an ID, so you can then apply a CSS rule for #services #services-menuitem, for instance. It's a serviceable method. Do you do something similar in a perhaps more elegant way? How do you do it?

Comments

01 Nick Lewis
04/21/06 @ 20:38

Why use the regular expression when you can use the arg(x)? It seems like this method would be more efficent and bulletproof... especially if you plan on using your code in multiple situations. Thus:

<?php
switch(arg(0)) { case &quot;admin&quot;:  $body_id = &quot;admin&quot; ;   break;    switch(arg(1)) {     case &quot;logs&quot;:      vars['body_class'] = &quot;logs&quot;;      break;   } break;}
?>

Thus your page.tpl.php body tag would look like

[body id="

<?php
print $body_id ;
?>
" class="
<?php
print $body_class&quot;;
?>
]

02 jibbajabba
04/21/06 @ 23:37

How would that help identify sections of this site? In the case of this page, arg(0) would be "node" and arg(1) would be the node id. That doesn't do anything to help identify that we are looking at a weblog entry rather than a page entry. To complicate things, my "Services", "Publications" and "Resources" sections are all "page" types, so I can't use $node->type == 'page' to isolate them as a page type. So my method has been to create custom paths and check the url.

One method could be to use flexinode and create a new content type for each section and then check for $node->type == 'flexinode-#'. But that seems like more work than doing what I'm doing. I don't know how expensive my method is in terms of server resources, but I don't imagine it is. My regex string match certainly took fewer characters to type. :) I'm lazy like that.

So the question is... given my situation, how could you do it more elegantly in a way that works and doesn't require too many steps.

Advertisement
03 Nick Lewis
04/22/06 @ 18:36

Oh, I goofed. For some reason I thought you were using taxonomy_menu... I can see why that wouldn't really help you.

Here's an alternative approach based on a node's taxonomy info.. I think it work for your site. But I don't really have enough info on your site's organization to be sure...

Its big advantage, IMHO, is that it requires no hardcoding of class names. So if you decided to add a new section, in many cases you'd never have to open up template.php -- you'd only have to start building out the style sheet. The only hard coded part that must be done is selecting the vocabulary ID('s) you want to use to generate dynamic body classes and IDs. However, depending on how you use your terms, this might not be necessary. (however, it would seem to be very necessary in your site's case).

To differentiate between blog entries and pages, I suppose you might want to add a $vars['node_type'] = $vars['node']->type; rule in your template.php file, and then pass that into the body, like a so [body id="

<?php
print $body_id;
?>
<?php
print $node_type;
?>
" ...

04 jibbajabba
04/22/06 @ 19:33

Ah. Now that's what I'm looking for. That method you posted on your site could probably work, Nick. I look forward to trying that on my site soon. Thanks!

05 AC
07/21/06 @ 04:06

This is a simple way to do this based on the first argument of the url:
In page.tpl.php

<div id="content" class="<?php $page_class = split ("/", $_SERVER["REQUEST_URI"]); print $page_class[1]; ?>">

Advertisement
06 jibbajabba
07/21/06 @ 06:19

Thanks, AC. That's a great tip.

07 Charity cds
01/20/08 @ 07:50

Thanks - its starting to make a bit more sense to me now.

08 Lisa
02/18/08 @ 20:51

Thanks for the info. Reading the blogs provide much needed support.

Lisa :)

09 Hitby
04/01/08 @ 05:15

This sounds similar to something that I'm trying to achieve. I don't know if it's possible but if you could help out at all It'd be much appreciated!

I'm building a site that is a repository for resources. I've used views to build the different sections of the site. for example Biology, chemistry, maths etc. Within these sections are the content_types, image, video etc.

These work fine except I need the node page to inherit the style of the referring page.

For example, ResourceA is available in both the biology and chemistry sections. If a user is in the biology/images view and they click on the node to visit the node page, it needs to be styled the same as the biology section. If they visit it from the chemistry section then it needs to use the chemistry style.

I thought this would be possible by setting the node to appear at

biology/images/node/nid or chemistry/images/node/nid dependent on the referring page but it seems this is not possible. Is there anyway to get the referring URL and use that to apply styles to the node page?

This is a killer for the site and I've spent the best part of a week trying to work it out with no success.

Unrelated but when I tried to register the capcha image didn't appear so I couldn't :)

10 jibbajabba
04/01/08 @ 07:31

Hitby: This is exactly what this tip is for. The code here uses the path of the url to set a body class. That body class is used to style the page. So in your example, you'd get:

<body class="biology">

in one instance, and in the other:

<body class="chemistry">

Try it using the code from AC's comment #5 above.

Post new comment

The content of this field is kept private and will not be shown publicly.
  • Allowed HTML tags: <a> <b> <strong> <dd> <dl> <dt> <i> <li> <ol> <u> <ul> <code> <blockquote>
  • Lines and paragraphs break automatically.
  • Web page addresses and e-mail addresses turn into links automatically.
  • You may post code using <code>...</code> (generic) or <?php ... ?> (highlighted PHP) tags.

More information about formatting options