11 January 2015

Cascading Style Sheets and Cascading Confusion

For an application developer who positions widgets and graphics on the screen using x, y positions, an introduction to HTML styling or CSS, drives them crazy!
There was a time when I found CSS to be very confusing.  But now....I'm so comfortable with it that I can create the HTML and CSS for a web-page using just a text editor.

I have a bit of an introduction that you can skip if you want to get to the meat directly. See the line below? Search for the next such line, and the 'meat' of this blog post will follow.

_________________________________________________________


Why the confusion

Dear Application Developer, HTML is a markup language; not a programming language, and the whole reason we have such a complex, patched-up language is because when Tim Berners-Lee tried creating a software for CERN scientists to exchange information with, he had to make sure the software was compatible with different networks, disks, data and character encoding schemes. He was trying to bring order to chaos.

Every browser has had its own way of interpreting styling. Many times, buggy softwares are released into the market just so that businesses can beat the competition. Web developers are well aware of the way Internet Explorer has been poorly patched up over the years. Although thankfully, they've now come up with a new browser named "Spartan". Hopefully, browser implementations will be more agreeable with each other in future.


Referencing HTML & CSS

Like the man pages, the best sources to refer information on HTML, are the RFC's and the links they provide.
For CSS, RFC2318 led me to an excellent reference which even many tutorials couldn't help me with. Do have a look at the page on CSS Level 1.


Learning it

Think of how you'd send your application screen across a network. Send the code and allow the client to render it? Send a pixel stream and position information of the widgets? When you come to think of it, you'll realize that HTML and CSS aren't so bad after-all.

But to be able to use it, you have no other option other than to go through the nerve-wracking process of learning it (even if you use Dreamweaver, you'll have to know the concepts behind it).

_________________________________________________________


First thing you need to know, is how CSS helps format HTML elements using margin, padding, border, width and height.
If you're packaging a fragile glass in a box, you'd stuff a lot of paper or foam between the glass and the box so that the glass wouldn't shake within the box and break. That internal protective layer is called padding. Same with CSS.

Now if that box is to be kept in a larger box full of similar such boxes, you'd want to prevent all these little boxes from colliding with each other, so you'd want to place them away from each other by a small distance, and you'd wrap these boxes with some thermocol or foam. This is called the margin.

Every one of those little boxes has their own thickness, which is the border.




The actual width of your content is just the width of the fragile glass.
But the width of the CSS box is = width of content + padding + border + margin


The problem: When you want a div in your code to have a 500px width, you'd suddenly find that the div appears to occupy more space than 500px, when it is given a border, margin and/or padding.



The solution: Specify your CSS as such:

.someCSSname  
{
  width: 500px;
  margin: 0px 15px 0px 15px;
  padding: 15px 20px 15px 20px;
  border-width: 10px;
  -webkit-box-sizing: border-box; /*for Safari browser*/
     -moz-box-sizing: border-box; /*for Firefox browser*/
          box-sizing: border-box; /*for other browsers*/
}


So instead of the div's width becoming 500+(20+20)+(10+10)+(15+15), the width of the total box will be 500px, but of course, your content will be shrunk automatically.
To apply this property on all elements, you can also use:
 
*  
{
  -webkit-box-sizing: border-box;
     -moz-box-sizing: border-box;
          box-sizing: border-box;
}

Noticed the dot in ".someCSSname"? The dot means it's a class selection. If it was an id selection, it'd be "#someCSSname".



Margin and padding short forms

While it's perfectly ok to specify CSS margins as:
margin-top: 1px; and so on, I prefer to write it the short way:

margin: 1px 2px 3px 4px;

Imagine it clockwise. 1px is a one pixel margin space at the top, 2px is a two pixel margin space on the right side, 3px for the bottom and 4px for the left.

Same pattern for specifying padding:

padding: 1px 2px 3px 4px;

As a beginner to CSS, you'll very likely forget to write "px". Careful of that. They syntax just won't work without px.



Selections in CSS

Elements of HTML can be given id's which have to be unique across the document or class names which can be repeated multiple times for any element.
So you basically use id's to apply specific properties to an element and classes to apply common properties.
For id selections, you use # and for class selections you use a dot. See this:

<html>
<style>
.bkg { background: rgb(2,2,2); }
#lightGrey { color: #777; }
#red { color: red; }
</style>
<body>

<p id="lightGrey" class="bkg">
Once upon a time there were a King and a Queen who had a Prince and a Princess and they lived happily ever after.
<p id="red" class="bkg">There were no villains in the story.</p>
</p>

</body>
</html>


See how the background colour got applied to both paragraphs using class. Also, see the different ways in which you can specify colours. The #777 is the same as #777777 which is the hexadecimal colour for light grey.



Static, absolute, relative, fixed

The other thing about CSS that drives people crazy is the positioning which has names that are absolutely un-intutive.

static

If you don't specify position for an element, the default position assumed for it is static. In fact, the element is said to not be positioned at all.

relative

Paste this code in an html file and open it in a browser:

<html>
<style>
.sameBoxSize
{
  -webkit-box-sizing: border-box;
     -moz-box-sizing: border-box;
          box-sizing: border-box;
}
.lightGrey
{
  background: #777;
  width: 300;
  height: 200; 

  position: relative;
  margin: 0px 0px 0px 0px;
}
.red
{
  background: red;
  width: 200;
  height: 100;
  position: relative;
  top: 0px;
  right: 10px;
  bottom: 5px;
  left: 0px;
}
</style>
<body>

<div class="lightGrey sameBoxSize">
Once upon a time there were a King and a Queen who had a Prince and a Princess and they lived happily ever after.
<div class="red">There were no villains in the story.</div>
Hey, then what's the point of the story?
</div>

</body>
</html>

This is the output you'll see:


Now if you change top: 0px; to top: -30px;, you'll notice that the red div moves up thirty pixels, but the text "Hey, then what's the point of the story" stays in position. This is because, the browser keeps in memory the actual position that the red div is supposed to occupy, and does not allow any other element to take up that space. The red div is just rendered 30 pixels up.


Noticed something else? I've used class = "lightGrey sameBoxSize". CSS allows you to use multiple classes on any element in this manner.



fixed

This interesting positioning syntax positions elements according to the browser's edges. For the same code as above, remove the lines containing top and left, and just see the difference when we use fixed instead of relative.

The red class would look like this now:

.red
{
  background: red;
  width: 200;
  height: 100;
  position: fixed;
  right: 10px;
  bottom: 5px;
}



absolute

On using fixed, the bottom: 5px; and right: 10px; code caused the red div to get positioned according to the browser's edges. On using absolute instead of fixed, the same thing will happen, except that this time, the positioning will be as per the parent element's edges (imagine the grey div to be the browser).




This basic knowledge is all you might need to get started off with CSS. The rest you'll be able to figure out with your excellent programming skills. Hope this blog post will save you hours of frustration.

One excellent quick reference for CSS is the Learn CSS Layout website. Do go through it. That's where I learnt some important lessons.


Oh one more thing: When using CSS in websites, keep the CSS in a separate CSS file and have multiple CSS files. One file for specifying the layout of your website. One file for the colour themes of the website, one for the fonts and so on. It'll save you a lot of headache in rework, extensibility and maintenance of the website.

All the best!!! :-)

No comments: