{:;} CSS in JS
Switch branches/tags
Nothing to show
Clone or download
Fetching latest commit…
Cannot retrieve the latest commit at this time.
Permalink
Type Name Latest commit message Commit time
Failed to load latest commit information.
src
test
.eslintrc
.gitignore
LICENSE
README.md
babel.js
circle.yml
package.json
yarn.lock

README.md

{:;} injected-css

Structured way to write CSS in JS file.

Usage

Install the package:

$ npm install injected-css

Add injected-css/babel to plugins section in your babel config:

{
  "plugins": [
    "injected-css/babel"
  ]
}

Define real CSS in your JS file using css{} template expression, and refer to resulted classes using style object.

import { css } from 'injected-css'
import { red, white, mobile } from '../my-theme' // use js variables

const style = css`
  text-align: center;

  &-button {
    background-color: ${red};
    width: 32rem;
    padding: 2rem;
    border-radius: 0.5rem;
    border: none;

    &:hover {
      background-color: ${white};
    }

    @media ${mobile} {
      width: 16rem;
    }
  }
`

document.innerHTML = `
  <div class="${style}">
    <button class="${style.button}">Click me!</button>
  </div>
`

It transforms to:

import { css } from 'injected-css';
import { red, white, mobile } from '../my-theme';

const style = css.inject({
  toString() { return 'c3423985940'; },
  button: 'c3423985940-button',
  _css: `.c3423985940 { text-align: center } .c3423985940-button { background-color: ${red}; width: 32rem; padding: 2rem; border-radius: 0.5rem; border: none
  } .c3423985940-button:hover { background-color: ${white} } @media ${mobile} { .c3423985940-button { width: 16rem } }`  
});

document.innerHTML = `
  <div class="${style}">
    <button class="${style.button}">Click me!</button>
  </div>
`;

Benefits

  • Write real CSS and use JS for import/export, variables and dynamic strings
  • Use powerful tools of JS world
    • ES modules to manage dependencies between styles and JS components
    • Eslint to ensure, it's hard to write bad CSS
    • Variables and functions
    • Webpack 2, Hot Module Replacement, code splitting, and server side render
  • Built-in naming convention for component world
  • Postcss integration (100s of plugins and custom syntaxes like SASS)
  • Minimal overhead (no parsing cost, 400 byte runtime)

Custom postcss config

Just create .postcssrc.js file with content similar to (read more about postcss config):

module.exports = (ctx) => ({
  plugins: [
    require('postcss-cssnext')({ 'features': { 'rem': false } }),
    ctx.env === 'production' ? require('cssnano')({ autoprefixer: false }) : false
  ]
})

Inject global styles

Use inject() method to insert global css string. Everything tagged literal with css`` will be preparsed with postcss.

import { inject, css } from 'injected-css'
import normalizeCss from 'normalize.css'
import { mobile } from '../my-theme';

// insert regular css, like normalize.css

inject(normalize)

// setup global typography

inject(css`
  html {
    font-family: "Helvetica Neue", Helvetica, Arial, "Lucida Grande", sans-serif;
    font-weight: normal;
    font-size: 62.5%; /* 1rem ~ 10px */

    @media ${mobile} {
      font-size: 56.25%; /* 1rem ~ 9px */
    }
  }
`)

Server side render

Use flush() method to get all css calls.

import { flush } from 'injected-css'
import { App } from './App'

const body = renderToStaticMarkup(<App />)
const css = reset._css + flush().join('')

const html = `
  <!doctype html>
  <html lang='en-US'>
    <head>      
      <title>My App</title>
      <style>${css}</style>
    </head>
    <body>
      ${body}
    </body>
  </html>
`

const reset = inject(css`
  html {
    -ms-text-size-adjust: 100%;
    -webkit-text-size-adjust: 100%;
    -webkit-tap-highlight-color: rgba(0, 0, 0, 0);
  }

  body {
    margin: 0;
  }
`)

Syntax highlight

Atom with language-babel plugin supports syntax highlight and autocompletion by default. atom-language-babel

Credits

  • BEM and SUIT CSS - for name convention, that works
  • CSS modules - for embracing CSS syntax and adding the way to reference on classes from JS code
  • style-loader - for concept of loading styles with js
  • styled-jsx - for idea of babel plugin and this credits section
  • @rtsao - for his open-source work on many css-in-js libraries
  • styling - for embracing ES modules to export CSS
  • react - for component approach and development philosophy
  • CSS: The Definitive Guide - for explaining me details of CSS
  • styled-components - for showing how to highlight CSS in tagged template literal

License

MIT