diff --git a/package-lock.json b/package-lock.json index bdf7d45..f1c33d4 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,6 +9,7 @@ "version": "0.0.1", "dependencies": { "@blockly/continuous-toolbox": "^5.0.2", + "@blockly/theme-dark": "^6.0.1", "@sveltejs/adapter-vercel": "^3.0.2", "file-saver": "^2.0.5", "js-beautify": "^1.14.9", @@ -46,6 +47,17 @@ "blockly": "^10.0.0" } }, + "node_modules/@blockly/theme-dark": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/@blockly/theme-dark/-/theme-dark-6.0.1.tgz", + "integrity": "sha512-fZa834SKstG31PNkoZ26DLIpevNVBWLDwDT/g99a6EtwqnkZg2VjCjbJDLA0xzrCmxN8AH6zmZU/lAdMoBH8sw==", + "engines": { + "node": ">=8.17.0" + }, + "peerDependencies": { + "blockly": "^10.0.0" + } + }, "node_modules/@esbuild/android-arm": { "version": "0.18.17", "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.18.17.tgz", @@ -2372,6 +2384,12 @@ "integrity": "sha512-7ayim3y4X4vwTLC+SYPijurlx/GoJI0ZemqnoYBcSuqkgnkFCYj8NSYejal1NLdzExjdVm3gsTwRVl9zJJ1cAA==", "requires": {} }, + "@blockly/theme-dark": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/@blockly/theme-dark/-/theme-dark-6.0.1.tgz", + "integrity": "sha512-fZa834SKstG31PNkoZ26DLIpevNVBWLDwDT/g99a6EtwqnkZg2VjCjbJDLA0xzrCmxN8AH6zmZU/lAdMoBH8sw==", + "requires": {} + }, "@esbuild/android-arm": { "version": "0.18.17", "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.18.17.tgz", diff --git a/package.json b/package.json index debade2..a16543a 100644 --- a/package.json +++ b/package.json @@ -16,6 +16,7 @@ "type": "module", "dependencies": { "@blockly/continuous-toolbox": "^5.0.2", + "@blockly/theme-dark": "^6.0.1", "@sveltejs/adapter-vercel": "^3.0.2", "file-saver": "^2.0.5", "js-beautify": "^1.14.9", diff --git a/src/app.html b/src/app.html index 2874a6e..a14fb4c 100644 --- a/src/app.html +++ b/src/app.html @@ -10,11 +10,17 @@ - + diff --git a/src/lib/MenuModals/ExtensionColors.svelte b/src/lib/MenuModals/ExtensionColors.svelte index 006751c..e438100 100644 --- a/src/lib/MenuModals/ExtensionColors.svelte +++ b/src/lib/MenuModals/ExtensionColors.svelte @@ -32,6 +32,9 @@ function getExampleData(color1, color2, color3, color3Included) { const tokens = ["[{{COLOR1}}]", "[{{COLOR2}}]", "[{{COLOR3}}]"]; + if (color3Included && !color3) { + color3 = "#000000"; + } if (!color3 || !color3Included) { const rgb = ColorUtil.hexToRGB(color1); const r = Math.max(0, rgb.r - 51); @@ -176,6 +179,13 @@ border: 1px solid rgba(0, 0, 0, 0.25); } + :global(body.dark) input[type="color"]::-webkit-color-swatch { + border-color: rgba(255, 255, 255, 0.5); + } + :global(body.dark) input[type="color"]::-moz-color-swatch { + border-color: rgba(255, 255, 255, 0.5); + } + .bg { position: fixed; left: 0px; @@ -200,6 +210,12 @@ align-items: center; overflow: hidden; } + :global(body.dark) .bg { + background-color: #333333b0; + } + :global(body.dark) .modal { + background-color: #111; + } .modal-title { width: 100%; @@ -211,6 +227,9 @@ align-items: center; justify-content: center; } + :global(body.dark) .modal-title { + background-color: #333; + } .modal-content { width: 100%; height: 75%; @@ -239,6 +258,13 @@ .extensionMenuPreview:active { background-color: #e9eef2; } + :global(body.dark) .extensionMenuPreview { + color: #ccc; + } + :global(body.dark) .extensionMenuPreview:focus, + :global(body.dark) .extensionMenuPreview:active { + background-color: #1e1e1e; + } .extensionBubbleIcon { width: 20px; height: 20px; diff --git a/src/lib/NavigationBar/Button.svelte b/src/lib/NavigationBar/Button.svelte index 90b55db..ccb776b 100644 --- a/src/lib/NavigationBar/Button.svelte +++ b/src/lib/NavigationBar/Button.svelte @@ -28,13 +28,14 @@ font-weight: bold; font-size: 0.75rem; color: white; - background: #ff4b4b; + background: transparent; cursor: pointer; border: 0; } - button:focus, - button:hover, - button:active { - background: rgb(211, 62, 62); + button:hover { + background: rgba(0, 0, 0, 0.2); + } + :global(body.dark) button:hover { + background: rgba(255, 255, 255, 0.2); } diff --git a/src/lib/NavigationBar/Divider.svelte b/src/lib/NavigationBar/Divider.svelte index eda524a..c299a36 100644 --- a/src/lib/NavigationBar/Divider.svelte +++ b/src/lib/NavigationBar/Divider.svelte @@ -3,7 +3,7 @@ diff --git a/src/lib/NavigationBar/NavigationBar.svelte b/src/lib/NavigationBar/NavigationBar.svelte index e1dbc67..91d4376 100644 --- a/src/lib/NavigationBar/NavigationBar.svelte +++ b/src/lib/NavigationBar/NavigationBar.svelte @@ -1,15 +1,33 @@
@@ -23,10 +41,8 @@ position: fixed; left: 0px; top: 0px; - width: calc(100% - 8px); - height: calc(var(--nav-height) - 8px); - - padding: 4px; + width: 100%; + height: var(--nav-height); display: flex; flex-direction: row; @@ -35,6 +51,29 @@ background: #ff4b4b; } .logo-margin { - margin-right: 8px; + margin: 0 6px; + margin-left: 10px; + } + .theme-switcher { + background: transparent; + height: 100%; + border: 0; + margin: 0; + cursor: pointer; + } + .theme-switcher:hover { + background: rgba(0, 0, 0, 0.2); + } + .theme-switcher > img { + width: 28px; + height: 28px; + } + + :global(body.dark) .theme-switcher:hover { + background: rgba(255, 255, 255, 0.2); + } + + :global(body.dark) .nav { + background: #333; } diff --git a/src/lib/StyledComponents/ToolboxButton.svelte b/src/lib/StyledComponents/ToolboxButton.svelte index 05b746e..52850b5 100644 --- a/src/lib/StyledComponents/ToolboxButton.svelte +++ b/src/lib/StyledComponents/ToolboxButton.svelte @@ -28,4 +28,14 @@ button:active { background: white; } + + :global(body.dark) button { + color: #ccc; + border-color: #c6c6c6; + } + :global(body.dark) button:focus, + :global(body.dark) button:hover, + :global(body.dark) button:active { + background: #111; + } diff --git a/src/resources/blocks/core.js b/src/resources/blocks/core.js index 78757d7..4a97b16 100644 --- a/src/resources/blocks/core.js +++ b/src/resources/blocks/core.js @@ -7,7 +7,7 @@ const categoryColor = '#ff4b4b'; function register() { // used in block creation menu registerBlock(`${categoryPrefix}builderblock`, { - message0: '...', + message0: '⠀', // empty character breaks block shape args0: [], previousStatement: null, nextStatement: null, diff --git a/src/resources/events/index.js b/src/resources/events/index.js new file mode 100644 index 0000000..38c332e --- /dev/null +++ b/src/resources/events/index.js @@ -0,0 +1,21 @@ +let canAccessWindow = false; +class EventManager { + static allowAttachment () { + canAccessWindow = true; + } + + static on (type, callback) { + if (!canAccessWindow) { + throw new Error('EventManager must be used after onMount allows attachment.'); + } + + window.tbevents_.push({ type, callback }); + } + + // enums + static get EVENT_THEME_CHANGED () { + return 'THEME'; + } +} + +export default EventManager; \ No newline at end of file diff --git a/src/routes/+page.svelte b/src/routes/+page.svelte index 91cacc8..aaf7de2 100644 --- a/src/routes/+page.svelte +++ b/src/routes/+page.svelte @@ -22,6 +22,7 @@ import Prism from "prismjs"; import * as FileSaver from "file-saver"; import fileDialog from "../resources/fileDialog"; + import EventManager from "../resources/events"; import Blockly from "blockly/core"; import * as ContinuousToolboxPlugin from "@blockly/continuous-toolbox"; @@ -67,9 +68,15 @@ disable: false, theme: Theme, renderer: "zelos", + grid: { + spacing: 25, + length: 3, + colour: "#00000022", + snap: false, + }, zoom: { controls: true, - wheel: true, + wheel: false, startScale: 0.8, maxScale: 4, minScale: 0.25, @@ -80,6 +87,14 @@ flyoutsVerticalToolbox: ContinuousToolboxPlugin.ContinuousFlyout, metricsManager: ContinuousToolboxPlugin.ContinuousMetrics, }, + move: { + scrollbars: { + horizontal: true, + vertical: true, + }, + drag: true, + wheel: true, + }, }; let workspace; @@ -134,6 +149,11 @@ compiler = new Compiler(workspace); // workspace was changed workspace.addChangeListener(updateGeneratedCode); + + EventManager.allowAttachment(); + EventManager.on(EventManager.EVENT_THEME_CHANGED, () => { + workspace.refreshTheme(); + }); }); let fileMenu; @@ -325,10 +345,8 @@ class="project-name" type="text" placeholder="Extension ID (ex: extensionID)" - style={"margin-left:4px;margin-right:4px" + - (isExtensionIDInvalid(projectID) - ? ";background-color:#ffabab;text-decoration:red underline;" - : "")} + style="margin-left:4px;margin-right:4px" + data-invalid={isExtensionIDInvalid(projectID)} bind:value={projectID} on:change={updateGeneratedCode} /> @@ -515,6 +533,28 @@ background: white; } + :global(body.dark) input[type="file"]::file-selector-button { + color: #ccc; + border-color: #c6c6c6; + } + :global(body.dark) input[type="file"]::file-selector-button:focus, + :global(body.dark) input[type="file"]::file-selector-button:hover, + :global(body.dark) input[type="file"]::file-selector-button:active { + background: #111; + } + + :global(body.dark) input[type="text"], + :global(body.dark) input[type="number"] { + background: transparent; + border: 1px solid rgba(255, 255, 255, 0.7); + color: white; + } + :global(body.dark) input[type="text"]:hover, + :global(body.dark) input[type="number"]:hover { + background: transparent; + border: 1px solid dodgerblue; + } + .main { position: absolute; left: 0px; @@ -561,6 +601,15 @@ transition: 0.25s; } + .project-name[data-invalid="true"] { + background-color: #ffabab; + text-decoration: red underline; + } + :global(body.dark) .project-name[data-invalid="true"] { + background-color: #9b0000 !important; + text-decoration: red underline; + } + .extensionIcon { width: 96px; height: 96px; @@ -607,6 +656,13 @@ .extensionMenuPreview:active { background-color: #e9eef2; } + :global(body.dark) .extensionMenuPreview { + color: #ccc; + } + :global(body.dark) .extensionMenuPreview:focus, + :global(body.dark) .extensionMenuPreview:active { + background-color: #1e1e1e; + } .extensionBubbleIcon { width: 20px; height: 20px; @@ -631,6 +687,9 @@ background: #f9f9f9; } + :global(body.dark) .blockMenuButtons { + background-color: #111; + } .blocklyWrapper { position: relative; @@ -656,6 +715,9 @@ background: #f9f9f9; } + :global(body.dark) .codeActionsWrapper { + background-color: #111; + } .codeWrapper { position: relative; width: 100%; @@ -674,6 +736,9 @@ white-space: pre-wrap; font-family: monospace !important; } + :global(body.dark) .codeDisplay { + background-color: #111; + } .warning { background-color: yellow; diff --git a/static/favicon_any.png b/static/favicon_any.png new file mode 100644 index 0000000..1f34a09 Binary files /dev/null and b/static/favicon_any.png differ diff --git a/static/favicon_dark.png b/static/favicon_dark.png new file mode 100644 index 0000000..8504d49 Binary files /dev/null and b/static/favicon_dark.png differ diff --git a/static/images/theme_switcher.svg b/static/images/theme_switcher.svg new file mode 100644 index 0000000..391ba91 --- /dev/null +++ b/static/images/theme_switcher.svg @@ -0,0 +1,2 @@ + + \ No newline at end of file