That CSS presentation layer Must Be Built

Time for Flexbox? Some Simple Examples to Convince You

It looks like the time has come to dive into Flexbox.  This layout technology has been lurking on the fringes of CSS for a while now but with sites like the BBC and with frameworks like Bootstrap 4 using it, now seems like the time to join the fray.

If you been a web designer /developer for a while you'll have seem many layout trends over the years and may be a little jaded over yet another change.  But you'll also appreciate that techniques such as float are not without there problems.  Here are three simple examples to convince you to take a look at flex box.

Example One: The Floated Grid Height Problem

Take this classic floated grid layout.

See the Pen Grid with Float by Martin Cooper (@mustbebuilt) on CodePen.0

By floating to the left, the grid stacks.  However, if you have one grid item that has higher content than the other grid items the stacking 'breaks'.  Cue messing around with heights or cutting content to sort out the problem.

With flexbox we can easily fix this:

See the Pen Grid with Flexbox by Martin Cooper (@mustbebuilt) on CodePen.0

Notice how the grid behaves itself and also notice how little CSS that took .... and no need to set heights.

How was this done?

With flexbox we have a new CSS display properties of flex.  (In fact there are variants on this but more later).

By setting a container element to display: flex, element becomes what is known as a 'flex container' and all child elements become 'flex items'.   These flex items will, by default, want to spread out to use the available horizontal space in the flex container .  By only adding display: flex to the container all 9 child flex items would be squashed to fit on one line.  We don't want this we want the width of the flex items respected so we need to add a second property to the flex container of flex-wrap and set this to wrap.  That way the items are allows to wrap on the horizontal and we get our grid.

Example Two: Evenly Spaced Menu Items

Behind most navigation bars sits a humble HTML list.  Then with display:inline or with float these are transformed into horizontal navigation bars.

See the Pen List to Navigation with Float by Martin Cooper (@mustbebuilt) on CodePen.0

But try and get the menu items evenly spaced.  This means messing about with padding and setting individual values for each menu item - not easy.

With flexbox we can do this:

See the Pen List to Navigation with Flexbox by Martin Cooper (@mustbebuilt) on CodePen.0

The menu items are now perfectly spaced.

How was this done?

The trick is that the <ul> is set to have a display: flex and thus becomes a flex container.  Then we can use a new CSS flex property of justify-content and set it to space-between  (other options are available). The justify-content property controls the justification, that is alignment, along what flexbox calls the 'main' axis. By default the main axis the horizontal. The value set by the justify-content property controls the alignment along the main axis of a flex container when the flex items do not use all the available space.

Example Three: Centring Vertically

Finally let us use flexbox to centre some content vertically.  This is notoriously tricky but flexbox has a solution.

See the Pen Centre Vertically with Flexbox by Martin Cooper (@mustbebuilt) on CodePen.0

How was this done?

This is achieved by again using justify-content but this time with a value of center.  In this example justify-content works on horizontal alignment of flex items in the flex container.

To centre vertically we use the align-items property and set it to a value of center.  In this example align-items works on vertical alignment of flex items in the flex container.

It is important to note that justify-content works on what is called the 'main axis' whereas as align-items works on the 'cross axis'. In our example the main axis is horizontal and cross axis is vertical as our flex container is using the default flex-direction value of row.

Hopefully this gives you a flavour of flexbox. My next post will dig deeper into these concepts.

Dividing Dynamic Content equally into Columns

The CSS float property is often used to create columns. Waiting in the wings are some newer techniques such as the CSS column-count property which will make adding columns much easier.

For example given a HTML snippet of :

	<li>ALFA ROMEO</li>
        .. etc etc

We can use the following CSS to put the list into 5 nice columns.


View Demo

This is particularly useful when your content (in this case a list) is dynamic and you don't know how many items you're doing to have and therefore how many items to place in each list.

A Javascript Fallback

However, as caniuse kindly tell us we can't use this technique with IE9 or earlier.

Here is a solution I came up with. Assuming we want 5 columns set up the HTML as follows:

<div id="colsContainer">

The dynamic data I am going to use here is a Javascript array.

var myArray = new Array('ALFA ROMEO','AUDI','AUSTIN','BMW', .... 'VOLKSWAGEN','VOLVO');

The following Javascript counts the number of values in the array and then works out how to distribute them evenly across, in this case, five columns. The maths trick here is the use of the modulus (%) to divide the items by the number of columns but distribute the remainder to the left-hand columns.

 var noCols = 5;
 var displayData = "";
 var startVal = 0;
 var endVal = 0;
 for(var i=0;i<noCols;i++){
     if(i < myData.length%noCols){
         endVal =+ (endVal+Math.floor(myData.length/noCols)+1);
         endVal =+ (endVal+Math.floor(myData.length/noCols));
     displayData = ""
     for(var j=startVal;j<endVal;j++){
         displayData += '<li><a href="">';
         displayData += myData[j];
         displayData += '</a></li>';
     startVal = endVal;
     $('#modelList div ul').eq(i).html(displayData);

View Demo

Margin Collapse - or Why Can't I Get Rid of That Margin at the Top?

Margin Collapse is a foxy little fox that dresses like George Clooney in the Fantastic Mr Fox. It's a sly one alright and has caused many a good web developer to bash their head in frustration when that pesky margin will just not disappear.

So what is margin collapse. Well usually it just happens and it passes unnoticed. Margin collapsing is where the browser will combine the margins of two elements and then only apply the larger of the two.

This can happen in a number of cases.

Firstly, when you have adjacent sibling elements ie

<p>My paragraph</p>
<p>I am your sibling</p>

In this situation if the first <p> has a margin-bottom of 50px and the second <p> has a margin-top of 100px - then the margin will collapse - ie will be equal to the larger of the two values ie 100px.

See a demo here.

Generally this can pass without notice.

The other scenario is where there are parent / child elements ie

<div>My content</div>

In this scenario if the margin-top of parent is not separated from the margin-top of the child then the margins collapse. This can also happen with the parent / child margin-bottom properties.

Have a look at this demo file.

Notice how the yellow container does not fill out to the top of the page. Now you may think that maybe this is because you need to put 0 margins and padding on the <body> and then the yellow of the container will fill to the top. Try it on the demo. Hmmm maybe not.

The margin-top of <body> needs to be separated from the margin-top of the <div> and can be done by adding a border, some padding or some inline content.

Return to the demo and click the button to apply padding to the top of the container and we now see the top margin removed.

Got yer you pesky foxy fox.

Old School with iFrames and Tables

Sorry Grandad, frames and tables - you're having a laugh aren't you? Before you abandon this post for been just soooo 1990s I only want to clear up a few things related to our old (friends!) frames and tables. Lately, and somewhat unbelievable, I have seen references to these technologies as layout techniques - noooooooo! You should have left these technologies behind with the Spice Girls. That said beyond layouts there are cases where you can be justified in using them.

You've Been Framed

Firstly frames. Reviled by designers for looking awful, detested by Marketeers for terrible SEO and pilloried for lack of accessibility, as I say these should be long forgotten. However, I would venture to say that they have tended to linger (like a fart in a spacesuit) in the murky world of backend content management systems - Blackboard or Sharepoint anybody. That said they have been formally removed from the HTML5 specification so it would be hoped that the days are numbered for these last few outposts.

There does remain one frame technology however that is in the W3C specification and has a very healthy usage. I am talking here about iframes. An iframe provides a convenient window through a page to other content. First introduced by Internet Explorer the iframe element creates an inline frame. This produces a window through a page to another HTML page. The iframe content can be changed by linking to the iframe using the target attribute of the anchor tag.

If you have ever embedded a Youtube video you will have used iframes. Youtube's code is like this:

<iframe width="560" height="315" src="http://www.youtube.com/embed/KUDjRZ30SNo" frameborder="0" allowfullscreen>

The attributes required for an iframe are all pretty obvious. Dimensions are set by width and height. The URL of the page to appear in the iframe is provided in the src attribute. The name attribute allows the iframe to be targeted in links. And the frameborder attribute controls a border around the iframe. A value of 1 switches the border on, a value of 0 will remove the border.

He is the code above with the lovely frameborder set to 1.

Trendy Tables

What of tables? Everywhere you look in the real world tables are used as a brilliant way of displaying data. And that is what you should use them for in a web page. Absolutely NOT for the layout of the page. Why not layout? Because the HTML is overly heavy, inflexible and semantically wrong.

By default HTML tables aren't that pretty but CSS can do its presentational sparkle on them easily enough. I am pretty sad and love nothing more than a nice looking table.

Yuck Table

The following table has its border attribute set to 1.

<table border="1">
Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

Not very pretty. So here are my top 5 table styling tricks.

1. Remove Old HTML

Remove all HTML attributes from your table like border, cellpadding and cellspacing. You can then add padding to all table cells via td and th as you see fit.

td, th{
Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

Also apply background colours as you would with any other element ie:


2. Table Headers

Use <th> elements for your table headers. Better semantics. These will be bold and centred by default but we can change that with CSS. The following CSS rule will change the style of the <th>s.

Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

3. Use the CSS property border-collapse

Use the CSS property border-collapse. This may seem strangely named but by setting the value to collapse it allows you to overrule the messy table borders set with HTML attributes and replace them with your own lovely CSS ones.

Add a CSS rule to target your table, setting border-collapse to collapse. Then apply a new border with CSS for example:

    /* my new border style */
    border:1px solid #C24704;

This would result in a table like:

Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

Other options include adding borders to rows via the tr.

    border:1px solid #C24704;
Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

We could also just have vertical borders by targeting the td with a rule to add left and right borders. You'll need to remove any borders added to the tr element for this.

	border-left:1px solid #f00;
	border-right:1px solid #f00;
Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

4. Align cell content with text-align and vertical-align

When placing content in cells use CSS text-align to align text horizontally and vertical-align to align text vertically ie:

    border:1px solid #f00;
Key values left, right and center.
Key values of top, bottom, or middle.

Use text-align and vertical-align over the likes of HTML td and tr attributes align and valign.

The table below uses text-align and vertical-align to align the table cell content.

Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

5. Use CSS3 tricks like nth selectors

If you fancy dabbling in a bit of CSS3 you could use nth selectors to stripe the rows.


This CSS3 selector will only target 'even' rows. You can target 'odd' rows as well.

Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

If you need to support older browser the same trick can be achieved with jQuery by creating a suitable class and adding to only 'odd' or 'even' rows.


Finally what about a lovely CSS3 box-shadow.

   box-shadow:4px 4px 4px #555;
Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration

Now that's better.

(CSS) Three Is A Magic Number

Many popular visual effects that previously required background images and the use of your Favourite Graphics Editor (FGE or Photoshop for short), can now be done with CSS3 magic. Here is a quick overview of six crucial CSS3 features.

Before We Start: Browser support is an issue with these features. You'll need a decent, lets say 'modern' browser, such as a recent version of Chrome, Safari, Firefox or Internet Explorer 9/10. Even then they can be inconsistencies. I'll draw out some of the inconsistencies amongst 'modern' browser but am going to ignore older versions of IE as We Need to Talk About Internet Explorer.

Border Radius

Everyone loves a rounded corner. Steve Jobs was positively nuts about them. Set all four at once or pick them off individually.

/* add a basic border */
border: 2px solid #555;
/* all four */
border-radius: 10px;
/* top left only */
Styled with border Radius

Values should be positive numbers. Bigger values are more curvy as what you are actually doing is setting the radius of the circle used to create the curve. Elements with higher widths and heights can take bigger values but eventually you can curve no more.

You can also apply two radii - horizontal first and vertical second to achieve other border effects.

/* add a basic border */
border: 2px solid #555;
/* all four */
border-radius: 4px 10px;
Styled with border Radius

As these features are not supported by all browsers we have the contentious issue of vendor prefixes. These are prefixes added to each property as a temporary stop gap until the standard is formalized. As such this can be a moveable feast. For border-radius we would need the following:

border-radius: 4px;
-webkit-border-radius: 4px;
-moz-border-radius: 4px;

The Vendor prefixes are as follows:

Browser Layout Engine Vendor Prefix Example
Chrome Webkit -webkit- -webkit-animation-duration
Firefox Gecko -moz- -moz-column-count
Internet Explorer Trident -ms- -ms-background-position-x
Opera Presto -o- *
Safari Webkit -webkit- -webkit-animation-duration
* Opera adopting -webkit

For adding rounded corners to pre-IE9 versions of IE we need to talk about Internet Explorer.

Box Shadow

Now we have a border time for a shadow (once the providence of Photoshop).

box-shadow: 4px 4px 4px #555;

Results in:

Box Shadow

box-shadow: ['inset'], horizontal offset, vertical offset, [blur distance, spread distance,colour value]

box-shadow: inset 2px 2px 8px 8px #555 ;

Results in:

Box Shadow

Vendor prefixes would be:

border-radius: 4px;
-webkit-border-radius: 4px;
-moz-border-radius: 4px;

Text Shadow

So shadows on boxes are okay but lets now have text shadow as well.

text-shadow: 2px 2px #fff;
Text Shadow

text-shadow: horizontal offset, vertical offset, [blur distance, spread distance,colour value]

More than one shadow can be added and when done subtly can look rather good.

.ts2 {
	font-family: Helvetica, Arial, sans-serif;
	font-size: 20px;
	color: #E0C9A5;
	text-shadow: -1px -1px #fff, 1px 1px #333;
.ts3 {
	text-shadow: 1px 1px #fff, -1px -1px #444;

When the two classes above are applied to an element it results in:

Text Shadow

As text-shadow boasts good browser support no vendor prefixes are needed.

Warning: Time for a timely reminder. Support for these features is lacking in old school IE6, IE7 and IE8.


Background gradients don't require a new CSS property but make use of the background property. Values can be either linear or radial with values dictating the colour, direction and strength of the gradient.

Syntax variables for linear and radial (and horizontal) gradients. There is also an issue that webkit based Safari prior to version 5.1 used a slightly different syntax to that now adopted.

  /* Safari 4+, Chrome */
  background: -webkit-gradient(linear, left top, left bottom, from(#ffff00), to(#ffffff));
  /* Chrome 10+, Safari 5.1+, iOS 5+ */
  background: -webkit-linear-gradient(top, #ffff00, #ffffff);
  /* Firefox 3.6-15 */
  background: -moz-linear-gradient(top, #ffff00, #ffffff);
  /* Opera 11.10-12.00 */
  background: -o-linear-gradient(top, #ffff00, #ffffff);
  /* Firefox 16+, IE10, Opera 12.50+ */
  background: linear-gradient(to bottom, #ffff00, #ffffff);
  /*  IE 10 */
  background: -ms-linear-gradient(top, #ffff00, #ffffff);

There are endless permutations of the gradient.

Check out the some of the great tools for generating gradients online:

Warning: IE9 does not support gradient. See We Need to Talk About Internet Explorer for workarounds.


Give elements transparency with opacity. Takes values of 1 to 0 where 1 is opaque and 0 transparent. As such decimal values such as 0.5 and 0.75 are the order of the day.

opacity: 0.5;


When we set colors in web design we use RGB - Red, Green, Blue.

... and we represent them as hexidecimal colours:

Red, Green, Blue

As any Photoshop user should know there is also something called Alpha. This represents the opacity of a colour known as it alpha channel. With CSS3 you can create colours with RGBA - the A been Alpha. Instead of using hexidecimal colour codes we values between 0-255 for the red, green the blue and then a value between 0 and 1 for alpha (as we did with opactiy).

Like gradients above this trick is used on the background property ie:


So we can create layer effects by nesting elements and using RGBA values on the child elements as follows:

A RGBA Example

Don't forget We Need to Talk About Internet Explorer.

Three is a magic number.

We Need To Talk About Internet Explorer

IE don't you just love it? No probably not but unfortunately we still live in a web world dominated by Internet Explorer - Microsoft were just way too successful in getting their browser everywhere.

Here in the UK, Internet Explorer in all its different guises, still has the largest market share as calculated by statcounter. In August 2012 there were double the users of IE8 compared to Safari on the iPad.

That means you cannot ignore it. You must have a strategy for dealing with it.


Pre IE9 versions of IE do not support HTML5. If you want to start you use HTML5 elements such a <nav>, <header> you can but beware.

Old IE versions will treat unknown elements (all HTML5 elements) as inline elements and it won't be able to style them. That means using the likes of <footer> and <nav> becomes problematic.

Help is at hand though.

However, a ‘fudge’ or ‘shim’ or ‘shiv’ has been made available by jQuery and Javascript wizard John Resig. Adding the following Javascript code to your pages will allow them to be styled.

<!--[if lt IE 9]>
<script src="http://html5shiv.googlecode.com/svn/trunk/html5.js"></script>

Here's a page pre-Shim and a page post-Shim (best viewed in IE8 - you don't hear that very often).

IE Conditional Comments

The above uses a feature of IE known as conditional comments. The lines that look like standard HTML comments are ignored by all browsers except IE that interpretes the conditional logic.

To detect Pre IE9 versions of IE we can use:

<!--[if lt IE 9]>
// detects running IE version less than (lt) 9

You can do other queries such as:

<!--[if IE 7]>
// detects running IE 7


<!--[if gte IE 8]>
// detects running IE version greater than or equal to 8

A full list of conditional comment syntax is available from Microsoft.

This gives you the opportunity to serve up different stylesheets to help deal with older versions of IE for example:

<!--[if IE 6]><link rel="stylesheet" type="text/css" href="/styles/style-ie6.css" /><![endif]-->
<!--[if IE 7]><link rel="stylesheet" type="text/css" href="/styles/style-ie7.css" /><![endif]-->
<!--[if IE 8]><link rel="stylesheet" type="text/css" href="/styles/style-ie8.css" /><![endif]-->
<!--[if IE]><link rel="stylesheet" type="text/css" href="/styles/style-ie.css" /><![endif]-->


As well as detecting which browser the user is running you can also detect which specific features are supported. This can be done through the rather nifty 'modernizr' javascript plugin.

Modernizr includes the 'shiv' for HTML5 and also adds 'feature-sniffing' to identify whether the browser supports various HTML5 and CSS3 features.


I am going to consider the six CSS3 features covered here and see how we can try and use them in older versions of Internet Explorer.

The web community is a wonderful thing and as well as Modernizr we have been provided with PIEs. Progressive Internet Explorer is a polyfil* that will give us the suport for border-radius, box-shadow and gradients.

Working with PIE is well documented. Download the files and upload them to your server. I find it best to place them in your styles folder. The crucial one is pie.htc.

Border Radius with PIE

To create a border radius with CSS3 you would use:

     border-radius: 15px;
    -moz-border-radius: 15px;
    -webkit-border-radius: 15px;
    -o-border-radius: 15px;
    border-radius: 15px;

Old IE cannot cope with this. So to fix it with PIE change it to:

     border-radius: 15px;
    -moz-border-radius: 15px;
    -webkit-border-radius: 15px;
    -o-border-radius: 15px;
    behavior: url(styles/PIE.htc);

Two tips with PIE.

  1. The url to the htc file is relative to the document that calls the stylesheet NOT relative to the stylesheet.
  2. If the htc does not seem to work for you and your server supports php then use PIE.php instead.

Box Shadow with PIE

We have done the ground work above. Box shadow can be added in the same way by just adding the necessary CSS3 properties (don't forget your vendor options).

     box-shadow:0 0 7px 0 #999999;
    -moz-box-shadow:0 0 7px 0 #999999;
    -webkit-box-shadow:0 0 7px 0 #999999;
    -o-box-shadow:0 0 7px 0 #999999;
     border-radius: 15px;
    -moz-border-radius: 15px;
    -webkit-border-radius: 15px;
    -o-border-radius: 15px;
    behavior: url(pie-css/PIE.htc);

Here is a page polyfilled with PIE.

Box Shadow with Microsoft Filters

Who ate all the pies?

If you are pie-less then there is another solution to Box Shadow support.

Microsoft has its own propriety solution for a range of visual effects that can be applied through their CSS filter property.

The filter CSS property will be ignored by other browsers so is quite safe to use.

It should also be used with the Microsoft vendor prefix of -ms-filter for IE8 whilst earlier versions just use filter.

/* for IE8 */
/* for pre IE8 */

The syntax is a strange compared to the general elegance of CSS but it does work of a fashion.

The shadow takes values for the strength and colour. The direction value is in degrees 0° been straight up so a value of 135 is off set to the right.

Check the Microsoft documentation for other options.

Text Shadow with Microsoft Filters

Text Shadow is not tackled by PIE but we can use the same Microsoft shadow filter to achieve the same effect.

*/ moderny way */
text-shadow: 2px 2px #ffffff;

The above would create a white shadow offset to the bottom right. However, this technique can look pretty ropey with small font sizes.

As such you may decide it is best not to attempt to style text in this way. Fair enough. There is even an intellectual justification, two in fact, you can use to cover yourself.


  1. Progressive Enhancement - If it looks good and is supported in the browser I'll use it. If not it is only decoration and not core.
  2. Graceful Degradation - As long as it can be read, I'll drop some decorative features from older browsers. Kind of the reverse of the Progressive Enhancement.

Gradients with Microsoft Filters

We can use Microsoft filters to add linear gradients.


The above would create a vertical linear gradient yellow to white.

Opacity with Microsoft Filters

Opacity is again handled by a Microsoft filter. The filter is in this case Alpha and takes an opacity value as a percentage (remember the opacity property in CSS3 takes a value between 0 and 1).

/* modern way */

RGBA with Microsoft Filters

Finally we can again use the Gradient filter to create a fallback for RGBA backgrounds that can be used in CSS3.

There are a number of steps here. First use background-color to provide a solid background colour. We need to do this as pre-IE9 the likes of background:rgba(255,255,0,125) would just not be understood and as a result just ignored.

Secondly add in another background-color property setting it to a value of transparent

And finally use the Gradient filter to apply the alpha setting. You are hopefully used to seeing colours expressed hexidecimally ie #RRGGBB. Here we need to use the #AARRGGBB format, where AA is the alpha hexadecimal value. As a result a value of 00 would be transparent and a value of FF opaque.

To create a yellow fading background we would therefore need the following:

background-color: #ffff00;
background-color: transparent;
/* modern way */
background: rgba(255,255,0,0.5);

Fire up your old Granny's Vista laptop and take a look at this page. Should be styled (of sorts).

Don't worry IE10 will be out soon.

* Polyfils fix the holes missing in the application

The Position on Position

In my 20/20 CSS properties to learn and love I didn't include 'position'. So what is the position on position? The odd thing with position is that despite its name you can do an awful lot of layout positioning without it. Lots of web designers, and indeed frameworks like the 960 grid, solved the layout issue without recourse to position but instead rely on float (float your boat here). Float itself relies on something called 'normal flow' and it is normal flow that really lies at the core of an understanding of 'position'.

Normal Flow

With all these references to CSS properties it is important to remember that your HTML Structure is very important - it dictates what is called 'normal flow'.

Normal Flow

Normal flow is the order in which the HTML elements would be displayed without any CSS interference. Block elements like <p>, <h1> and <div>, when in the normal flow, appear top to bottom. That is elements higher in the code go at the top, ones that follow go after them. Inline elements like <a>, <img> and <span>, when in normal flow, appear left to right. So content you add after other inline content is placed to the right of it.

Normal flow is kinda common sense when you think about it. When you open a new document in a word processor - the cursor is blinking away in the top left corner. Paragraphs follow one after another down the page and text flows left to right.

Tip: Remember the CSS display property can be used to change the default display type of an element ie make a block <li> behave as if it is an inline element.

Position Absolute

The most likely position value you will come across is 'position:absolute'. This value removes the targeted element from the normal flow of the document. As such its position in the document is no longer impacted by other elements. This has the effect of letting the absolutely positioned element float (lets not use that word), sit or layer on top of the other elements in the page.

If more than one element is positioned absolutely then the z-index property can be used to stack the elements on top of each other like a pack of cards, or like layers in Photoshop (one for you crazy Graphic Designers out there). The higher the z-index the higher the element is in the stack. When no z-index property is provided then normal flow comes back into play in that the last element 'in' sits on top of the stack. If you think about it that makes perfect sense as content lower down the normal flow is rendered by the browser after content before it - so ends up on top.

When positioning something absolutely the CSS properties 'top', 'bottom', 'left' and 'right' can be used to place the element a given value from the chosen margin ie top:100px would see the element placed 100px from the top of the page.

One last thought on absolute positioning. When something is positioned absolutely the top, bottom, left and right values are 'relative' to any (non static) positioned parent. What, run that by me again? If you nest a <div> within a <div> and the first is given a top property value of 10px and the nested <div> a top property value of 20px - then the nested <div> is 30 pixels from the top of the document. We could describe this as 'relative' to its parent - BUT THIS IS NOT relative positioning. We'll see what that is next.

View Demo

And another one last think - we often use position:absolute with some Javascript magic to create animations.

CodePen Demo

Position Relative

By setting the position property to the value 'relative' an element can then be repositioned using the top, bottom, left and right CSS properties. The element is moved relative to where it would appear in the normal flow. Unlike with absolute positioning the relatively positioned element stays in the normal flow.

Where would you use this?

You can use position relative to nudge content/offset it from its normal flow position. The word offset here has been set relatively with a bottom value of 5px so it appears above the line.

Another trick is to give a container element a relative position but no top, bottom, left or right values. This means the element stays exactly where it was. However, because it has a position property (admittedly doing nothing), nested elements inside the container can use position absolute 'relative' to the relatively positioned container.

To help grasp these concepts have a play in the position playground.

Hopefully you are getting a picture as to why float remains a popular first choice when laying out a page with CSS!

View Demo

Position Fixed

When an element has the position property fixed, you guessed it, it is fixed. When the page is scrolled the element remains fixed. Where it is fixed depends on the top, bottom, left or right property values assigned to the element. In actual fact 'fixed' is very similar to 'absolute' in that the element is removed from normal flow thus allowing other content to be scrolled underneath it. This trick is often used to create permanent headers and footers that can be placed above the other content of the page.

Warning: If you are unlucky enough to have to support IE6 then sorry position:fixed is not supported.

View Demo

Position Static

Before we get onto some new goodies we must not forget position:static. This is the default value for position. It is the value that an element will have if no position property is set. And as you now appreciate that means it will appear in the normal flow.

When would you use position static?

If this is the default why would you ever set it. Good question. Well you may need this if in your wiz bang Javascript you are messing about with the position property and want to, for example, put an absolutely positioned element back into the normal flow.

The Future Sound of Layout

With CSS3 there are new tools coming to help out us poor web designers. Look out for the multi-column module with the likes of column-count, column-width and column-gap to make column design easier.

Also we will one day be able to use something called 'FlexBox' with its flex-grow, flex-shrink and flex-basis. Good old float will also find itself under siege from the likes of display:grid, grid-columns and grid-rows.

Finally the position property may get a new property 'center'. Centring content horizontally and vertically with CSS is somewhat counter intuitive at the moment, but 'center' promises to do it in one fabulous piece of CSS wizardry. Keyword here - promises. It appears in the W3C CSS3 spec but I haven't yet seen it working in a browser.

The future's so bright I've got to set opacity to 75%.

Position Properties Summary

Property Effect
absolute Removed from normal flow. Has z-index and top, bottom, left and right properties used to place absolutely where required.
relative Element placed with reference to top, bottom, left or right properties relative to where it would normally appear.
Fixed Element fixed in position. Does not move from given top, bottom, left or right properties.
Static Element returned to the normal flow.
center Not yet with us but is supposed to centre the element horizontally and vertically within its parent.

Simple jQuery Accordian

An accordion effect is a nice way to efficiently use the limited space available for menus.

In this simple example the staring HTML is a nested <ul> list.

The HTML is:

       <li class="top">item 1
       	<li>item 1 Sub 1</li>
        <li>item 1 Sub 2</li>
        <li>item 1 Sub 3</li>

       <li class="top">item 2
       	<li>item 2 Sub 1</li>
        <li>item 2 Sub 2</li>
        <li>item 2 Sub 3</li>
       </ul> </li>

       <li class="top">item 3
       	<li>item 3 Sub 1</li>
        <li>item 3 Sub 2</li>
        <li>item 3 Sub 3</li>
        <li>item 3 Sub 4</li>
        <li>item 3 Sub 5</li>

       </ul> </li>
       <li class="top">item 4
       	<li>item 4 Sub 1</li>
        <li>item 4 Sub 2</li>

The CSS for this is as follows:

nav ul{
nav ul li{
    cursor: pointer;
    font-weight: bold;
    font-size : 14px;
    line-height: 30px;
    background: #e3e3e3;
    border-bottom: 1px solid #c5c5c5;
    border-top: 1px solid white;
nav ul li a{
nav ul li:first-child{
	border-top: none;
nav ul li:last-child{
	border-bottom: none;
nav ul li ul{
nav ul li ul li{

The key line here is the display:none set for the child <ul> elements.

The jQuery is incredibly compact.

	   var menuItem = $("nav ul li.top");
	   menuItem.on("click", function(){  
		  var clickedItem = $(this).index();
			 if(clickedItem != i){

View the demo of this.


Still here? Then you must want the explanation.

First up we create a jQuery selector for the top level menu items - those marked as class="top" in the HTML.

An 'on' event is attached to this selector listening out for the ubiquitous click.

The goal is to have any menus that are already rolled down, roll up, and have the clicked menu roll down.

The roll down is easy to do and will be done last. To roll up any menus currently rolled down we'll loop around the list and use the slideUp() method. The loop is performed with a jQuery each. To prevent the clicked item from rolling down before the loop is executed we find the index() of the clicked element.

The index() of the clicked element is an integer representing the order of the element amongst its siblings - that is all the other 'top' level menu items. With this valued stored as the variable clickedItem, we use an if statement inside the loop to prevent the slideUp() on the clicked list item.

Finally the children of the clicked element, that is all the child <li> elements are feed to the slideToggle() method to slide Up or Down the nested list dependent on its starting state.

Read more about animation methods.

Advanced CSS Selectors

Moving beyond HTML, Class and ID selector there are some more CSS tools in the CSS toolkit. These selectors are part of the CSS2 specification. None of your fancy CSS3 here, so you can be assured of good browser support.

Relational Selectors

Relational Selectors allow the designer to target content based on the relation of element within your HTML structure. An easy one is:

div h1{
 /* Some properties */

The above will target all h1 tags inside div tags.

The child selector allows the designer to match any element that is a direct child of the element. For example:

ol>li {
 /* Some properties */

Here the li is targeted only if it is a child of <ol>. Therefore the <li> elements inside of <ul> are not targeted.

For browser compatibility make sure there is no white space around the  >  character.

This selector is supported by all modern browser and even supported by IE7. This allows designers to use the  >  to create rules that they know will be ignored by IE6.

The universal selector * is a wildcard that will match all elements on the page. This is often used for reseting all margins and paddings for example:

* {
    margin: 0;
    padding: 0;

* An aside on asterisk

The asterisk is also used as a hack for applying properties to IE7 and below. By prefixing a CSS property with an asterisk (*) that property will be ignored by all other browsers apart from IE7 and below.

ul.menu li{
    zoom: 1;

The code above, for example, would be used to change the targeted <li> elements from display block to inline-block. As IE7 does not support inline-block we prefix the display property with an asterisk display to set it to inline. Incidentally, the zoom: 1 is another IE hack known as the hasLayout fix.

Attribute Selectors

Attribute selectors can be used to target content based on the attribute of a HTML element. For example take the following HTML:

<a href="index.html" title="Home">Back to Home Page</a>

The HTML anchor tag has a title attribute. This can be targeted with the following CSS:


In the above example all <a> tags with an attribute or 'title' received the rule. The attribute selector can be refined by targeting particular values of an attribute. For example:


A common use case is to target all <input> text fields of type 'text' for example:


Pseudo Classes - First and Last and Always

You may be familiar with the Pseudo Class selectors that help style hyperlinks such as link, visited, hover and active. But there are others. The 'focus' pseudo class can be used with form elements to apply styling when an element gets focus. Great for forms.

<input class="myForm" type="text" name="first name" />

The above can be targeted with the following CSS such that when the user places the cursor inside the text field its background colour changes.


Try the demo:

Bringing this together with attribute selectors you could use:


... such that all text fields have the focus behaviour as in this demo.

Focus is fun, but there are more. We can use 'first-child' to target the first child of a element. This is great for lists. Take the following:


We can target the first item in the list with:


Have a read of 'Horizontal Menus from Humble HTML Lists' to see a fuller example.

The then, of course, 'last-child' gets the pesky last child.


Here is a demo of this little trick.

Note: That it is not <ul> that is used in the rule but <li> even though we are targeting the last-child of <ul>. Specifically what 'last-child' does is target the 'last-child' of the parent element, and the parent of <li> is the <ul>.

Adobe MAXing it Out

Loads of news coming out from Adobe this week as they hold their Annual Beanfeast MAX. There was the obligatory Photoshop pixel fairy magic.  The one that got people most excited appeared to be the 'deblur' tool.  Expect this to replace the Content Aware Fill as the killer Photoshop demo to wow your audience.

But beyond the gimmicky and the usual corporate hyperbole their is the distinct feeling that Adobe have rediscovered their mojo and our motoring forward (all be it sometimes via the chequebook) with some very interesting ideas.


Adobe have acquired typekit. This I am sure will be give @fontface / web typography an all mighty boot up the backside. The days of the old web safe fonts looked numbered. Of course you could do this yourself through services liked the wonderful font squirrel but Adobe have the nack of making this kind of stuff easy.

I reakon we'll be seeing this integrated with Dreamweaver, Fireworks and the recently revealed Project Muse.  Designing web fonts directly into these Adobe products looks like a very slick idea and shows Adobe going all CSS3 on us.

Adobe Buys PhoneGap

Next up is another chequebook job.  Adobe have acquired PhoneGap.

Now very excited about this one.  PhoneGap, if you have missed it, is the open source tool that will take your lovely HTML5, CSS  and Javascript and package it up as an Android, Blackberry or IoS App.  Very cool.  I can see this been integrated into (again) Dreamweaver (CS5.5 already has jQuery Mobile) but also Flash.  That is Flash Professional, Flash Builder and Flash Catalyst - all development environments we associate with producing content for the Flash Player but which are been subtlely refocused as development environments that, yes do Flash Player SWFs, but also do other stuff too.

Then they announce a whole splash of tablet apps.  Coming to Android first but promised to be available on iPads by 2012 there are 6 apps known collectively as the Adobe Creative Cloud.  This are all very touchy feelie drawing / inspiration / mood board type apps.  Expect a flurry of handdrawn style content as designers get their grubby little hands (and of course fingers) on these new creative tools.  I am feeling all flowly and floaty just thinking about it.

Could we be witnessing the emerging shape of a Post-Flash Adobe.