diff --git a/.prettierrc b/.prettierrc
index 9573023..20c211a 100644
--- a/.prettierrc
+++ b/.prettierrc
@@ -4,5 +4,6 @@
"trailingComma": "none",
"printWidth": 100,
"plugins": ["prettier-plugin-svelte"],
- "overrides": [{ "files": "*.svelte", "options": { "parser": "svelte" } }]
+ "overrides": [{ "files": "*.svelte", "options": { "parser": "svelte" } }],
+ "bracketSameLine": true
}
diff --git a/bun.lockb b/bun.lockb
index 5e87b52..f7ea78b 100755
Binary files a/bun.lockb and b/bun.lockb differ
diff --git a/package.json b/package.json
index f165e8e..bd86d69 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@selenite/commons",
- "version": "0.1.4",
+ "version": "0.2.1",
"scripts": {
"dev": "vite dev",
"build": "vite build && npm run package",
@@ -36,16 +36,19 @@
"@sveltejs/vite-plugin-svelte": "^3.0.0",
"@types/eslint": "^8.56.7",
"@types/lodash-es": "^4.17.12",
+ "autoprefixer": "^10.4.19",
"eslint": "^9.0.0",
"eslint-config-prettier": "^9.1.0",
"eslint-plugin-svelte": "^2.36.0",
"globals": "^15.0.0",
"lodash-es": "^4.17.21",
+ "postcss": "^8.4.39",
"prettier": "^3.1.1",
"prettier-plugin-svelte": "^3.1.2",
"publint": "^0.1.9",
"svelte": "^5.0.0-next.1",
"svelte-check": "^3.6.0",
+ "tailwindcss": "^3.4.4",
"tslib": "^2.4.1",
"typescript": "^5.0.0",
"typescript-eslint": "^8.0.0-alpha.20",
diff --git a/postcss.config.js b/postcss.config.js
new file mode 100644
index 0000000..2e7af2b
--- /dev/null
+++ b/postcss.config.js
@@ -0,0 +1,6 @@
+export default {
+ plugins: {
+ tailwindcss: {},
+ autoprefixer: {},
+ },
+}
diff --git a/src/app.css b/src/app.css
new file mode 100644
index 0000000..bd6213e
--- /dev/null
+++ b/src/app.css
@@ -0,0 +1,3 @@
+@tailwind base;
+@tailwind components;
+@tailwind utilities;
\ No newline at end of file
diff --git a/src/app.html b/src/app.html
index f22aeaa..de8f7a8 100644
--- a/src/app.html
+++ b/src/app.html
@@ -6,7 +6,7 @@
%sveltekit.head%
-
- %sveltekit.body%
+
+ %sveltekit.body%
diff --git a/src/lib/actions/canvas.ts b/src/lib/actions/canvas.ts
new file mode 100644
index 0000000..94b26a1
--- /dev/null
+++ b/src/lib/actions/canvas.ts
@@ -0,0 +1,64 @@
+import { lerp } from '$lib/utils';
+import type { Action } from 'svelte/action';
+
+export type Transform = { x: number; y: number; k: number };
+
+function drawLines({
+ canvas,
+ transform,
+ spacing: baseSpacing = 80
+ }: {
+ canvas: HTMLCanvasElement;
+
+ transform: Transform;
+ spacing?: number;
+ }) {
+ if (transform.k < 0.01) return;
+ const ctx = canvas.getContext('2d');
+ if (!ctx) {
+ throw new Error('Canvas is not a 2d canvas.');
+ }
+ ctx.save();
+ ctx.beginPath();
+ const scalingFactor = Math.floor(1 + -Math.log(transform.k) / Math.log(3));
+ const spacing = scalingFactor > 0 ? baseSpacing * scalingFactor : baseSpacing;
+ console.log('spacing\t', spacing);
+ const step = spacing * transform.k;
+ console.log('zoom\t', transform.k);
+ // Draw vertical lines
+ for (let x = (transform.x % step) - step; x <= canvas.width; x += step) {
+ ctx.moveTo(x, 0);
+ ctx.lineTo(x, canvas.height);
+ }
+
+ // Draw horizontal lines
+ for (let y = (transform.y % step) - step; y <= canvas.height; y += step) {
+ ctx.moveTo(0, y);
+ ctx.lineTo(canvas.width, y);
+ }
+ // Stroke the lines
+ ctx.strokeStyle = '#ddd';
+ ctx.lineWidth = transform.k > 0.1 ? 0.08 : lerp(0.08, 0, (transform.k - 0.01) / 0.09);
+ ctx.stroke();
+ ctx.restore();
+ }
+
+export const gridLines: Action = (
+ canvas,
+ params
+) => {
+ const ctx = canvas.getContext('2d');
+ if (!ctx) {
+ throw new Error('Canvas is not a 2d canvas.');
+ }
+
+ drawLines({ ...params, canvas });
+
+ return {
+ destroy() {},
+ update(params) {
+ ctx.clearRect(0, 0, canvas.width, canvas.height);
+ drawLines({ canvas, ...params });
+ }
+ };
+};
diff --git a/src/lib/actions/index.ts b/src/lib/actions/index.ts
index 00f349a..007994c 100644
--- a/src/lib/actions/index.ts
+++ b/src/lib/actions/index.ts
@@ -1,6 +1,7 @@
import type { Action } from 'svelte/action';
export * from './focusTrap.js'
export * from './shortcut.js'
+export * from './canvas.js'
let handleFocusLeaveRefCount = 0;
let handleFocusLeaveCallbacks: ((isKeyboard: boolean) => void)[] = [];
function handleKeydown(e: KeyboardEvent) {
diff --git a/src/lib/utils/index.ts b/src/lib/utils/index.ts
index 3e63952..d464d98 100644
--- a/src/lib/utils/index.ts
+++ b/src/lib/utils/index.ts
@@ -4,7 +4,7 @@
export * from './string.js';
export * from './eventListeners.js';
export * from './array/index.js'
-
+export * from './math.js'
export { v4 as uuidv4 } from 'uuid';
import {v4 as uuid} from 'uuid'
let idCount = 0;
diff --git a/src/lib/utils/math.ts b/src/lib/utils/math.ts
new file mode 100644
index 0000000..b64a4d4
--- /dev/null
+++ b/src/lib/utils/math.ts
@@ -0,0 +1,3 @@
+export function lerp(start: number, end: number, alpha: number) {
+ return start + (end - start) * alpha;
+}
\ No newline at end of file
diff --git a/src/routes/+layout.svelte b/src/routes/+layout.svelte
new file mode 100644
index 0000000..093ea88
--- /dev/null
+++ b/src/routes/+layout.svelte
@@ -0,0 +1,18 @@
+
+
+
+
+
+
\ No newline at end of file
diff --git a/src/routes/canvas/+page.svelte b/src/routes/canvas/+page.svelte
new file mode 100644
index 0000000..88bfa48
--- /dev/null
+++ b/src/routes/canvas/+page.svelte
@@ -0,0 +1,43 @@
+
+
+
+
+
+
+
+
+
diff --git a/tailwind.config.ts b/tailwind.config.ts
new file mode 100644
index 0000000..d4be033
--- /dev/null
+++ b/tailwind.config.ts
@@ -0,0 +1,9 @@
+/** @type {import('tailwindcss').Config} */
+export default {
+ content: ['./src/**/*.{html,js,ts,svelte}'],
+ theme: {
+ extend: {}
+ },
+ plugins: []
+};
+
diff --git a/tsconfig.json b/tsconfig.json
index 6f788f1..815029b 100644
--- a/tsconfig.json
+++ b/tsconfig.json
@@ -9,7 +9,7 @@
"skipLibCheck": true,
"sourceMap": true,
"strict": true,
- "module": "NodeNext",
- "moduleResolution": "NodeNext"
+ "module": "ES2022",
+ "moduleResolution": "Bundler"
}
}