Adding nested regions

We encourage users to post events happening in the community to the community events group on https://www.drupal.org.
You are viewing a wiki page. You are welcome to join the group and then edit it. Be bold!

<< Back to documentation Home

What do we do?

In this example we will add three regions that are inside the content region. A lot of people ask "How to place region above content zone" or "how to add a content bottom zone". With this technique you can exactly do that.

Code for the .info file

You need to add the regions to your .info file. In this example I've added three regions.

regions[content_top_first] = 'Content Top First'
regions[content_top_second] = 'Content Top Second'
regions[content_top_third] = 'Content Top Third'

Code for template.php

The following code adds three regions into the content zone.

"omegasub_alpha" is the name of your subtheme.

function omegasub_alpha_page_alter(&$vars) {
  $vars['content']['content']['content']['#sorted'] = FALSE;

  if (!empty($vars['#excluded']['content_top_first'])) {
    $vars['#excluded']['content_top_first']['#weight'] = -92;
    $vars['content']['content']['content']['content_top_first'] = $vars['#excluded']['content_top_first'];
  }

if (!empty($vars['#excluded']['content_top_second'])) {
    $vars['#excluded']['content_top_second']['#weight'] = -91;
    $vars['content']['content']['content']['content_top_second'] = $vars['#excluded']['content_top_second'];
  }

  if (!empty($vars['#excluded']['content_top_third'])) {
    $vars['#excluded']['content_top_third']['#weight'] = -90;
    $vars['content']['content']['content']['content_top_third'] = $vars['#excluded']['content_top_third'];
  }
}

Css modifications

Like every region each one will have a margin left and right. Eventually you want to remove that. If you do use a custom css like grid-hacks.css and do it there to keep everything structured.

Info

These regions appear on the zones and regions config page but should not be assigned manually because we do that in the code in template.php

Advantage

See the attached clearfix.html. I personally wanted to do that so i can have some kind of a wrapper around the 2 blocks i float left and which are above the content. With a extra region inside the content region i had a warpper around those two blocks and so could apply .clearfix to it. Remember .clearfix has to be applied to the wrapper in whcih both floated blocks are. Thats why i did this.

You can do this with panels too. but ...

Reference issues

http://drupal.org/node/1230110

Example 1, adding 3 regions top and 3 regions bottom to content zone

.info code

;CUSTOM REGIONS, stacked content regions

regions[content_top_first] = content top first
regions[content_top_second] = content top secondary
regions[content_top_third] = content top third

regions[content_bottom_first] = content bottom first
regions[content_bottom_second] = content bottom secondary
regions[content_bottom_third] = content bottom third

template.php

function YOURTHEMENAME_alpha_page_structure_alter(&$vars) {
  $vars['content']['content']['content']['#sorted'] = FALSE;

  //content top
  if (!empty($vars['#excluded']['content_top_first'])) {
    $vars['#excluded']['content_top_first']['#weight'] = -92;
    $vars['content']['content']['content']['content_top_first'] = $vars['#excluded']['content_top_first'];
  }

  if (!empty($vars['#excluded']['content_top_second'])) {
    $vars['#excluded']['content_top_second']['#weight'] = -91;
    $vars['content']['content']['content']['content_top_second'] = $vars['#excluded']['content_top_second'];
  }

  if (!empty($vars['#excluded']['content_top_third'])) {
    $vars['#excluded']['content_top_third']['#weight'] = -90;
    $vars['content']['content']['content']['content_top_third'] = $vars['#excluded']['content_top_third'];
  }

  //content bottom
  if (!empty($vars['#excluded']['content_bottom_first'])) {
    $vars['#excluded']['content_bottom_first']['#weight'] = 90;
    $vars['content']['content']['content']['content_bottom_first'] = $vars['#excluded']['content_bottom_first'];
  }

  if (!empty($vars['#excluded']['content_bottom_second'])) {
    $vars['#excluded']['content_bottom_second']['#weight'] = 91;
    $vars['content']['content']['content']['content_bottom_second'] = $vars['#excluded']['content_bottom_second'];
  }

  if (!empty($vars['#excluded']['content_bottom_third'])) {
    $vars['#excluded']['content_bottom_third']['#weight'] = 92;
    $vars['content']['content']['content']['content_bottom_third'] = $vars['#excluded']['content_bottom_third'];
  }
}

css to remove margins

/* hacks for the grid /

/
hacking the nested regions */


  #region-content-top-first {
    margin-right: 0px;
    margin-left: 0px;
  }

  #region-content-top-second {
    margin-left: 0px;
  }

  #region-content-top-third {
    margin-right: 0px;
  }


  #region-content-bottom-first {
      margin-right: 0px;
      margin-left: 0px;
  }

  #region-content-bottom-second {
    margin-left: 0px;
  }

  #region-content-bottom-third {
      margin-right: 0px;
  }

Visually the content zone now looks like

---3---
-1- -2-
---c---
---3---
-1- -2-

remember to assign the regions colums in the ui, but DO NOT try to assign them to a region via the ui

<< Back to documentation Home

AttachmentSize
clearfix.html2.31 KB

Comments

michaellenahan's picture

With thanks to rlhawk on irc.

  1. Add a region to your subtheme's .info file as described above.

  2. In /admin/appearance/settings/SUBTHEMENAME:
    Select Zone and region configuration
    Go to UNASSIGNED REGIONS at the bottom of the page
    Add the Region to the desired Zone, and click Save configuration.

responsive layouts?

dooug's picture

Does this technique maintain the responsive layout functionality of these regions? (will these nested regions drop below each other on smaller window/screen size?)

it seems to work. my tests

marcoka's picture

it seems to work. my tests worked so far

Hi, Is this not a bit of a

samwillc's picture

Hi,

Is this not a bit of a long winded way of doing something that panels could achieve? I nest views blocks into regions via views global custom text field but even that requires manual code with the correct classes (and removal of the margins in the right places). The nesting idea clearly can be done as seen in your great work above, but I think it really should be done via the UI so you can change it easily without hacking away at template.php. I wouldn't know (yet) how to get this working purely through the theme.

Sam.

its not possible through the

marcoka's picture

its not possible through the ui with 3.1. yes you can use panels but on small pages this is overdose.

panels vs custom code

suntog's picture

It only seems long winded because of the coding. I did a side by side comparison, one page has panels another uses this method. Panels took longer, because it was difficult to get all three block areas to be the exact width without resorting to CSS. That being said, I still like panels, and will prolly use it for this project.

here's my version in order to

dasjo's picture

here's my version

in order to have vertically stacked sidebar_second regions of the following structure.

Rearrage sidebar_second to the following structure
sidebar_second
- sidebar_second_top
- sidebar_second_content
- sidebar_second_bottom

// Region definitions.
regions[sidebar_second_top] = Sidebar Second Top
regions[sidebar_second_bottom] = Sidebar Second Bottom

// Exported settings.
settings[alpha_region_sidebar_second_top_force] = '0'
settings[alpha_region_sidebar_second_top_zone] = ''
settings[alpha_region_sidebar_second_top_prefix] = '1'
settings[alpha_region_sidebar_second_top_columns] = '7'
settings[alpha_region_sidebar_second_top_suffix] = '0'
settings[alpha_region_sidebar_second_top_weight] = '3'
settings[alpha_region_sidebar_second_top_position] = '0'
settings[alpha_region_sidebar_second_top_css] = ''
settings[alpha_region_sidebar_second_top_equal_height_element] = ''
settings[alpha_region_sidebar_second_top_equal_height_container] = '0'

settings[alpha_region_sidebar_second_bottom_force] = '0'
settings[alpha_region_sidebar_second_bottom_zone] = ''
settings[alpha_region_sidebar_second_bottom_prefix] = '1'
settings[alpha_region_sidebar_second_bottom_columns] = '7'
settings[alpha_region_sidebar_second_bottom_suffix] = '0'
settings[alpha_region_sidebar_second_bottom_weight] = '5'
settings[alpha_region_sidebar_second_bottom_position] = '0'
settings[alpha_region_sidebar_second_bottom_css] = ''
settings[alpha_region_sidebar_second_bottom_equal_height_element] = ''
settings[alpha_region_sidebar_second_bottom_equal_height_container] = '0'

<?php
/**
* Implements hook_alpha_page_structure_alter().
*/
function yourtheme_alpha_page_structure_alter(&$vars) {

  if (isset(
$vars['content']['content']['sidebar_second'])) {
   
// Rearrage sidebar_second to the following structure
    // sidebar_second (wrapper sidebar_second without blocks & fixed grid settings)
    // - sidebar_second_top (additional, from #excluded regions)
    // - sidebar_second_content (original sidebar_second)
    // - sidebar_second_bottom (additional, from #excluded regions)
   
$blocks = array();
   
$sidebar_second_content = $vars['content']['content']['sidebar_second'];
   
$sidebar_second = $sidebar_second_content;

   
// Remove blocks from wrapper.
   
foreach ($sidebar_second as $key => $item) {
      if (
is_array($item) && (isset($item['#region']) || isset($item['#block']))) {
       
$blocks[$key] = $item;
        unset(
$sidebar_second[$key]);
       }
    }

   
// Hack: remove reference.
   
unset($sidebar_second['#grid']);
   
$sidebar_second['#grid'] = $sidebar_second_content['#grid'];

   
// Fix grid settings for wrapper.
   
$sidebar_second['#grid']['columns'] += $sidebar_second['#grid']['prefix'];
   
$sidebar_second['#grid']['prefix'] = 0;

   
// Add sidebar_top, content & bottom to wrapper.
   
if (isset($vars['#excluded']['sidebar_second_top'])) {
     
$sidebar_second['sidebar_second_top'] = $vars['#excluded']['sidebar_second_top'];
    }
   
$sidebar_second['sidebar_second_content'] = $sidebar_second_content;
    if (isset(
$vars['#excluded']['sidebar_second_bottom'])) {
     
$sidebar_second['sidebar_second_bottom'] = $vars['#excluded']['sidebar_second_bottom'];
    }
   
$vars['content']['content']['sidebar_second'] = $sidebar_second;
  }
}
?>

Hi dasjo, Looks good. I think

samwillc's picture

Hi dasjo,

Looks good. I think a future release of Omega will allow regions within regions via the UI. However, not yet, so @dasjo:

Can I ask what the difference would be to using this technique compared to having just one region 'sidebar second' and stacking three blocks inside it vertically via context?

Thanks.

Sam.

What?

CLEE25's picture

Could someone please explain to me what this means:

remember to assign the regions colums in the ui, but DO NOT try to assign them to a region via the ui

--never mind.

Adjusting the margins on new regions.

rylowry@gmail.com's picture

Like every region each one will have a margin left and right. Eventually you want to remove that. If you do use a custom css like grid-hacks.css and do it there to keep everything structured.

You can fix these up nicely by adding the "alpha" class to your first region, and the "omega" class to your last region. This can even be done in your .info file. For example, I added 2 columns below the main content region. Here are snippets from my .info:

settings[alpha_region_content_bottom_first_css] = 'alpha'
settings[alpha_region_content_bottom_second_css] = 'omega'

That will make your regions line up nicely with the main content on the outter sides.

that didn't work for me. I

dotman's picture

that didn't work for me. I did get my two bottom content columns using the preprocess method in the other thread, and was told to add this to adjust my margins with the following css, which looks fine in narrow and wide, but when resized to mobile, they look off.:

  #region-content-bottom-first {
      margin-right: 10px;
      margin-left: 0px;
  }

  #region-content-bottom-second {
    margin-left: 10px;
  }

Are you saying you used both the css above and the setting code in you .info file?

Would you mind posting the code you put in all three files: template.php, .info and whichever css file you may have added code to? I put the above css in my global.css file, but I'm not sure that is correct.

thanks.

More info

rylowry@gmail.com's picture

I did not use any of the css described in the above article. I am not adding any styling through global.css to the new regions. I only added classes through the .info file. This has worked alright for me in Firefox and IE7. Also, I am using D7 and Omega 7.x-3.1.

Here are screenshots taken from IE7:
With added classes: http://imgur.com/iYni1
Without added classes: http://imgur.com/HjDpL

Here is the entire .info file:

theme.info

regions[content_bottom_first] = 'Content Bottom First'
regions[content_bottom_second] = 'Content Bottom Second'
regions[content_bottom_third] = 'Content Bottom Third'

settings[alpha_region_content_bottom_first_equal_height_container] = ''
settings[alpha_region_content_bottom_first_equal_height_element] = ''
settings[alpha_region_content_bottom_first_force] = ''
settings[alpha_region_content_bottom_first_prefix] = ''
settings[alpha_region_content_bottom_first_columns] = '2'
settings[alpha_region_content_bottom_first_suffix] = ''
settings[alpha_region_content_bottom_first_weight] = '0'
settings[alpha_region_content_bottom_first_css] = ''

settings[alpha_region_content_bottom_second_equal_height_container] = ''
settings[alpha_region_content_bottom_second_equal_height_element] = ''
settings[alpha_region_content_bottom_second_force] = ''
settings[alpha_region_content_bottom_second_prefix] = ''
settings[alpha_region_content_bottom_second_columns] = '2'
settings[alpha_region_content_bottom_second_suffix] = ''
settings[alpha_region_content_bottom_second_weight] = '1'
settings[alpha_region_content_bottom_second_css] = ''

settings[alpha_region_content_bottom_third_equal_height_container] = ''
settings[alpha_region_content_bottom_third_equal_height_element] = ''
settings[alpha_region_content_bottom_third_force] = ''
settings[alpha_region_content_bottom_third_prefix] = ''
settings[alpha_region_content_bottom_third_columns] = '2'
settings[alpha_region_content_bottom_third_suffix] = ''
settings[alpha_region_content_bottom_third_weight] = '2'
settings[alpha_region_content_bottom_third_css] = ''

template.php

function hook_alpha_page_structure_alter(&$vars) {
    $vars['content']['content']['content']['#sorted'] = FALSE;

  if (!empty($vars['#excluded']['content_bottom_first'])) {
    $vars['#excluded']['content_bottom_first']['#weight'] = 100;
    $vars['content']['content']['content']['content_bottom_first'] = $vars['#excluded']['content_bottom_first'];
  }

  if (!empty($vars['#excluded']['content_bottom_second'])) {
    $vars['#excluded']['content_bottom_second']['#weight'] = 110;
    $vars['content']['content']['content']['content_bottom_second'] = $vars['#excluded']['content_bottom_second'];
  }

  if (!empty($vars['#excluded']['content_bottom_third'])) {
    $vars['#excluded']['content_bottom_third']['#weight'] = 120;
    $vars['content']['content']['content']['content_bottom_third'] = $vars['#excluded']['content_bottom_third'];
  }
}

You might want to make sure you don't have any borders applied to those regions, as the extra width might push a region down a row.

Does your code work in IE 8 and lower?

dotman's picture

Hey rylowry,

You may see my post below about the sidebar floating left under my 2 content subregions in IE 8 or lower. Are you getting good results in those browsers with your code? Works fine in all others.

Here's my site if you wouldn't mind taking a look at it in IE:

http://mircdev.mplp.org/

here's a screen shot as well:

http://mircdev.mplp.org/IE8-9.jpg

UPDATE: Ok, I just used Adobe Browser lab and it seems to render fine in 7 and 9 (I'm not sure if I care about 6, do you still?), but IE 8 seems to be the one it fails on.

And my code in the template.php:

<?php

/**
* @file
* This file is empty by default because the base theme chain (Alpha & Omega) provides
* all the basic functionality. However, in case you wish to customize the output that Drupal
* generates through Alpha & Omega this file is a good place to do so.
*
* Alpha comes with a neat solution for keeping this file as clean as possible while the code
* for your subtheme grows. Please read the README.txt in the /preprocess and /process subfolders
* for more information on this topic.
*/
  function wm_alpha_page_structure_alter(&$vars) {
  $vars['content']['content']['content']['#sorted'] = FALSE;



  //content bottom
  if (!empty($vars['#excluded']['content_bottom_first'])) {
    $vars['#excluded']['content_bottom_first']['#weight'] = 90;
    $vars['content']['content']['content']['content_bottom_first'] = $vars['#excluded']['content_bottom_first'];
  }

  if (!empty($vars['#excluded']['content_bottom_second'])) {
    $vars['#excluded']['content_bottom_second']['#weight'] = 91;
    $vars['content']['content']['content']['content_bottom_second'] = $vars['#excluded']['content_bottom_second'];
  }

  if (!empty($vars['#excluded']['content_bottom_third'])) {
    $vars['#excluded']['content_bottom_third']['#weight'] = 92;
    $vars['content']['content']['content']['content_bottom_third'] = $vars['#excluded']['content_bottom_third'];
  }
}

Do you have any idea how I could fix this? I'm stumped.

Thanks,
Doug

I had the same problem, but fixed it in css

suntog's picture

I fixed it by clearing all margins and then resetting them then set them to float-left to fit below the main conent area, see the bottom blocks in. www.unitedparishbrookline.org. Here is the css I used to fix the alignment problem:

region-content-bottom-first {

margin-right: 0px;
margin-left: 10px;
width: 30%;
float: left;

}

region-content-bottom-second {

margin-right: 0px;
margin-left: 10px;
width: 30%;
float: left;
}

region-content-bottom-third {

margin-right: 0px;
margin-left: 10px;
width: 30%;
float: left;
}

It breaks in IE 8 and below

dotman's picture

I got my two content sub-regions to work, but they break in IE 8 and below. My sidebar floats left under the 2 content sub regions. What are you guys doing to prevent that? Would appreciate the advice.

thanks.

May have to resort to panels

gjangelo's picture

Using the code in the original post, I was able to get get the new regions added to my content area, but the display was off.

What I wanted was:

+-------------+------+
| content     | side   |
| cont bttom   | bar   |
+-------------+------+

what I got was:

+-------------+------+
| content     | side   |
|             | bar   |
+-------------+------+
| cont bttom   |      |
+-------------+------+

I played with the weights & margins, but was still unable to get the content bottom to share space with the content area.

Any enlightenment on how to accomplish this?

Hey Lrrr, I have accomplished

Ankabout's picture

Hey Lrrr,

I have accomplished this before, but usually with some clever CSS. I've never worked with Panels, so no idea how that would work. But with some clever CSS it works.

Can somebody clarify this

bserem's picture

Can somebody clarify this line:
$vars['content']['content']['content']['content_top_first'] = $vars['#excluded']['content_top_first'];

What does content-content-content mean?
I'm trying to understand what else is possible with the above technique!

Bill Seremetis
http://srm.gr - working with Drupal in Greece

Content

rlhawk's picture

The first 'content' is added by Drupal core. The second refers to the section, the third refers to the zone, and 'content_top_first' is of course the region. That's a lot of contents.

Thank you for the reply

bserem's picture

Thank you for the reply rlhawk (amazingly fast). Yeap, to many contents in this code.

Bill Seremetis
http://srm.gr - working with Drupal in Greece

Works but doesn't quite work for me

louloubug's picture

I have been able to finally add a region that is right of side bar first and spans above content and sidebar second. However, it's going to the bottom of the page rather than the top. I have the weight set (in template.php) as -91. I have no idea how to fix it. Any suggestions? here is the coding I used in my template.php:

<?php
function mytheme_alpha_page_structure_alter(&$vars) {
$vars['content']['content']['content']['#sorted'] = FALSE;

if (!empty($vars['#excluded']['inside_page_slider'])) {
$vars['#excluded']['inside_page_slider']['#weight'] = -91;
$vars['content']['content']['inside_page_slider'] = $vars['#excluded']['inside_page_slider']; }

}

Frontpage

eugen80's picture

On frontpage I have all the new regions, but the title of the content is ABOVE these regions. How can I fix this?