From c9a54d4c1402acc9a6688d676be8a814774199df Mon Sep 17 00:00:00 2001 From: Ozzie Gooen Date: Thu, 26 May 2022 10:08:19 -0400 Subject: [PATCH] First attempt at playground configurable toggles --- packages/components/package.json | 5 +- .../src/components/FunctionChart.tsx | 5 +- .../components/src/components/JsonEditor.tsx | 55 +++++++++++ .../src/components/SquiggleChart.tsx | 1 + .../src/components/SquigglePlayground.tsx | 95 +++++++++++++++++-- yarn.lock | 62 ++++++++++-- 6 files changed, 205 insertions(+), 18 deletions(-) create mode 100644 packages/components/src/components/JsonEditor.tsx diff --git a/packages/components/package.json b/packages/components/package.json index 67b2eeb5..3b594bc5 100644 --- a/packages/components/package.json +++ b/packages/components/package.json @@ -3,18 +3,21 @@ "version": "0.2.20", "license": "MIT", "dependencies": { + "@hookform/resolvers": "^2.8.10", "@quri/squiggle-lang": "^0.2.8", "@react-hook/size": "^2.1.2", "lodash": "^4.17.21", "react": "^18.1.0", "react-ace": "^10.1.0", "react-dom": "^18.1.0", + "react-hook-form": "^7.31.2", "react-use": "^17.4.0", "react-vega": "^7.5.1", "styled-components": "^5.3.5", "vega": "^5.22.1", "vega-embed": "^6.20.6", - "vega-lite": "^5.2.0" + "vega-lite": "^5.2.0", + "yup": "^0.32.11" }, "devDependencies": { "@babel/plugin-proposal-private-property-in-object": "^7.17.12", diff --git a/packages/components/src/components/FunctionChart.tsx b/packages/components/src/components/FunctionChart.tsx index 242bf719..d774f3db 100644 --- a/packages/components/src/components/FunctionChart.tsx +++ b/packages/components/src/components/FunctionChart.tsx @@ -45,6 +45,7 @@ interface FunctionChartProps { fn: lambdaValue; chartSettings: FunctionChartSettings; environment: environment; + height: number; } type percentiles = { @@ -149,6 +150,7 @@ export const FunctionChart: React.FC = ({ fn, chartSettings, environment, + height }: FunctionChartProps) => { let [mouseOverlay, setMouseOverlay] = React.useState(0); function handleHover(_name: string, value: unknown) { @@ -172,7 +174,7 @@ export const FunctionChart: React.FC = ({ ) : ( @@ -188,6 +190,7 @@ export const FunctionChart: React.FC = ({ <> diff --git a/packages/components/src/components/JsonEditor.tsx b/packages/components/src/components/JsonEditor.tsx new file mode 100644 index 00000000..eeac3de8 --- /dev/null +++ b/packages/components/src/components/JsonEditor.tsx @@ -0,0 +1,55 @@ +import _ from "lodash"; +import React, { FC } from "react"; +import AceEditor from "react-ace"; + +import "ace-builds/src-noconflict/mode-json"; +import "ace-builds/src-noconflict/theme-github"; +import { + jsImports, + defaultImports, +} from "@quri/squiggle-lang"; + +interface CodeEditorProps { + value: string; + onChange: (value: string) => void; + oneLine?: boolean; + width?: number; + height: number; + showGutter?: boolean; +} + +export let JsonEditor: FC = ({ + value, + onChange, + oneLine = false, + showGutter = false, + height, +}: CodeEditorProps) => { + let lineCount = value.split("\n").length; + let id = _.uniqueId(); + return ( + + ); +}; + +export default JsonEditor; diff --git a/packages/components/src/components/SquiggleChart.tsx b/packages/components/src/components/SquiggleChart.tsx index 50fcebb3..5cbebc8e 100644 --- a/packages/components/src/components/SquiggleChart.tsx +++ b/packages/components/src/components/SquiggleChart.tsx @@ -207,6 +207,7 @@ const SquiggleItem: React.FC = ({ = ({ initialSquiggleString = "", height = 300, @@ -95,9 +125,12 @@ let SquigglePlayground: FC = ({ showSummary = false, }: PlaygroundProps) => { let [squiggleString, setSquiggleString] = useState(initialSquiggleString); - let [sampleCount, setSampleCount] = useState(1000); - let [outputXYPoints, setOutputXYPoints] = useState(1000); - let [pointDistLength, setPointDistLength] = useState(1000); + let [importString, setImportString] = useState("{}"); + let [imports, setImports] = useState({}); + let [importsAreValid, setImportsAreValid] = useState(true); + let [showTypesInput, setShowTypesInput] = useState(showTypes); + let [showControlsInput, setShowControlsInput] = useState(showControls); + let [showSummaryInput, setShowSummaryInput] = useState(showSummary); let [diagramStart, setDiagramStart] = useState(0); let [diagramStop, setDiagramStop] = useState(10); let [diagramCount, setDiagramCount] = useState(20); @@ -106,12 +139,46 @@ let SquigglePlayground: FC = ({ stop: diagramStop, count: diagramCount, }; + const { + register, + formState: { errors }, + control, + } = useForm({ + resolver: yupResolver(schema), + defaultValues: { + sampleCount: 1000, + xyPointLength: 1000, + chartHeight: 150, + showTypes: showTypes, + showControls: showControls, + showSummary: showSummary, + }, + }); + const foo = useWatch({ + control, + }); let env: environment = { - sampleCount: sampleCount, - xyPointLength: outputXYPoints, + sampleCount: Number(foo.sampleCount), + xyPointLength: Number(foo.xyPointLength), + }; + let getChangeJson = (r: string) => { + setImportString(r); + try { + setImports(JSON.parse(r)); + setImportsAreValid(true); + } catch (e) { + setImportsAreValid(false); + } + (""); }; return ( + + + + + + = ({ showGutter={true} height={height - 3} /> + + {importsAreValid ? "Valid" : "INVALID"} @@ -128,12 +203,12 @@ let SquigglePlayground: FC = ({ squiggleString={squiggleString} environment={env} chartSettings={chartSettings} - height={150} - showTypes={showTypes} - showControls={showControls} + height={foo.chartHeight} + showTypes={foo.showTypes} + showControls={foo.showControls} bindings={defaultBindings} - jsImports={defaultImports} - showSummary={showSummary} + jsImports={imports} + showSummary={foo.showSummary} /> diff --git a/yarn.lock b/yarn.lock index 39329f75..680465a1 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1245,6 +1245,13 @@ dependencies: regenerator-runtime "^0.13.4" +"@babel/runtime@^7.15.4": + version "7.18.3" + resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.18.3.tgz#c7b654b57f6f63cf7f8b418ac9ca04408c4579f4" + integrity sha512-38Y8f7YUhce/K7RMwTp7m0uCumpv9hZkitCbBClqQIow1qSbCvGkcegKOXpEWCQLfWmevgRiWokZ1GkpfhbZug== + dependencies: + regenerator-runtime "^0.13.4" + "@babel/template@^7.12.7", "@babel/template@^7.16.7", "@babel/template@^7.3.3": version "7.16.7" resolved "https://registry.yarnpkg.com/@babel/template/-/template-7.16.7.tgz#8d126c8701fde4d66b264b3eba3d96f07666d155" @@ -1839,6 +1846,11 @@ dependencies: "@hapi/hoek" "^9.0.0" +"@hookform/resolvers@^2.8.10": + version "2.8.10" + resolved "https://registry.yarnpkg.com/@hookform/resolvers/-/resolvers-2.8.10.tgz#b66d7a7848b1b1dd5b976a73fff36bb366666e7d" + integrity sha512-DDFtNlugsbwAhCJHYp3NcN5LvJrwSsCLPi41Wo5O8UAIbUFnBfY/jW+zKnlX57BZ4jE0j/g6R9rB3JlO89ad0g== + "@humanwhocodes/config-array@^0.9.2": version "0.9.5" resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.9.5.tgz#2cbaf9a89460da24b5ca6531b8bbfc23e1df50c7" @@ -4163,7 +4175,7 @@ resolved "https://registry.yarnpkg.com/@types/katex/-/katex-0.11.1.tgz#34de04477dcf79e2ef6c8d23b41a3d81f9ebeaf5" integrity sha512-DUlIj2nk0YnJdlWgsFuVKcX27MLW0KbKmGVoUHmFr+74FYYNUDAaj9ZqTADvsbE8rfxuVmSFc7KczYn5Y09ozg== -"@types/lodash@^4.14.167", "@types/lodash@^4.14.182": +"@types/lodash@^4.14.167", "@types/lodash@^4.14.175", "@types/lodash@^4.14.182": version "4.14.182" resolved "https://registry.yarnpkg.com/@types/lodash/-/lodash-4.14.182.tgz#05301a4d5e62963227eaafe0ce04dd77c54ea5c2" integrity sha512-/THyiqyQAP9AfARo4pF+aCGcyiQ94tX/Is2I7HofNRqoYLgN1PBoOWu2/zTA5zMxzP5EFutMtWtGAFRKUe961Q== @@ -4298,10 +4310,10 @@ dependencies: "@types/react" "*" -"@types/react@*", "@types/react@^18.0.1", "@types/react@^18.0.9": - version "18.0.9" - resolved "https://registry.yarnpkg.com/@types/react/-/react-18.0.9.tgz#d6712a38bd6cd83469603e7359511126f122e878" - integrity sha512-9bjbg1hJHUm4De19L1cHiW0Jvx3geel6Qczhjd0qY5VKVE2X5+x77YxAepuCwVh4vrgZJdgEJw48zrhRIeF4Nw== +"@types/react@*", "@types/react@17.0.43", "@types/react@^18.0.9": + version "17.0.43" + resolved "https://registry.yarnpkg.com/@types/react/-/react-17.0.43.tgz#4adc142887dd4a2601ce730bc56c3436fdb07a55" + integrity sha512-8Q+LNpdxf057brvPu1lMtC5Vn7J119xrP1aq4qiaefNioQUYANF/CYeK4NsKorSZyUGJ66g0IM+4bbjwx45o2A== dependencies: "@types/prop-types" "*" "@types/scheduler" "*" @@ -11601,6 +11613,11 @@ locate-path@^6.0.0: dependencies: p-locate "^5.0.0" +lodash-es@^4.17.21: + version "4.17.21" + resolved "https://registry.yarnpkg.com/lodash-es/-/lodash-es-4.17.21.tgz#43e626c46e6591b7750beb2b50117390c609e3ee" + integrity sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw== + lodash.assignin@^4.0.9: version "4.2.0" resolved "https://registry.yarnpkg.com/lodash.assignin/-/lodash.assignin-4.2.0.tgz#ba8df5fb841eb0a3e8044232b0e263a8dc6a28a2" @@ -12290,6 +12307,11 @@ nano-css@^5.3.1: stacktrace-js "^2.0.2" stylis "^4.0.6" +nanoclone@^0.2.1: + version "0.2.1" + resolved "https://registry.yarnpkg.com/nanoclone/-/nanoclone-0.2.1.tgz#dd4090f8f1a110d26bb32c49ed2f5b9235209ed4" + integrity sha512-wynEP02LmIbLpcYw8uBKpcfF6dmg2vcpKqxeH5UcoKEYdExslsdUA4ugFauuaeYdTB76ez6gJW8XAZ6CgkXYxA== + nanoid@^3.3.1, nanoid@^3.3.3: version "3.3.4" resolved "https://registry.yarnpkg.com/nanoid/-/nanoid-3.3.4.tgz#730b67e3cd09e2deacf03c027c81c9d9dbc5e8ab" @@ -13998,6 +14020,11 @@ prop-types@^15.0.0, prop-types@^15.6.2, prop-types@^15.7.2, prop-types@^15.8.1: object-assign "^4.1.1" react-is "^16.13.1" +property-expr@^2.0.4: + version "2.0.5" + resolved "https://registry.yarnpkg.com/property-expr/-/property-expr-2.0.5.tgz#278bdb15308ae16af3e3b9640024524f4dc02cb4" + integrity sha512-IJUkICM5dP5znhCckHSv30Q4b5/JA5enCtkRHYaOVOAocnH/1BQEYTC5NMfT3AVl/iXKdr3aqQbQn9DxyWknwA== + property-information@^5.0.0, property-information@^5.3.0: version "5.6.0" resolved "https://registry.yarnpkg.com/property-information/-/property-information-5.6.0.tgz#61675545fb23002f245c6540ec46077d4da3ed69" @@ -14328,6 +14355,11 @@ react-helmet-async@*, react-helmet-async@^1.3.0: react-fast-compare "^3.2.0" shallowequal "^1.1.0" +react-hook-form@^7.31.2: + version "7.31.2" + resolved "https://registry.yarnpkg.com/react-hook-form/-/react-hook-form-7.31.2.tgz#efb7ac469810954488b7cf40be4e5017122c6e5e" + integrity sha512-oPudn3YuyzWg//IsT9z2cMEjWocAgHWX/bmueDT8cmsYQnGY5h7/njjvMDfLVv3mbdhYBjslTRnII2MIT7eNCA== + react-inspector@^5.1.0: version "5.1.1" resolved "https://registry.yarnpkg.com/react-inspector/-/react-inspector-5.1.1.tgz#58476c78fde05d5055646ed8ec02030af42953c8" @@ -14525,7 +14557,7 @@ react-vega@^7.5.1: prop-types "^15.8.1" vega-embed "^6.5.1" -react@^18.0.0, react@^18.1.0: +react@^18.1.0: version "18.1.0" resolved "https://registry.yarnpkg.com/react/-/react-18.1.0.tgz#6f8620382decb17fdc5cc223a115e2adbf104890" integrity sha512-4oL8ivCz5ZEPyclFQXaNksK3adutVS8l2xzZU0cqEFrE9Sb7fC0EFK5uEk74wIreL1DERyjvsU915j1pcT2uEQ== @@ -16559,6 +16591,11 @@ topojson-client@^3.1.0: dependencies: commander "2" +toposort@^2.0.2: + version "2.0.2" + resolved "https://registry.yarnpkg.com/toposort/-/toposort-2.0.2.tgz#ae21768175d1559d48bef35420b2f4962f09c330" + integrity sha1-riF2gXXRVZ1IvvNUILL0li8JwzA= + totalist@^1.0.0: version "1.1.0" resolved "https://registry.yarnpkg.com/totalist/-/totalist-1.1.0.tgz#a4d65a3e546517701e3e5c37a47a70ac97fe56df" @@ -18440,6 +18477,19 @@ yocto-queue@^0.1.0: resolved "https://registry.yarnpkg.com/yocto-queue/-/yocto-queue-0.1.0.tgz#0294eb3dee05028d31ee1a5fa2c556a6aaf10a1b" integrity sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q== +yup@^0.32.11: + version "0.32.11" + resolved "https://registry.yarnpkg.com/yup/-/yup-0.32.11.tgz#d67fb83eefa4698607982e63f7ca4c5ed3cf18c5" + integrity sha512-Z2Fe1bn+eLstG8DRR6FTavGD+MeAwyfmouhHsIUgaADz8jvFKbO/fXc2trJKZg+5EBjh4gGm3iU/t3onKlXHIg== + dependencies: + "@babel/runtime" "^7.15.4" + "@types/lodash" "^4.14.175" + lodash "^4.17.21" + lodash-es "^4.17.21" + nanoclone "^0.2.1" + property-expr "^2.0.4" + toposort "^2.0.2" + zwitch@^1.0.0: version "1.0.5" resolved "https://registry.yarnpkg.com/zwitch/-/zwitch-1.0.5.tgz#d11d7381ffed16b742f6af7b3f223d5cd9fe9920"