One of my last duties at my previous job was to migrate the site’s CSS into the Bootstrap CSS framework. By “duty” I mean “project I pitched and advocated for a whole lot”.
Bootstrap is eerily similar to the CSS framework I had cobbled together over my time there, only much better written (Bootstrap has many very smart contributors; I am, alas, only one man with many hats).
It’s uncommon to find web developers with a strong understanding of client-side and server-side technologies and techniques. Bootstrap is very well documented and has many how-to examples. By converting the site’s core CSS over to Bootstrap I removed the burden of having to maintain, or even understand, those core style rules.
Any remaining, additional CSS is custom stuff, special widgets, or one-off styles for special pages. This simplifies day-to-day development a lot and makes it easier for a mostly-server-side-developer to successfully lay out a page.
Lessening other burdens
Bootstrap, and the css rules for the fabulous icon font Font-Awesome are written in LESS.
LESS is a preprocessing language for of standard CSS which provides many obvious and much needed features to CSS like variables, easy nesting of rules, automatic combining and minifying of files, and the like. Here’s how LESS solves a common, obvious problem:
Your site uses a particular color as part of the branding and design. Sometimes it’s used as the color of headings. Sometimes it’s the background color on buttons. Sometimes it’s the color of block quotes. In regular CSS you have to specify the same color in many places, or you have to have a weird rule that defines the same colors for lots of different unrelated selectors. In LESS you just set that color as a variable, then set that variable to be the value of other variables.
@brandColor: #336699; // this color is used over and over
// Other variables can reference the first value
@headingFontColor: @brandColor;
@splashPageBackgroundColor: @brandColor;
@buttonBackgroundColor: @brandColor;
// now it can be reused all over the place
h1, h2, h3 {color: @headingFontColor;}
button, input[type="submit"] {background-color: @buttonBackgroundColor;}
// .. and so on
When you realize that now you can make a site-wide color update by changing one line of code you do a little happy dance.
There are similar CSS pre-processing languages out there, and they all have their merits. But, since Bootstrap is written in LESS, and Font Awesome is written in LESS, I chose LESS as the CSS preprocessor for the project.
Approaching LESS
To move all of the site’s styles into LESS, first I needed to solve the workflow problem. The team is standardized on PHPStorm – which might just be the best PHP IDE on the market.
Digression: A lot of developers who work in PHP or Ruby on the Mac choose to use text editors like TextMate or BBEdit instead of using an IDE. Powerful, general purpose text editors like these are great tools and are incredibly useful to have around. But if you’re not using a modern IDE with code completion and inspection, integrated unit testing, integrated source control, and integrated debugging you must just like to waste time or type a lot. You probably also use spaces instead of tabs. Freak.
WebStorm is the HTML/CSS/JavaScript editor built into PHPStorm. It understands LESS files and provides syntax highlighting, code navigation and completion, and highlights syntax errors.
Add the LESS Compiler plugin and your LESS files are automatically compiled down to CSS with each and every save.
This makes LESS compilation pretty much automatic and built in to the developer’s workflow. Of course if PHP were Ruby or Java, CSS asset management would be baked into your framework and you wouldn’t need stuff like this. Sigh.
Organizing the project
Bootstrap’s LES source is organized logically into a reset, components, variables, and mixins (a LESS feature of reusable style code like a function). A common and reasonable approach to using Bootstrap is to open up variables.less and modify the base colors and grid system to suit your needs and go to town.
This works fine, but I wanted to completely isolate Bootstrap from any customizations, so it could be easily replaced or upgraded without having to gut the rest of the framework. I organized things like so:
/styles
/less
/bootstrap
/font-awesome
/project
/hacks
project.less
/css
The styles directory (in the web root of the site) contains a less directory and a css directory (and other stuff like web fonts and images in their own directories, just not shown here). LESS files are stored in the “less” directory and are compiled into the “css” director as CSS.
Here “project” stands in for the name of the site. If I were using this system on Abouthalf, the directory would be “abouthalf” and the LESS file would be “abouthalf.less”. The “project” directory contains one LESS file per major component or area of the site. For example a special UI widget might have a corresponding LESS file “/project/special-ui-widget.less” and all the static content styles might be “/project/content.less”.
Project.less is mostly “@import” statements. When the compiler processes LESS files it reads import rules and combines files together. Bootstrap takes a similar approach in bootstrap.less. Bootstrap.less is the master file which pulls together the Bootstrap framework. Project.less is the master file for the project.
Project.less begins by duplicating the contents of bootstrap.less, that is, a list of import rules for Bootstrap components. This list is modified to includes the customizations required for Font Awesome integration. Following the import statements, I duplicate the contents of varibles.less – which defines all the variables used within Bootstrap. This allowed me to reset all of the Bootstrap variables to suit the project’s needs without ever touching Bootstrap code itself. Now both Bootstrap and Font Awesome can be upgraded by replacing their entire directory. No LESS code need be updated.
Following the variable reset is the project level reset, that is a few customizations for the page layout and tweaking of Bootstrap rules to fit the site design.
At the very end, all of the components from the “projects” directory are imported. And last, the contents of the “hacks” directory are imported. “Hacks” contains special rules for legacy versions of Internet Explorer.
Now developers can make changes to any component file, re-save project.less, and a complete, compiled, minified stylesheet is created with all the style rules for the site.
Of course the real work was going through all of the HTML in the site and updating CSS classes to use Bootstrap CSS classes and then repairing any damage…but at least the project was well organized.