Convert Figma logo to code with AI

robinweser logofela

State-Driven Styling in JavaScript

2,274
184
2,274
4

Top Related Projects

7,084

JSS is an authoring tool for CSS which uses JavaScript as a host language.

Visual primitives for the component age. Use the best bits of ES6 and CSS to style your apps without stress 💅

17,606

👩‍🎤 CSS-in-JS library designed for high performance style composition

11,764

Zero-runtime CSS in JS library

3,147

🥜 goober, a less than 1KB 🎉 css-in-js alternative with a familiar API

[Not Actively Maintained] CSS-in-JS with near-zero runtime, SSR, multi-variant support, and a best-in-class developer experience.

Quick Overview

Fela is a small, high-performance JavaScript library for creating and managing dynamic CSS styles in JavaScript. It provides a powerful API for generating CSS rules, handling media queries, and managing keyframes, all while offering excellent performance through efficient style rendering and caching mechanisms.

Pros

  • Highly performant due to its atomic CSS approach and efficient style rendering
  • Framework-agnostic, can be used with any JavaScript framework or vanilla JS
  • Supports server-side rendering for improved initial load times
  • Offers a plugin system for extending functionality and customization

Cons

  • Learning curve for developers used to traditional CSS methodologies
  • Requires additional setup and configuration compared to plain CSS
  • May lead to increased HTML size due to many small atomic classes
  • Limited browser support for older versions (IE11 and below)

Code Examples

Creating a simple style rule:

import { createRenderer } from 'fela'

const renderer = createRenderer()

const rule = ({ color, fontSize }) => ({
  backgroundColor: 'white',
  color: color,
  fontSize: fontSize + 'px'
})

const className = renderer.renderRule(rule, { color: 'red', fontSize: 12 })

Using media queries:

const responsiveRule = ({ small, large }) => ({
  fontSize: small + 'px',
  '@media (min-width: 1024px)': {
    fontSize: large + 'px'
  }
})

const className = renderer.renderRule(responsiveRule, { small: 14, large: 18 })

Creating keyframe animations:

const keyframe = () => ({
  '0%': { opacity: 0 },
  '100%': { opacity: 1 }
})

const animationName = renderer.renderKeyframe(keyframe)

Getting Started

To start using Fela in your project:

  1. Install Fela:

    npm install fela
    
  2. Create a renderer and use it in your application:

    import { createRenderer } from 'fela'
    import { render } from 'react-dom'
    import { Provider } from 'react-fela'
    
    const renderer = createRenderer()
    
    render(
      <Provider renderer={renderer}>
        <App />
      </Provider>,
      document.getElementById('root')
    )
    
  3. Create and use style rules in your components:

    import { useFela } from 'react-fela'
    
    const rule = ({ color }) => ({
      color: color,
      fontSize: '16px'
    })
    
    function MyComponent() {
      const { css } = useFela()
      return <div className={css(rule, { color: 'blue' })}>Hello, Fela!</div>
    }
    

Competitor Comparisons

7,084

JSS is an authoring tool for CSS which uses JavaScript as a host language.

Pros of JSS

  • More mature and widely adopted, with a larger ecosystem and community support
  • Offers a wider range of plugins and integrations out of the box
  • Provides better performance for larger applications due to its optimized rendering approach

Cons of JSS

  • Steeper learning curve, especially for developers new to CSS-in-JS
  • More verbose syntax compared to Fela's simpler API
  • Requires additional setup and configuration for optimal usage

Code Comparison

JSS:

const styles = {
  myButton: {
    color: 'green',
    margin: {
      top: 5,
      right: 0,
      bottom: 0,
      left: '1rem'
    }
  }
};

Fela:

const myButton = () => ({
  color: 'green',
  marginTop: 5,
  marginRight: 0,
  marginBottom: 0,
  marginLeft: '1rem'
})

Both JSS and Fela are powerful CSS-in-JS libraries, but they differ in their approach and syntax. JSS offers a more feature-rich experience with its extensive plugin system, while Fela focuses on simplicity and flexibility. The choice between the two often depends on project requirements, team preferences, and performance considerations.

Visual primitives for the component age. Use the best bits of ES6 and CSS to style your apps without stress 💅

Pros of styled-components

  • More intuitive syntax for developers familiar with CSS
  • Better integration with React components
  • Automatic critical CSS extraction

Cons of styled-components

  • Larger bundle size
  • Slower runtime performance for complex applications
  • Less flexibility in terms of rendering targets

Code Comparison

styled-components:

const Button = styled.button`
  background-color: ${props => props.primary ? 'blue' : 'white'};
  color: ${props => props.primary ? 'white' : 'blue'};
  padding: 10px 20px;
`;

Fela:

const button = ({ primary }) => ({
  backgroundColor: primary ? 'blue' : 'white',
  color: primary ? 'white' : 'blue',
  padding: '10px 20px'
})

const Button = createComponent(button)

Both libraries offer CSS-in-JS solutions, but they differ in approach. styled-components provides a more CSS-like syntax and tighter React integration, while Fela offers a more programmatic approach with better performance for complex scenarios. styled-components is often easier for teams transitioning from traditional CSS, but Fela provides more flexibility and better performance at scale. The choice between them depends on project requirements, team preferences, and performance considerations.

17,606

👩‍🎤 CSS-in-JS library designed for high performance style composition

Pros of emotion

  • Larger community and ecosystem, with more frequent updates and contributions
  • Built-in support for server-side rendering and critical CSS extraction
  • Seamless integration with popular frameworks like React and Next.js

Cons of emotion

  • Slightly larger bundle size compared to Fela
  • Less flexible in terms of low-level customization and plugin system
  • May have a steeper learning curve for developers new to CSS-in-JS

Code Comparison

emotion:

import { css } from '@emotion/react'

const style = css`
  color: hotpink;
  font-size: 24px;
`

Fela:

import { createRenderer } from 'fela'

const renderer = createRenderer()
const rule = () => ({
  color: 'hotpink',
  fontSize: '24px'
})

Both emotion and Fela are popular CSS-in-JS libraries, offering developers the ability to write styles directly in JavaScript. emotion provides a more opinionated and feature-rich approach, while Fela focuses on flexibility and performance. The choice between the two often depends on specific project requirements and developer preferences.

11,764

Zero-runtime CSS in JS library

Pros of Linaria

  • Zero-runtime CSS-in-JS with full CSS support
  • Built-in critical CSS extraction for improved performance
  • Supports static analysis and type-checking for styles

Cons of Linaria

  • Requires a build step, which may increase complexity
  • Limited dynamic styling capabilities compared to runtime solutions
  • Steeper learning curve for developers new to CSS-in-JS concepts

Code Comparison

Linaria:

import { css } from '@linaria/core';

const button = css`
  background-color: blue;
  color: white;
  padding: 10px 20px;
`;

Fela:

import { createRenderer } from 'fela';

const renderer = createRenderer();
const button = renderer.renderRule(() => ({
  backgroundColor: 'blue',
  color: 'white',
  padding: '10px 20px'
}));

Both Linaria and Fela are CSS-in-JS solutions, but they take different approaches. Linaria focuses on zero-runtime, static extraction of CSS, while Fela provides a more dynamic, runtime-based styling solution. Linaria's approach can lead to better performance in production, but may sacrifice some flexibility compared to Fela's runtime capabilities. The choice between the two depends on specific project requirements and performance considerations.

3,147

🥜 goober, a less than 1KB 🎉 css-in-js alternative with a familiar API

Pros of Goober

  • Smaller bundle size (1kb gzipped) compared to Fela's larger footprint
  • Simpler API with fewer concepts to learn
  • Supports CSS-in-JS with a more familiar syntax for CSS authors

Cons of Goober

  • Less feature-rich compared to Fela's extensive plugin system
  • Limited server-side rendering support
  • Fewer optimization options for performance-critical applications

Code Comparison

Goober:

import { styled } from 'goober';

const Button = styled('button')`
  background: ${props => props.primary ? 'palevioletred' : 'white'};
  color: ${props => props.primary ? 'white' : 'palevioletred'};
`;

Fela:

import { createComponent } from 'react-fela';

const Button = createComponent(props => ({
  background: props.primary ? 'palevioletred' : 'white',
  color: props.primary ? 'white' : 'palevioletred'
}));

Both libraries offer CSS-in-JS solutions, but Goober uses a more traditional styled-components-like API, while Fela uses a function-based approach. Goober's syntax may be more intuitive for developers familiar with CSS, while Fela's approach offers more flexibility and composability.

[Not Actively Maintained] CSS-in-JS with near-zero runtime, SSR, multi-variant support, and a best-in-class developer experience.

Pros of Stitches

  • Zero-runtime CSS-in-JS for better performance
  • Built-in theming support with variants and responsive styles
  • TypeScript-first approach with excellent type inference

Cons of Stitches

  • Less flexible than Fela's plugin system
  • Smaller ecosystem and community compared to Fela
  • Limited server-side rendering support

Code Comparison

Stitches:

const Button = styled('button', {
  backgroundColor: 'gainsboro',
  borderRadius: '9999px',
  fontSize: '13px',
  padding: '10px 15px',
  '&:hover': {
    backgroundColor: 'lightgray',
  },
});

Fela:

const button = ({ theme }) => ({
  backgroundColor: 'gainsboro',
  borderRadius: '9999px',
  fontSize: '13px',
  padding: '10px 15px',
  ':hover': {
    backgroundColor: 'lightgray',
  },
});

Both Stitches and Fela offer CSS-in-JS solutions, but they differ in their approaches. Stitches focuses on zero-runtime performance and a TypeScript-first design, making it excellent for projects prioritizing type safety and performance. Fela, on the other hand, provides a more flexible plugin system and has a larger ecosystem, making it suitable for complex styling needs and projects requiring extensive customization.

Convert Figma logo designs to code with AI

Visual Copilot

Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.

Try Visual Copilot

README

Fela

Fela is a small, high-performant and framework-agnostic toolbelt to handle state-driven styling in JavaScript.
It is dynamic by design and renders your styles depending on your application state.

It generates atomic CSS and supports all common CSS features such as media queries, pseudo classes, keyframes and font-faces. Fela ships with a powerful plugin API adding e.g. vendor prefixing or fallback value support.

Fela can be used with React or with any other view library. It even supports React Native.

Bundlephobia npm downloads Spectrum

Support Us

Support Robin Weser's work on Fela and its ecosystem directly via GitHub Sponsors.

Benefits

  • Predictable Styling
  • Scoped Atomic CSS
  • Minimal Bundle Size
  • No Specificity Issues
  • No Naming Conflicts
  • Framework-Agnostic
  • Huge Ecosystem
  • RTL Support

Read more about the benefits!

The Gist

Fela's core principle is to consider style as a function of state.
The whole API and all plugins and bindings are built on that idea.
It is reactive and auto-updates once registered to the DOM.

The following example illustrates the key parts of Fela though it only shows the very basics.

import { createRenderer } from 'fela'

// a simple style rule is a pure function of state
// that returns an object of style declarations
const rule = (state) => ({
  textAlign: 'center',
  padding: '5px 10px',
  // directly use the state to compute style values
  fontSize: state.fontSize + 'pt',
  borderRadius: 5,
  // deeply nest media queries and pseudo classes
  ':hover': {
    fontSize: state.fontSize + 2 + 'pt',
    boxShadow: '0 0 2px rgb(70, 70, 70)',
  },
})

const renderer = createRenderer()

// fela generates atomic CSS classes in order to achieve
// maximal style reuse and minimal CSS output
const className = renderer.renderRule(rule, {
  fontSize: 14,
}) // =>  a b c d e f

The generated CSS output would look like this:

.a { text-align: center }
.b { padding: 5px 10px }
.c { font-size: 14pt }
.d { border-radius: 5px }
.e:hover { font-size: 16pt }
.f:hover { box-shadow: 0 0 2px rgb(70, 70, 70) }

Primitive Components

If you're using Fela, you're most likely also using React.
Using the React bindings, you get powerful APIs to create primitive components.

Read: Usage with React for a full guide.

import * as React from 'react'
import { useFela } from 'react-fela'

const rule = ({ fontSize }) => ({
  textAlign: 'center',
  padding: '5px 10px',
  // directly use the props to compute style values
  fontSize: fontSize + 'pt',
  borderRadius: 5,
  ':hover': {
    fontSize: fontSize + 2 + 'pt',
    boxShadow: '0 0 2px rgb(70, 70, 70)',
  },
})

function Button({ fontSize, children }) {
  const { css } = useFela({ fontSize })

  return <button className={css(rule)}>{children}</button>
}

Check this example on CodeSandbox

Examples

Documentation

Workshop

If you are coming from CSS and want to learn JavaScript Styling with Fela, there is a full-feature fela-workshop which demonstrates typical Fela use cases. It teaches all important parts, step by step with simple examples. If you already know other CSS in JS solutions and are just switching to Fela, you might not need to do the whole workshop, but it still provides useful information to get started quickly.

Talks

Posts

Ecosystem

There are tons of useful packages maintained within this repository including plugins, enhancers, bindings and tools that can be used together with Fela. Check the Ecosystem documentation for a quick overview.

Community

Apart from all the packages managed within this repository, there are many community third-party projects that are worth mentioning:

Support

Got a question? Come and join us on Github Discussion!
We'd love to help out. We also highly appreciate any feedback.
Don't want to miss any update? Follow us on Twitter.

Who's using Fela?

Check all the logos on the website.

Want to add yours? Please create a new issue with your logo attached and we will add it!

Contributing

This project exists thanks to all the people who contribute.

We highly appreciate any contribution.
For more information follow the contribution guide.
Also, please read our code of conduct.

License

Fela is licensed under the MIT License.
Documentation is licensed under Creative Commons License.
Created with ♥ by @robinweser and all the great contributors.

NPM DownloadsLast 30 Days