|
1 |
| -import {useState, useLayoutEffect} from 'react'; |
2 |
| -const {create} = require('nano-css'); |
3 |
| -const {addon: addonCssom} = require('nano-css/addon/cssom'); |
4 |
| -const {addon: addonPipe} = require('nano-css/addon/pipe'); |
5 |
| - |
6 |
| -export interface CssPipe { |
7 |
| - className: string; |
8 |
| - css: (css: object) => void; |
9 |
| - remove: () => void; |
10 |
| -} |
11 |
| - |
12 |
| -const flattenSelectors = (css) => { |
13 |
| - const flatenned = {}; |
14 |
| - const amp = {}; |
15 |
| - let hasAmp = false; |
16 |
| - |
17 |
| - for (const key in css) { |
18 |
| - const value = css[key]; |
19 |
| - if (typeof value === 'object') { |
20 |
| - flatenned[key] = value; |
21 |
| - } else { |
22 |
| - hasAmp = true; |
23 |
| - amp[key] = value; |
24 |
| - } |
25 |
| - } |
26 |
| - if (hasAmp) { |
27 |
| - flatenned['&'] = amp; |
28 |
| - } |
29 |
| - |
30 |
| - return flatenned; |
31 |
| -}; |
32 |
| - |
33 |
| -const nano = create(); |
34 |
| -addonCssom(nano); |
35 |
| -addonPipe(nano); |
| 1 | +import {useLayoutEffect, useMemo} from 'react'; |
| 2 | +import {create, NanoRenderer} from 'nano-css'; |
| 3 | +import {addon as addonCSSOM, CSSOMAddon} from 'nano-css/addon/cssom'; |
| 4 | +import {addon as addonVCSSOM, VCSSOMAddon} from 'nano-css/addon/vcssom'; |
| 5 | +import {cssToTree} from 'nano-css/addon/vcssom/cssToTree'; |
| 6 | + |
| 7 | +type Nano = |
| 8 | + & NanoRenderer |
| 9 | + & CSSOMAddon |
| 10 | + & VCSSOMAddon |
| 11 | + ; |
| 12 | +const nano = create() as Nano; |
| 13 | +addonCSSOM(nano); |
| 14 | +addonVCSSOM(nano); |
| 15 | + |
| 16 | +let counter = 0; |
36 | 17 |
|
37 | 18 | const useCss = (css: object): string => {
|
38 |
| - const [pipe] = useState<CssPipe>(nano.pipe()); |
| 19 | + const className = useMemo(() => 'react-use-css-' + (counter++).toString(36), []); |
| 20 | + const sheet = useMemo(() => new nano.VSheet(), []); |
39 | 21 |
|
40 | 22 | useLayoutEffect(() => {
|
41 |
| - pipe.css(flattenSelectors(css)); |
42 |
| - return () => pipe.remove(); |
| 23 | + const tree = {}; |
| 24 | + cssToTree(tree, css, '.' + className, ''); |
| 25 | + sheet.diff(tree); |
| 26 | + |
| 27 | + return () => { |
| 28 | + sheet.diff({}); |
| 29 | + }; |
43 | 30 | });
|
44 | 31 |
|
45 |
| - return pipe.className; |
| 32 | + return className; |
46 | 33 | };
|
47 | 34 |
|
48 | 35 | export default useCss;
|
0 commit comments