DEV Community

Cover image for ๐ŸŽจ react-colorful โ€” 1,8 KB color picker for React. Fast, dependency-free, customizable, and accessible
Vlad Shilov
Vlad Shilov

Posted on

๐ŸŽจ react-colorful โ€” 1,8 KB color picker for React. Fast, dependency-free, customizable, and accessible

๐Ÿ“† The Story

Several months ago I was searching for an open-source color picker component to use in my React project.

I spent a lot of time looking for a good package and noticed that the most popular React color picker, react-color, is 140 KB (far larger than the entirety ofย react-dom), is not tree-shakeable, is not accessible, does not support keyboard navigation, pulls in 11 dependencies, and is not as fast as it could be.

Despite this,ย react-colorย is super popular and has 1,7 million downloads weekly. One of the largest reasons for this is there were no lighter alternatives aligned with modern requirements.

So we decided to create one. The primary goal was to create a modern color picker component that would be 10+ times lighter thanย react-color.

Ryan Christian,ย Alex Taktarov, and I had been working hard since July to create the tiniest and fastest color picker for the React community.

๐ŸŽ‰ That's howย react-colorfulย was born!

Demo:
https://omgovich.github.io/react-colorful

Docs:
https://github.com/omgovich/react-colorful

The current version ofย react-colorfulย (v4.1) is 18 times lighter thanย react-color. It's just 1,8 KB!

๐Ÿ—œ How isย react-colorfulย so small and fast?

1. No dependencies

While most of the popular pickers import entire color manipulation libraries that cost more than 10 KB,ย react-colorfulย ships only a minimal amount of manually optimized color conversion algorithms.

For example,ย react-colorย pulls in 11 dependencies includingย tinycolor2ย that costs 14,4 KB and doesn't support tree-shaking at all.

We have spent a lot of time making react-colorful dependency-free to ensure it is the lightest of the competition. Not to mention that this thoroughly reduces the surface for vulnerability issues to arise.

2. No classes

ES6 classes are good when you need to encapsulate something, but if you want to create a tiny JS library then class declarations will be one of your worst enemies. Current minifiers cannot minify ES6 class fields and member functions because they are not able to track the class when a method is called on an object.

That's why react-colorful is built with functions, functional components, and hooks only.

It's also one of the reasons why our picker is so fast.

3. No polyfills and extra code transforms

We aim to support not only modern browsers but legacy ones as well. So we have Babel configured to make our code compatible even with IE11.

Writing a library using modern language features such as async/await often trades end user experience for source developer experience. While these modern features may be nicer and more terse to write, they often result in much larger statements when transpiled for use in older browsers.

That's why our source code is so humble in terms of modern ECMAScript features. For example, we use Object.assign({}, color, { alpha }) instead of { ...color, alpha }. While yes, the source uses the older and more verbose API, this results in the bundle size being ~150 bytes lighter due to the lack of the polyfill.

4. Manually optimized

We have installed size-limit and tried many, many different things to find the smallest (in terms of bundle size) variation for each part of the library.

It's pretty hard to put into words, so I just share an example with you:

We have a simple function that clamps a value between an upper and lower bound. That's the first version of this function:

export const clamp = (number, min = 0, max = 1) => {
  return Math.min(Math.max(number, min), max);
};
Enter fullscreen mode Exit fullscreen mode

But after a few experiments we have replaced it with:

export const clamp = (number, min = 0, max = 1) => {
  return number > max ? max : number < min ? min : number;
};
Enter fullscreen mode Exit fullscreen mode

Your eyes do not deceive you: we chose the option that is longer. Why? Because the minification makes the second code almost 2 times shorter. See:

Math.min(Math.max(n,i),a)
n>a?a:n<i?i:n
Enter fullscreen mode Exit fullscreen mode

โค๏ธ Thanks for reading

react-colorful cares about size, performance, and accessibility. I hope that the React community shares our values and will find it useful for further projects.

It will help us a lot if you star the repo on GitHub or share the link to this article with your friends ๐Ÿ™

GitHub logo omgovich / react-colorful

๐ŸŽจ A tiny (2,8 KB) color picker component for React and Preact apps

react-colorful is a tiny color picker component for React and Preact apps

Features

  • ๐Ÿ—œ Small: Just 2,8 KB gzipped (13x lighter than react-color).
  • ๐ŸŒณ Tree-shakeable: Only the parts you use will be imported into your app's bundle.
  • ๐Ÿš€ Fast: Built with hooks and functional components only.
  • ๐Ÿ›ก Bulletproof: Written in strict TypeScript and has 100% test coverage.
  • ๐Ÿ—‚ Typed: Ships with types included
  • ๐Ÿ˜ Simple: The interface is straightforward and easy to use.
  • ๐Ÿ‘ซ Cross-browser: Works out-of-the-box for most browsers, regardless of version.
  • ๐Ÿ“ฒ Mobile-friendly: Supports mobile devices and touch screens.
  • ๐Ÿ’ฌ Accessible: Follows the WAI-ARIA guidelines to support users of assistive technologies.
  • ๐Ÿ’จ No dependencies

Live demos

Table of Contents





Oldest comments (12)

Collapse
 
dungmidside profile image
Dung Tran

Great library. I definitely use it someday

Collapse
 
omgovich profile image
Vlad Shilov • Edited

Thanks! Glad you like it)

Collapse
 
calag4n profile image
calag4n

Cool , I'll need it soon !
That's a good initiative and there are still many components that need that update too.

Collapse
 
omgovich profile image
Vlad Shilov

Thanks!
If you know any other "heavy" popular open-source component, let me know. I would be glad to work on a lightweight version of it.

Collapse
 
futureistaken profile image
R Z
Collapse
 
daviddalbusco profile image
David Dal Busco

Nice Vlad ๐Ÿ‘

We are having a discussion about the future of our color Web Component picker and I really like how you managed to put everything in place.

It can be a source of inspiration for our discussion, so, thank you for the share and work!

Collapse
 
griffadev profile image
Collapse
 
daviddalbusco profile image
David Dal Busco

We also need some more features such as keeping an history of what users selected for colors in our editor and others stuffs, not to mention that we tend to try to be as much agnostic as possible but, that being said, definitely cool stuffs ๐Ÿ‘

Thanks for pointing this out, if it is not for this project, it is worth to know what cool libs exist out there for another one ๐Ÿ˜‰

Collapse
 
omgovich profile image
Vlad Shilov • Edited

If you're looking for a web components based solution you should definitely check vanilla-colorful. It has all the benefits of react-colorful. The only thing you need to be aware of is that vanilla-colorful doesn't support IE11 or Edge 12โ€“18.

Collapse
 
daviddalbusco profile image
David Dal Busco

Not looking for another solution currently and our project, but who knows in the future. Thx for pointing this out and again for the inspiration ๐Ÿ‘

Collapse
 
futureistaken profile image
R Z

I am dreaming about writing code supporting donkey 11

Collapse
 
futureistaken profile image
R Z

Sometimes it's a good solution because the native browser color pickers suck!