From 5f347517b3fa364109c99daa26e5e449b5ff0f2e Mon Sep 17 00:00:00 2001 From: Diel Duarte Date: Tue, 18 May 2021 23:37:07 -0300 Subject: [PATCH] rescript parser WIP --- src/parser/.bsb.lock | 1 + src/parser/.merlin | 10 ++++ src/parser/bsconfig.json | 17 ++++++ src/parser/package-lock.json | 83 ++++++++++++++++++++++++++ src/parser/package.json | 20 +++++++ src/parser/src/AnimatedComponent.bs.js | 17 ++++++ src/parser/src/AnimatedComponent.res | 21 +++++++ src/parser/src/bindings/CssTree.bs.js | 2 + src/parser/src/bindings/CssTree.res | 15 +++++ src/parser/src/index.bs.js | 18 ++++++ src/parser/src/index.res | 33 ++++++++++ 11 files changed, 237 insertions(+) create mode 100644 src/parser/.bsb.lock create mode 100644 src/parser/.merlin create mode 100644 src/parser/bsconfig.json create mode 100644 src/parser/package-lock.json create mode 100644 src/parser/package.json create mode 100644 src/parser/src/AnimatedComponent.bs.js create mode 100644 src/parser/src/AnimatedComponent.res create mode 100644 src/parser/src/bindings/CssTree.bs.js create mode 100644 src/parser/src/bindings/CssTree.res create mode 100644 src/parser/src/index.bs.js create mode 100644 src/parser/src/index.res diff --git a/src/parser/.bsb.lock b/src/parser/.bsb.lock new file mode 100644 index 0000000..1d1a1e6 --- /dev/null +++ b/src/parser/.bsb.lock @@ -0,0 +1 @@ +49528 \ No newline at end of file diff --git a/src/parser/.merlin b/src/parser/.merlin new file mode 100644 index 0000000..80ce9b6 --- /dev/null +++ b/src/parser/.merlin @@ -0,0 +1,10 @@ +####{BSB GENERATED: NO EDIT +FLG -ppx '/Users/dielduarte/localhost/animate-css-styled-components/src/parser/node_modules/rescript/darwin/bsc.exe -as-ppx ' +S /Users/dielduarte/localhost/animate-css-styled-components/src/parser/node_modules/rescript/lib/ocaml +B /Users/dielduarte/localhost/animate-css-styled-components/src/parser/node_modules/rescript/lib/ocaml +FLG -w +a-4-9-20-40-41-42-50-61-102 +S src +B lib/bs/src +S src/bindings +B lib/bs/src/bindings +####BSB GENERATED: NO EDIT} diff --git a/src/parser/bsconfig.json b/src/parser/bsconfig.json new file mode 100644 index 0000000..49e18b4 --- /dev/null +++ b/src/parser/bsconfig.json @@ -0,0 +1,17 @@ +{ + "name": "your-project-name", + "sources": [ + { + "dir": "src", + "subdirs": true + } + ], + "package-specs": [ + { + "module": "commonjs", + "in-source": true + } + ], + "suffix": ".bs.js", + "bs-dependencies": [] +} \ No newline at end of file diff --git a/src/parser/package-lock.json b/src/parser/package-lock.json new file mode 100644 index 0000000..3e6c6be --- /dev/null +++ b/src/parser/package-lock.json @@ -0,0 +1,83 @@ +{ + "name": "parser", + "version": "1.0.0", + "lockfileVersion": 2, + "requires": true, + "packages": { + "": { + "version": "1.0.0", + "license": "ISC", + "dependencies": { + "css-tree": "^1.1.3" + }, + "devDependencies": { + "rescript": "^9.1.2" + } + }, + "node_modules/css-tree": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-1.1.3.tgz", + "integrity": "sha512-tRpdppF7TRazZrjJ6v3stzv93qxRcSsFmW6cX0Zm2NVKpxE1WV1HblnghVv9TreireHkqI/VDEsfolRF1p6y7Q==", + "dependencies": { + "mdn-data": "2.0.14", + "source-map": "^0.6.1" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/mdn-data": { + "version": "2.0.14", + "resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.14.tgz", + "integrity": "sha512-dn6wd0uw5GsdswPFfsgMp5NSB0/aDe6fK94YJV/AJDYXL6HVLWBsxeq7js7Ad+mU2K9LAlwpk6kN2D5mwCPVow==" + }, + "node_modules/rescript": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/rescript/-/rescript-9.1.2.tgz", + "integrity": "sha512-4wHvTDv3nyYnAPJHcg1RGG8z7u3HDiBf6RN3P/dITDv859Qo35aKOzJWQtfBzbAs0EKNafLqei3TnUqiAv6BwQ==", + "dev": true, + "hasInstallScript": true, + "bin": { + "bsc": "bsc", + "bsrefmt": "bsrefmt", + "bstracing": "lib/bstracing", + "rescript": "rescript" + } + }, + "node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "engines": { + "node": ">=0.10.0" + } + } + }, + "dependencies": { + "css-tree": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-1.1.3.tgz", + "integrity": "sha512-tRpdppF7TRazZrjJ6v3stzv93qxRcSsFmW6cX0Zm2NVKpxE1WV1HblnghVv9TreireHkqI/VDEsfolRF1p6y7Q==", + "requires": { + "mdn-data": "2.0.14", + "source-map": "^0.6.1" + } + }, + "mdn-data": { + "version": "2.0.14", + "resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.0.14.tgz", + "integrity": "sha512-dn6wd0uw5GsdswPFfsgMp5NSB0/aDe6fK94YJV/AJDYXL6HVLWBsxeq7js7Ad+mU2K9LAlwpk6kN2D5mwCPVow==" + }, + "rescript": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/rescript/-/rescript-9.1.2.tgz", + "integrity": "sha512-4wHvTDv3nyYnAPJHcg1RGG8z7u3HDiBf6RN3P/dITDv859Qo35aKOzJWQtfBzbAs0EKNafLqei3TnUqiAv6BwQ==", + "dev": true + }, + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" + } + } +} diff --git a/src/parser/package.json b/src/parser/package.json new file mode 100644 index 0000000..074f6f6 --- /dev/null +++ b/src/parser/package.json @@ -0,0 +1,20 @@ +{ + "name": "parser", + "version": "1.0.0", + "description": "", + "main": "index.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1", + "re:build": "rescript", + "re:start": "rescript build -w" + }, + "keywords": [], + "author": "", + "license": "ISC", + "devDependencies": { + "rescript": "^9.1.2" + }, + "dependencies": { + "css-tree": "^1.1.3" + } +} diff --git a/src/parser/src/AnimatedComponent.bs.js b/src/parser/src/AnimatedComponent.bs.js new file mode 100644 index 0000000..1f78e5f --- /dev/null +++ b/src/parser/src/AnimatedComponent.bs.js @@ -0,0 +1,17 @@ +// Generated by ReScript, PLEASE EDIT WITH CARE +'use strict'; + +var Curry = require("rescript/lib/js/curry.js"); + +function generateAnimatedComponent(animationCode, componentName) { + var partial_arg = /\${componentName}/g; + var replaceComponentName = function (param) { + return param.replace(partial_arg, componentName); + }; + var partial_arg$1 = /\${animationCode}/g; + var param = Curry._1(replaceComponentName, "\n import styled, { keyframes } from 'styled-components';\n import BaseAnimation from '../BaseAnimation';\n\n const ${componentName}Animation = keyframes`\n ${animationCode}\n `;\n\n const ${componentName} = styled(BaseAnimation)`\n animation-name: ${${componentName}Animation};\n `;\n\n export default ${componentName};\n "); + return param.replace(partial_arg$1, animationCode); +} + +exports.generateAnimatedComponent = generateAnimatedComponent; +/* No side effect */ diff --git a/src/parser/src/AnimatedComponent.res b/src/parser/src/AnimatedComponent.res new file mode 100644 index 0000000..7b52f2e --- /dev/null +++ b/src/parser/src/AnimatedComponent.res @@ -0,0 +1,21 @@ +let generateAnimatedComponent = (~animationCode, ~componentName) => { + let result = " + import styled, { keyframes } from 'styled-components'; + import BaseAnimation from '../BaseAnimation'; + + const ${componentName}Animation = keyframes` + ${animationCode} + `; + + const ${componentName} = styled(BaseAnimation)` + animation-name: ${${componentName}Animation}; + `; + + export default ${componentName}; + " + + let replaceComponentName = Js.String.replaceByRe(%re("/\${componentName}/g"), componentName) + let replaceAnimationCode = Js.String.replaceByRe(%re("/\${animationCode}/g"), animationCode) + + result->replaceComponentName->replaceAnimationCode +} diff --git a/src/parser/src/bindings/CssTree.bs.js b/src/parser/src/bindings/CssTree.bs.js new file mode 100644 index 0000000..d856702 --- /dev/null +++ b/src/parser/src/bindings/CssTree.bs.js @@ -0,0 +1,2 @@ +// Generated by ReScript, PLEASE EDIT WITH CARE +/* This output is empty. Its source's type definitions, externals and/or unused code got optimized away. */ diff --git a/src/parser/src/bindings/CssTree.res b/src/parser/src/bindings/CssTree.res new file mode 100644 index 0000000..6d5a388 --- /dev/null +++ b/src/parser/src/bindings/CssTree.res @@ -0,0 +1,15 @@ +type node = { + "type": string, + @set + "name": string, + "block": {"type": string, "children": array}, +} + +@module("css-tree") +external parse: string => 'a = "parse" + +@module("css-tree") +external generate: 'a => string = "generate" + +@module("css-tree") +external walk: ('a, node => unit) => unit = "walk" diff --git a/src/parser/src/index.bs.js b/src/parser/src/index.bs.js new file mode 100644 index 0000000..fc2a3db --- /dev/null +++ b/src/parser/src/index.bs.js @@ -0,0 +1,18 @@ +// Generated by ReScript, PLEASE EDIT WITH CARE +'use strict'; + +var CssTree = require("css-tree"); +var AnimatedComponent = require("./AnimatedComponent.bs.js"); + +var ast = CssTree.parse("@keyframes zoomInLeft {\n from {\n opacity: 0;\n transform: scale3d(0.1, 0.1, 0.1) translate3d(-1000px, 0, 0);\n animation-timing-function: cubic-bezier(0.55, 0.055, 0.675, 0.19);\n }\n\n 60% {\n opacity: 1;\n transform: scale3d(0.475, 0.475, 0.475) translate3d(10px, 0, 0);\n animation-timing-function: cubic-bezier(0.175, 0.885, 0.32, 1);\n }\n}\n\n.zoomInLeft {\n animation-name: zoomInLeft;\n}"); + +CssTree.walk(ast, (function (node) { + if (node.type === "Atrule") { + console.log(AnimatedComponent.generateAnimatedComponent(CssTree.generate(node.block), "NameOne")); + return ; + } + + })); + +exports.ast = ast; +/* ast Not a pure module */ diff --git a/src/parser/src/index.res b/src/parser/src/index.res new file mode 100644 index 0000000..87cd1ce --- /dev/null +++ b/src/parser/src/index.res @@ -0,0 +1,33 @@ +let ast = CssTree.parse("@keyframes zoomInLeft { + from { + opacity: 0; + transform: scale3d(0.1, 0.1, 0.1) translate3d(-1000px, 0, 0); + animation-timing-function: cubic-bezier(0.55, 0.055, 0.675, 0.19); + } + + 60% { + opacity: 1; + transform: scale3d(0.475, 0.475, 0.475) translate3d(10px, 0, 0); + animation-timing-function: cubic-bezier(0.175, 0.885, 0.32, 1); + } +} + +.zoomInLeft { + animation-name: zoomInLeft; +}") + +CssTree.walk(ast, node => { + if node["type"] === "Atrule" { + AnimatedComponent.generateAnimatedComponent( + ~animationCode=CssTree.generate(node["block"]), + ~componentName="NameOne", + )->Js.log + } +}) + +// @TODO +// - get animation name +// - get Animation extra styles +// - import animation file +// - script to clone animate css and read files +// - script to generate a new animat-css-library version