This post was sparked by a conversation on Twitter. I've written about organising CSS before, numerous times, years ago; but I use SCSS now, and it's a little different. SCSS offers includes without the multi-http-request penalty you'd get using HTML/CSS includes. That makes it practical to use includes while writing 'CSS', where before it was not.
In SCSS, what I think of as 'includes' are called 'imports'. It's a constant thing I mess up, but @import is the command which includes a file into another in SCSS.
Using @import in SCSS
@import file.scss
Does what you might expect, you place this line inside a SCSS file and it references an external file which is included wholesale into the stylesheet you're working on. So you can create a main.scss
to act as a collection bucket for your SCSS partials (and to output main.css
) and then just include dozens of partials into it. You would then work in each partial file. Usually those partials are logically split, though the theme of splitting varies from person to person. Some people may like to have them called things like homepage.scss
, aboutpage.scss
and gallerypage.scss
, working on page level. Others might split them via 'modules' such as header.scss
, footer.scss
, slider.scss
. And there will be a little overlap from each approach too. In any case, the goal is to be able to logically group SCSS code so it's easier to work with and easier to understand for anyone else coming into a project later.
I don't find this method (most of the code in @import files) overly helpful while I'm working on a site. If I need to go edit something in one of the included files I have to navigate my file-browser to go get it, and that breaks my flow a bit. Likewise, if you're new to a project you still have to read through the main.scss file to see what's getting included (and where, because include order matters).
Code Folding
Code folding is something almost every editor has and has been common for a decade or more, but can be invaluable as a method to help quickly navigate within a file. With code folding you'd usually retain a single main.scss
file but have all of your code directly in the file. The trick with code folding is to be meticulous in your indentation, and smart with your commenting. Code folding works by hiding the code at a deeper level of indentation than the point where you 'fold' it – so indentation matters. With code folding the entire SCSS is there already, but hidden away behind a fold until you want it. This can work very similarly to @import but without the need to go to the file-system to find the code to edit. Likewise, you can organise your folded blocks just as you would organise your @import files.
The downside is that if someone works on your project that doesn't know about folding (surprisingly many web-developers seem not to) then they'll see a very long file that's hard to navigate or get an overview of.
Combining the two approaches
In practice, I use both in a single project. I use @import at the top of my main.scss
file to pull in blocks of code that I know will not be changed or which I'll want to refer to often from another window/tab; things like a cssreset.scss
, typography.scss
, mixins.scss
would be things that once written (usually at the very start of a project) never change. I also have a variables.scss
file that stores colours and measures which I'll add to throughout the project and want to refer to as I work (it's usually open in another tab in a split-pane view, and I can just glance to the left to see which variable I need as I code).
Those includes are, for me, a useful way of using them. The rest of my main.scss
file is done as code-folding. I organise these as modules (pagination, header, footer, slider, etc). I'll then have a section for page-specific styling after the modules section.
My modules try to take care of anything related to their own styling and their own internal layout – but they don't take care of their position on a finished page. The page-specific parts of my SCSS are the parts that control where a module is located within a page, and allows any page-specific styling over-ride that might be needed (e.g., for some reason the headings on Specific Page are green instead of blue).
The nice thing about code folding (and Sublime Text in particular) is that I can open a file which is completely un-folded, and by pressing Cmd+k
, Cmd+2
I fold everything two-levels of indentation deep. For me, because I'm strict with indentation and commenting, this reveals an instant overview of the files contents, as comments, with no SCSS visible. I can then toggle a fold point and work inside the particular section I'm interested in.
This is what my main.scss
file looks like while I'm working on it (note the disclosure triangles to indicate folded code, and the fact this is a 912 line file).
Which is best?
There is no best approach. Arguments can be made for the efficiency and clarity of any approach, but really it's down to personal preference. The goal of all of these methods is to have a readable, easily understood, easy to work with structure to your code. As long as it does that, the method doesn't really matter.
I'd suggest that you should comment liberally so people new to a project can figure out how you've organised it, and call it a day. Comments will be stripped out by the SCSS parser when you generate your CSS anyway so it's no overhead on the wire.