Motivations for Using CSS
To be effective at HTML, you will not get very far without learning Cascading Stylesheets. Even if you are not a web designer, having an understanding of how CSS properties affect the presentation of a web page will help you lay out your page in a readable manner for your audience.
HTML Without CSS
Why is CSS important? Let’s view the simplest example of a web page with no CSS whatsoever:
Without having specified anything in the HTML markup, the browser renders the page according to its default settings, which, in this case is only black text on a white background, using the default font (Figure 1).
As you add additional content to the page, the rendered web page simply elongates as a single column. If we copy and paste the same sentence into the markup several times, the rendered web document automatically grows to accommodate the content (Figure 2). This is how text in HTML is supposed to flow within a document: left-to-right until there is no display room on that line, then to the next line and continuing left-to-right, and so forth. If you keep adding content in this manner, ad infinitum, and the web page continues to stretch as a single column of text, until even the browser window is too small to display it all, it will provide a scrollbar so that you can read the rest of the document (Figure 3).
Left-to-right, top-to-bottom; that is how it works.
What is being demonstrated in the examples so far is the flow of text within a container. Specifically, we placed the content directly into the body tag of the document’s markup (Figures 4 and 5):
This is the role of HTML elements: To organize information into logical components. Each HTML element acts as an individual container, with its text flowing within its parent container according to the behavior that we have described so far.
Block Elements and Inline Elements
An obvious way to break up a long document in order to aid readability, is to divide the content into paragraphs (Figure 6):
Not only are a few paragraphs (p) added to break up the content, but a header (h1) has also been added to the top of the document. Each of these elements are containers themselves (Figures 7 and 8). If imagined as a tree hierarchy, the body element contains the h1 and p elements.
If you look closely at Figure 6, the usual flow of text is interrupted with the closing tags of the h1 and p elements, called block elements because of this behavior. This is one of the ways that HTML makes it possible to visually organize content. When a block element is encountered by the web browser, the flow of text starts again on a new line.
Not all HTML elements are block elements. Some are inline elements, containers that do not introduce a new line in the browser after all of its content is displayed. You are probably already familiar with these: anchors (a), spans (span) and emphases (em) are examples of inline elements. These are all containers, just like block elements, only they do not create new lines when rendering their contents.
Positioning Footer Content
What if you would like to add some footer content to the bottom of this web page, such as a copyright notice, a permalink, or a comments box? If you just add markup for an additional paragraph for this content, they simply are placed directly below the previous element in the document, just as it’s supposed to (Figure 9):
Footer content, however, should really occupy the last visible line of the browser window. You could achieve this with HTML, perhaps by introducing several line-break elements (br) and forcing the footer content lower into the document (Figure 10 and Figure 11):
The problem with this approach is that when you re-size the window or modify the browser settings to enlarge the text, the footer content is no longer positioned at the bottom of the browser window’s visible area (Figure 12).
Figures 13 and 14 demonstrate a solution that will properly position the footer content at the bottom of the page, even when the window or the text is re-sized.
How did we accomplish this? First, our simple web page is becoming more complex with the additional content. To aid in the readability of the markup, the CSS has been moved to a separate file (simple.css) and referenced from the HTML (line 5, above). Second, in simple.css a css class has been defined: footer. This new class specifies everything that we need to visually specify the footer content, consisting of a copyright notice, a permalink and a comments link. Third, the footer class is applied to the addition of a div element, which acts as the container for the aforementioned footer content (line 24, above).
Class footer uses a few CSS properties that achieve the desired effect:
- The position property, set to absolute, instructs the browser to allow an exact positioning of the element, relative to its nearest ancestor (the body, in this example).
- Specifying the bottom property to 0px instructs the browser to position the element by its bottom margin. If you imagine the nearest ancestor sitting on a Cartesian axis, 0 would be the lowest point along the y-axis (Figure 15). In combination with the position property set for this example (absolute), this would be the lowest position of the body tag (its nearest ancestor).
- In the HTML markup, we specified the footer content to be center-aligned, however, for this work in an absolutely-positioned div, we need to specify the (absolutely-positioned) left and right positions to be both 0px.
To move the footer content exactly where we want it, we override the default relative positioning with absolute positioning. Relative positioning instructs the browser to position the element relative to where it would normally appear, when any of the top, left, bottom or right properties are specified. In other words, the imaginary Cartesian axes’ origin would be set to where the element would normally be displayed when nothing is specified for its position (Figure 16)
The important point is that HTML should not be used to arrange content. This is the role of cascading stylesheets. HTML logically organizes content, and CSS describes its visual presentation.
A Newspaper Example
Let us take a look at a typical newspaper layout (Figure 17).
How would we replicate this layout in HTML and CSS? If we identify the major sections of the front page, we could say it consists of the following content:
- Top Three Stories
- Sidebar Stories
If we mark up the major sections of the front page, it might look like this (Figures 18 and 19):
As you can see, the major divs have been identified, but will not be positioned in the proper places without CSS. (For illustrative purposes, a border styling has been applied to each one.)
Absolute Positioning, Once Again
To properly position each div, we will once again use absolute positioning, each div being positioned relative to the body, the nearest ancestor in the document for each of them. CSS classes for the following are defined in a separate CSS file (and, accordingly, the CSS file referenced in the HTML file with a link tag, line 13 of Figure 18):
Figures 20 and 21 show the CSS in its entirety. It requires some experimenting to determine the proper positions for each of the divs to ensure that none of the content overlaps and that each is positioned to precise pixel coordinates (lines 3, 10, 17, 24, 31, 37 – 38).
The widths and heights are expressed as a percentage of the nearest ancestor’s dimensions for those properties. When the browser is resized or maximized, everything maintains its position and proportions within the document. It is important to remember that the pixel coordinates are relative to the coordinate origin of the body tag, the nearest ancestor for each of the divs. The percentages are a proportion (0% – 100%) of the body tag. This is shown below (Figure 22):
Another Implementation with Grid Layout
Although we have successfully set up the layout for our hypothetical newspaper, the design will not work if the content substantially changes in its organization. For example, what if we want to add an additional top story, or if we were to add an additional sidebar along the left-hand margin of the front page? What if we need to remove something?
Is there a way to flexibly accommodate these changes without substantially affecting the markup?
Another way to visualize a document could be as a grid, with a set number of columns and rows. If we were to think of our newspaper front page in this way, you could say that our example might be visualized as a grid of two columns and three rows (Figure 23). More specifically,
- Row 1 consists of the header, spanning two columns
- Row 2, Column 1 consists of all three top stories
- Row 2, Column 2 consists of the sidebar stories
- Row 3 consists of the footer, spanning two columns
Relatively speaking, the column used for the top stories is significantly wider than the column occupied by the sidebar. The exact proportions are up to you, the designer. To provide plenty of flexibility, you could visualize the layout as being composed of more than two columns. You could, for example, think of the composition as being a grid of three rows and five columns (Figure 24), instead of two:
- Row 1 consists of the header, spanning five columns
- Row 2, Column 1 consists of all three top stories, spanning four columns
- Row 2, Column 2 consists of the sidebar stories, spanning one column
- Row 3 consists of the footer, spanning five columns
CSS Attributes Important to Grid Layouts
The reasoning behind conceptualizing your layout in this way is that the more columns you plan into your stylesheet, the more flexibility you have to change the layout and to add additional content later. Figure 25 demonstrates a couple of new things.
The box-sizing property set to border-box instructs the browser to take into consideration the content, padding, and border of the element when calculating its width, but does not include margins. By default, this property is normally content-box, which excludes the padding and border when calculating width. For calculating widths in a grid layout, border-box is desirable because it makes possible the accurate calculation of column widths, so that their sum total is exactly 100% of the browser width.
In our proposed grid stylesheet, we are specifying that all elements in the document (*) have their widths calculated as border-boxes. The stylesheet also defines classes that define the widths for containers of varying width, each class expressed as multiples of a single column-width. As you can see, five CSS classes are defined to accommodate widths of 20%, 40% 60%, 80% and 100% of the available browser width.
The Newspaper Example, as a Grid
Utilizing these new CSS instructions for the browser, we layout the front page, using the column-width unit of measurement (Figure 26):
Taking a look at how it renders (Figure 27), the widths appear to be what we desire, but the individual divs are not where we want them to be. Why is that?
The elements are rendering according to the rules for their container (the body): Left-to-right, top-to-bottom. Take a closer look at Figure 26, lines 16 through 21. The header div element appears first after the body, so it renders at the top of the document. The div for the sidebar content is listed next in the markup, so it renders on the next line after the header. The three divs for the top stories then render next, each on their own line. Finally, the footer div, is listed last in the markup. They are all rendering according to the flow rules we have described so far.
Our design requires that the sidebar content occupy the right-hand margin of the front page, and that top stories be next to it, on the left. How do we instruct the browser to position these elements in this manner?
The Float Property
To break the normal flow of content in this situation, we want to force the sidebar content over to the right. Let’s modify the stylesheet to do this, using the float property (Figure 28). We also take away the instructions for the margin property from the outline class so that column widths add up to 100%. (Remember that margin is not included in border-box calculations.)
The tricky thing with float is that once you apply it to one element, elements that follow in the document will flow according to where the floating element finishes rendering (Figure 29). This may or may not be a desirable thing. If you need to fix this so that the next (non-floating) element renders beginning at the left-most of its container, apply the CSS clear property to the element following the floating element.
Figure 30 illustrates the desired effect, now that the stylesheet is complete. You might have noticed that we are using fewer CSS classes than the previous layout example. This is one of the benefits of using this implementation of a grid layout. Because widths are calculated as multiples of a single-column width, it simplifies the instructions provided to the browser.
With mobile devices an important part of many people’s lives, it is practically a given that web content should render well on small screens. A sophisticated layout that looks great on a high-resolution, desktop monitor loses its appeal when viewed from a mobile phone or a tablet computer. When a layout readily renders a web page so that it maintains readability regardless of the device that is used to view it, we call its design responsive.
A responsive design takes into first consideration the likelihood of web content being accessed with a small device. Conscientious designers consider the needs of these audiences and ensure that the CSS stylesheet is able to detect when to render web content for small devices. If a sufficiently large screen is detected, the full experience continues to be available for those audiences as well.
Only small modifications to the newspaper grid layout are required to accommodate both large and small screens (Figure 31).
@media is called a media query. Line 8 is specifying that if the maximum width of the device’s screen is 500 pixels or less, the browser must apply the stylesheet rules at lines 9 and 10. More specifically, line 9 modifies the sidebar class so that it no longer displays any element defined with it. In addition, line 10 specifies that CSS class names that match “colwidth-” (e.g. colwidth-1, colwidth-2, etc.) should set their width properties to 100%.
The overall effect of lines 8 – 11 is that the sidebar content is not presented on small screens, and the remaining content displays at full width. No modification to the HTML markup is required. Figure 32 demonstrates a special Responsive Design Mode on Safari browser that simulates the actual behavior on small devices. This is a handy feature to have. As you can see, with Safari you can select the device emulated, and the content renders appropriately.
One HTML Document Needed
It is not necessary to maintain multiple versions of a web page, to support different devices, thanks to the media query feature of CSS. All you need is a well-written stylesheet to accommodate all of the devices that you intend to support.
Media query has many more capabilities. Hopefully, this example gives you a useful glimpse into what it can do to enable a responsive layout for your web content.
This article has covered some fundamentals in preparing page layout for your web content. Hopefully, you have gotten a sense of some of the rules that govern the flow of text, the role of containers, and the effects of a few important CSS properties. We also tried a couple of different layouts, learning that there is often more than one way to implement a stylesheet to achieve the same effect. We also learned how to manage the varying display capabilities of browsers across devices. CSS is able to specify how to render content in a manner that suits each device best.
Cascading Stylesheets are very powerful. It takes experimentation and practice to fully comprehend the breadth and depth of their application. Fortunately, the web community has pooled together its collective experience, making it often unnecessary to design page layouts entirely from scratch. There are many, considerably more sophisticated, templates available to help you get a head start with your web page layouts.