Compare commits
12 Commits
Author | SHA1 | Date | |
---|---|---|---|
5cc21d68ae | |||
d919b1a26d | |||
e719223d3b | |||
54126098bb | |||
7560c6cb4c | |||
722605131a | |||
280b89b22a | |||
5b6e40e087 | |||
f3be0eb4ae | |||
4abe4ab7e0 | |||
e4dd1f6dbe | |||
81147084c2 |
47
palette-switcher-v2/.gitignore
vendored
Normal file
47
palette-switcher-v2/.gitignore
vendored
Normal file
@ -0,0 +1,47 @@
|
||||
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
|
||||
|
||||
# dependencies
|
||||
/node_modules
|
||||
/.pnp
|
||||
.pnp.js
|
||||
|
||||
# testing
|
||||
/coverage
|
||||
|
||||
# production
|
||||
/build
|
||||
/dist
|
||||
|
||||
# misc
|
||||
.DS_Store
|
||||
.env.local
|
||||
.env.development.local
|
||||
.env.test.local
|
||||
.env.production.local
|
||||
|
||||
npm-debug.log*
|
||||
yarn-debug.log*
|
||||
yarn-error.log*
|
||||
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
|
||||
|
||||
# dependencies
|
||||
/node_modules
|
||||
/.pnp
|
||||
.pnp.js
|
||||
|
||||
# testing
|
||||
/coverage
|
||||
|
||||
# production
|
||||
/build
|
||||
|
||||
# misc
|
||||
.DS_Store
|
||||
.env.local
|
||||
.env.development.local
|
||||
.env.test.local
|
||||
.env.production.local
|
||||
|
||||
npm-debug.log*
|
||||
yarn-debug.log*
|
||||
yarn-error.log*
|
2
palette-switcher-v2/.tool-versions
Normal file
2
palette-switcher-v2/.tool-versions
Normal file
@ -0,0 +1,2 @@
|
||||
pnpm 8.14.1
|
||||
nodejs 21.5.0
|
34
palette-switcher-v2/README.md
Normal file
34
palette-switcher-v2/README.md
Normal file
@ -0,0 +1,34 @@
|
||||
## Usage
|
||||
|
||||
Those templates dependencies are maintained via [pnpm](https://pnpm.io) via `pnpm up -Lri`.
|
||||
|
||||
This is the reason you see a `pnpm-lock.yaml`. That being said, any package manager will work. This file can be safely be removed once you clone a template.
|
||||
|
||||
```bash
|
||||
$ npm install # or pnpm install or yarn install
|
||||
```
|
||||
|
||||
### Learn more on the [Solid Website](https://solidjs.com) and come chat with us on our [Discord](https://discord.com/invite/solidjs)
|
||||
|
||||
## Available Scripts
|
||||
|
||||
In the project directory, you can run:
|
||||
|
||||
### `npm run dev` or `npm start`
|
||||
|
||||
Runs the app in the development mode.<br>
|
||||
Open [http://localhost:3000](http://localhost:3000) to view it in the browser.
|
||||
|
||||
The page will reload if you make edits.<br>
|
||||
|
||||
### `npm run build`
|
||||
|
||||
Builds the app for production to the `dist` folder.<br>
|
||||
It correctly bundles Solid in production mode and optimizes the build for the best performance.
|
||||
|
||||
The build is minified and the filenames include the hashes.<br>
|
||||
Your app is ready to be deployed!
|
||||
|
||||
## Deployment
|
||||
|
||||
You can deploy the `dist` folder to any static host provider (netlify, surge, now, etc.)
|
17
palette-switcher-v2/index.html
Normal file
17
palette-switcher-v2/index.html
Normal file
@ -0,0 +1,17 @@
|
||||
<!doctype html>
|
||||
<html lang="en" class="h-full bg-gray-100">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<meta name="theme-color" content="#000000" />
|
||||
<link rel="shortcut icon" type="image/ico" href="/src/assets/favicon.ico" />
|
||||
<title>Palette Switcher</title>
|
||||
</head>
|
||||
<body class="h-full">
|
||||
<noscript>You need to enable JavaScript to run this app.</noscript>
|
||||
<div id="root"></div>
|
||||
|
||||
<!-- <script src="/src/wasm-exec.js"></script> -->
|
||||
<script src="/src/index.tsx" type="module"></script>
|
||||
</body>
|
||||
</html>
|
31
palette-switcher-v2/package.json
Normal file
31
palette-switcher-v2/package.json
Normal file
@ -0,0 +1,31 @@
|
||||
{
|
||||
"name": "vite-template-solid",
|
||||
"version": "0.0.0",
|
||||
"description": "",
|
||||
"scripts": {
|
||||
"start": "vite",
|
||||
"dev": "vite",
|
||||
"build": "vite build",
|
||||
"serve": "vite preview"
|
||||
},
|
||||
"license": "MIT",
|
||||
"devDependencies": {
|
||||
"autoprefixer": "^10.4.16",
|
||||
"postcss": "^8.4.33",
|
||||
"solid-devtools": "^0.27.3",
|
||||
"tailwindcss": "^3.4.1",
|
||||
"typescript": "^5.1.3",
|
||||
"vite": "^4.3.9",
|
||||
"vite-plugin-solid": "^2.7.0",
|
||||
"vite-plugin-wasm": "^3.3.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"@fortawesome/free-brands-svg-icons": "^6.5.1",
|
||||
"@fortawesome/free-solid-svg-icons": "^6.5.1",
|
||||
"@solid-primitives/workers": "^0.2.6",
|
||||
"@solidjs/router": "^0.10.9",
|
||||
"flowbite": "^2.2.1",
|
||||
"solid-fa": "^0.2.0",
|
||||
"solid-js": "^1.8.11"
|
||||
}
|
||||
}
|
2751
palette-switcher-v2/pnpm-lock.yaml
Normal file
2751
palette-switcher-v2/pnpm-lock.yaml
Normal file
File diff suppressed because it is too large
Load Diff
6
palette-switcher-v2/postcss.config.js
Normal file
6
palette-switcher-v2/postcss.config.js
Normal file
@ -0,0 +1,6 @@
|
||||
module.exports = {
|
||||
plugins: {
|
||||
tailwindcss: {},
|
||||
autoprefixer: {},
|
||||
},
|
||||
};
|
14
palette-switcher-v2/src/App.tsx
Normal file
14
palette-switcher-v2/src/App.tsx
Normal file
@ -0,0 +1,14 @@
|
||||
import type { ParentComponent } from "solid-js";
|
||||
import Header from "./Header";
|
||||
import "flowbite";
|
||||
import Footer from "./Footer";
|
||||
|
||||
const App: ParentComponent = (props) => (
|
||||
<div class="flex flex-col h-screen">
|
||||
<Header />
|
||||
<main class="mb-auto">{props.children}</main>
|
||||
<Footer />
|
||||
</div>
|
||||
);
|
||||
|
||||
export default App;
|
28
palette-switcher-v2/src/Footer.tsx
Normal file
28
palette-switcher-v2/src/Footer.tsx
Normal file
@ -0,0 +1,28 @@
|
||||
import { faGit, faMastodon } from "@fortawesome/free-brands-svg-icons";
|
||||
import Fa from "solid-fa";
|
||||
import { Component } from "solid-js";
|
||||
|
||||
const Footer: Component = () => (
|
||||
<footer class="p-4 bg-white sm:p-6 dark:bg-gray-800">
|
||||
<div class="mx-auto max-w-screen-xl">
|
||||
<div class="sm:flex sm:items-center sm:justify-between">
|
||||
<div class="flex mt-4 space-x-6 sm:justify-center sm:mt-0">
|
||||
<a
|
||||
href="https://gitea.bruyant.xyz/alexandre/PaletteSwitcher"
|
||||
class="text-gray-500 hover:text-gray-900 dark:hover:text-white"
|
||||
>
|
||||
<Fa icon={faGit} />
|
||||
</a>
|
||||
<a
|
||||
href="https://piaille.fr/@cattusinarca"
|
||||
class="text-gray-500 hover:text-gray-900 dark:hover:text-white"
|
||||
>
|
||||
<Fa icon={faMastodon} />
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</footer>
|
||||
);
|
||||
|
||||
export default Footer;
|
25
palette-switcher-v2/src/Header.tsx
Normal file
25
palette-switcher-v2/src/Header.tsx
Normal file
@ -0,0 +1,25 @@
|
||||
import type { Component } from "solid-js";
|
||||
|
||||
const Header: Component = () => (
|
||||
<header>
|
||||
<nav class="bg-white border-gray-200 px-4 lg:px-6 py-2.5 dark:bg-gray-800">
|
||||
<div class="flex flex-wrap justify-between items-center mx-auto max-w-screen-xl">
|
||||
<a href="/" class="flex items-center">
|
||||
<span class="self-center text-xl font-semibold whitespace-nowrap dark:text-white">
|
||||
Palette Switcher
|
||||
</span>
|
||||
</a>
|
||||
<div class="flex items-center lg:order-2">
|
||||
<a
|
||||
href="/about"
|
||||
class="text-gray-800 dark:text-white hover:bg-gray-50 focus:ring-4 focus:ring-gray-300 font-medium rounded-lg text-sm px-4 lg:px-5 py-2 lg:py-2.5 mr-2 dark:hover:bg-gray-700 focus:outline-none dark:focus:ring-gray-800"
|
||||
>
|
||||
About
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
</header>
|
||||
);
|
||||
|
||||
export default Header;
|
BIN
palette-switcher-v2/src/assets/favicon.ico
Normal file
BIN
palette-switcher-v2/src/assets/favicon.ico
Normal file
Binary file not shown.
After Width: | Height: | Size: 15 KiB |
3
palette-switcher-v2/src/index.css
Normal file
3
palette-switcher-v2/src/index.css
Normal file
@ -0,0 +1,3 @@
|
||||
@tailwind base;
|
||||
@tailwind components;
|
||||
@tailwind utilities;
|
26
palette-switcher-v2/src/index.tsx
Normal file
26
palette-switcher-v2/src/index.tsx
Normal file
@ -0,0 +1,26 @@
|
||||
/* @refresh reload */
|
||||
import { render } from "solid-js/web";
|
||||
|
||||
import "./index.css";
|
||||
import App from "./App";
|
||||
import { Router, Route } from "@solidjs/router";
|
||||
import About from "./pages/About";
|
||||
import Switcher from "./pages/Switcher/Switcher";
|
||||
|
||||
const root = document.getElementById("root");
|
||||
|
||||
if (import.meta.env.DEV && !(root instanceof HTMLElement)) {
|
||||
throw new Error(
|
||||
"Root element not found. Did you forget to add it to your index.html? Or maybe the id attribute got misspelled?",
|
||||
);
|
||||
}
|
||||
|
||||
render(
|
||||
() => (
|
||||
<Router root={App}>
|
||||
<Route path="/about" component={About} />
|
||||
<Route path="/" component={Switcher} />
|
||||
</Router>
|
||||
),
|
||||
root!,
|
||||
);
|
3
palette-switcher-v2/src/lib/algorithm.ts
Normal file
3
palette-switcher-v2/src/lib/algorithm.ts
Normal file
@ -0,0 +1,3 @@
|
||||
import { BaseJob } from "./job"
|
||||
|
||||
type Algorithm = typeof BaseJob.kind;
|
18
palette-switcher-v2/src/lib/ditherer.ts
Normal file
18
palette-switcher-v2/src/lib/ditherer.ts
Normal file
@ -0,0 +1,18 @@
|
||||
import { createSignal } from "solid-js";
|
||||
import { createSignaledWorker } from "@solid-primitives/workers";
|
||||
import { Job } from "./job";
|
||||
|
||||
const [job, setJob] = createSignal<Job>();
|
||||
const [image, setImage] = createSignal<string>();
|
||||
|
||||
const [start, stop] = createSignaledWorker({
|
||||
input: job,
|
||||
output: setImage,
|
||||
func: function process(job: Job) {
|
||||
console.log("Job triggered");
|
||||
|
||||
return job.kind;
|
||||
},
|
||||
});
|
||||
|
||||
export { setJob, image };
|
35
palette-switcher-v2/src/lib/job.ts
Normal file
35
palette-switcher-v2/src/lib/job.ts
Normal file
@ -0,0 +1,35 @@
|
||||
type Color = string;
|
||||
|
||||
export enum Algorithm {
|
||||
FLOYD_STEINBERG = "FLOYD_STEINBERG",
|
||||
BAYER = "BAYER",
|
||||
PIXEL_MAPPER = "PIXEL_MAPPER"
|
||||
};
|
||||
|
||||
type AlgorithmName = {
|
||||
[T in Algorithm]: {
|
||||
[Algorithm.FLOYD_STEINBERG]: "Floyd-Steinberg",
|
||||
[Algorithm.BAYER]: "Bayer",
|
||||
[Algorithm.PIXEL_MAPPER]: "Pixel Mapper"
|
||||
}[T]
|
||||
}
|
||||
|
||||
interface BaseJob {
|
||||
kind: Algorithm;
|
||||
image: ArrayBuffer;
|
||||
palette: Color[];
|
||||
}
|
||||
|
||||
interface FloydSteinberg extends BaseJob {
|
||||
kind: Algorithm.FLOYD_STEINBERG;
|
||||
}
|
||||
|
||||
interface Bayer extends BaseJob {
|
||||
kind: Algorithm.BAYER;
|
||||
}
|
||||
|
||||
interface PixelMapper extends BaseJob {
|
||||
kind: Algorithm.PIXEL_MAPPER;
|
||||
}
|
||||
|
||||
export type Job = FloydSteinberg | Bayer | PixelMapper;
|
48
palette-switcher-v2/src/pages/About.tsx
Normal file
48
palette-switcher-v2/src/pages/About.tsx
Normal file
@ -0,0 +1,48 @@
|
||||
import { Component, ParentComponent } from "solid-js";
|
||||
import { faQuestionCircle } from "@fortawesome/free-solid-svg-icons";
|
||||
import Fa from "solid-fa";
|
||||
|
||||
const AboutItemHeader: ParentComponent = (props) => (
|
||||
<h3 class="flex items-center mb-4 text-lg font-medium text-gray-900 dark:text-white">
|
||||
<Fa
|
||||
class="flex-shrink-0 mr-2 w-5 h-5 text-gray-500 dark:text-gray-400"
|
||||
icon={faQuestionCircle}
|
||||
/>
|
||||
{props.children}
|
||||
</h3>
|
||||
);
|
||||
|
||||
const AboutItemParagraph: ParentComponent = (props) => (
|
||||
<p class="text-gray-500 dark:text-gray-400">{props.children}</p>
|
||||
);
|
||||
|
||||
const AboutItem: ParentComponent = (props) => (
|
||||
<div class="mb-10">{props.children}</div>
|
||||
);
|
||||
|
||||
const About: Component = () => (
|
||||
<section class="bg-white dark:bg-gray-900">
|
||||
<div class="py-8 px-4 mx-auto max-w-screen-xl sm:py-16 lg:px-6">
|
||||
<h2 class="mb-8 text-4xl tracking-tight font-extrabold text-gray-900 dark:text-white">
|
||||
About Palette Switcher
|
||||
</h2>
|
||||
<div class="grid pt-8 text-left border-t border-gray-200 md:gap-16 dark:border-gray-700 md:grid-cols-2">
|
||||
<div>
|
||||
<AboutItem>
|
||||
<AboutItemHeader>How ?</AboutItemHeader>
|
||||
<AboutItemParagraph>Because.</AboutItemParagraph>
|
||||
<AboutItemParagraph>Because, also.</AboutItemParagraph>
|
||||
</AboutItem>
|
||||
</div>
|
||||
<div>
|
||||
<AboutItem>
|
||||
<AboutItemHeader>Why ?</AboutItemHeader>
|
||||
<AboutItemParagraph>Because, in another card.</AboutItemParagraph>
|
||||
</AboutItem>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
);
|
||||
|
||||
export default About;
|
57
palette-switcher-v2/src/pages/Switcher/Switcher.tsx
Normal file
57
palette-switcher-v2/src/pages/Switcher/Switcher.tsx
Normal file
@ -0,0 +1,57 @@
|
||||
import { Component, For, JSX, createSignal, splitProps } from "solid-js";
|
||||
import { image, setJob } from "../../lib/ditherer";
|
||||
import { Algorithm, AlgorithmName } from "../../lib/job";
|
||||
|
||||
|
||||
const Switcher: Component = () => {
|
||||
const handler = () => {
|
||||
setJob({
|
||||
kind: Algorithm.FLOYD_STEINBERG,
|
||||
image: new ArrayBuffer(1),
|
||||
palette: ["FFFFFF"],
|
||||
});
|
||||
};
|
||||
|
||||
const [algorithms, setAlgorithms] = createSignal(Object.keys(Algorithm));
|
||||
|
||||
return (
|
||||
<div class="mx-auto max-w-7xl py-6 sm:px-6 lg:px-8">
|
||||
<main class="p-4 h-auto">
|
||||
<div class="grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-4 gap-4 mb-4">
|
||||
<div class="border-2 border-dashed rounded-lg border-gray-300 dark:border-gray-600 h-32 md:h-64 lg:col-span-3">
|
||||
<span>Image Goes Here</span>
|
||||
</div>
|
||||
<div class="rounded-lg">
|
||||
<section class="bg-white dark:bg-gray-900">
|
||||
<div class="p-4 mx-auto max-w-2xl">
|
||||
<h2 class="mb-4 text-xl font-bold text-gray-900 dark:text-white">Configuration</h2>
|
||||
<form action="#">
|
||||
<div class="grid gap-4 sm:grid-cols-2 sm:gap-6">
|
||||
<div>
|
||||
<label for="category" class="block mb-2 text-sm font-medium text-gray-900 dark:text-white">Algorithm</label>
|
||||
<select id="category" class="bg-gray-50 border border-gray-300 text-gray-900 text-sm rounded-lg focus:ring-primary-500 focus:border-primary-500 block w-full p-2.5 dark:bg-gray-700 dark:border-gray-600 dark:placeholder-gray-400 dark:text-white dark:focus:ring-primary-500 dark:focus:border-primary-500">
|
||||
<option >Select Algorithm</option>
|
||||
<For each={algorithms()}>{(algo, _) => <option value={algo}>{AlgorithmName[algo]}</option>}</For>
|
||||
<option value="FS">Floyd-Steinberg</option>
|
||||
<option value="NC">Nearest color</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<button type="submit"
|
||||
class="text-white bg-blue-700 hover:bg-blue-800 focus:ring-4 focus:ring-blue-300 font-medium rounded-lg text-sm px-5 py-2.5 me-2 mb-2 mt-4 dark:bg-blue-600 dark:hover:bg-blue-700 focus:outline-none dark:focus:ring-blue-800"
|
||||
>
|
||||
Start processing
|
||||
</button>
|
||||
</form>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
|
||||
<span>{image()}</span>
|
||||
</div >
|
||||
);
|
||||
};
|
||||
|
||||
export default Switcher;
|
8
palette-switcher-v2/tailwind.config.js
Normal file
8
palette-switcher-v2/tailwind.config.js
Normal file
@ -0,0 +1,8 @@
|
||||
/** @type {import('tailwindcss').Config} */
|
||||
module.exports = {
|
||||
content: ["./src/**/*.{js,jsx,ts,tsx}", "./node_modules/flowbite/**/*.js"],
|
||||
theme: {
|
||||
extend: {},
|
||||
},
|
||||
plugins: [require("flowbite/plugin")],
|
||||
};
|
16
palette-switcher-v2/tsconfig.json
Normal file
16
palette-switcher-v2/tsconfig.json
Normal file
@ -0,0 +1,16 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
"allowJs": true,
|
||||
"strict": true,
|
||||
"target": "ESNext",
|
||||
"module": "ESNext",
|
||||
"moduleResolution": "node",
|
||||
"allowSyntheticDefaultImports": true,
|
||||
"esModuleInterop": true,
|
||||
"jsx": "preserve",
|
||||
"jsxImportSource": "solid-js",
|
||||
"types": ["vite/client"],
|
||||
"noEmit": true,
|
||||
"isolatedModules": true
|
||||
}
|
||||
}
|
27
palette-switcher-v2/vite.config.ts
Normal file
27
palette-switcher-v2/vite.config.ts
Normal file
@ -0,0 +1,27 @@
|
||||
import { defineConfig } from "vite";
|
||||
import solidPlugin from "vite-plugin-solid";
|
||||
import wasm from "vite-plugin-wasm";
|
||||
// import devtools from 'solid-devtools/vite';
|
||||
|
||||
export default defineConfig({
|
||||
plugins: [
|
||||
/*
|
||||
Uncomment the following line to enable solid-devtools.
|
||||
For more info see https://github.com/thetarnav/solid-devtools/tree/main/packages/extension#readme
|
||||
*/
|
||||
// devtools(),
|
||||
solidPlugin(),
|
||||
wasm(),
|
||||
],
|
||||
server: {
|
||||
port: 3000,
|
||||
},
|
||||
build: {
|
||||
target: "esnext",
|
||||
},
|
||||
worker: {
|
||||
// Not needed with vite-plugin-top-level-await >= 1.3.0
|
||||
// format: "es",
|
||||
plugins: [wasm()],
|
||||
},
|
||||
});
|
Loading…
Reference in New Issue
Block a user