From a658e571ef245a200884ea96198c54188ae650da Mon Sep 17 00:00:00 2001 From: Josh Kingsley Date: Sat, 25 Oct 2025 16:24:53 +0300 Subject: feat(web): setup components --- web/components/app/index.ts | 13 +++++++++++++ web/components/grid/index.ts | 14 ++++++++++++++ web/components/index.ts | 2 ++ web/global.d.ts | 9 +++++++++ web/html.ts | 26 ++++++++++++++++++++++++++ web/index.css | 10 ++++++++++ web/index.html | 4 +++- web/index.ts | 38 +++++++++++++++++++++++++++++++++++--- web/package.json | 3 +++ web/tsconfig.json | 12 ++++++++++++ 10 files changed, 127 insertions(+), 4 deletions(-) create mode 100644 web/components/app/index.ts create mode 100644 web/components/grid/index.ts create mode 100644 web/components/index.ts create mode 100644 web/global.d.ts create mode 100644 web/html.ts create mode 100644 web/index.css create mode 100644 web/tsconfig.json (limited to 'web') diff --git a/web/components/app/index.ts b/web/components/app/index.ts new file mode 100644 index 0000000..f4eaff1 --- /dev/null +++ b/web/components/app/index.ts @@ -0,0 +1,13 @@ +import ntvGrid from "../grid"; + +class NotiveAppElement extends HTMLElement { + connectedCallback() { + this.append( + ...window.notive.doc.grids.map((_grid) => { + return ntvGrid({ foo: "1" }); + }), + ); + } +} + +customElements.define("ntv-app", NotiveAppElement); diff --git a/web/components/grid/index.ts b/web/components/grid/index.ts new file mode 100644 index 0000000..7faf6b1 --- /dev/null +++ b/web/components/grid/index.ts @@ -0,0 +1,14 @@ +import h, { type CreateElement } from "../../html"; + +class NotiveGridElement extends HTMLElement { + foo: string; + + connectedCallback() { + this.appendChild(h.p("OK: " + this.foo)); + } +} + +customElements.define("ntv-grid", NotiveGridElement); + +export default ((...args: any[]): NotiveGridElement => + (h as any)["ntv-grid"](...args)) as CreateElement; diff --git a/web/components/index.ts b/web/components/index.ts new file mode 100644 index 0000000..8bc14e7 --- /dev/null +++ b/web/components/index.ts @@ -0,0 +1,2 @@ +import "./app"; +import "./grid"; diff --git a/web/global.d.ts b/web/global.d.ts new file mode 100644 index 0000000..3b6d980 --- /dev/null +++ b/web/global.d.ts @@ -0,0 +1,9 @@ +import type Notive from "./index"; + +declare global { + interface Window { + notive: Notive; + } +} + +export {}; diff --git a/web/html.ts b/web/html.ts new file mode 100644 index 0000000..5bfff21 --- /dev/null +++ b/web/html.ts @@ -0,0 +1,26 @@ +export type CreateElement = { + (...children: (Node | string)[]): T; + (attrs: Partial, ...children: (Node | string)[]): T; +}; + +type ElementCreator = { + [K in keyof HTMLElementTagNameMap]: CreateElement; +}; + +const h = new Proxy({} as ElementCreator, { + get: + (_, tag: string) => + (...args: any[]) => { + const el = document.createElement(tag); + + if (typeof args[0] === "object") { + Object.assign(el, args.shift()); + } + + el.append(...args.flat()); + + return el; + }, +}); + +export default h; diff --git a/web/index.css b/web/index.css new file mode 100644 index 0000000..f578562 --- /dev/null +++ b/web/index.css @@ -0,0 +1,10 @@ +@import "open-color"; + +body { + background: var(--oc-gray-9); + color: var(--oc-white); + font-weight: normal; + font-family: + Seravek, "Gill Sans Nova", Ubuntu, Calibri, "DejaVu Sans", source-sans-pro, + sans-serif; +} diff --git a/web/index.html b/web/index.html index b7231ea..846f5be 100644 --- a/web/index.html +++ b/web/index.html @@ -3,9 +3,11 @@ Notive + + -

Hello, World!

+ diff --git a/web/index.ts b/web/index.ts index a34c8b4..1524b04 100644 --- a/web/index.ts +++ b/web/index.ts @@ -1,5 +1,37 @@ -console.log("OK"); +interface Cell { + value: string; +} + +interface Row { + cells: Cell[]; +} + +interface Part { + rows: Row[]; +} + +interface Grid { + parts: Part[]; +} -function foo() { - return "foo"; +interface Doc { + grids: Grid[]; } + +function defaultDoc(): Doc { + const defaultCells = Array(16).map(() => ({ value: "1" })); + + return { + grids: [ + { parts: [{ rows: Array(4).map(() => ({ cells: [...defaultCells] })) }] }, + ], + }; +} + +export default class Notive { + doc: Doc = defaultDoc(); +} + +window.notive = new Notive(); + +window.dispatchEvent(new CustomEvent("ntv:initialized")); diff --git a/web/package.json b/web/package.json index bc3b744..e0b674d 100644 --- a/web/package.json +++ b/web/package.json @@ -6,5 +6,8 @@ }, "devDependencies": { "vite": "^7.1.12" + }, + "dependencies": { + "open-color": "^1.9.1" } } diff --git a/web/tsconfig.json b/web/tsconfig.json new file mode 100644 index 0000000..7ef66ad --- /dev/null +++ b/web/tsconfig.json @@ -0,0 +1,12 @@ +{ + "compilerOptions": { + "target": "ES2020", + "module": "ESNext", + "lib": ["ES2020", "DOM", "DOM.Iterable"], + "moduleResolution": "bundler", + "strict": true, + "skipLibCheck": true, + "esModuleInterop": true + }, + "include": ["*.ts", "**/*.ts"] +} -- cgit v1.2.3