From 0116cc9fed16ad2a0a451cec02e144267379a240 Mon Sep 17 00:00:00 2001 From: streamich Date: Fri, 22 Mar 2019 20:51:06 +0100 Subject: [PATCH] =?UTF-8?q?feat:=20=F0=9F=8E=B8=20refresh=20useCss=20hook?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- package.json | 2 +- src/useCss.ts | 65 +++++++++++++++++++++------------------------------ yarn.lock | 8 +++---- 3 files changed, 31 insertions(+), 44 deletions(-) diff --git a/package.json b/package.json index 8b1505a98d..63bdc67150 100644 --- a/package.json +++ b/package.json @@ -32,7 +32,7 @@ "dependencies": { "@types/react": "^16.8.2", "keyboardjs": "^2.5.1", - "nano-css": "^3.4.0", + "nano-css": "^5.0.0", "react-wait": "^0.3.0", "rebound": "^0.1.0", "throttle-debounce": "^2.0.1", diff --git a/src/useCss.ts b/src/useCss.ts index d98ea23ee8..904578fd52 100644 --- a/src/useCss.ts +++ b/src/useCss.ts @@ -1,48 +1,35 @@ -import {useState, useLayoutEffect} from 'react'; -const {create} = require('nano-css'); -const {addon: addonCssom} = require('nano-css/addon/cssom'); -const {addon: addonPipe} = require('nano-css/addon/pipe'); - -export interface CssPipe { - className: string; - css: (css: object) => void; - remove: () => void; -} - -const flattenSelectors = (css) => { - const flatenned = {}; - const amp = {}; - let hasAmp = false; - - for (const key in css) { - const value = css[key]; - if (typeof value === 'object') { - flatenned[key] = value; - } else { - hasAmp = true; - amp[key] = value; - } - } - if (hasAmp) { - flatenned['&'] = amp; - } - - return flatenned; -}; - -const nano = create(); -addonCssom(nano); -addonPipe(nano); +import {useLayoutEffect, useMemo} from 'react'; +import {create, NanoRenderer} from 'nano-css'; +import {addon as addonCSSOM, CSSOMAddon} from 'nano-css/addon/cssom'; +import {addon as addonVCSSOM, VCSSOMAddon} from 'nano-css/addon/vcssom'; +import {cssToTree} from 'nano-css/addon/vcssom/cssToTree'; + +type Nano = + & NanoRenderer + & CSSOMAddon + & VCSSOMAddon + ; +const nano = create() as Nano; +addonCSSOM(nano); +addonVCSSOM(nano); + +let counter = 0; const useCss = (css: object): string => { - const [pipe] = useState(nano.pipe()); + const className = useMemo(() => 'react-use-css-' + (counter++).toString(36), []); + const sheet = useMemo(() => new nano.VSheet(), []); useLayoutEffect(() => { - pipe.css(flattenSelectors(css)); - return () => pipe.remove(); + const tree = {}; + cssToTree(tree, css, '.' + className, ''); + sheet.diff(tree); + + return () => { + sheet.diff({}); + }; }); - return pipe.className; + return className; }; export default useCss; diff --git a/yarn.lock b/yarn.lock index 5037034cd9..0e3103a355 100644 --- a/yarn.lock +++ b/yarn.lock @@ -7301,10 +7301,10 @@ nan@^2.9.2: resolved "https://registry.yarnpkg.com/nan/-/nan-2.11.1.tgz#90e22bccb8ca57ea4cd37cc83d3819b52eea6766" integrity sha512-iji6k87OSXa0CcrLl9z+ZiYSuR2o+c0bGuNmXdrhTQTakxytAFsC56SArGYoiHlJlFoHSnvmhpceZJaXkVuOtA== -nano-css@^3.4.0: - version "3.4.0" - resolved "https://registry.yarnpkg.com/nano-css/-/nano-css-3.4.0.tgz#b8086a6ee5e198e31c74897187d44f52c0177cd7" - integrity sha512-75LqVARJoJDMGlRpRA8LtzlU8NxkxqkCR67DZgk0LP7tsglfjCFdNJcG4NNEDLLeLvCdnhyljdn54wAVWHoEeg== +nano-css@^5.0.0: + version "5.0.0" + resolved "https://registry.yarnpkg.com/nano-css/-/nano-css-5.0.0.tgz#faad380ef64a307a7fe63145a8d70ebe26cf5331" + integrity sha512-pk63UbtYcjndBNeIv8OBfknhDHchc6d/V3ROwFDSS2kxfy6Dp5Ab+6mcDy7q3i6JEmSbNyd2EJcYk9ZdxJj/FQ== dependencies: css-tree "^1.0.0-alpha.28" csstype "^2.5.5"