diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml
index c6c8985..9c5b40b 100644
--- a/.github/workflows/build.yaml
+++ b/.github/workflows/build.yaml
@@ -31,9 +31,16 @@ jobs:
- rust
- rustjswasm
- cppjswasm
+ - uitk-svelte
+ - uitk-webawesome
os:
- ubuntu-latest
- macos-latest
+ exclude:
+ - template: uitk-svelte
+ os: macos-latest
+ - template: uitk-webawesome
+ os: macos-latest
runs-on: ${{ matrix.os }}
steps:
- name: Checkout
@@ -79,7 +86,7 @@ jobs:
version: 22.x
pnpm_version: 11.11.0
js_folder: "."
- if: matrix.template == 'js' || matrix.template == 'jupyter' || matrix.template == 'cppjswasm' || matrix.template == 'rustjswasm'
+ if: matrix.template == 'js' || matrix.template == 'jupyter' || matrix.template == 'cppjswasm' || matrix.template == 'rustjswasm' || matrix.template == 'uitk-svelte' || matrix.template == 'uitk-webawesome'
- name: Setup Rust
uses: actions-ext/rust/setup@2db8e3e4c56beb7320c7d730bd2c2d6a6447bf6b
@@ -93,7 +100,15 @@ jobs:
run: cargo build
if: matrix.template == 'rust' || matrix.template == 'rustjswasm'
- - name: Generate and test template
+ - name: Generate template
+ run: make gen-${{ matrix.template }}
+
+ - name: Install UI toolkit dependencies and browser
run: |
- make gen-${{ matrix.template }}
- make test-${{ matrix.template }}
+ cd ../javascript-template-${{ matrix.template }}
+ pnpm install
+ pnpm exec playwright install --with-deps chromium
+ if: matrix.template == 'uitk-svelte' || matrix.template == 'uitk-webawesome'
+
+ - name: Test template
+ run: make test-${{ matrix.template }}
diff --git a/Makefile b/Makefile
index 61bc10c..9efcfd3 100644
--- a/Makefile
+++ b/Makefile
@@ -24,7 +24,7 @@ fix: ## fix formatting in this repo
format: fix
test: ## run tests for this repo
-.PHONY: gen-python gen-cpp gen-js gen-jupyter gen-rust gen-rustjswasm
+.PHONY: gen-python gen-cpp gen-js gen-jupyter gen-rust gen-rustjswasm gen-cppjswasm gen-uitk-svelte gen-uitk-webawesome
gen-python: ## regenerate the python template from scratch
mkdir -p ../python-template && cd ../python-template && rm -rf ./* && rm -rf .copier-answers.yaml .gitignore .github .gitattributes
copier copy -w . ../python-template --data-file examples/python.yaml
@@ -60,7 +60,15 @@ gen-cppjswasm: ## regenerate the cppjswasm template from scratch
copier copy -w . ../python-template-cppjswasm --data-file examples/cppjswasm.yaml
cd ../python-template-cppjswasm && $(SED) 's#_src_path: .#_src_path: https://github.com/python-project-templates/base.git#g' ./.copier-answers.yaml
-.PHONY: test-python test-cpp test-js test-jupyter test-rust test-rustjswasm
+gen-uitk-svelte: ## regenerate the Svelte UI toolkit template from scratch
+ mkdir -p ../javascript-template-uitk-svelte && cd ../javascript-template-uitk-svelte && rm -rf ./* && rm -rf .copier-answers.yaml .github .gitignore .prettierignore .prettierrc
+ copier copy -w . ../javascript-template-uitk-svelte --data-file examples/uitk-svelte.yaml
+
+gen-uitk-webawesome: ## regenerate the Lit and Web Awesome UI toolkit template from scratch
+ mkdir -p ../javascript-template-uitk-webawesome && cd ../javascript-template-uitk-webawesome && rm -rf ./* && rm -rf .copier-answers.yaml .github .gitignore .prettierignore .prettierrc
+ copier copy -w . ../javascript-template-uitk-webawesome --data-file examples/uitk-webawesome.yaml
+
+.PHONY: test-python test-cpp test-js test-jupyter test-rust test-rustjswasm test-cppjswasm test-uitk-svelte test-uitk-webawesome
test-python:
cd ../python-template && git config --global user.name "github-actions" && git config --global user.email "41898282+github-actions[bot]@users.noreply.github.c@example.com" && git init && git add . && git commit -m "initial commit"
cd ../python-template && make develop
@@ -115,3 +123,21 @@ test-cppjswasm:
cd ../python-template-cppjswasm && make lint
cd ../python-template-cppjswasm && make checks
cd ../python-template-cppjswasm && make test
+
+test-uitk-svelte:
+ cd ../javascript-template-uitk-svelte && pnpm install
+ cd ../javascript-template-uitk-svelte && pnpm exec playwright install chromium
+ cd ../javascript-template-uitk-svelte && pnpm lint
+ cd ../javascript-template-uitk-svelte && pnpm check
+ cd ../javascript-template-uitk-svelte && pnpm build
+ cd ../javascript-template-uitk-svelte && pnpm test:unit
+ cd ../javascript-template-uitk-svelte && CI=1 pnpm test:e2e
+
+test-uitk-webawesome:
+ cd ../javascript-template-uitk-webawesome && pnpm install
+ cd ../javascript-template-uitk-webawesome && pnpm exec playwright install chromium
+ cd ../javascript-template-uitk-webawesome && pnpm lint
+ cd ../javascript-template-uitk-webawesome && pnpm check
+ cd ../javascript-template-uitk-webawesome && pnpm build
+ cd ../javascript-template-uitk-webawesome && pnpm test:unit
+ cd ../javascript-template-uitk-webawesome && CI=1 pnpm test:e2e
diff --git a/README.md b/README.md
index ced99cf..1735885 100644
--- a/README.md
+++ b/README.md
@@ -1,6 +1,6 @@
-# Python Project Template Base
+# Project Template Base
-This project uses [copier](https://copier.readthedocs.io/en/stable/) to provide several python project templates. See our [homepage](https://github.com/python-project-templates) for more information!
+This project uses [copier](https://copier.readthedocs.io/en/stable/) to provide Python and JavaScript project templates. See our [homepage](https://github.com/python-project-templates) for more information.
[](https://github.com/python-project-templates)
[](https://copier.readthedocs.io/en/stable/)
@@ -13,3 +13,9 @@ copier copy https://github.com/python-project-templates/base.git path/to/new/pro
> [!NOTE]
> Install the [Python Templates Copier Update GitHub App](https://github.com/apps/python-templates-copier-update) on repositories generated from this template to receive weekly template update pull requests.
+
+One selector chooses a template:
+
+- `Python / …` options generate pure Python, C++, JavaScript, Jupyter, Rust, and WebAssembly-backed Python packages from `python/`.
+- `JavaScript / UI Toolkit / Svelte` generates a Svelte package and showcase from `javascript/uitk-svelte/`.
+- `JavaScript / UI Toolkit / Lit + Web Awesome` generates custom elements and a showcase from `javascript/uitk-webawesome/`.
diff --git a/copier.yaml b/copier.yaml
index 16f9151..045d39f 100644
--- a/copier.yaml
+++ b/copier.yaml
@@ -29,30 +29,37 @@ github:
team:
type: str
help: What is your name or your team's name?
+ when: "{{ add_extension not in ['uitk-svelte', 'uitk-webawesome'] }}"
email:
type: str
help: What is your email?
+ when: "{{ add_extension not in ['uitk-svelte', 'uitk-webawesome'] }}"
add_extension:
type: str
+ help: Which project template should Copier use?
choices:
- none:
+ Python / Pure:
value: python
- "C++":
+ Python / C++:
value: cpp
- JavaScript:
+ Python / JavaScript:
value: js
- Rust:
+ Python / Rust:
value: rust
- Jupyter Widget:
+ Python / Jupyter Widget:
value: jupyter
- Rust JavaScript WebAssembly:
+ Python / Rust + JavaScript + WebAssembly:
value: rustjswasm
- "C++ JavaScript WebAssembly":
+ Python / C++ + JavaScript + WebAssembly:
value: cppjswasm
+ JavaScript / UI Toolkit / Svelte:
+ value: uitk-svelte
+ JavaScript / UI Toolkit / Lit + Web Awesome:
+ value: uitk-webawesome
-_subdirectory: "{{ add_extension }}"
+_subdirectory: "{% if add_extension == 'python' %}python/pure{% elif add_extension in ['uitk-svelte', 'uitk-webawesome'] %}javascript/{{ add_extension }}{% else %}python/{{ add_extension }}{% endif %}"
add_vcpkg:
type: bool
@@ -73,13 +80,40 @@ python_version_primary:
"3.13":
value: "3.13"
help: Primary version of Python to use in CI/CD
+ when: "{{ add_extension not in ['uitk-svelte', 'uitk-webawesome'] }}"
add_docs:
type: bool
default: false
help: Add documentation using Yardang/Sphinx
+ when: "{{ add_extension not in ['uitk-svelte', 'uitk-webawesome'] }}"
add_wiki:
type: bool
default: false
help: Add documentation using GitHub wiki
+ when: "{{ add_extension not in ['uitk-svelte', 'uitk-webawesome'] }}"
+
+package_name:
+ type: str
+ help: What is the npm package name?
+ default: "@example/branding"
+ when: "{{ add_extension in ['uitk-svelte', 'uitk-webawesome'] }}"
+
+brand_name:
+ type: str
+ help: What is the human-readable brand name?
+ default: "{{ project_name }}"
+ when: "{{ add_extension in ['uitk-svelte', 'uitk-webawesome'] }}"
+
+css_prefix:
+ type: str
+ help: What prefix should global CSS custom properties use?
+ default: brand
+ when: "{{ add_extension in ['uitk-svelte', 'uitk-webawesome'] }}"
+
+element_prefix:
+ type: str
+ help: What prefix should custom elements use?
+ default: brand
+ when: "{{ add_extension == 'uitk-webawesome' }}"
diff --git a/examples/uitk-svelte.yaml b/examples/uitk-svelte.yaml
new file mode 100644
index 0000000..1c266be
--- /dev/null
+++ b/examples/uitk-svelte.yaml
@@ -0,0 +1,8 @@
+---
+add_extension: uitk-svelte
+brand_name: Example
+css_prefix: example
+github: example
+package_name: '@example/branding'
+project_description: Shared brand identity, design tokens, and reusable Svelte components.
+project_name: example-branding
diff --git a/examples/uitk-webawesome.yaml b/examples/uitk-webawesome.yaml
new file mode 100644
index 0000000..15afff5
--- /dev/null
+++ b/examples/uitk-webawesome.yaml
@@ -0,0 +1,9 @@
+---
+add_extension: uitk-webawesome
+brand_name: Example
+css_prefix: example
+element_prefix: example
+github: example
+package_name: '@example/branding'
+project_description: Shared brand identity, design tokens, and reusable Lit and Web Awesome components.
+project_name: example-branding
diff --git a/javascript/uitk-svelte/.github/workflows/build.yml.jinja b/javascript/uitk-svelte/.github/workflows/build.yml.jinja
new file mode 100644
index 0000000..938a559
--- /dev/null
+++ b/javascript/uitk-svelte/.github/workflows/build.yml.jinja
@@ -0,0 +1,33 @@
+name: Build Status
+
+on:
+ push:
+ branches: [main]
+ tags: [v*]
+ pull_request:
+ workflow_dispatch:
+
+permissions:
+ contents: read
+
+jobs:
+ build:
+ runs-on: ubuntu-latest
+ steps:
+ - uses: actions/checkout@v7
+ - uses: pnpm/action-setup@v6
+ with:
+ version: 11
+ - uses: actions/setup-node@v7
+ with:
+ node-version: 22.x
+ cache: pnpm
+ - run: pnpm install
+ - run: pnpm build
+ - run: pnpm check
+ - run: pnpm lint
+ - run: pnpm test:unit
+ - run: pnpm exec playwright install --with-deps chromium
+ - run: pnpm test:e2e
+ env:
+ CI: '1'
diff --git a/javascript/uitk-svelte/.gitignore.jinja b/javascript/uitk-svelte/.gitignore.jinja
new file mode 100644
index 0000000..f2d0bc3
--- /dev/null
+++ b/javascript/uitk-svelte/.gitignore.jinja
@@ -0,0 +1,8 @@
+node_modules
+/dist
+/.svelte-kit
+/build
+/coverage
+/playwright-report
+/test-results
+.DS_Store
diff --git a/javascript/uitk-svelte/.prettierignore.jinja b/javascript/uitk-svelte/.prettierignore.jinja
new file mode 100644
index 0000000..4e6c2de
--- /dev/null
+++ b/javascript/uitk-svelte/.prettierignore.jinja
@@ -0,0 +1,9 @@
+.copier-answers.yaml
+node_modules
+dist
+pnpm-lock.yaml
+.svelte-kit
+build
+coverage
+playwright-report
+test-results
diff --git a/javascript/uitk-svelte/.prettierrc.jinja b/javascript/uitk-svelte/.prettierrc.jinja
new file mode 100644
index 0000000..6b53085
--- /dev/null
+++ b/javascript/uitk-svelte/.prettierrc.jinja
@@ -0,0 +1,9 @@
+{
+ "printWidth": 120,
+ "semi": true,
+ "singleQuote": true,
+ "tabWidth": 2,
+ "trailingComma": "none",
+ "plugins": ["prettier-plugin-svelte"],
+ "overrides": [{ "files": "*.svelte", "options": { "parser": "svelte" } }]
+}
diff --git a/javascript/uitk-svelte/BRAND.md.jinja b/javascript/uitk-svelte/BRAND.md.jinja
new file mode 100644
index 0000000..a7a0058
--- /dev/null
+++ b/javascript/uitk-svelte/BRAND.md.jinja
@@ -0,0 +1,37 @@
+# {{ brand_name }} Brand Guide
+
+Canonical source for the {{ brand_name }} identity. Replace each placeholder before publishing the first consumer.
+
+## Identity
+
+Describe what {{ brand_name }} is, who it serves, and what it must not be confused with.
+
+## Mark
+
+Document primary mark, clear space, minimum size, and approved variants.
+
+## Color
+
+| Role | Light | Dark | Usage |
+| ------ | --------- | --------- | ------------------ |
+| Paper | `#f5f5f0` | `#151515` | Page surfaces |
+| Ink | `#151515` | `#f5f5f0` | Primary content |
+| Muted | `#666660` | `#aaa9a0` | Supporting content |
+| Line | `#d0d0c8` | `#3a3a36` | Borders and rules |
+| Accent | `#6cff8f` | `#6cff8f` | Focus and emphasis |
+
+## Typography
+
+Document font families, weights, scale, tracking, and fallback behavior.
+
+## Composition
+
+Document spacing, layout, shape, imagery, and data-visualization rules.
+
+## Motion
+
+Document purposeful transitions and reduced-motion behavior.
+
+## Voice
+
+Document preferred vocabulary, sentence style, capitalization, and examples.
diff --git a/javascript/uitk-svelte/README.md.jinja b/javascript/uitk-svelte/README.md.jinja
new file mode 100644
index 0000000..71615b6
--- /dev/null
+++ b/javascript/uitk-svelte/README.md.jinja
@@ -0,0 +1,40 @@
+# {{ package_name }}
+
+{{ project_description }}
+
+See [`BRAND.md`](./BRAND.md) for the canonical brand guide.
+
+## Install
+
+```bash
+pnpm add {{ package_name }}
+```
+
+Import design tokens once at the application root:
+
+```css
+@import '{{ package_name }}/tokens.css';
+```
+
+```svelte
+
+
+
+
+```
+
+## Develop
+
+```bash
+pnpm install
+pnpm dev
+pnpm check
+pnpm lint
+pnpm fix
+pnpm test
+pnpm build
+```
+
+After customizing the showcase, run `pnpm test:e2e:update` once to establish its visual baseline.
diff --git a/javascript/uitk-svelte/package.json.jinja b/javascript/uitk-svelte/package.json.jinja
new file mode 100644
index 0000000..a187ed6
--- /dev/null
+++ b/javascript/uitk-svelte/package.json.jinja
@@ -0,0 +1,65 @@
+{
+ "name": "{{ package_name }}",
+ "version": "0.1.0",
+ "description": "{{ project_description }}",
+ "license": "Apache-2.0",
+ "private": true,
+ "packageManager": "pnpm@11.9.0",
+ "engines": {
+ "node": ">=22"
+ },
+ "type": "module",
+ "files": [
+ "dist",
+ "!dist/**/*.test.*",
+ "!dist/**/*.spec.*"
+ ],
+ "svelte": "./dist/index.js",
+ "types": "./dist/index.d.ts",
+ "exports": {
+ ".": {
+ "types": "./dist/index.d.ts",
+ "svelte": "./dist/index.js",
+ "default": "./dist/index.js"
+ },
+ "./tokens.css": "./dist/styles/tokens.css",
+ "./package.json": "./package.json"
+ },
+ "sideEffects": [
+ "**/*.css"
+ ],
+ "scripts": {
+ "dev": "vite dev",
+ "build": "svelte-kit sync && svelte-package && publint",
+ "prepare": "svelte-kit sync",
+ "check": "svelte-kit sync && svelte-check --tsconfig ./tsconfig.json",
+ "preview": "vite preview",
+ "lint": "prettier --check .",
+ "fix": "prettier --write .",
+ "test": "pnpm test:unit && pnpm test:e2e",
+ "test:unit": "vitest run",
+ "test:e2e": "playwright test",
+ "test:e2e:update": "playwright test --update-snapshots"
+ },
+ "peerDependencies": {
+ "svelte": "^5.0.0"
+ },
+ "devDependencies": {
+ "@axe-core/playwright": "^4.12.1",
+ "@playwright/test": "^1.60.0",
+ "@sveltejs/adapter-static": "^3.0.10",
+ "@sveltejs/kit": "^2.70.1",
+ "@sveltejs/package": "^2.5.5",
+ "@sveltejs/vite-plugin-svelte": "^7.1.2",
+ "@types/node": "^24.0.0",
+ "jsdom": "^29.0.0",
+ "prettier": "^3.8.4",
+ "prettier-plugin-svelte": "^4.1.1",
+ "publint": "^0.3.21",
+ "svelte": "^5.56.0",
+ "svelte-check": "^4.3.0",
+ "typescript": "^5.9.3",
+ "vite": "^8.1.5",
+ "vitest": "^4.1.8"
+ }
+}
diff --git a/javascript/uitk-svelte/playwright.config.ts.jinja b/javascript/uitk-svelte/playwright.config.ts.jinja
new file mode 100644
index 0000000..f09c961
--- /dev/null
+++ b/javascript/uitk-svelte/playwright.config.ts.jinja
@@ -0,0 +1,28 @@
+import { defineConfig, devices } from '@playwright/test';
+
+export default defineConfig({
+ testDir: 'tests',
+ testIgnore: process.env.CI ? ['**/visual/**'] : [],
+ snapshotPathTemplate: '{testDir}/{testFilePath}-snapshots/{arg}-{projectName}{ext}',
+ fullyParallel: true,
+ forbidOnly: !!process.env.CI,
+ retries: process.env.CI ? 2 : 0,
+ reporter: process.env.CI ? 'github' : 'list',
+ use: {
+ baseURL: 'http://127.0.0.1:4177',
+ trace: 'retain-on-failure',
+ screenshot: 'only-on-failure'
+ },
+ webServer: {
+ command: 'vite build && vite preview --host 127.0.0.1 --port 4177 --strictPort',
+ port: 4177,
+ reuseExistingServer: !process.env.CI,
+ timeout: 120_000
+ },
+ projects: [
+ {
+ name: 'desktop',
+ use: { ...devices['Desktop Chrome'], viewport: { width: 1280, height: 800 } }
+ }
+ ]
+});
diff --git a/javascript/uitk-svelte/src/app.d.ts.jinja b/javascript/uitk-svelte/src/app.d.ts.jinja
new file mode 100644
index 0000000..a6911e5
--- /dev/null
+++ b/javascript/uitk-svelte/src/app.d.ts.jinja
@@ -0,0 +1,5 @@
+declare global {
+ namespace App {}
+}
+
+export {};
diff --git a/javascript/uitk-svelte/src/app.html.jinja b/javascript/uitk-svelte/src/app.html.jinja
new file mode 100644
index 0000000..4f8e04a
--- /dev/null
+++ b/javascript/uitk-svelte/src/app.html.jinja
@@ -0,0 +1,23 @@
+
+
+
+
+
+
+ %sveltekit.head%
+
+
+ %sveltekit.body%
+
+
diff --git a/javascript/uitk-svelte/src/lib/components/BrandMark.svelte.jinja b/javascript/uitk-svelte/src/lib/components/BrandMark.svelte.jinja
new file mode 100644
index 0000000..55e5c54
--- /dev/null
+++ b/javascript/uitk-svelte/src/lib/components/BrandMark.svelte.jinja
@@ -0,0 +1,31 @@
+
+
+{{ brand_name[0] | upper }}{{ brand_name }}
+
+
diff --git a/javascript/uitk-svelte/src/lib/components/ThemeToggle.svelte.jinja b/javascript/uitk-svelte/src/lib/components/ThemeToggle.svelte.jinja
new file mode 100644
index 0000000..07aaf24
--- /dev/null
+++ b/javascript/uitk-svelte/src/lib/components/ThemeToggle.svelte.jinja
@@ -0,0 +1,28 @@
+
+
+
+
+
diff --git a/javascript/uitk-svelte/src/lib/index.ts.jinja b/javascript/uitk-svelte/src/lib/index.ts.jinja
new file mode 100644
index 0000000..dbcb124
--- /dev/null
+++ b/javascript/uitk-svelte/src/lib/index.ts.jinja
@@ -0,0 +1,12 @@
+export {
+ getTheme,
+ resolveTheme,
+ applyTheme,
+ setTheme,
+ toggleTheme,
+ initTheme,
+ type Theme,
+ type ResolvedTheme
+} from './theme.js';
+export { default as BrandMark } from './components/BrandMark.svelte';
+export { default as ThemeToggle } from './components/ThemeToggle.svelte';
diff --git a/javascript/uitk-svelte/src/lib/styles/tokens.css.jinja b/javascript/uitk-svelte/src/lib/styles/tokens.css.jinja
new file mode 100644
index 0000000..ad77451
--- /dev/null
+++ b/javascript/uitk-svelte/src/lib/styles/tokens.css.jinja
@@ -0,0 +1,34 @@
+:root {
+ --{{ css_prefix }}-color-paper: #f5f5f0;
+ --{{ css_prefix }}-color-ink: #151515;
+ --{{ css_prefix }}-color-muted: #666660;
+ --{{ css_prefix }}-color-line: #d0d0c8;
+ --{{ css_prefix }}-color-accent: #6cff8f;
+ --{{ css_prefix }}-font-sans: ui-sans-serif, system-ui, sans-serif;
+ --{{ css_prefix }}-font-mono: ui-monospace, monospace;
+ color-scheme: light;
+}
+
+:root[data-theme='dark'] {
+ --{{ css_prefix }}-color-paper: #151515;
+ --{{ css_prefix }}-color-ink: #f5f5f0;
+ --{{ css_prefix }}-color-muted: #aaa9a0;
+ --{{ css_prefix }}-color-line: #3a3a36;
+ color-scheme: dark;
+}
+
+:root {
+ color: var(--{{ css_prefix }}-color-ink);
+ font-family: var(--{{ css_prefix }}-font-sans);
+ background: var(--{{ css_prefix }}-color-paper);
+}
+
+body {
+ margin: 0;
+}
+
+button:focus-visible,
+a:focus-visible {
+ outline: 2px solid var(--{{ css_prefix }}-color-accent);
+ outline-offset: 4px;
+}
diff --git a/javascript/uitk-svelte/src/lib/theme.test.ts.jinja b/javascript/uitk-svelte/src/lib/theme.test.ts.jinja
new file mode 100644
index 0000000..1a4e513
--- /dev/null
+++ b/javascript/uitk-svelte/src/lib/theme.test.ts.jinja
@@ -0,0 +1,17 @@
+import { beforeEach, describe, expect, it } from 'vitest';
+import { getTheme, setTheme, toggleTheme } from './theme.js';
+
+beforeEach(() => localStorage.clear());
+
+describe('theme', () => {
+ it('persists an explicit choice', () => {
+ setTheme('dark');
+ expect(getTheme()).toBe('dark');
+ expect(document.documentElement.dataset.theme).toBe('dark');
+ });
+
+ it('toggles the resolved choice', () => {
+ setTheme('dark');
+ expect(toggleTheme()).toBe('light');
+ });
+});
diff --git a/javascript/uitk-svelte/src/lib/theme.ts.jinja b/javascript/uitk-svelte/src/lib/theme.ts.jinja
new file mode 100644
index 0000000..509c8d5
--- /dev/null
+++ b/javascript/uitk-svelte/src/lib/theme.ts.jinja
@@ -0,0 +1,36 @@
+export type Theme = 'dark' | 'light' | 'system';
+export type ResolvedTheme = Exclude;
+
+export const THEME_STORAGE_KEY = '{{ project_name }}.theme';
+
+export function resolveTheme(theme: Theme): ResolvedTheme {
+ if (theme !== 'system') return theme;
+ if (typeof window === 'undefined' || typeof window.matchMedia !== 'function') return 'light';
+ return window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light';
+}
+
+export function getTheme(): Theme {
+ if (typeof localStorage === 'undefined') return 'system';
+ const value = localStorage.getItem(THEME_STORAGE_KEY);
+ return value === 'light' || value === 'dark' ? value : 'system';
+}
+
+export function applyTheme(theme: Theme): ResolvedTheme {
+ const resolved = resolveTheme(theme);
+ if (typeof document !== 'undefined') document.documentElement.dataset.theme = resolved;
+ return resolved;
+}
+
+export function setTheme(theme: Theme): ResolvedTheme {
+ if (theme === 'system') localStorage.removeItem(THEME_STORAGE_KEY);
+ else localStorage.setItem(THEME_STORAGE_KEY, theme);
+ return applyTheme(theme);
+}
+
+export function toggleTheme(): ResolvedTheme {
+ return setTheme(resolveTheme(getTheme()) === 'dark' ? 'light' : 'dark');
+}
+
+export function initTheme(): ResolvedTheme {
+ return applyTheme(getTheme());
+}
diff --git a/javascript/uitk-svelte/src/routes/+layout.svelte.jinja b/javascript/uitk-svelte/src/routes/+layout.svelte.jinja
new file mode 100644
index 0000000..33df299
--- /dev/null
+++ b/javascript/uitk-svelte/src/routes/+layout.svelte.jinja
@@ -0,0 +1,6 @@
+
+
+{@render children()}
diff --git a/javascript/uitk-svelte/src/routes/+layout.ts.jinja b/javascript/uitk-svelte/src/routes/+layout.ts.jinja
new file mode 100644
index 0000000..189f71e
--- /dev/null
+++ b/javascript/uitk-svelte/src/routes/+layout.ts.jinja
@@ -0,0 +1 @@
+export const prerender = true;
diff --git a/javascript/uitk-svelte/src/routes/+page.svelte.jinja b/javascript/uitk-svelte/src/routes/+page.svelte.jinja
new file mode 100644
index 0000000..03333e7
--- /dev/null
+++ b/javascript/uitk-svelte/src/routes/+page.svelte.jinja
@@ -0,0 +1,36 @@
+
+
+{{ brand_name }} brand kit
+
+
+ Brand toolkit
+
+ {{ brand_name }}
+ {{ project_description }}
+
+
+
+
diff --git a/javascript/uitk-svelte/svelte.config.js.jinja b/javascript/uitk-svelte/svelte.config.js.jinja
new file mode 100644
index 0000000..d664bea
--- /dev/null
+++ b/javascript/uitk-svelte/svelte.config.js.jinja
@@ -0,0 +1,11 @@
+import adapter from '@sveltejs/adapter-static';
+
+/** @type {import('@sveltejs/kit').Config} */
+const config = {
+ kit: {
+ adapter: adapter({ fallback: '404.html' }),
+ prerender: { entries: ['*'] }
+ }
+};
+
+export default config;
diff --git a/javascript/uitk-svelte/tests/a11y/audit.spec.ts.jinja b/javascript/uitk-svelte/tests/a11y/audit.spec.ts.jinja
new file mode 100644
index 0000000..cc912a5
--- /dev/null
+++ b/javascript/uitk-svelte/tests/a11y/audit.spec.ts.jinja
@@ -0,0 +1,9 @@
+import AxeBuilder from '@axe-core/playwright';
+import { expect, test } from '@playwright/test';
+
+test('showcase has no serious or critical accessibility violations', async ({ page }) => {
+ await page.goto('/');
+ const results = await new AxeBuilder({ page }).withTags(['wcag2a', 'wcag2aa', 'wcag21a', 'wcag21aa']).analyze();
+ const violations = results.violations.filter((violation) => ['serious', 'critical'].includes(violation.impact ?? ''));
+ expect(violations).toEqual([]);
+});
diff --git a/javascript/uitk-svelte/tests/behavior/theme.spec.ts.jinja b/javascript/uitk-svelte/tests/behavior/theme.spec.ts.jinja
new file mode 100644
index 0000000..087d2e5
--- /dev/null
+++ b/javascript/uitk-svelte/tests/behavior/theme.spec.ts.jinja
@@ -0,0 +1,12 @@
+import { expect, test } from '@playwright/test';
+
+test('theme toggle persists the choice', async ({ page }) => {
+ await page.goto('/');
+ await page.evaluate(() => localStorage.removeItem('{{ project_name }}.theme'));
+ await page.reload();
+ const initial = await page.locator('html').getAttribute('data-theme');
+ await page.getByTestId('theme-toggle').click();
+ const expected = initial === 'dark' ? 'light' : 'dark';
+ await expect(page.locator('html')).toHaveAttribute('data-theme', expected);
+ expect(await page.evaluate(() => localStorage.getItem('{{ project_name }}.theme'))).toBe(expected);
+});
diff --git a/javascript/uitk-svelte/tests/visual/showcase.spec.ts.jinja b/javascript/uitk-svelte/tests/visual/showcase.spec.ts.jinja
new file mode 100644
index 0000000..5560ec3
--- /dev/null
+++ b/javascript/uitk-svelte/tests/visual/showcase.spec.ts.jinja
@@ -0,0 +1,6 @@
+import { expect, test } from '@playwright/test';
+
+test('showcase', async ({ page }) => {
+ await page.goto('/');
+ await expect(page).toHaveScreenshot('showcase.png', { fullPage: true });
+});
diff --git a/javascript/uitk-svelte/tsconfig.json.jinja b/javascript/uitk-svelte/tsconfig.json.jinja
new file mode 100644
index 0000000..4344710
--- /dev/null
+++ b/javascript/uitk-svelte/tsconfig.json.jinja
@@ -0,0 +1,14 @@
+{
+ "extends": "./.svelte-kit/tsconfig.json",
+ "compilerOptions": {
+ "allowJs": true,
+ "checkJs": true,
+ "esModuleInterop": true,
+ "forceConsistentCasingInFileNames": true,
+ "resolveJsonModule": true,
+ "skipLibCheck": true,
+ "sourceMap": true,
+ "strict": true,
+ "moduleResolution": "bundler"
+ }
+}
diff --git a/javascript/uitk-svelte/vite.config.ts.jinja b/javascript/uitk-svelte/vite.config.ts.jinja
new file mode 100644
index 0000000..1180a91
--- /dev/null
+++ b/javascript/uitk-svelte/vite.config.ts.jinja
@@ -0,0 +1,4 @@
+import { sveltekit } from '@sveltejs/kit/vite';
+import { defineConfig } from 'vite';
+
+export default defineConfig({ plugins: [sveltekit()] });
diff --git a/javascript/uitk-svelte/vitest.config.ts.jinja b/javascript/uitk-svelte/vitest.config.ts.jinja
new file mode 100644
index 0000000..a1bc41b
--- /dev/null
+++ b/javascript/uitk-svelte/vitest.config.ts.jinja
@@ -0,0 +1,9 @@
+import { defineConfig } from 'vitest/config';
+
+export default defineConfig({
+ test: {
+ include: ['src/**/*.test.ts'],
+ environment: 'jsdom',
+ setupFiles: ['./vitest.setup.ts']
+ }
+});
diff --git a/javascript/uitk-svelte/vitest.setup.ts.jinja b/javascript/uitk-svelte/vitest.setup.ts.jinja
new file mode 100644
index 0000000..0d50ddd
--- /dev/null
+++ b/javascript/uitk-svelte/vitest.setup.ts.jinja
@@ -0,0 +1,25 @@
+import { vi } from 'vitest';
+
+if (typeof globalThis.localStorage === 'undefined') {
+ const store = new Map();
+ globalThis.localStorage = {
+ getItem: (key: string) => store.get(key) ?? null,
+ setItem: (key: string, value: string) => void store.set(key, String(value)),
+ removeItem: (key: string) => void store.delete(key),
+ clear: () => store.clear(),
+ key: (index: number) => [...store.keys()][index] ?? null,
+ get length() {
+ return store.size;
+ }
+ } as Storage;
+}
+
+Object.defineProperty(window, 'matchMedia', {
+ writable: true,
+ value: vi.fn().mockImplementation((query: string) => ({
+ matches: false,
+ media: query,
+ addEventListener: vi.fn(),
+ removeEventListener: vi.fn()
+ }))
+});
diff --git a/javascript/uitk-svelte/{{_copier_conf.answers_file}}.jinja b/javascript/uitk-svelte/{{_copier_conf.answers_file}}.jinja
new file mode 100644
index 0000000..090c992
--- /dev/null
+++ b/javascript/uitk-svelte/{{_copier_conf.answers_file}}.jinja
@@ -0,0 +1,2 @@
+# Changes here will be overwritten by Copier
+{{ _copier_answers|to_nice_yaml }}
diff --git a/javascript/uitk-webawesome/.github/workflows/build.yml.jinja b/javascript/uitk-webawesome/.github/workflows/build.yml.jinja
new file mode 100644
index 0000000..938a559
--- /dev/null
+++ b/javascript/uitk-webawesome/.github/workflows/build.yml.jinja
@@ -0,0 +1,33 @@
+name: Build Status
+
+on:
+ push:
+ branches: [main]
+ tags: [v*]
+ pull_request:
+ workflow_dispatch:
+
+permissions:
+ contents: read
+
+jobs:
+ build:
+ runs-on: ubuntu-latest
+ steps:
+ - uses: actions/checkout@v7
+ - uses: pnpm/action-setup@v6
+ with:
+ version: 11
+ - uses: actions/setup-node@v7
+ with:
+ node-version: 22.x
+ cache: pnpm
+ - run: pnpm install
+ - run: pnpm build
+ - run: pnpm check
+ - run: pnpm lint
+ - run: pnpm test:unit
+ - run: pnpm exec playwright install --with-deps chromium
+ - run: pnpm test:e2e
+ env:
+ CI: '1'
diff --git a/javascript/uitk-webawesome/.gitignore.jinja b/javascript/uitk-webawesome/.gitignore.jinja
new file mode 100644
index 0000000..f2d0bc3
--- /dev/null
+++ b/javascript/uitk-webawesome/.gitignore.jinja
@@ -0,0 +1,8 @@
+node_modules
+/dist
+/.svelte-kit
+/build
+/coverage
+/playwright-report
+/test-results
+.DS_Store
diff --git a/javascript/uitk-webawesome/.prettierignore.jinja b/javascript/uitk-webawesome/.prettierignore.jinja
new file mode 100644
index 0000000..4e6c2de
--- /dev/null
+++ b/javascript/uitk-webawesome/.prettierignore.jinja
@@ -0,0 +1,9 @@
+.copier-answers.yaml
+node_modules
+dist
+pnpm-lock.yaml
+.svelte-kit
+build
+coverage
+playwright-report
+test-results
diff --git a/javascript/uitk-webawesome/.prettierrc.jinja b/javascript/uitk-webawesome/.prettierrc.jinja
new file mode 100644
index 0000000..5c4f4a6
--- /dev/null
+++ b/javascript/uitk-webawesome/.prettierrc.jinja
@@ -0,0 +1,9 @@
+{
+ "printWidth": 120,
+ "semi": true,
+ "singleQuote": true,
+ "tabWidth": 2,
+ "trailingComma": "none",
+ "plugins": [],
+ "overrides": []
+}
diff --git a/javascript/uitk-webawesome/BRAND.md.jinja b/javascript/uitk-webawesome/BRAND.md.jinja
new file mode 100644
index 0000000..a7a0058
--- /dev/null
+++ b/javascript/uitk-webawesome/BRAND.md.jinja
@@ -0,0 +1,37 @@
+# {{ brand_name }} Brand Guide
+
+Canonical source for the {{ brand_name }} identity. Replace each placeholder before publishing the first consumer.
+
+## Identity
+
+Describe what {{ brand_name }} is, who it serves, and what it must not be confused with.
+
+## Mark
+
+Document primary mark, clear space, minimum size, and approved variants.
+
+## Color
+
+| Role | Light | Dark | Usage |
+| ------ | --------- | --------- | ------------------ |
+| Paper | `#f5f5f0` | `#151515` | Page surfaces |
+| Ink | `#151515` | `#f5f5f0` | Primary content |
+| Muted | `#666660` | `#aaa9a0` | Supporting content |
+| Line | `#d0d0c8` | `#3a3a36` | Borders and rules |
+| Accent | `#6cff8f` | `#6cff8f` | Focus and emphasis |
+
+## Typography
+
+Document font families, weights, scale, tracking, and fallback behavior.
+
+## Composition
+
+Document spacing, layout, shape, imagery, and data-visualization rules.
+
+## Motion
+
+Document purposeful transitions and reduced-motion behavior.
+
+## Voice
+
+Document preferred vocabulary, sentence style, capitalization, and examples.
diff --git a/javascript/uitk-webawesome/README.md.jinja b/javascript/uitk-webawesome/README.md.jinja
new file mode 100644
index 0000000..965d988
--- /dev/null
+++ b/javascript/uitk-webawesome/README.md.jinja
@@ -0,0 +1,39 @@
+# {{ package_name }}
+
+{{ project_description }}
+
+See [`BRAND.md`](./BRAND.md) for the canonical brand guide.
+
+## Install
+
+```bash
+pnpm add {{ package_name }}
+```
+
+Import design tokens once at the application root:
+
+```css
+@import '{{ package_name }}/tokens.css';
+```
+
+```ts
+import '{{ package_name }}';
+```
+
+```html
+<{{ element_prefix }}-brand-mark>{{ element_prefix }}-brand-mark> <{{ element_prefix }}-theme-toggle>{{ element_prefix }}-theme-toggle>
+```
+
+## Develop
+
+```bash
+pnpm install
+pnpm dev
+pnpm check
+pnpm lint
+pnpm fix
+pnpm test
+pnpm build
+```
+
+After customizing the showcase, run `pnpm test:e2e:update` once to establish its visual baseline.
diff --git a/javascript/uitk-webawesome/index.html.jinja b/javascript/uitk-webawesome/index.html.jinja
new file mode 100644
index 0000000..2e9d947
--- /dev/null
+++ b/javascript/uitk-webawesome/index.html.jinja
@@ -0,0 +1,29 @@
+
+
+
+
+
+ {{ brand_name }} brand kit
+
+
+
+
+ Brand toolkit
+ <{{ element_prefix }}-brand-mark>{{ element_prefix }}-brand-mark>
+ {{ project_description }}
+ <{{ element_prefix }}-theme-toggle data-testid="theme-toggle">{{ element_prefix }}-theme-toggle>
+
+
+
+
diff --git a/javascript/uitk-webawesome/package.json.jinja b/javascript/uitk-webawesome/package.json.jinja
new file mode 100644
index 0000000..35ae98b
--- /dev/null
+++ b/javascript/uitk-webawesome/package.json.jinja
@@ -0,0 +1,59 @@
+{
+ "name": "{{ package_name }}",
+ "version": "0.1.0",
+ "description": "{{ project_description }}",
+ "license": "Apache-2.0",
+ "private": true,
+ "packageManager": "pnpm@11.9.0",
+ "engines": {
+ "node": ">=22"
+ },
+ "type": "module",
+ "files": [
+ "dist",
+ "!dist/**/*.test.*",
+ "!dist/**/*.spec.*"
+ ],
+ "types": "./dist/index.d.ts",
+ "exports": {
+ ".": {
+ "types": "./dist/index.d.ts",
+ "import": "./dist/index.js",
+ "default": "./dist/index.js"
+ },
+ "./tokens.css": "./dist/tokens.css",
+ "./package.json": "./package.json"
+ },
+ "sideEffects": [
+ "**/*.css"
+ ],
+ "scripts": {
+ "dev": "vite dev",
+ "build": "vite build && tsc -p tsconfig.build.json --emitDeclarationOnly && publint",
+ "check": "tsc --noEmit",
+ "preview": "vite preview",
+ "lint": "prettier --check .",
+ "fix": "prettier --write .",
+ "test": "pnpm test:unit && pnpm test:e2e",
+ "test:unit": "vitest run",
+ "test:e2e": "playwright test",
+ "test:e2e:update": "playwright test --update-snapshots"
+ },
+ "peerDependencies": {
+ "@awesome.me/webawesome": "^3.11.0",
+ "lit": "^3.3.3"
+ },
+ "devDependencies": {
+ "@axe-core/playwright": "^4.12.1",
+ "@playwright/test": "^1.60.0",
+ "@awesome.me/webawesome": "^3.11.0",
+ "lit": "^3.3.3",
+ "@types/node": "^24.0.0",
+ "jsdom": "^29.0.0",
+ "prettier": "^3.8.4",
+ "publint": "^0.3.21",
+ "typescript": "^5.9.3",
+ "vite": "^8.1.5",
+ "vitest": "^4.1.8"
+ }
+}
diff --git a/javascript/uitk-webawesome/playwright.config.ts.jinja b/javascript/uitk-webawesome/playwright.config.ts.jinja
new file mode 100644
index 0000000..16ae963
--- /dev/null
+++ b/javascript/uitk-webawesome/playwright.config.ts.jinja
@@ -0,0 +1,28 @@
+import { defineConfig, devices } from '@playwright/test';
+
+export default defineConfig({
+ testDir: 'tests',
+ testIgnore: process.env.CI ? ['**/visual/**'] : [],
+ snapshotPathTemplate: '{testDir}/{testFilePath}-snapshots/{arg}-{projectName}{ext}',
+ fullyParallel: true,
+ forbidOnly: !!process.env.CI,
+ retries: process.env.CI ? 2 : 0,
+ reporter: process.env.CI ? 'github' : 'list',
+ use: {
+ baseURL: 'http://127.0.0.1:4177',
+ trace: 'retain-on-failure',
+ screenshot: 'only-on-failure'
+ },
+ webServer: {
+ command: 'vite dev --host 127.0.0.1 --port 4177 --strictPort',
+ port: 4177,
+ reuseExistingServer: !process.env.CI,
+ timeout: 120_000
+ },
+ projects: [
+ {
+ name: 'desktop',
+ use: { ...devices['Desktop Chrome'], viewport: { width: 1280, height: 800 } }
+ }
+ ]
+});
diff --git a/javascript/uitk-webawesome/src/demo.ts.jinja b/javascript/uitk-webawesome/src/demo.ts.jinja
new file mode 100644
index 0000000..d6b53c5
--- /dev/null
+++ b/javascript/uitk-webawesome/src/demo.ts.jinja
@@ -0,0 +1,3 @@
+import '@awesome.me/webawesome/dist/styles/webawesome.css';
+import '@awesome.me/webawesome/dist/styles/themes/default.css';
+import './lit/index.js';
diff --git a/javascript/uitk-webawesome/src/lit/components/brand-mark.ts.jinja b/javascript/uitk-webawesome/src/lit/components/brand-mark.ts.jinja
new file mode 100644
index 0000000..ce4e8eb
--- /dev/null
+++ b/javascript/uitk-webawesome/src/lit/components/brand-mark.ts.jinja
@@ -0,0 +1,37 @@
+import { LitElement, css, html } from 'lit';
+import { customElement } from 'lit/decorators.js';
+
+@customElement('{{ element_prefix }}-brand-mark')
+export class BrandMark extends LitElement {
+ static styles = css`
+ a {
+ display: inline-flex;
+ align-items: center;
+ gap: 0.625rem;
+ color: inherit;
+ font-weight: 700;
+ text-decoration: none;
+ }
+
+ span {
+ display: grid;
+ width: 2rem;
+ height: 2rem;
+ place-items: center;
+ border-radius: 50%;
+ color: var(--{{ css_prefix }}-color-paper);
+ background: var(--{{ css_prefix }}-color-ink);
+ box-shadow: 3px 3px 0 var(--{{ css_prefix }}-color-accent);
+ }
+ `;
+
+ render() {
+ return html`{{ brand_name[0] | upper }}{{ brand_name }}`;
+ }
+}
+
+declare global {
+ interface HTMLElementTagNameMap {
+ '{{ element_prefix }}-brand-mark': BrandMark;
+ }
+}
diff --git a/javascript/uitk-webawesome/src/lit/components/theme-toggle.ts.jinja b/javascript/uitk-webawesome/src/lit/components/theme-toggle.ts.jinja
new file mode 100644
index 0000000..a882c7d
--- /dev/null
+++ b/javascript/uitk-webawesome/src/lit/components/theme-toggle.ts.jinja
@@ -0,0 +1,39 @@
+import '@awesome.me/webawesome/dist/components/button/button.js';
+import { LitElement, css, html } from 'lit';
+import { customElement, state } from 'lit/decorators.js';
+import { initTheme, toggleTheme, type ResolvedTheme } from '../theme.js';
+
+@customElement('{{ element_prefix }}-theme-toggle')
+export class ThemeToggle extends LitElement {
+ @state() private theme: ResolvedTheme = 'light';
+
+ static styles = css`
+ wa-button::part(base) {
+ border-color: var(--{{ css_prefix }}-color-line);
+ color: var(--{{ css_prefix }}-color-ink);
+ background: var(--{{ css_prefix }}-color-paper);
+ }
+ `;
+
+ connectedCallback() {
+ super.connectedCallback();
+ this.theme = initTheme();
+ }
+
+ private toggle() {
+ this.theme = toggleTheme();
+ }
+
+ render() {
+ const next = this.theme === 'dark' ? 'light' : 'dark';
+ return html`
+ ${next === 'dark' ? 'Dark' : 'Light'}
+ `;
+ }
+}
+
+declare global {
+ interface HTMLElementTagNameMap {
+ '{{ element_prefix }}-theme-toggle': ThemeToggle;
+ }
+}
diff --git a/javascript/uitk-webawesome/src/lit/index.ts.jinja b/javascript/uitk-webawesome/src/lit/index.ts.jinja
new file mode 100644
index 0000000..eba66bd
--- /dev/null
+++ b/javascript/uitk-webawesome/src/lit/index.ts.jinja
@@ -0,0 +1,14 @@
+import './styles/tokens.css';
+
+export { BrandMark } from './components/brand-mark.js';
+export { ThemeToggle } from './components/theme-toggle.js';
+export {
+ getTheme,
+ resolveTheme,
+ applyTheme,
+ setTheme,
+ toggleTheme,
+ initTheme,
+ type Theme,
+ type ResolvedTheme
+} from './theme.js';
diff --git a/javascript/uitk-webawesome/src/lit/styles/tokens.css.jinja b/javascript/uitk-webawesome/src/lit/styles/tokens.css.jinja
new file mode 100644
index 0000000..5107b0e
--- /dev/null
+++ b/javascript/uitk-webawesome/src/lit/styles/tokens.css.jinja
@@ -0,0 +1,45 @@
+:root {
+ --{{ css_prefix }}-color-paper: #f5f5f0;
+ --{{ css_prefix }}-color-ink: #151515;
+ --{{ css_prefix }}-color-muted: #666660;
+ --{{ css_prefix }}-color-line: #d0d0c8;
+ --{{ css_prefix }}-color-accent: #6cff8f;
+ --{{ css_prefix }}-font-sans: ui-sans-serif, system-ui, sans-serif;
+ --{{ css_prefix }}-font-mono: ui-monospace, monospace;
+ --wa-color-surface-default: var(--{{ css_prefix }}-color-paper);
+ --wa-color-text-normal: var(--{{ css_prefix }}-color-ink);
+ --wa-color-brand-fill-loud: var(--{{ css_prefix }}-color-accent);
+ color-scheme: light;
+}
+
+:root[data-theme='dark'] {
+ --{{ css_prefix }}-color-paper: #151515;
+ --{{ css_prefix }}-color-ink: #f5f5f0;
+ --{{ css_prefix }}-color-muted: #aaa9a0;
+ --{{ css_prefix }}-color-line: #3a3a36;
+ color-scheme: dark;
+}
+
+:root {
+ color: var(--{{ css_prefix }}-color-ink);
+ font-family: var(--{{ css_prefix }}-font-sans);
+ background: var(--{{ css_prefix }}-color-paper);
+}
+
+body {
+ margin: 0;
+}
+
+main {
+ width: min(calc(100% - 3rem), 72rem);
+ margin: 0 auto;
+ padding: 6rem 0;
+}
+
+.eyebrow {
+ color: var(--{{ css_prefix }}-color-muted);
+ font-family: var(--{{ css_prefix }}-font-mono);
+ font-size: 0.75rem;
+ letter-spacing: 0.14em;
+ text-transform: uppercase;
+}
diff --git a/javascript/uitk-webawesome/src/lit/theme.test.ts.jinja b/javascript/uitk-webawesome/src/lit/theme.test.ts.jinja
new file mode 100644
index 0000000..1a4e513
--- /dev/null
+++ b/javascript/uitk-webawesome/src/lit/theme.test.ts.jinja
@@ -0,0 +1,17 @@
+import { beforeEach, describe, expect, it } from 'vitest';
+import { getTheme, setTheme, toggleTheme } from './theme.js';
+
+beforeEach(() => localStorage.clear());
+
+describe('theme', () => {
+ it('persists an explicit choice', () => {
+ setTheme('dark');
+ expect(getTheme()).toBe('dark');
+ expect(document.documentElement.dataset.theme).toBe('dark');
+ });
+
+ it('toggles the resolved choice', () => {
+ setTheme('dark');
+ expect(toggleTheme()).toBe('light');
+ });
+});
diff --git a/javascript/uitk-webawesome/src/lit/theme.ts.jinja b/javascript/uitk-webawesome/src/lit/theme.ts.jinja
new file mode 100644
index 0000000..509c8d5
--- /dev/null
+++ b/javascript/uitk-webawesome/src/lit/theme.ts.jinja
@@ -0,0 +1,36 @@
+export type Theme = 'dark' | 'light' | 'system';
+export type ResolvedTheme = Exclude;
+
+export const THEME_STORAGE_KEY = '{{ project_name }}.theme';
+
+export function resolveTheme(theme: Theme): ResolvedTheme {
+ if (theme !== 'system') return theme;
+ if (typeof window === 'undefined' || typeof window.matchMedia !== 'function') return 'light';
+ return window.matchMedia('(prefers-color-scheme: dark)').matches ? 'dark' : 'light';
+}
+
+export function getTheme(): Theme {
+ if (typeof localStorage === 'undefined') return 'system';
+ const value = localStorage.getItem(THEME_STORAGE_KEY);
+ return value === 'light' || value === 'dark' ? value : 'system';
+}
+
+export function applyTheme(theme: Theme): ResolvedTheme {
+ const resolved = resolveTheme(theme);
+ if (typeof document !== 'undefined') document.documentElement.dataset.theme = resolved;
+ return resolved;
+}
+
+export function setTheme(theme: Theme): ResolvedTheme {
+ if (theme === 'system') localStorage.removeItem(THEME_STORAGE_KEY);
+ else localStorage.setItem(THEME_STORAGE_KEY, theme);
+ return applyTheme(theme);
+}
+
+export function toggleTheme(): ResolvedTheme {
+ return setTheme(resolveTheme(getTheme()) === 'dark' ? 'light' : 'dark');
+}
+
+export function initTheme(): ResolvedTheme {
+ return applyTheme(getTheme());
+}
diff --git a/javascript/uitk-webawesome/tests/a11y/audit.spec.ts.jinja b/javascript/uitk-webawesome/tests/a11y/audit.spec.ts.jinja
new file mode 100644
index 0000000..cc912a5
--- /dev/null
+++ b/javascript/uitk-webawesome/tests/a11y/audit.spec.ts.jinja
@@ -0,0 +1,9 @@
+import AxeBuilder from '@axe-core/playwright';
+import { expect, test } from '@playwright/test';
+
+test('showcase has no serious or critical accessibility violations', async ({ page }) => {
+ await page.goto('/');
+ const results = await new AxeBuilder({ page }).withTags(['wcag2a', 'wcag2aa', 'wcag21a', 'wcag21aa']).analyze();
+ const violations = results.violations.filter((violation) => ['serious', 'critical'].includes(violation.impact ?? ''));
+ expect(violations).toEqual([]);
+});
diff --git a/javascript/uitk-webawesome/tests/behavior/theme.spec.ts.jinja b/javascript/uitk-webawesome/tests/behavior/theme.spec.ts.jinja
new file mode 100644
index 0000000..087d2e5
--- /dev/null
+++ b/javascript/uitk-webawesome/tests/behavior/theme.spec.ts.jinja
@@ -0,0 +1,12 @@
+import { expect, test } from '@playwright/test';
+
+test('theme toggle persists the choice', async ({ page }) => {
+ await page.goto('/');
+ await page.evaluate(() => localStorage.removeItem('{{ project_name }}.theme'));
+ await page.reload();
+ const initial = await page.locator('html').getAttribute('data-theme');
+ await page.getByTestId('theme-toggle').click();
+ const expected = initial === 'dark' ? 'light' : 'dark';
+ await expect(page.locator('html')).toHaveAttribute('data-theme', expected);
+ expect(await page.evaluate(() => localStorage.getItem('{{ project_name }}.theme'))).toBe(expected);
+});
diff --git a/javascript/uitk-webawesome/tests/visual/showcase.spec.ts.jinja b/javascript/uitk-webawesome/tests/visual/showcase.spec.ts.jinja
new file mode 100644
index 0000000..5560ec3
--- /dev/null
+++ b/javascript/uitk-webawesome/tests/visual/showcase.spec.ts.jinja
@@ -0,0 +1,6 @@
+import { expect, test } from '@playwright/test';
+
+test('showcase', async ({ page }) => {
+ await page.goto('/');
+ await expect(page).toHaveScreenshot('showcase.png', { fullPage: true });
+});
diff --git a/javascript/uitk-webawesome/tsconfig.build.json.jinja b/javascript/uitk-webawesome/tsconfig.build.json.jinja
new file mode 100644
index 0000000..469a4e8
--- /dev/null
+++ b/javascript/uitk-webawesome/tsconfig.build.json.jinja
@@ -0,0 +1,11 @@
+{
+ "extends": "./tsconfig.json",
+ "compilerOptions": {
+ "rootDir": "src/lit",
+ "declaration": true,
+ "declarationDir": "dist",
+ "emitDeclarationOnly": true
+ },
+ "include": ["src/lit/**/*.ts"],
+ "exclude": ["src/lit/**/*.test.ts"]
+}
diff --git a/javascript/uitk-webawesome/tsconfig.json.jinja b/javascript/uitk-webawesome/tsconfig.json.jinja
new file mode 100644
index 0000000..217244f
--- /dev/null
+++ b/javascript/uitk-webawesome/tsconfig.json.jinja
@@ -0,0 +1,16 @@
+{
+ "compilerOptions": {
+ "target": "ES2022",
+ "useDefineForClassFields": false,
+ "experimentalDecorators": true,
+ "module": "ESNext",
+ "moduleResolution": "bundler",
+ "strict": true,
+ "declaration": true,
+ "declarationDir": "dist",
+ "emitDeclarationOnly": false,
+ "skipLibCheck": true,
+ "types": ["vite/client"]
+ },
+ "include": ["src/lit/**/*.ts", "src/demo.ts", "vite.config.ts", "vitest.config.ts"]
+}
diff --git a/javascript/uitk-webawesome/vite.config.ts.jinja b/javascript/uitk-webawesome/vite.config.ts.jinja
new file mode 100644
index 0000000..aac5f2d
--- /dev/null
+++ b/javascript/uitk-webawesome/vite.config.ts.jinja
@@ -0,0 +1,16 @@
+import { resolve } from 'node:path';
+import { defineConfig } from 'vite';
+
+export default defineConfig({
+ build: {
+ lib: {
+ entry: resolve(import.meta.dirname, 'src/lit/index.ts'),
+ formats: ['es'],
+ fileName: 'index',
+ cssFileName: 'tokens'
+ },
+ rollupOptions: {
+ external: ['lit', /^@awesome.me\/webawesome/]
+ }
+ }
+});
diff --git a/javascript/uitk-webawesome/vitest.config.ts.jinja b/javascript/uitk-webawesome/vitest.config.ts.jinja
new file mode 100644
index 0000000..a1bc41b
--- /dev/null
+++ b/javascript/uitk-webawesome/vitest.config.ts.jinja
@@ -0,0 +1,9 @@
+import { defineConfig } from 'vitest/config';
+
+export default defineConfig({
+ test: {
+ include: ['src/**/*.test.ts'],
+ environment: 'jsdom',
+ setupFiles: ['./vitest.setup.ts']
+ }
+});
diff --git a/javascript/uitk-webawesome/vitest.setup.ts.jinja b/javascript/uitk-webawesome/vitest.setup.ts.jinja
new file mode 100644
index 0000000..0d50ddd
--- /dev/null
+++ b/javascript/uitk-webawesome/vitest.setup.ts.jinja
@@ -0,0 +1,25 @@
+import { vi } from 'vitest';
+
+if (typeof globalThis.localStorage === 'undefined') {
+ const store = new Map();
+ globalThis.localStorage = {
+ getItem: (key: string) => store.get(key) ?? null,
+ setItem: (key: string, value: string) => void store.set(key, String(value)),
+ removeItem: (key: string) => void store.delete(key),
+ clear: () => store.clear(),
+ key: (index: number) => [...store.keys()][index] ?? null,
+ get length() {
+ return store.size;
+ }
+ } as Storage;
+}
+
+Object.defineProperty(window, 'matchMedia', {
+ writable: true,
+ value: vi.fn().mockImplementation((query: string) => ({
+ matches: false,
+ media: query,
+ addEventListener: vi.fn(),
+ removeEventListener: vi.fn()
+ }))
+});
diff --git a/javascript/uitk-webawesome/{{_copier_conf.answers_file}}.jinja b/javascript/uitk-webawesome/{{_copier_conf.answers_file}}.jinja
new file mode 100644
index 0000000..090c992
--- /dev/null
+++ b/javascript/uitk-webawesome/{{_copier_conf.answers_file}}.jinja
@@ -0,0 +1,2 @@
+# Changes here will be overwritten by Copier
+{{ _copier_answers|to_nice_yaml }}
diff --git a/cpp/.clang-format b/python/cpp/.clang-format
similarity index 100%
rename from cpp/.clang-format
rename to python/cpp/.clang-format
diff --git a/cpp/.github/CODE_OF_CONDUCT.md b/python/cpp/.github/CODE_OF_CONDUCT.md
similarity index 100%
rename from cpp/.github/CODE_OF_CONDUCT.md
rename to python/cpp/.github/CODE_OF_CONDUCT.md
diff --git a/cpp/.github/ISSUE_TEMPLATE/bug_report.md.jinja b/python/cpp/.github/ISSUE_TEMPLATE/bug_report.md.jinja
similarity index 100%
rename from cpp/.github/ISSUE_TEMPLATE/bug_report.md.jinja
rename to python/cpp/.github/ISSUE_TEMPLATE/bug_report.md.jinja
diff --git a/cpp/.github/ISSUE_TEMPLATE/feature_request.md b/python/cpp/.github/ISSUE_TEMPLATE/feature_request.md
similarity index 100%
rename from cpp/.github/ISSUE_TEMPLATE/feature_request.md
rename to python/cpp/.github/ISSUE_TEMPLATE/feature_request.md
diff --git a/cpp/.github/ISSUE_TEMPLATE/question.md b/python/cpp/.github/ISSUE_TEMPLATE/question.md
similarity index 100%
rename from cpp/.github/ISSUE_TEMPLATE/question.md
rename to python/cpp/.github/ISSUE_TEMPLATE/question.md
diff --git a/cpp/.github/dependabot.yaml b/python/cpp/.github/dependabot.yaml
similarity index 100%
rename from cpp/.github/dependabot.yaml
rename to python/cpp/.github/dependabot.yaml
diff --git a/cpp/.github/pull_request_template.md b/python/cpp/.github/pull_request_template.md
similarity index 100%
rename from cpp/.github/pull_request_template.md
rename to python/cpp/.github/pull_request_template.md
diff --git a/cpp/.github/workflows/build.yaml.jinja b/python/cpp/.github/workflows/build.yaml.jinja
similarity index 100%
rename from cpp/.github/workflows/build.yaml.jinja
rename to python/cpp/.github/workflows/build.yaml.jinja
diff --git a/cpp/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja b/python/cpp/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
similarity index 100%
rename from cpp/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
rename to python/cpp/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
diff --git a/cpp/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja b/python/cpp/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
similarity index 100%
rename from cpp/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
rename to python/cpp/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
diff --git a/cpp/.gitignore.jinja b/python/cpp/.gitignore.jinja
similarity index 100%
rename from cpp/.gitignore.jinja
rename to python/cpp/.gitignore.jinja
diff --git a/cpp/LICENSE.jinja b/python/cpp/LICENSE.jinja
similarity index 100%
rename from cpp/LICENSE.jinja
rename to python/cpp/LICENSE.jinja
diff --git a/cpp/Makefile.jinja b/python/cpp/Makefile.jinja
similarity index 100%
rename from cpp/Makefile.jinja
rename to python/cpp/Makefile.jinja
diff --git a/cpp/README.md.jinja b/python/cpp/README.md.jinja
similarity index 100%
rename from cpp/README.md.jinja
rename to python/cpp/README.md.jinja
diff --git a/cpp/cpp/{{project_name_formatted}}/extension.cpp.jinja b/python/cpp/cpp/{{project_name_formatted}}/extension.cpp.jinja
similarity index 100%
rename from cpp/cpp/{{project_name_formatted}}/extension.cpp.jinja
rename to python/cpp/cpp/{{project_name_formatted}}/extension.cpp.jinja
diff --git a/cpp/cpp/{{project_name_formatted}}/extension.hpp b/python/cpp/cpp/{{project_name_formatted}}/extension.hpp
similarity index 100%
rename from cpp/cpp/{{project_name_formatted}}/extension.hpp
rename to python/cpp/cpp/{{project_name_formatted}}/extension.hpp
diff --git a/cpp/pyproject.toml.jinja b/python/cpp/pyproject.toml.jinja
similarity index 100%
rename from cpp/pyproject.toml.jinja
rename to python/cpp/pyproject.toml.jinja
diff --git a/cpp/{% if add_vcpkg %}vcpkg-overlays{% endif %}/.gitkeep b/python/cpp/{% if add_vcpkg %}vcpkg-overlays{% endif %}/.gitkeep
similarity index 100%
rename from cpp/{% if add_vcpkg %}vcpkg-overlays{% endif %}/.gitkeep
rename to python/cpp/{% if add_vcpkg %}vcpkg-overlays{% endif %}/.gitkeep
diff --git a/cpp/{% if add_vcpkg %}vcpkg.json{% endif %}.jinja b/python/cpp/{% if add_vcpkg %}vcpkg.json{% endif %}.jinja
similarity index 100%
rename from cpp/{% if add_vcpkg %}vcpkg.json{% endif %}.jinja
rename to python/cpp/{% if add_vcpkg %}vcpkg.json{% endif %}.jinja
diff --git a/cpp/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja b/python/cpp/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
similarity index 100%
rename from cpp/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
rename to python/cpp/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
diff --git a/cpp/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja b/python/cpp/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
similarity index 100%
rename from cpp/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
rename to python/cpp/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
diff --git a/cpp/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja b/python/cpp/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
similarity index 100%
rename from cpp/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
rename to python/cpp/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
diff --git a/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja b/python/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
similarity index 100%
rename from cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
rename to python/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
diff --git a/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja b/python/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
similarity index 100%
rename from cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
rename to python/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
diff --git a/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja b/python/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
similarity index 100%
rename from cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
rename to python/cpp/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
diff --git a/cpp/{{_copier_conf.answers_file}}.jinja b/python/cpp/{{_copier_conf.answers_file}}.jinja
similarity index 100%
rename from cpp/{{_copier_conf.answers_file}}.jinja
rename to python/cpp/{{_copier_conf.answers_file}}.jinja
diff --git a/cpp/{{module}}/__init__.py b/python/cpp/{{module}}/__init__.py
similarity index 100%
rename from cpp/{{module}}/__init__.py
rename to python/cpp/{{module}}/__init__.py
diff --git a/cpp/{{module}}/tests/test_all.py.jinja b/python/cpp/{{module}}/tests/test_all.py.jinja
similarity index 100%
rename from cpp/{{module}}/tests/test_all.py.jinja
rename to python/cpp/{{module}}/tests/test_all.py.jinja
diff --git a/cppjswasm/.clang-format b/python/cppjswasm/.clang-format
similarity index 100%
rename from cppjswasm/.clang-format
rename to python/cppjswasm/.clang-format
diff --git a/cppjswasm/.gitattributes b/python/cppjswasm/.gitattributes
similarity index 100%
rename from cppjswasm/.gitattributes
rename to python/cppjswasm/.gitattributes
diff --git a/cppjswasm/.github/CODE_OF_CONDUCT.md.jinja b/python/cppjswasm/.github/CODE_OF_CONDUCT.md.jinja
similarity index 100%
rename from cppjswasm/.github/CODE_OF_CONDUCT.md.jinja
rename to python/cppjswasm/.github/CODE_OF_CONDUCT.md.jinja
diff --git a/cppjswasm/.github/ISSUE_TEMPLATE/bug_report.md.jinja b/python/cppjswasm/.github/ISSUE_TEMPLATE/bug_report.md.jinja
similarity index 100%
rename from cppjswasm/.github/ISSUE_TEMPLATE/bug_report.md.jinja
rename to python/cppjswasm/.github/ISSUE_TEMPLATE/bug_report.md.jinja
diff --git a/cppjswasm/.github/ISSUE_TEMPLATE/feature_request.md b/python/cppjswasm/.github/ISSUE_TEMPLATE/feature_request.md
similarity index 100%
rename from cppjswasm/.github/ISSUE_TEMPLATE/feature_request.md
rename to python/cppjswasm/.github/ISSUE_TEMPLATE/feature_request.md
diff --git a/cppjswasm/.github/ISSUE_TEMPLATE/question.md b/python/cppjswasm/.github/ISSUE_TEMPLATE/question.md
similarity index 100%
rename from cppjswasm/.github/ISSUE_TEMPLATE/question.md
rename to python/cppjswasm/.github/ISSUE_TEMPLATE/question.md
diff --git a/cppjswasm/.github/dependabot.yaml b/python/cppjswasm/.github/dependabot.yaml
similarity index 100%
rename from cppjswasm/.github/dependabot.yaml
rename to python/cppjswasm/.github/dependabot.yaml
diff --git a/cppjswasm/.github/pull_request_template.md b/python/cppjswasm/.github/pull_request_template.md
similarity index 100%
rename from cppjswasm/.github/pull_request_template.md
rename to python/cppjswasm/.github/pull_request_template.md
diff --git a/cppjswasm/.github/workflows/build.yaml.jinja b/python/cppjswasm/.github/workflows/build.yaml.jinja
similarity index 100%
rename from cppjswasm/.github/workflows/build.yaml.jinja
rename to python/cppjswasm/.github/workflows/build.yaml.jinja
diff --git a/cppjswasm/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja b/python/cppjswasm/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
similarity index 100%
rename from cppjswasm/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
rename to python/cppjswasm/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
diff --git a/cppjswasm/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja b/python/cppjswasm/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
similarity index 100%
rename from cppjswasm/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
rename to python/cppjswasm/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
diff --git a/cppjswasm/.gitignore.jinja b/python/cppjswasm/.gitignore.jinja
similarity index 100%
rename from cppjswasm/.gitignore.jinja
rename to python/cppjswasm/.gitignore.jinja
diff --git a/cppjswasm/.vscode/settings.json b/python/cppjswasm/.vscode/settings.json
similarity index 100%
rename from cppjswasm/.vscode/settings.json
rename to python/cppjswasm/.vscode/settings.json
diff --git a/cppjswasm/LICENSE.jinja b/python/cppjswasm/LICENSE.jinja
similarity index 100%
rename from cppjswasm/LICENSE.jinja
rename to python/cppjswasm/LICENSE.jinja
diff --git a/cppjswasm/Makefile.jinja b/python/cppjswasm/Makefile.jinja
similarity index 100%
rename from cppjswasm/Makefile.jinja
rename to python/cppjswasm/Makefile.jinja
diff --git a/cppjswasm/README.md.jinja b/python/cppjswasm/README.md.jinja
similarity index 100%
rename from cppjswasm/README.md.jinja
rename to python/cppjswasm/README.md.jinja
diff --git a/cppjswasm/cpp/Makefile.jinja b/python/cppjswasm/cpp/Makefile.jinja
similarity index 100%
rename from cppjswasm/cpp/Makefile.jinja
rename to python/cppjswasm/cpp/Makefile.jinja
diff --git a/cppjswasm/cpp/{{project_name_formatted}}/example.cpp.jinja b/python/cppjswasm/cpp/{{project_name_formatted}}/example.cpp.jinja
similarity index 100%
rename from cppjswasm/cpp/{{project_name_formatted}}/example.cpp.jinja
rename to python/cppjswasm/cpp/{{project_name_formatted}}/example.cpp.jinja
diff --git a/cppjswasm/cpp/{{project_name_formatted}}/example.hpp b/python/cppjswasm/cpp/{{project_name_formatted}}/example.hpp
similarity index 100%
rename from cppjswasm/cpp/{{project_name_formatted}}/example.hpp
rename to python/cppjswasm/cpp/{{project_name_formatted}}/example.hpp
diff --git a/cppjswasm/cpp/{{project_name_formatted}}/extension.cpp.jinja b/python/cppjswasm/cpp/{{project_name_formatted}}/extension.cpp.jinja
similarity index 100%
rename from cppjswasm/cpp/{{project_name_formatted}}/extension.cpp.jinja
rename to python/cppjswasm/cpp/{{project_name_formatted}}/extension.cpp.jinja
diff --git a/cppjswasm/js/build.mjs.jinja b/python/cppjswasm/js/build.mjs.jinja
similarity index 100%
rename from cppjswasm/js/build.mjs.jinja
rename to python/cppjswasm/js/build.mjs.jinja
diff --git a/cppjswasm/js/package.json.jinja b/python/cppjswasm/js/package.json.jinja
similarity index 100%
rename from cppjswasm/js/package.json.jinja
rename to python/cppjswasm/js/package.json.jinja
diff --git a/cppjswasm/js/playwright.config.js b/python/cppjswasm/js/playwright.config.js
similarity index 100%
rename from cppjswasm/js/playwright.config.js
rename to python/cppjswasm/js/playwright.config.js
diff --git a/cppjswasm/js/pnpm-workspace.yaml b/python/cppjswasm/js/pnpm-workspace.yaml
similarity index 100%
rename from cppjswasm/js/pnpm-workspace.yaml
rename to python/cppjswasm/js/pnpm-workspace.yaml
diff --git a/cppjswasm/js/src/cpp/bindings.cpp.jinja b/python/cppjswasm/js/src/cpp/bindings.cpp.jinja
similarity index 100%
rename from cppjswasm/js/src/cpp/bindings.cpp.jinja
rename to python/cppjswasm/js/src/cpp/bindings.cpp.jinja
diff --git a/cppjswasm/js/src/css/index.css b/python/cppjswasm/js/src/css/index.css
similarity index 100%
rename from cppjswasm/js/src/css/index.css
rename to python/cppjswasm/js/src/css/index.css
diff --git a/cppjswasm/js/src/html/index.html.jinja b/python/cppjswasm/js/src/html/index.html.jinja
similarity index 100%
rename from cppjswasm/js/src/html/index.html.jinja
rename to python/cppjswasm/js/src/html/index.html.jinja
diff --git a/cppjswasm/js/src/ts/css.d.ts b/python/cppjswasm/js/src/ts/css.d.ts
similarity index 100%
rename from cppjswasm/js/src/ts/css.d.ts
rename to python/cppjswasm/js/src/ts/css.d.ts
diff --git a/cppjswasm/js/src/ts/index.ts.jinja b/python/cppjswasm/js/src/ts/index.ts.jinja
similarity index 100%
rename from cppjswasm/js/src/ts/index.ts.jinja
rename to python/cppjswasm/js/src/ts/index.ts.jinja
diff --git a/cppjswasm/js/tests/index.spec.js b/python/cppjswasm/js/tests/index.spec.js
similarity index 100%
rename from cppjswasm/js/tests/index.spec.js
rename to python/cppjswasm/js/tests/index.spec.js
diff --git a/cppjswasm/js/tools/bundle.mjs b/python/cppjswasm/js/tools/bundle.mjs
similarity index 100%
rename from cppjswasm/js/tools/bundle.mjs
rename to python/cppjswasm/js/tools/bundle.mjs
diff --git a/cppjswasm/js/tools/css.mjs b/python/cppjswasm/js/tools/css.mjs
similarity index 100%
rename from cppjswasm/js/tools/css.mjs
rename to python/cppjswasm/js/tools/css.mjs
diff --git a/cppjswasm/js/tools/externals.mjs b/python/cppjswasm/js/tools/externals.mjs
similarity index 100%
rename from cppjswasm/js/tools/externals.mjs
rename to python/cppjswasm/js/tools/externals.mjs
diff --git a/cppjswasm/js/tools/getarg.mjs b/python/cppjswasm/js/tools/getarg.mjs
similarity index 100%
rename from cppjswasm/js/tools/getarg.mjs
rename to python/cppjswasm/js/tools/getarg.mjs
diff --git a/cppjswasm/js/tools/html.mjs b/python/cppjswasm/js/tools/html.mjs
similarity index 100%
rename from cppjswasm/js/tools/html.mjs
rename to python/cppjswasm/js/tools/html.mjs
diff --git a/cppjswasm/js/tsconfig.json b/python/cppjswasm/js/tsconfig.json
similarity index 100%
rename from cppjswasm/js/tsconfig.json
rename to python/cppjswasm/js/tsconfig.json
diff --git a/cppjswasm/pyproject.toml.jinja b/python/cppjswasm/pyproject.toml.jinja
similarity index 100%
rename from cppjswasm/pyproject.toml.jinja
rename to python/cppjswasm/pyproject.toml.jinja
diff --git a/cppjswasm/{% if add_vcpkg %}vcpkg-overlays{% endif %}/.gitkeep b/python/cppjswasm/{% if add_vcpkg %}vcpkg-overlays{% endif %}/.gitkeep
similarity index 100%
rename from cppjswasm/{% if add_vcpkg %}vcpkg-overlays{% endif %}/.gitkeep
rename to python/cppjswasm/{% if add_vcpkg %}vcpkg-overlays{% endif %}/.gitkeep
diff --git a/cppjswasm/{% if add_vcpkg %}vcpkg.json{% endif %}.jinja b/python/cppjswasm/{% if add_vcpkg %}vcpkg.json{% endif %}.jinja
similarity index 100%
rename from cppjswasm/{% if add_vcpkg %}vcpkg.json{% endif %}.jinja
rename to python/cppjswasm/{% if add_vcpkg %}vcpkg.json{% endif %}.jinja
diff --git a/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja b/python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
similarity index 100%
rename from cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
rename to python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
diff --git a/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja b/python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
similarity index 100%
rename from cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
rename to python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
diff --git a/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja b/python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
similarity index 100%
rename from cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
rename to python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
diff --git a/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja b/python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
similarity index 100%
rename from cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
rename to python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
diff --git a/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja b/python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
similarity index 100%
rename from cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
rename to python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
diff --git a/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja b/python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
similarity index 100%
rename from cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
rename to python/cppjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
diff --git a/cppjswasm/{{_copier_conf.answers_file}}.jinja b/python/cppjswasm/{{_copier_conf.answers_file}}.jinja
similarity index 100%
rename from cppjswasm/{{_copier_conf.answers_file}}.jinja
rename to python/cppjswasm/{{_copier_conf.answers_file}}.jinja
diff --git a/cppjswasm/{{module}}/__init__.py b/python/cppjswasm/{{module}}/__init__.py
similarity index 100%
rename from cppjswasm/{{module}}/__init__.py
rename to python/cppjswasm/{{module}}/__init__.py
diff --git a/cppjswasm/{{module}}/tests/test_all.py.jinja b/python/cppjswasm/{{module}}/tests/test_all.py.jinja
similarity index 100%
rename from cppjswasm/{{module}}/tests/test_all.py.jinja
rename to python/cppjswasm/{{module}}/tests/test_all.py.jinja
diff --git a/js/.gitattributes b/python/js/.gitattributes
similarity index 100%
rename from js/.gitattributes
rename to python/js/.gitattributes
diff --git a/js/.github/CODE_OF_CONDUCT.md.jinja b/python/js/.github/CODE_OF_CONDUCT.md.jinja
similarity index 100%
rename from js/.github/CODE_OF_CONDUCT.md.jinja
rename to python/js/.github/CODE_OF_CONDUCT.md.jinja
diff --git a/js/.github/ISSUE_TEMPLATE/bug_report.md.jinja b/python/js/.github/ISSUE_TEMPLATE/bug_report.md.jinja
similarity index 100%
rename from js/.github/ISSUE_TEMPLATE/bug_report.md.jinja
rename to python/js/.github/ISSUE_TEMPLATE/bug_report.md.jinja
diff --git a/js/.github/ISSUE_TEMPLATE/feature_request.md b/python/js/.github/ISSUE_TEMPLATE/feature_request.md
similarity index 100%
rename from js/.github/ISSUE_TEMPLATE/feature_request.md
rename to python/js/.github/ISSUE_TEMPLATE/feature_request.md
diff --git a/js/.github/ISSUE_TEMPLATE/question.md b/python/js/.github/ISSUE_TEMPLATE/question.md
similarity index 100%
rename from js/.github/ISSUE_TEMPLATE/question.md
rename to python/js/.github/ISSUE_TEMPLATE/question.md
diff --git a/js/.github/dependabot.yaml b/python/js/.github/dependabot.yaml
similarity index 100%
rename from js/.github/dependabot.yaml
rename to python/js/.github/dependabot.yaml
diff --git a/js/.github/pull_request_template.md b/python/js/.github/pull_request_template.md
similarity index 100%
rename from js/.github/pull_request_template.md
rename to python/js/.github/pull_request_template.md
diff --git a/js/.github/workflows/build.yaml.jinja b/python/js/.github/workflows/build.yaml.jinja
similarity index 100%
rename from js/.github/workflows/build.yaml.jinja
rename to python/js/.github/workflows/build.yaml.jinja
diff --git a/js/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja b/python/js/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
similarity index 100%
rename from js/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
rename to python/js/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
diff --git a/js/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja b/python/js/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
similarity index 100%
rename from js/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
rename to python/js/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
diff --git a/js/.gitignore.jinja b/python/js/.gitignore.jinja
similarity index 100%
rename from js/.gitignore.jinja
rename to python/js/.gitignore.jinja
diff --git a/js/.vscode/settings.json b/python/js/.vscode/settings.json
similarity index 100%
rename from js/.vscode/settings.json
rename to python/js/.vscode/settings.json
diff --git a/js/LICENSE.jinja b/python/js/LICENSE.jinja
similarity index 100%
rename from js/LICENSE.jinja
rename to python/js/LICENSE.jinja
diff --git a/js/Makefile.jinja b/python/js/Makefile.jinja
similarity index 100%
rename from js/Makefile.jinja
rename to python/js/Makefile.jinja
diff --git a/js/README.md.jinja b/python/js/README.md.jinja
similarity index 100%
rename from js/README.md.jinja
rename to python/js/README.md.jinja
diff --git a/js/js/build.mjs.jinja b/python/js/js/build.mjs.jinja
similarity index 100%
rename from js/js/build.mjs.jinja
rename to python/js/js/build.mjs.jinja
diff --git a/js/js/package.json.jinja b/python/js/js/package.json.jinja
similarity index 100%
rename from js/js/package.json.jinja
rename to python/js/js/package.json.jinja
diff --git a/js/js/playwright.config.js b/python/js/js/playwright.config.js
similarity index 100%
rename from js/js/playwright.config.js
rename to python/js/js/playwright.config.js
diff --git a/js/js/pnpm-workspace.yaml b/python/js/js/pnpm-workspace.yaml
similarity index 100%
rename from js/js/pnpm-workspace.yaml
rename to python/js/js/pnpm-workspace.yaml
diff --git a/js/js/src/css/index.css b/python/js/js/src/css/index.css
similarity index 100%
rename from js/js/src/css/index.css
rename to python/js/js/src/css/index.css
diff --git a/js/js/src/html/index.html.jinja b/python/js/js/src/html/index.html.jinja
similarity index 100%
rename from js/js/src/html/index.html.jinja
rename to python/js/js/src/html/index.html.jinja
diff --git a/js/js/src/ts/css.d.ts b/python/js/js/src/ts/css.d.ts
similarity index 100%
rename from js/js/src/ts/css.d.ts
rename to python/js/js/src/ts/css.d.ts
diff --git a/js/js/src/ts/index.ts b/python/js/js/src/ts/index.ts
similarity index 100%
rename from js/js/src/ts/index.ts
rename to python/js/js/src/ts/index.ts
diff --git a/js/js/tests/index.spec.js b/python/js/js/tests/index.spec.js
similarity index 100%
rename from js/js/tests/index.spec.js
rename to python/js/js/tests/index.spec.js
diff --git a/js/js/tools/bundle.mjs b/python/js/js/tools/bundle.mjs
similarity index 100%
rename from js/js/tools/bundle.mjs
rename to python/js/js/tools/bundle.mjs
diff --git a/js/js/tools/css.mjs b/python/js/js/tools/css.mjs
similarity index 100%
rename from js/js/tools/css.mjs
rename to python/js/js/tools/css.mjs
diff --git a/js/js/tools/externals.mjs b/python/js/js/tools/externals.mjs
similarity index 100%
rename from js/js/tools/externals.mjs
rename to python/js/js/tools/externals.mjs
diff --git a/js/js/tools/getarg.mjs b/python/js/js/tools/getarg.mjs
similarity index 100%
rename from js/js/tools/getarg.mjs
rename to python/js/js/tools/getarg.mjs
diff --git a/js/js/tools/html.mjs b/python/js/js/tools/html.mjs
similarity index 100%
rename from js/js/tools/html.mjs
rename to python/js/js/tools/html.mjs
diff --git a/js/js/tsconfig.json b/python/js/js/tsconfig.json
similarity index 100%
rename from js/js/tsconfig.json
rename to python/js/js/tsconfig.json
diff --git a/js/pyproject.toml.jinja b/python/js/pyproject.toml.jinja
similarity index 100%
rename from js/pyproject.toml.jinja
rename to python/js/pyproject.toml.jinja
diff --git a/js/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja b/python/js/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
similarity index 100%
rename from js/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
rename to python/js/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
diff --git a/js/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja b/python/js/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
similarity index 100%
rename from js/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
rename to python/js/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
diff --git a/js/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja b/python/js/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
similarity index 100%
rename from js/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
rename to python/js/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
diff --git a/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja b/python/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
similarity index 100%
rename from js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
rename to python/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
diff --git a/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja b/python/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
similarity index 100%
rename from js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
rename to python/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
diff --git a/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja b/python/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
similarity index 100%
rename from js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
rename to python/js/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
diff --git a/js/{{_copier_conf.answers_file}}.jinja b/python/js/{{_copier_conf.answers_file}}.jinja
similarity index 100%
rename from js/{{_copier_conf.answers_file}}.jinja
rename to python/js/{{_copier_conf.answers_file}}.jinja
diff --git a/js/{{module}}/__init__.py b/python/js/{{module}}/__init__.py
similarity index 100%
rename from js/{{module}}/__init__.py
rename to python/js/{{module}}/__init__.py
diff --git a/js/{{module}}/tests/test_all.py.jinja b/python/js/{{module}}/tests/test_all.py.jinja
similarity index 100%
rename from js/{{module}}/tests/test_all.py.jinja
rename to python/js/{{module}}/tests/test_all.py.jinja
diff --git a/jupyter/.gitattributes b/python/jupyter/.gitattributes
similarity index 100%
rename from jupyter/.gitattributes
rename to python/jupyter/.gitattributes
diff --git a/jupyter/.github/CODE_OF_CONDUCT.md.jinja b/python/jupyter/.github/CODE_OF_CONDUCT.md.jinja
similarity index 100%
rename from jupyter/.github/CODE_OF_CONDUCT.md.jinja
rename to python/jupyter/.github/CODE_OF_CONDUCT.md.jinja
diff --git a/jupyter/.github/ISSUE_TEMPLATE/bug_report.md.jinja b/python/jupyter/.github/ISSUE_TEMPLATE/bug_report.md.jinja
similarity index 100%
rename from jupyter/.github/ISSUE_TEMPLATE/bug_report.md.jinja
rename to python/jupyter/.github/ISSUE_TEMPLATE/bug_report.md.jinja
diff --git a/jupyter/.github/ISSUE_TEMPLATE/feature_request.md b/python/jupyter/.github/ISSUE_TEMPLATE/feature_request.md
similarity index 100%
rename from jupyter/.github/ISSUE_TEMPLATE/feature_request.md
rename to python/jupyter/.github/ISSUE_TEMPLATE/feature_request.md
diff --git a/jupyter/.github/ISSUE_TEMPLATE/question.md b/python/jupyter/.github/ISSUE_TEMPLATE/question.md
similarity index 100%
rename from jupyter/.github/ISSUE_TEMPLATE/question.md
rename to python/jupyter/.github/ISSUE_TEMPLATE/question.md
diff --git a/jupyter/.github/dependabot.yaml b/python/jupyter/.github/dependabot.yaml
similarity index 100%
rename from jupyter/.github/dependabot.yaml
rename to python/jupyter/.github/dependabot.yaml
diff --git a/jupyter/.github/pull_request_template.md b/python/jupyter/.github/pull_request_template.md
similarity index 100%
rename from jupyter/.github/pull_request_template.md
rename to python/jupyter/.github/pull_request_template.md
diff --git a/jupyter/.github/workflows/build.yaml.jinja b/python/jupyter/.github/workflows/build.yaml.jinja
similarity index 100%
rename from jupyter/.github/workflows/build.yaml.jinja
rename to python/jupyter/.github/workflows/build.yaml.jinja
diff --git a/jupyter/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja b/python/jupyter/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
similarity index 100%
rename from jupyter/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
rename to python/jupyter/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
diff --git a/jupyter/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja b/python/jupyter/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
similarity index 100%
rename from jupyter/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
rename to python/jupyter/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
diff --git a/jupyter/.gitignore.jinja b/python/jupyter/.gitignore.jinja
similarity index 100%
rename from jupyter/.gitignore.jinja
rename to python/jupyter/.gitignore.jinja
diff --git a/jupyter/.vscode/settings.json b/python/jupyter/.vscode/settings.json
similarity index 100%
rename from jupyter/.vscode/settings.json
rename to python/jupyter/.vscode/settings.json
diff --git a/jupyter/LICENSE.jinja b/python/jupyter/LICENSE.jinja
similarity index 100%
rename from jupyter/LICENSE.jinja
rename to python/jupyter/LICENSE.jinja
diff --git a/jupyter/Makefile.jinja b/python/jupyter/Makefile.jinja
similarity index 100%
rename from jupyter/Makefile.jinja
rename to python/jupyter/Makefile.jinja
diff --git a/jupyter/README.md.jinja b/python/jupyter/README.md.jinja
similarity index 100%
rename from jupyter/README.md.jinja
rename to python/jupyter/README.md.jinja
diff --git a/jupyter/js/.eslintrc.js b/python/jupyter/js/.eslintrc.js
similarity index 100%
rename from jupyter/js/.eslintrc.js
rename to python/jupyter/js/.eslintrc.js
diff --git a/jupyter/js/babel.config.js b/python/jupyter/js/babel.config.js
similarity index 100%
rename from jupyter/js/babel.config.js
rename to python/jupyter/js/babel.config.js
diff --git a/jupyter/js/jest.config.js b/python/jupyter/js/jest.config.js
similarity index 100%
rename from jupyter/js/jest.config.js
rename to python/jupyter/js/jest.config.js
diff --git a/jupyter/js/package.json.jinja b/python/jupyter/js/package.json.jinja
similarity index 100%
rename from jupyter/js/package.json.jinja
rename to python/jupyter/js/package.json.jinja
diff --git a/jupyter/js/pnpm-workspace.yaml b/python/jupyter/js/pnpm-workspace.yaml
similarity index 100%
rename from jupyter/js/pnpm-workspace.yaml
rename to python/jupyter/js/pnpm-workspace.yaml
diff --git a/jupyter/js/src/extension/install.json.jinja b/python/jupyter/js/src/extension/install.json.jinja
similarity index 100%
rename from jupyter/js/src/extension/install.json.jinja
rename to python/jupyter/js/src/extension/install.json.jinja
diff --git a/jupyter/js/src/extension/{{module}}.json.jinja b/python/jupyter/js/src/extension/{{module}}.json.jinja
similarity index 100%
rename from jupyter/js/src/extension/{{module}}.json.jinja
rename to python/jupyter/js/src/extension/{{module}}.json.jinja
diff --git a/jupyter/js/src/index.js.jinja b/python/jupyter/js/src/index.js.jinja
similarity index 100%
rename from jupyter/js/src/index.js.jinja
rename to python/jupyter/js/src/index.js.jinja
diff --git a/jupyter/js/src/notebook.js b/python/jupyter/js/src/notebook.js
similarity index 100%
rename from jupyter/js/src/notebook.js
rename to python/jupyter/js/src/notebook.js
diff --git a/jupyter/js/style/index.css b/python/jupyter/js/style/index.css
similarity index 100%
rename from jupyter/js/style/index.css
rename to python/jupyter/js/style/index.css
diff --git a/jupyter/js/tests/activate.test.js b/python/jupyter/js/tests/activate.test.js
similarity index 100%
rename from jupyter/js/tests/activate.test.js
rename to python/jupyter/js/tests/activate.test.js
diff --git a/jupyter/js/tests/assetsTransformer.js b/python/jupyter/js/tests/assetsTransformer.js
similarity index 100%
rename from jupyter/js/tests/assetsTransformer.js
rename to python/jupyter/js/tests/assetsTransformer.js
diff --git a/jupyter/js/tests/export.test.js b/python/jupyter/js/tests/export.test.js
similarity index 100%
rename from jupyter/js/tests/export.test.js
rename to python/jupyter/js/tests/export.test.js
diff --git a/jupyter/js/tests/fileMock.js b/python/jupyter/js/tests/fileMock.js
similarity index 100%
rename from jupyter/js/tests/fileMock.js
rename to python/jupyter/js/tests/fileMock.js
diff --git a/jupyter/js/tests/setup.js b/python/jupyter/js/tests/setup.js
similarity index 100%
rename from jupyter/js/tests/setup.js
rename to python/jupyter/js/tests/setup.js
diff --git a/jupyter/js/tests/styleMock.js b/python/jupyter/js/tests/styleMock.js
similarity index 100%
rename from jupyter/js/tests/styleMock.js
rename to python/jupyter/js/tests/styleMock.js
diff --git a/jupyter/pyproject.toml.jinja b/python/jupyter/pyproject.toml.jinja
similarity index 100%
rename from jupyter/pyproject.toml.jinja
rename to python/jupyter/pyproject.toml.jinja
diff --git a/jupyter/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja b/python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
similarity index 100%
rename from jupyter/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
rename to python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
diff --git a/jupyter/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja b/python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
similarity index 100%
rename from jupyter/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
rename to python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
diff --git a/jupyter/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja b/python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
similarity index 100%
rename from jupyter/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
rename to python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
diff --git a/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja b/python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
similarity index 100%
rename from jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
rename to python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
diff --git a/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja b/python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
similarity index 100%
rename from jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
rename to python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
diff --git a/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja b/python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
similarity index 100%
rename from jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
rename to python/jupyter/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
diff --git a/jupyter/{{_copier_conf.answers_file}}.jinja b/python/jupyter/{{_copier_conf.answers_file}}.jinja
similarity index 100%
rename from jupyter/{{_copier_conf.answers_file}}.jinja
rename to python/jupyter/{{_copier_conf.answers_file}}.jinja
diff --git a/jupyter/{{module}}/__init__.py.jinja b/python/jupyter/{{module}}/__init__.py.jinja
similarity index 100%
rename from jupyter/{{module}}/__init__.py.jinja
rename to python/jupyter/{{module}}/__init__.py.jinja
diff --git a/jupyter/{{module}}/tests/test_all.py.jinja b/python/jupyter/{{module}}/tests/test_all.py.jinja
similarity index 100%
rename from jupyter/{{module}}/tests/test_all.py.jinja
rename to python/jupyter/{{module}}/tests/test_all.py.jinja
diff --git a/python/.gitattributes b/python/pure/.gitattributes
similarity index 100%
rename from python/.gitattributes
rename to python/pure/.gitattributes
diff --git a/python/.github/CODE_OF_CONDUCT.md.jinja b/python/pure/.github/CODE_OF_CONDUCT.md.jinja
similarity index 100%
rename from python/.github/CODE_OF_CONDUCT.md.jinja
rename to python/pure/.github/CODE_OF_CONDUCT.md.jinja
diff --git a/python/.github/ISSUE_TEMPLATE/bug_report.md.jinja b/python/pure/.github/ISSUE_TEMPLATE/bug_report.md.jinja
similarity index 100%
rename from python/.github/ISSUE_TEMPLATE/bug_report.md.jinja
rename to python/pure/.github/ISSUE_TEMPLATE/bug_report.md.jinja
diff --git a/python/.github/ISSUE_TEMPLATE/feature_request.md b/python/pure/.github/ISSUE_TEMPLATE/feature_request.md
similarity index 100%
rename from python/.github/ISSUE_TEMPLATE/feature_request.md
rename to python/pure/.github/ISSUE_TEMPLATE/feature_request.md
diff --git a/python/.github/ISSUE_TEMPLATE/question.md b/python/pure/.github/ISSUE_TEMPLATE/question.md
similarity index 100%
rename from python/.github/ISSUE_TEMPLATE/question.md
rename to python/pure/.github/ISSUE_TEMPLATE/question.md
diff --git a/python/.github/dependabot.yaml b/python/pure/.github/dependabot.yaml
similarity index 100%
rename from python/.github/dependabot.yaml
rename to python/pure/.github/dependabot.yaml
diff --git a/python/.github/pull_request_template.md b/python/pure/.github/pull_request_template.md
similarity index 100%
rename from python/.github/pull_request_template.md
rename to python/pure/.github/pull_request_template.md
diff --git a/python/.github/workflows/build.yaml.jinja b/python/pure/.github/workflows/build.yaml.jinja
similarity index 100%
rename from python/.github/workflows/build.yaml.jinja
rename to python/pure/.github/workflows/build.yaml.jinja
diff --git a/python/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja b/python/pure/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
similarity index 100%
rename from python/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
rename to python/pure/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
diff --git a/python/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja b/python/pure/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
similarity index 100%
rename from python/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
rename to python/pure/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
diff --git a/python/.gitignore.jinja b/python/pure/.gitignore.jinja
similarity index 100%
rename from python/.gitignore.jinja
rename to python/pure/.gitignore.jinja
diff --git a/python/LICENSE.jinja b/python/pure/LICENSE.jinja
similarity index 100%
rename from python/LICENSE.jinja
rename to python/pure/LICENSE.jinja
diff --git a/python/Makefile.jinja b/python/pure/Makefile.jinja
similarity index 100%
rename from python/Makefile.jinja
rename to python/pure/Makefile.jinja
diff --git a/python/README.md.jinja b/python/pure/README.md.jinja
similarity index 100%
rename from python/README.md.jinja
rename to python/pure/README.md.jinja
diff --git a/python/pyproject.toml.jinja b/python/pure/pyproject.toml.jinja
similarity index 100%
rename from python/pyproject.toml.jinja
rename to python/pure/pyproject.toml.jinja
diff --git a/python/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja b/python/pure/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
similarity index 100%
rename from python/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
rename to python/pure/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
diff --git a/python/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja b/python/pure/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
similarity index 100%
rename from python/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
rename to python/pure/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
diff --git a/python/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja b/python/pure/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
similarity index 100%
rename from python/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
rename to python/pure/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
diff --git a/python/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja b/python/pure/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
similarity index 100%
rename from python/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
rename to python/pure/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
diff --git a/python/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja b/python/pure/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
similarity index 100%
rename from python/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
rename to python/pure/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
diff --git a/python/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja b/python/pure/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
similarity index 100%
rename from python/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
rename to python/pure/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
diff --git a/python/{{_copier_conf.answers_file}}.jinja b/python/pure/{{_copier_conf.answers_file}}.jinja
similarity index 100%
rename from python/{{_copier_conf.answers_file}}.jinja
rename to python/pure/{{_copier_conf.answers_file}}.jinja
diff --git a/python/{{module}}/__init__.py b/python/pure/{{module}}/__init__.py
similarity index 100%
rename from python/{{module}}/__init__.py
rename to python/pure/{{module}}/__init__.py
diff --git a/python/{{module}}/tests/test_all.py.jinja b/python/pure/{{module}}/tests/test_all.py.jinja
similarity index 100%
rename from python/{{module}}/tests/test_all.py.jinja
rename to python/pure/{{module}}/tests/test_all.py.jinja
diff --git a/rust/.gitattributes b/python/rust/.gitattributes
similarity index 100%
rename from rust/.gitattributes
rename to python/rust/.gitattributes
diff --git a/rust/.github/CODE_OF_CONDUCT.md.jinja b/python/rust/.github/CODE_OF_CONDUCT.md.jinja
similarity index 100%
rename from rust/.github/CODE_OF_CONDUCT.md.jinja
rename to python/rust/.github/CODE_OF_CONDUCT.md.jinja
diff --git a/rust/.github/ISSUE_TEMPLATE/bug_report.md.jinja b/python/rust/.github/ISSUE_TEMPLATE/bug_report.md.jinja
similarity index 100%
rename from rust/.github/ISSUE_TEMPLATE/bug_report.md.jinja
rename to python/rust/.github/ISSUE_TEMPLATE/bug_report.md.jinja
diff --git a/rust/.github/ISSUE_TEMPLATE/feature_request.md b/python/rust/.github/ISSUE_TEMPLATE/feature_request.md
similarity index 100%
rename from rust/.github/ISSUE_TEMPLATE/feature_request.md
rename to python/rust/.github/ISSUE_TEMPLATE/feature_request.md
diff --git a/rust/.github/ISSUE_TEMPLATE/question.md b/python/rust/.github/ISSUE_TEMPLATE/question.md
similarity index 100%
rename from rust/.github/ISSUE_TEMPLATE/question.md
rename to python/rust/.github/ISSUE_TEMPLATE/question.md
diff --git a/rust/.github/dependabot.yaml b/python/rust/.github/dependabot.yaml
similarity index 100%
rename from rust/.github/dependabot.yaml
rename to python/rust/.github/dependabot.yaml
diff --git a/rust/.github/pull_request_template.md b/python/rust/.github/pull_request_template.md
similarity index 100%
rename from rust/.github/pull_request_template.md
rename to python/rust/.github/pull_request_template.md
diff --git a/rust/.github/workflows/build.yaml.jinja b/python/rust/.github/workflows/build.yaml.jinja
similarity index 100%
rename from rust/.github/workflows/build.yaml.jinja
rename to python/rust/.github/workflows/build.yaml.jinja
diff --git a/rust/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja b/python/rust/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
similarity index 100%
rename from rust/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
rename to python/rust/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
diff --git a/rust/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja b/python/rust/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
similarity index 100%
rename from rust/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
rename to python/rust/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
diff --git a/rust/.gitignore.jinja b/python/rust/.gitignore.jinja
similarity index 100%
rename from rust/.gitignore.jinja
rename to python/rust/.gitignore.jinja
diff --git a/rust/Cargo.toml.jinja b/python/rust/Cargo.toml.jinja
similarity index 100%
rename from rust/Cargo.toml.jinja
rename to python/rust/Cargo.toml.jinja
diff --git a/rust/LICENSE.jinja b/python/rust/LICENSE.jinja
similarity index 100%
rename from rust/LICENSE.jinja
rename to python/rust/LICENSE.jinja
diff --git a/rust/Makefile.jinja b/python/rust/Makefile.jinja
similarity index 100%
rename from rust/Makefile.jinja
rename to python/rust/Makefile.jinja
diff --git a/rust/README.md.jinja b/python/rust/README.md.jinja
similarity index 100%
rename from rust/README.md.jinja
rename to python/rust/README.md.jinja
diff --git a/rust/pyproject.toml.jinja b/python/rust/pyproject.toml.jinja
similarity index 100%
rename from rust/pyproject.toml.jinja
rename to python/rust/pyproject.toml.jinja
diff --git a/rust/rust/.config/nextest.toml b/python/rust/rust/.config/nextest.toml
similarity index 100%
rename from rust/rust/.config/nextest.toml
rename to python/rust/rust/.config/nextest.toml
diff --git a/rust/rust/Cargo.lock b/python/rust/rust/Cargo.lock
similarity index 100%
rename from rust/rust/Cargo.lock
rename to python/rust/rust/Cargo.lock
diff --git a/rust/rust/Cargo.toml.jinja b/python/rust/rust/Cargo.toml.jinja
similarity index 100%
rename from rust/rust/Cargo.toml.jinja
rename to python/rust/rust/Cargo.toml.jinja
diff --git a/rust/rust/Makefile.jinja b/python/rust/rust/Makefile.jinja
similarity index 100%
rename from rust/rust/Makefile.jinja
rename to python/rust/rust/Makefile.jinja
diff --git a/rust/rust/python/example/mod.rs.jinja b/python/rust/rust/python/example/mod.rs.jinja
similarity index 100%
rename from rust/rust/python/example/mod.rs.jinja
rename to python/rust/rust/python/example/mod.rs.jinja
diff --git a/rust/rust/python/lib.rs.jinja b/python/rust/rust/python/lib.rs.jinja
similarity index 100%
rename from rust/rust/python/lib.rs.jinja
rename to python/rust/rust/python/lib.rs.jinja
diff --git a/rust/rust/src/lib.rs.jinja b/python/rust/rust/src/lib.rs.jinja
similarity index 100%
rename from rust/rust/src/lib.rs.jinja
rename to python/rust/rust/src/lib.rs.jinja
diff --git a/rust/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja b/python/rust/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
similarity index 100%
rename from rust/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
rename to python/rust/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
diff --git a/rust/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja b/python/rust/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
similarity index 100%
rename from rust/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
rename to python/rust/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
diff --git a/rust/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja b/python/rust/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
similarity index 100%
rename from rust/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
rename to python/rust/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
diff --git a/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja b/python/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
similarity index 100%
rename from rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
rename to python/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
diff --git a/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja b/python/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
similarity index 100%
rename from rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
rename to python/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
diff --git a/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja b/python/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
similarity index 100%
rename from rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
rename to python/rust/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
diff --git a/rust/{{_copier_conf.answers_file}}.jinja b/python/rust/{{_copier_conf.answers_file}}.jinja
similarity index 100%
rename from rust/{{_copier_conf.answers_file}}.jinja
rename to python/rust/{{_copier_conf.answers_file}}.jinja
diff --git a/rust/{{module}}/__init__.py b/python/rust/{{module}}/__init__.py
similarity index 100%
rename from rust/{{module}}/__init__.py
rename to python/rust/{{module}}/__init__.py
diff --git a/rust/{{module}}/tests/test_all.py.jinja b/python/rust/{{module}}/tests/test_all.py.jinja
similarity index 100%
rename from rust/{{module}}/tests/test_all.py.jinja
rename to python/rust/{{module}}/tests/test_all.py.jinja
diff --git a/rustjswasm/.gitattributes b/python/rustjswasm/.gitattributes
similarity index 100%
rename from rustjswasm/.gitattributes
rename to python/rustjswasm/.gitattributes
diff --git a/rustjswasm/.github/CODE_OF_CONDUCT.md.jinja b/python/rustjswasm/.github/CODE_OF_CONDUCT.md.jinja
similarity index 100%
rename from rustjswasm/.github/CODE_OF_CONDUCT.md.jinja
rename to python/rustjswasm/.github/CODE_OF_CONDUCT.md.jinja
diff --git a/rustjswasm/.github/ISSUE_TEMPLATE/bug_report.md.jinja b/python/rustjswasm/.github/ISSUE_TEMPLATE/bug_report.md.jinja
similarity index 100%
rename from rustjswasm/.github/ISSUE_TEMPLATE/bug_report.md.jinja
rename to python/rustjswasm/.github/ISSUE_TEMPLATE/bug_report.md.jinja
diff --git a/rustjswasm/.github/ISSUE_TEMPLATE/feature_request.md b/python/rustjswasm/.github/ISSUE_TEMPLATE/feature_request.md
similarity index 100%
rename from rustjswasm/.github/ISSUE_TEMPLATE/feature_request.md
rename to python/rustjswasm/.github/ISSUE_TEMPLATE/feature_request.md
diff --git a/rustjswasm/.github/ISSUE_TEMPLATE/question.md b/python/rustjswasm/.github/ISSUE_TEMPLATE/question.md
similarity index 100%
rename from rustjswasm/.github/ISSUE_TEMPLATE/question.md
rename to python/rustjswasm/.github/ISSUE_TEMPLATE/question.md
diff --git a/rustjswasm/.github/dependabot.yaml b/python/rustjswasm/.github/dependabot.yaml
similarity index 100%
rename from rustjswasm/.github/dependabot.yaml
rename to python/rustjswasm/.github/dependabot.yaml
diff --git a/rustjswasm/.github/pull_request_template.md b/python/rustjswasm/.github/pull_request_template.md
similarity index 100%
rename from rustjswasm/.github/pull_request_template.md
rename to python/rustjswasm/.github/pull_request_template.md
diff --git a/rustjswasm/.github/workflows/build.yaml.jinja b/python/rustjswasm/.github/workflows/build.yaml.jinja
similarity index 100%
rename from rustjswasm/.github/workflows/build.yaml.jinja
rename to python/rustjswasm/.github/workflows/build.yaml.jinja
diff --git a/rustjswasm/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja b/python/rustjswasm/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
similarity index 100%
rename from rustjswasm/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
rename to python/rustjswasm/.github/workflows/{% if add_docs %}docs.yaml{% endif %}.jinja
diff --git a/rustjswasm/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja b/python/rustjswasm/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
similarity index 100%
rename from rustjswasm/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
rename to python/rustjswasm/.github/workflows/{% if add_wiki %}wiki.yaml{% endif %}.jinja
diff --git a/rustjswasm/.gitignore.jinja b/python/rustjswasm/.gitignore.jinja
similarity index 100%
rename from rustjswasm/.gitignore.jinja
rename to python/rustjswasm/.gitignore.jinja
diff --git a/rustjswasm/.vscode/settings.json b/python/rustjswasm/.vscode/settings.json
similarity index 100%
rename from rustjswasm/.vscode/settings.json
rename to python/rustjswasm/.vscode/settings.json
diff --git a/rustjswasm/Cargo.toml.jinja b/python/rustjswasm/Cargo.toml.jinja
similarity index 100%
rename from rustjswasm/Cargo.toml.jinja
rename to python/rustjswasm/Cargo.toml.jinja
diff --git a/rustjswasm/LICENSE.jinja b/python/rustjswasm/LICENSE.jinja
similarity index 100%
rename from rustjswasm/LICENSE.jinja
rename to python/rustjswasm/LICENSE.jinja
diff --git a/rustjswasm/Makefile.jinja b/python/rustjswasm/Makefile.jinja
similarity index 100%
rename from rustjswasm/Makefile.jinja
rename to python/rustjswasm/Makefile.jinja
diff --git a/rustjswasm/README.md.jinja b/python/rustjswasm/README.md.jinja
similarity index 100%
rename from rustjswasm/README.md.jinja
rename to python/rustjswasm/README.md.jinja
diff --git a/rustjswasm/js/Cargo.toml.jinja b/python/rustjswasm/js/Cargo.toml.jinja
similarity index 100%
rename from rustjswasm/js/Cargo.toml.jinja
rename to python/rustjswasm/js/Cargo.toml.jinja
diff --git a/rustjswasm/js/build.mjs.jinja b/python/rustjswasm/js/build.mjs.jinja
similarity index 100%
rename from rustjswasm/js/build.mjs.jinja
rename to python/rustjswasm/js/build.mjs.jinja
diff --git a/rustjswasm/js/package.json.jinja b/python/rustjswasm/js/package.json.jinja
similarity index 100%
rename from rustjswasm/js/package.json.jinja
rename to python/rustjswasm/js/package.json.jinja
diff --git a/rustjswasm/js/playwright.config.js b/python/rustjswasm/js/playwright.config.js
similarity index 100%
rename from rustjswasm/js/playwright.config.js
rename to python/rustjswasm/js/playwright.config.js
diff --git a/rustjswasm/js/pnpm-workspace.yaml b/python/rustjswasm/js/pnpm-workspace.yaml
similarity index 100%
rename from rustjswasm/js/pnpm-workspace.yaml
rename to python/rustjswasm/js/pnpm-workspace.yaml
diff --git a/rustjswasm/js/src/css/index.css b/python/rustjswasm/js/src/css/index.css
similarity index 100%
rename from rustjswasm/js/src/css/index.css
rename to python/rustjswasm/js/src/css/index.css
diff --git a/rustjswasm/js/src/html/index.html.jinja b/python/rustjswasm/js/src/html/index.html.jinja
similarity index 100%
rename from rustjswasm/js/src/html/index.html.jinja
rename to python/rustjswasm/js/src/html/index.html.jinja
diff --git a/rustjswasm/js/src/rust/lib.rs b/python/rustjswasm/js/src/rust/lib.rs
similarity index 100%
rename from rustjswasm/js/src/rust/lib.rs
rename to python/rustjswasm/js/src/rust/lib.rs
diff --git a/rustjswasm/js/src/ts/css.d.ts b/python/rustjswasm/js/src/ts/css.d.ts
similarity index 100%
rename from rustjswasm/js/src/ts/css.d.ts
rename to python/rustjswasm/js/src/ts/css.d.ts
diff --git a/rustjswasm/js/src/ts/index.ts.jinja b/python/rustjswasm/js/src/ts/index.ts.jinja
similarity index 100%
rename from rustjswasm/js/src/ts/index.ts.jinja
rename to python/rustjswasm/js/src/ts/index.ts.jinja
diff --git a/rustjswasm/js/tests/index.spec.js b/python/rustjswasm/js/tests/index.spec.js
similarity index 100%
rename from rustjswasm/js/tests/index.spec.js
rename to python/rustjswasm/js/tests/index.spec.js
diff --git a/rustjswasm/js/tools/bundle.mjs b/python/rustjswasm/js/tools/bundle.mjs
similarity index 100%
rename from rustjswasm/js/tools/bundle.mjs
rename to python/rustjswasm/js/tools/bundle.mjs
diff --git a/rustjswasm/js/tools/css.mjs b/python/rustjswasm/js/tools/css.mjs
similarity index 100%
rename from rustjswasm/js/tools/css.mjs
rename to python/rustjswasm/js/tools/css.mjs
diff --git a/rustjswasm/js/tools/externals.mjs b/python/rustjswasm/js/tools/externals.mjs
similarity index 100%
rename from rustjswasm/js/tools/externals.mjs
rename to python/rustjswasm/js/tools/externals.mjs
diff --git a/rustjswasm/js/tools/getarg.mjs b/python/rustjswasm/js/tools/getarg.mjs
similarity index 100%
rename from rustjswasm/js/tools/getarg.mjs
rename to python/rustjswasm/js/tools/getarg.mjs
diff --git a/rustjswasm/js/tools/html.mjs b/python/rustjswasm/js/tools/html.mjs
similarity index 100%
rename from rustjswasm/js/tools/html.mjs
rename to python/rustjswasm/js/tools/html.mjs
diff --git a/rustjswasm/js/tsconfig.json b/python/rustjswasm/js/tsconfig.json
similarity index 100%
rename from rustjswasm/js/tsconfig.json
rename to python/rustjswasm/js/tsconfig.json
diff --git a/rustjswasm/pyproject.toml.jinja b/python/rustjswasm/pyproject.toml.jinja
similarity index 100%
rename from rustjswasm/pyproject.toml.jinja
rename to python/rustjswasm/pyproject.toml.jinja
diff --git a/rustjswasm/rust/.config/nextest.toml b/python/rustjswasm/rust/.config/nextest.toml
similarity index 100%
rename from rustjswasm/rust/.config/nextest.toml
rename to python/rustjswasm/rust/.config/nextest.toml
diff --git a/rustjswasm/rust/Cargo.lock b/python/rustjswasm/rust/Cargo.lock
similarity index 100%
rename from rustjswasm/rust/Cargo.lock
rename to python/rustjswasm/rust/Cargo.lock
diff --git a/rustjswasm/rust/Cargo.toml.jinja b/python/rustjswasm/rust/Cargo.toml.jinja
similarity index 100%
rename from rustjswasm/rust/Cargo.toml.jinja
rename to python/rustjswasm/rust/Cargo.toml.jinja
diff --git a/rustjswasm/rust/Makefile.jinja b/python/rustjswasm/rust/Makefile.jinja
similarity index 100%
rename from rustjswasm/rust/Makefile.jinja
rename to python/rustjswasm/rust/Makefile.jinja
diff --git a/rustjswasm/rust/python/example/mod.rs.jinja b/python/rustjswasm/rust/python/example/mod.rs.jinja
similarity index 100%
rename from rustjswasm/rust/python/example/mod.rs.jinja
rename to python/rustjswasm/rust/python/example/mod.rs.jinja
diff --git a/rustjswasm/rust/python/lib.rs.jinja b/python/rustjswasm/rust/python/lib.rs.jinja
similarity index 100%
rename from rustjswasm/rust/python/lib.rs.jinja
rename to python/rustjswasm/rust/python/lib.rs.jinja
diff --git a/rustjswasm/rust/src/lib.rs.jinja b/python/rustjswasm/rust/src/lib.rs.jinja
similarity index 100%
rename from rustjswasm/rust/src/lib.rs.jinja
rename to python/rustjswasm/rust/src/lib.rs.jinja
diff --git a/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja b/python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
similarity index 100%
rename from rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
rename to python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/Installation.md.jinja
diff --git a/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja b/python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
similarity index 100%
rename from rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
rename to python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Footer.md.jinja
diff --git a/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja b/python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
similarity index 100%
rename from rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
rename to python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/_Sidebar.md.jinja
diff --git a/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja b/python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
similarity index 100%
rename from rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
rename to python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Build-from-Source.md.jinja
diff --git a/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja b/python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
similarity index 100%
rename from rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
rename to python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Contribute.md.jinja
diff --git a/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja b/python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
similarity index 100%
rename from rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
rename to python/rustjswasm/{% if add_wiki %}docs{% endif %}/wiki/contribute/Local-Development-Setup.md.jinja
diff --git a/rustjswasm/{{_copier_conf.answers_file}}.jinja b/python/rustjswasm/{{_copier_conf.answers_file}}.jinja
similarity index 100%
rename from rustjswasm/{{_copier_conf.answers_file}}.jinja
rename to python/rustjswasm/{{_copier_conf.answers_file}}.jinja
diff --git a/rustjswasm/{{module}}/__init__.py b/python/rustjswasm/{{module}}/__init__.py
similarity index 100%
rename from rustjswasm/{{module}}/__init__.py
rename to python/rustjswasm/{{module}}/__init__.py
diff --git a/rustjswasm/{{module}}/tests/test_all.py.jinja b/python/rustjswasm/{{module}}/tests/test_all.py.jinja
similarity index 100%
rename from rustjswasm/{{module}}/tests/test_all.py.jinja
rename to python/rustjswasm/{{module}}/tests/test_all.py.jinja