skelJS

v0.4.9

Overview

skelJS is a lightweight frontend framework for building responsive sites and apps. Consisting of only a single JS file (weighing in at just 20kb as of this version), it gives designers and developers access to four powerful components:

An Example

The best way to learn how skelJS works is to see it in action, so here's a very common use case: building a responsive homepage.

index.html

<!DOCTYPE HTML>
<html>
	<head>
		<title>skelJS Example</title>
		// @@@ (skelJS Loader) Loads, configures, and initializes skelJS in one shot.
		<script src="skel.min.js">
		// Starts an inline configuration (one of two ways to configure skelJS).
		{
			// Determines our stylesheet names. Used in conjunction with the breakpoint names below. In this case, we're telling skelJS to look for "style.css" (our global stylesheet) and "style-wide.css", "style-narrow.css", and "style-mobile.css" (our breakpoint stylesheets).
			prefix: "style",
			// Resets default browser styles so we start with a nice clean slate.
			resetCSS: true,
			// Sets the global box model to "border-box".
			boxModel: "border",
			// Sets global grid options. In this case we're just going to set the gutter size to 30px.
			grid: { gutters: 30 },
			// Sets up the responsive handler, which determines the stylesheets and options to use at different viewport widths. Any number of breakpoints can be created and their ranges can even overlap (allowing more than one to be active at a time).
			breakpoints: {
				// A breakpoint. In this case it's called "wide", applies when the viewport width is at least 1200px, uses 1140px containers, and 50px gutters on grids (overriding the global 30px we set earlier).
				wide: { range: "1200-", containers: 1140, grid: { gutters: 50 } },
				// Another breakpoint. Kicks in between 481px and 1199px and uses 960px containers.
				narrow: { range: "481-1199", containers: 960 },
				// Our final breakpoint (which we'll use to target mobile devices). Only applies at or below 480px, uses fluid width containers, locks the viewport (required for mobile devices), and collapses all grids (which forces all cells to 100% width).
				mobile: { range: "-480", containers: "fluid", lockViewport: true, grid: { collapse: true } }
			}
		}
		</script>
		// @@@
	</head>
	<body>
		<div class="container">
			<!-- Header -->
				// A grid row. Holds up to 12 "units" (12u) of grid cells in any combination.
				<div id="header" class="row">
					// A grid cell. Can be anywhere between 1u and 12u wide. In this case, it's 4u wide.
					<div class="4u">
						<h1>Example</h1>
					</div>
					// Another cell. This time it's 8u, so combined with the previous 4u cell the row is now full (4u + 8u = 12u).
					<nav id="nav" class="8u">
						<a href="#">Home</a>
						<a href="#">About Me</a>
						<a href="#">Blog</a>
						<a href="#">Contact</a>
					</nav>
				</div>
			<!-- Hero -->
				// Rows and non-rows (like this one) can be adjacent to one another. The grid system doesn't care.
				<section id="hero">
					<h2>Hello world.</h2>
					<p>Lorem ipsum dolor sit amet sed magna etiam adipiscing.</p>
					<a href="#" class="button">Get Started</a>
				</section>
			<!-- Features -->
				// Just another row.
				<div class="row">
					// A 4u cell.
					<section class="4u">
						<h2>Heading</h2>
						<p>Lorem ipsum dolor sit amet sed magna etiam adipiscing elit.
						adipiscing elit nec fringilla urna tempor in. Cras et sodales
						consectetur viverra lorem ipsum.</p>
					</section>
					// Another 4u cell.
					<section class="4u">
						<h2>Heading</h2>
						<p>Lorem ipsum dolor sit amet sed magna etiam adipiscing elit.
						adipiscing elit nec fringilla urna tempor in. Cras et sodales
						consectetur viverra lorem ipsum.</p>
					</section>
					// And another 4u grid cell, rounding out this row (4u + 4u + 4u = 12u).
					<section class="4u">
						<h2>Heading</h2>
						<p>Lorem ipsum dolor sit amet sed magna etiam adipiscing elit.
						adipiscing elit nec fringilla urna tempor in. Cras et sodales
						consectetur viverra lorem ipsum.</p>
					</section>
				</div>
			<!-- Main -->
				// Another row.
				<div class="row">
					<!-- Content -->
						// An 8u cell.
						<section class="8u">
							<h2>Heading</h2>
							<p>Lorem ipsum dolor sit amet sed magna etiam adipiscing elit.
							adipiscing elit nec fringilla urna tempor in. Cras et sodales
							consectetur viverra lorem ipsum. Lorem ipsum dolor sit amet
							sed magna etiam adipiscing elit adipiscing elit nec fringilla
							urna tempor in. Cras et sodales consectetur viverra.</p>
						</section>
					<!-- Sidebar -->
						// And a 4u cell, which ends this row (8u + 4u = 12u).
						<section class="4u">
							<h2>Heading</h2>
							<p>Lorem ipsum dolor sit amet sed magna etiam adipiscing elit.
							adipiscing elit nec fringilla urna tempor in. Cras et sodales
							consectetur viverra lorem ipsum.</p>
						</section>
				</div>
			<!-- Footer -->
				<div id="footer">
					© Example. All rights reserved.
				</div>
		</div>
	</body>
</html>

Stylesheets

  • style.css

    Global Stylesheet: Contains styles shared by all breakpoints. Always gets loaded.
    body {
    	background: #2c373b;
    	color: #b2b9bC;
    	line-height: 2em;
    }
    
    h1, h2, h3, h4, h5, h6 {
    	color: #fff;
    	font-weight: bold;
    }
    
    .button {
    	border-radius: 0.5em;
    	box-shadow: inset 0 0 0 2px rgba(255,255,255,0.5);
    	color: #369ab8;
    	color: #fff;
    	display: inline-block;
    	text-decoration: none;
    }
    
    #nav a {
    	color: #fff;
    	font-style: italic;
    	text-decoration: none;
    }
    
    #hero {
    	background: #369ab8;
    	color: #fff;
    	text-align: center;
    }
    
    #footer {
    	color: #62696c;
    	text-align: center;
    }
    
  • style-wide.css

    Breakpoint Stylesheet: Only applies when wide is active (1200px and up).
    body {
    	font-size: 15pt;
    	letter-spacing: 0.035em;
    	line-height: 1.75em;
    }
    
    h1 {
    	font-size: 1.5em;
    }
    
    h2 {
    	font-size: 1.25em;
    	margin-bottom: 0.75em;
    }
    
    .button {
    	font-size: 1.25em;
    	padding: 0.65em 2.25em 0.65em 2.25em;
    }
    
    #header {
    	margin-top: 3em;
    }
    
    #nav {
    	text-align: right;
    }
    
    #nav a {
    	margin-left: 2em;
    }
    
    #hero {
    	border-radius: 0.5em;
    	margin: 3em 0 3em 0;
    	padding: 4em 0 4em 0;
    }
    
    #hero h2 {
    	font-size: 2.5em;
    	margin-bottom: 1em;
    }
    
    #hero p {
    	font-size: 1.25em;
    	margin-bottom: 1.75em;
    }
    
    #footer {
    	margin: 3em 0 3em 0;
    }
    
  • style-narrow.css

    Breakpoint Stylesheet: Only applies when narrow is active (481px - 1199px).
    body {
    	font-size: 14pt;
    	letter-spacing: 0.035em;
    	line-height: 1.5em;
    }
    
    h1 {
    	font-size: 1.25em;
    }
    
    h2 {
    	font-size: 1.1em;
    	margin-bottom: 0.5em;
    }
    
    .container {
    	padding: 0 2em 0 2em;
    }
    
    .button {
    	font-size: 1.25em;
    	padding: 0.75em 2em 0.75em 2em;
    }
    
    #header {
    	margin-top: 3em;
    }
    
    #nav {
    	text-align: right;
    }
    
    #nav a {
    	margin-left: 2em;
    }
    
    #hero {
    	border-radius: 0.5em;
    	margin: 2em 0 2em 0;
    	padding: 3em 0 3em 0;
    }
    
    #hero h2 {
    	font-size: 2.5em;
    	margin-bottom: 0.75em;
    }
    
    #hero p {
    	font-size: 1.25em;
    	margin-bottom: 1.5em;
    }
    
    #footer {
    	margin: 3em 0 3em 0;
    }
    
  • style-mobile.css

    Breakpoint Stylesheet: Only applies when mobile is active (480px and below).
    body {
    	font-size: 12.5pt;
    	line-height: 1.5em;
    }
    
    h1 {
    	font-size: 1.5em;
    	margin-bottom: 1em;
    }
    
    h2 {
    	font-size: 1.25em;
    	margin-bottom: 0.5em;
    }
    
    section {
    	padding-bottom: 2em;
    }
    
    .container {
    	padding: 0 1em 0 1em;
    }
    
    .button {
    	display: block;
    	font-size: 1.25em;
    	padding: 0.65em 0 0.65em 0;
    	width: 100%;
    }
    
    #header {
    	margin-top: 2.5em;
    	text-align: center;
    }
    
    #nav a {
    	margin: 0 0.5em 0 0.5em;
    }
    
    #hero {
    	border-radius: 0.5em;
    	line-height: 2em;
    	margin: 2em 0 2em 0;
    	padding: 3em 2em 3em 2em;
    }
    
    #hero h2 {
    	font-size: 2em;
    	margin-bottom: 0.75em;
    }
    
    #hero p {
    	font-size: 1.25em;
    	margin-bottom: 1.5em;
    }
    
    #footer {
    	margin-bottom: 2em;
    }
    

The Output

  • wide
  • narrow
  • mobile

And that's all there is to it. For a more in depth look, download the actual example or continue on to Setting Up.

Setting Up

1. Pick a Configuration Style

skelJS uses a JSON-like configuration that can be defined in one of two ways:

Inline

<script src="skel.min.js">
{
	option: value,
	option: value,
	option: value,
	option: {
		option: value,
		option: value,
		option: value,
		...
	},
	...
}
</script>

Preconfigured

<script>
	window._skel_config = {
		option: value,
		option: value,
		option: value,
		option: {
			option: value,
			option: value,
			...
		},
		...
	};
</script>
<script src="skel.min.js"></script>

Inline is good for testing and smaller projects, while Preconfigured is better for production as it allows the configuration to live in a separate JS file. For demonstration purposes we'll just stick to Inline.

2. Get Configured

The next step is to build your configuration. Two ways to go about this:

Option 1: Use a preset

Presets are, as the name implies, preset configurations. You can use one like this:

<script src="skel.min.js">{preset:(name_of_preset)}</script>

Where (name_of_preset) is any of the following:

default
standard
  • Stylesheet prefix set to "style"
  • Breakpoints set to mobile (480px and below), 1000px (481px to 1000px), and desktop (481px and up)
  • 40px gutters on all grids
  • 1200px containers on desktop, 960px containers on 1000px, and fluid containers on mobile (with collapse enabled)

(more to come later)

Option 2: Use your own (recommended)

While slightly more involved, this approach gives you far more control over how skelJS does its thing. For example, here's a configuration with 5 entirely custom breakpoints and a few additional options:

<script src="skel.min.js">
{
	// Stylesheet prefix.
	prefix: "style",
	// Resets default browser styles.
	resetCSS: true,
	// Sets the global box model to "border-box".
	boxModel: "border",
	// Sets global grid gutters to 40px.
	grid: { gutters: 40 },
	// Our list of breakpoints.
	breakpoints: {
		// Applies at 1300px and up, uses 1280px containers, and 60px grid gutters.
		wide: { range: "1300-", containers: 1280, grid: { gutters: 60 } },
		// Applies at and below 1299px, uses fluid containers, and 50px gutters on grids.
		narrow: { range: "-1299", containers: "fluid", grid: { gutters: 50 } },
		// Applies at and below 960px.
		narrow960: { range: "-960" },
		// Applies at and below 740px.
		narrow740: { range: "-740" },
		// Applies at and below 460px and collapses grids.
		narrow460: { range: "-460", grid: { collapse: true } }
	}
}
</script>

If you go this route, be sure to read up on the many configuration options you have at your disposal.

3. Profit?

And with that, skelJS is fully configured and ready to go. Head on down to Usage or hit the Configuration Reference if you want to further flesh out your configuration.

Usage

Containers

Containers are special wrapper elements whose widths are determined by whatever breakpoint happens to be active. By setting a container width on each breakpoint (using the containers option) and wrapping stuff in a container, like so:

<!DOCTYPE HTML>
<html>
	<head>
		<script src="skel.min.js">
		{
			prefix: "style",
			breakpoints: {
				// 1140px containers.
				wide: { range: "1200-", containers: 1140, grid: { gutters: 40 } },
				// 960px containers.
				narrow: { range: "481-1199", containers: 960 },
				// Fluid containers.
				mobile: { range: "-480", containers: "fluid", lockViewport: true, grid: { collapse: true } }
			}
		}
		</script>
	</head>
	<body>
		// The container. Can be any block-level element (div, form, etc).
		<div class="container">
				Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed tempus, 
				nisi sit amet feugiat elementum, est justo sapien, et pellentesque 
				sem dui eu nunc. Lorem ipsum dolor sit amet, consectetur adipiscing 
				elit. Sed tempus, nisi sit amet feugiat elementum, est justo sapien, 
				et pellentesque sem dui eu nunc. 
		</div>
	</body>
</html>
			

Said stuff will automatically adjust to the active breakpoint's container width. In this case, it'll become 1140px wide when wide is active, 960px wide when narrow is active, and fluid when mobile is active.

Modifiers

These alter the width of a particular container. To use one, simply include it in the container's class attribute (eg. <div class="container big">).

small
Decreases the container's width by 25%.
big
Increases the container's width by 25% (up to the viewport width, but no less than the default container width).

Grid System

One of the cornerstones of skelJS is its grid system. In case you've never used one before, it's basically a simple way to build page layouts (even complex ones) without developing an unbridled hatred for CSS.

Overview

The skelJS grid system is based around 12 vertical columns of equal width, with gutters (also of equal width) separating each one. The width of a column is, in skelJS terminology, a unit. The system uses two types of elements:

Cell
  • Basic building block of the grid system.
  • Used to contain your content.
  • Can be between 1 unit wide (1u) and 12 units wide (12u).
Row
  • All you need to start a grid (no parent "grid" element is required).
  • Fits up to 12u worth of cells in any combination (4u+8u, 3u+3u+3u, 1u+12u, and so on).
  • Fluid width (so it'll fit anywhere you need it).
  • Can be wrapped by other elements (including containers).
  • Can be placed inside cells to form complex nested grids.

And here's how one actually looks:

<div class="row">
  <div class="12u">12u</div>
</div>
<div class="row">
  <div class="8u">8u</div>
  <div class="4u">4u</div>
</div>
<div class="row">
  <div class="2u">2u</div>
  <div class="4u">4u</div>
  <div class="4u">4u</div>
  <div class="2u">2u</div>
</div>
12u
8u
4u
2u
4u
4u
2u

More examples below.

Configuration

Certain aspects of the grid system's behavior (such as gutter size) can be configured on a global level as well as per-breakpoint. Check out the configuration reference for more details.

Modifiers

These change the behavior of a particular row. To use one, simply include it in the row's class attribute (eg. <div class="row flush">).

flush
Removes the gutters between each cell (similar to setting gutters to 0 in your configuration, only localized to a single row).
quarter
Decreases gutter size to 25%.
half
Decreases gutter size to 50%.
oneandhalf
Increases gutter size to 150%.
double
Increases gutter size to 200%.
no-collapse
Retains grid structure even if collapse is enabled.

Offsets

Offsets can be used to nudge a cell to the right by a number of units. They're applied like a cell's width class only prefixed with a dash (eg. -3u, which means "nudge this cell right by 3 units"). Here's an example:

<div class="row">
	<div class="12u">12u</div>
</div>
<div class="row">
	<div class="-3u 9u">9u</div>
</div>
<div class="row">
	<div class="-6u 6u">6u</div>
</div>
<div class="row">
	<div class="-9u 3u">3u</div>
</div>
<div class="row">
	<div class="-3u 3u">3u</div>
	<div class="-3u 3u">3u</div>
</div>
<div class="row">
	<div class="6u">6u</div>
	<div class="-3u 3u">3u</div>
</div>
12u
9u
6u
3u
3u
3u
6u
3u

Examples

1 Row (8u + 4u)
<div class="row">
	<div class="8u">8u</div>
	<div class="4u">4u</div>
</div>
8u
4u
2 Rows (3u+6u+3u, 4u+4u+4u)
<div class="row">
	<div class="3u">3u</div>
	<div class="6u">6u</div>
	<div class="3u">3u</div>
</div>
<div class="row">
	<div class="4u">4u</div>
	<div class="4u">4u</div>
	<div class="4u">4u</div>
</div>
3u
6u
3u
4u
4u
4u
4 Rows (12u, 3u+9u, 6u+6u, 6u+6u)
<div class="row">
	<div class="12u">12u</div>
</div>
<div class="row">
	<div class="3u">3u</div>
	<div class="9u">9u</div>
</div>
<div class="row">
	<div class="6u">6u</div>
	<div class="6u">6u</div>
</div>
<div class="row">
	<div class="6u">6u</div>
	<div class="6u">6u</div>
</div>
12u
3u
9u
6u
6u
6u
6u
3 Rows (3u+6u+3u, 4u+4u+4u, 6u+6u), flush modifier
<div class="row flush">
	<div class="3u">3u</div>
	<div class="6u">6u</div>
	<div class="3u">3u</div>
</div>
<div class="row flush">
	<div class="4u">4u</div>
	<div class="4u">4u</div>
	<div class="4u">4u</div>
</div>
<div class="row flush">
	<div class="6u">6u</div>
	<div class="6u">6u</div>
</div>
3u
6u
3u
4u
4u
4u
6u
6u
1 Row (4u+4u+4u), inside cell of another row (2 Rows (9u+3u, 6u+6u))
<div class="row">
	<div class="9u">
		<div class="row">
			<div class="4u">4u</div>
			<div class="4u">4u</div>
			<div class="4u">4u</div>
		</div>
	</div>
	<div class="3u">3u</div>
</div>
<div class="row">
	<div class="4u">4u</div>
	<div class="4u">4u</div>
	<div class="4u">4u</div>
</div>
4u
4u
4u
3u
6u
6u

Conditionals

Conditionals are classes that hide or show elements based on what breakpoints are active.

not-(breakpoint name)
Hides the element when (breakpoint name) is active.
only-(breakpoint name)
Only shows the element when (breakpoint name) is active.

Here's an example:

<!DOCTYPE HTML>
<html>
	<head>
		<script src="skel.min.js">
		{
			prefix: "style",
			breakpoints: {
				// Our "wide" breakpoint.
				wide: { range: "1200-", containers: 1140, grid: { gutters: 40 } },
				// Our "narrow" breakpoint.
				narrow: { range: "481-1199", containers: 960 },
				// Our "mobile" breakpoint.
				mobile: { range: "-480", containers: "fluid", lockViewport: true, grid: { collapse: true } }
			}
		}
		</script>
	</head>
	<body>
		<h1>Hello World</h1>
		// Hidden when "wide" is active.
		<div class="not-wide">I'm hidden when "wide" is active.</div>
		// Hidden when "narrow" is active.
		<div class="not-narrow">I'm hidden when "narrow" is active.</div>
		// Hidden when "mobile" is active.
		<div class="not-mobile">I'm hidden when "mobile" is active.</div>
		// Visible when "wide" is active.
		<div class="only-wide">I'm only visible when "wide" is active.</div>
		// Visible when "narrow" is active.
		<div class="only-narrow">I'm only visible when "narrow" is active.</div>
		// Visible when "mobile" is active.
		<div class="only-mobile">I'm only visible when "mobile" is active.</div>
	</body>
</html>
		

<noscript> Fallback

skelJS, as you might have already guessed, needs JS to work. Users with JS disabled will therefore be greeted with something reminiscent of the WWW circa 1993. To fix this:

  1. Download the noscript stylesheet (skel-noscript.css).
  2. Decide on which of your breakpoints best represents your site (hint: most likely the one targeting desktops).
  3. Go through the noscript stylesheet and comment/uncomment stuff to match your breakpoint.
  4. Add a <noscript> block to your <head> element that adds the noscript stylesheet, your global stylesheet, and all stylesheets that apply to your breakpoint. For example

    <noscript>
    	// The noscript stylesheet.
    	<link rel="stylesheet" href="skel-noscript.css" />
    	// Global stylesheet.
    	<link rel="stylesheet" href="style.css" />
    	// Breakpoint stylesheet for "wide".
    	<link rel="stylesheet" href="style-wide.css" />	
    </noscript>
    				

And there you go. Users with JS disabled will now have an experience almost identical to that of their JS-enabled counterparts (minus the responsiveness).

Manual Initialization

For simplicity, skelJS will automatically initialize as soon as it sees a configuration (be it Inline or Preconfigured). If you'd rather initialize it manually, simply load skelJS without one:

<script src="skel.min.js"></script>
		

Then when you're ready to initialize, simply call skel.init() with your configuration as the first argument:

<script>
	skel.init({
		option: value,
		option: value,
		option: value,
		option: {
			option: value,
			option: value,
			option: value,
			...
		}
		...
	});
</script>
		

You can also include plugin configurations with the second argument:

<script>
	skel.init({
		option: value,
		option: value,
		option: value,
		option: {
			option: value,
			option: value,
			option: value,
			...
		},
		...
	},{
		plugin: {
			option: value,
			option: value,
			option: value,
			option: {
				option: value,
				option: value,
				option: value,
				...
			},
			...
		},
		...
	});
</script>
		

<html> Breakpoint Classes

Just in case you need them, skelJS will automatically append a list of active breakpoints to the <html> element's class attribute. For example, if the desktop and wide breakpoints are active:

<html class="desktop wide">
...
</html>
		

API

skelJS exposes a handful of methods via the skel object that can be used to obtain information on its current state as well as alter its behavior:

skel.vars.key

Gets the value of an internal skelJS variable.

key

(String) Key of value to retrieve. Can be any of the following:

viewportWidth(Integer) Calculated viewport width. Used to determine what breakpoints are active.
devicePixelRatio(Float) Calculated device pixel ratio. Used to calculate viewportWidth.
stateId(String) Current state ID (a space-delimited list of all active breakpoint names).
lastStateId(String) Previous state ID.
IEVersion(Integer) Client's version of Internet Explorer (set to 99 if they're not using IE).
deviceType(String) Client's device type (android, ios, wp, or other).
deviceVersion(Float) Client's device version.
isTouch(Boolean) If true, client is using a device with touch capabilities.
skel.isActive( breakpointName )

Determines if a breakpoint is active. Returns true if it is, or false if it isn't.

breakpointName(String) A breakpoint name.
skel.wasActive( breakpointName )

Determines if a breakpoint was active prior to the last state change. Returns true if it was, or false if it wasn't.

breakpointName(String) A breakpoint name.
skel.canUse( breakpointName )

Determines if a given breakpoint applies to the current viewport. Returns true if it can, or false if it cannot.

breakpointName(String) A breakpoint name.
skel.lock( viewportWidth )

Locks skelJS into always using the given viewport width instead of calculating one on the fly. When called, the value is stored in a cookie (to preserve it between page loads; see the note below) and the page is automatically refreshed. Can be cleared with skel.unlock().

viewportWidth(Integer) Viewport width to use (in pixels).

Since the viewport width determines active breakpoints, locking it to a specific value means the same ones will always be active regardless of the actual viewport size. Used in conjunction with skel.unlock() and skel.canUse() this allows for some pretty interesting stuff; for example, given the breakpoints from our example (wide, narrow, mobile), we can create a simple "Switch to Desktop" toggle that lets mobile devices pull up the desktop (wide) layout:

// Wait until the DOM is ready. Note that we're using jQuery here for the sake of brevity, but it's not required to use any of skelJS's API calls.
$(function() {

	// Make sure the client can use the "mobile" breakpoint (so our toggle doesn't show up for folks who aren't on mobile devices).
	if (skel.canUse('mobile'))
	{
		// Create the toggle element and append it to the page body.
		var toggle = $('<span></span>').appendTo($('body'));
			
		// If a lock isn't in place yet ...
		if (!skel.isLocked())
			toggle
				// Label the toggle "Switch to Desktop".
				.text('Switch to Desktop')
				// Bind a click event. When triggered, lock the viewport to 1200px (which falls within the range of our "wide" breakpoint). When the page automatically refreshes, we'll see the "wide" layout even though we'd normally just see the "mobile" one.
				.click(function(e) { skel.lock(1200); });
		// Otherwise ...
		else
			toggle
				// Label the toggle "Switch to Mobile".
				.text('Switch to Mobile')
				// Bind a click event. When triggered, the lock will be cleared and when the page refreshes, we'll be back to the "mobile" layout.
				.click(function(e) { skel.unlock(); });
	}

});
				

Note: A single client-side cookie is used to preserve the locked viewport width between page loads. However, be aware this won't work locally as browsers usually don't store cookies for pages accessed via file://.

skel.unlock()
Clears a lock (if one's been set). See skel.lock() for more info.

Configuration Reference

Options

prefix
TypeString
Defaultnull (Disables stylesheet management)

Sets the stylesheet prefix. If set, skelJS will use this to figure out the names of your global and breakpoint stylesheets. For example, setting it to "style" with the following breakpoints configured:

  • wide
  • narrow
  • narrow960
  • narrow720
  • narrow480

will result in skelJS looking for these stylesheets:

  • style.css – global stylesheet (always applies)
  • style-wide.css – applies when wide is active
  • style-narrow.css – applies when narrow is active
  • style-narrow960.css – applies when narrow960 is active
  • style-narrow720.css – applies when narrow720 is active
  • style-narrow480.css – applies when narrow480 is active

A prefix can also include a path name. For example, setting it to "/assets/css/style" with the same breakpoints as above results in:

  • /assets/css/style.css – global stylesheet (always applies)
  • /assets/css/style-wide.css – applies when wide is active
  • /assets/css/style-narrow.css – applies when narrow is active
  • /assets/css/style-narrow960.css – applies when narrow960 is active
  • /assets/css/style-narrow720.css – applies when narrow720 is active
  • /assets/css/style-narrow480.css – applies when narrow480 is active

Setting prefix to null (the default) disables stylesheet management entirely.

containers
TypeInteger
Default960

Sets the global container width. Can be an integer (implies pixel units), any valid CSS measurement (eg. "40em"), or "fluid" (equivalent to "100%").

grid
TypeGrid Options
Default{ gutters: 40, collapse: false }

Sets global grid options.

breakpoints
TypeBreakpoint Options
Default{ "all": { range: "*", hasStyleSheet: false } }

Your breakpoints, listed in the following format:

{
	"(breakpointName)": { (Breakpoint Options) },
	"(breakpointName)": { (Breakpoint Options) },
	"(breakpointName)": { (Breakpoint Options) },
	...
}

You can also use the following shorthand format if you only need to specify a range for each breakpoint:

{
	"(breakpointName)": "(range)",
	"(breakpointName)": "(range)",
	"(breakpointName)": "(range)",
	...
}

Note: Since breakpoint ranges are allowed to overlap, more than one can be active at any given time. When this happens, the options of each are combined in order with those defined last taking precedence.

resetCSS
TypeBoolean
Defaultfalse

If true, default browser styles will be reset using Erik Meyer's CSS resets (built in to skelJS).

normalizeCSS
TypeBoolean
Defaultfalse

If true, default browser styles will be normalized using normalize.css (built in to skelJS).

boxModel
TypeString
Defaultnull

Sets the global CSS box model. Can be "border", "content", "margin", or "padding".

useOrientation
TypeBoolean
Defaultfalse

For simplicity, skelJS ignores device orientation (where applicable) and always assumes it's being used in portrait mode. This results in the same viewport width regardless of actual orientation and greatly simplifies breakpoint configuration. However, if you do want orientation to be a factor, set this to true.

useRTL
TypeBoolean
Defaultfalse

If you're using a right-to-left language (such as Arabic or Hebrew), set this to true to enable RTL compatibility.

preloadStyleSheets
TypeBoolean
Defaultfalse

By default, skelJS will dynamically load breakpoint stylesheets only when it needs them. Setting this option to true will instead preload them all ahead of time.

pollOnce
TypeBoolean
Defaultfalse

If true, breakpoint checks will only be performed the first time the page is loaded, disabling breakpoint switching on resize.

pollOnLock
TypeBoolean
Defaultfalse

If true, skelJS will immediately perform breakpoint checks after every skel.lock() or skel.unlock() call.

usePerpetualLock
TypeBoolean
Defaulttrue

If true, the effects of a skel.lock() call will last until skel.unlock() has been called. If false, the effects will go away at the end of the user's session.

useDomainLock
TypeBoolean
Defaulttrue

If true, the effects of a skel.lock() call will be applied to the domain (not just the current page or path). If false, the effects will only be applied to the current page or path.

Breakpoint Options

range
TypeString
Default"*" (any width)

Sets the breakpoint's active width range (in pixels). Can be any of the following:

"*"
Matches any viewport width.
"X"
Viewport width must be exactly X.
"X-Y"
Viewport width must be between X and Y (inclusive).
"-X"
Viewport width must be less than or equal to X.
"X-"
Viewport width must be greater than or equal to X.

Note: Ranges can overlap with that of other breakpoints.

lockViewport
TypeBoolean
Defaultfalse

If true, skelJS will (where applicable) disable viewport zooming and resizing. Should only be enabled on breakpoints targeting small devices (such as phones and smaller tablets).

viewportWidth
TypeInteger
Defaultfalse

If set, determines the viewport width on mobile devices (equivalent to <meta name="viewport" content="width=(value)" />).

hasStyleSheet
TypeBoolean
Defaulttrue

Determines if there's a stylesheet for the breakpoint. By default this is true, but there are times when setting this to false makes sense (for example, when a breakpoint exists only to change the container size).

containers
TypeInteger
Default960

Sets the breakpoint's container width. Can be an integer (implies pixel units), any valid CSS measurement (eg. "40em"), or "fluid" (equivalent to "100%"). Overrides the global container width.

grid
TypeGrid Options
Defaultnull

Sets the breakpoint's grid options. Overrides global grid options.

Grid Options

gutters
TypeInteger
Default40

Sets the gutter size. Can be an integer (implies pixel units) or any valid CSS measurement (eg. "2%").

collapse
TypeBoolean
Defaultfalse

If true, all cells (except those in no-collapse rows) are forced to be 100% wide regardless of their actual unit size ("collapsing" the grid). Should only be enabled on breakpoints targeting small devices (such as phones and smaller tablets).

FAQ

What browsers work with skelJS?

Pretty much all modern (and a few not-so-modern) browsers:

  • Chrome
  • Firefox
  • Safari
  • Opera
  • Internet Explorer 8+
  • Android Browser (2.x and up)
  • Safari/iOS (4.x and up)