diff --git a/bau/bau.d.ts b/bau/bau.d.ts index 87be55ff..d4e5a97b 100644 --- a/bau/bau.d.ts +++ b/bau/bau.d.ts @@ -135,118 +135,12 @@ export type TagFunc = ( ...rest: readonly ChildDom[] ) => Result; -interface TagsBase { - readonly [key: string]: TagFunc; -} - -interface Tags extends TagsBase { - // Register known element types - // Source: https://developer.mozilla.org/en-US/docs/Web/HTML/Element - - // Main root - readonly html: TagFunc; - - // Document metadata - readonly base: TagFunc; - readonly head: TagFunc; - readonly link: TagFunc; - readonly meta: TagFunc; - readonly style: TagFunc; - readonly title: TagFunc; - - // Sectioning root - readonly body: TagFunc; - - // Content sectioning - readonly h1: TagFunc; - readonly h2: TagFunc; - readonly h3: TagFunc; - readonly h4: TagFunc; - readonly h5: TagFunc; - readonly h6: TagFunc; - - // Text content - readonly blockquote: TagFunc; - readonly div: TagFunc; - readonly dl: TagFunc; - readonly hr: TagFunc; - readonly li: TagFunc; - readonly menu: TagFunc; - readonly ol: TagFunc; - readonly p: TagFunc; - readonly pre: TagFunc; - readonly ul: TagFunc; - - // Inline text semantics - readonly a: TagFunc; - readonly br: TagFunc; - readonly data: TagFunc; - readonly q: TagFunc; - readonly span: TagFunc; - readonly time: TagFunc; - - // Image and multimedia - readonly area: TagFunc; - readonly audio: TagFunc; - readonly img: TagFunc; - readonly map: TagFunc; - readonly track: TagFunc; - readonly video: TagFunc; - - // Embedded content - readonly embed: TagFunc; - readonly iframe: TagFunc; - readonly object: TagFunc; - readonly picture: TagFunc; - readonly source: TagFunc; - - // Scripting - readonly canvas: TagFunc; - readonly script: TagFunc; - - // Demarcating edits - readonly del: TagFunc; - readonly ins: TagFunc; - - // Table content - readonly caption: TagFunc; - readonly col: TagFunc; - readonly colgroup: TagFunc; - readonly table: TagFunc; - readonly tbody: TagFunc; - readonly td: TagFunc; - readonly tfoot: TagFunc; - readonly th: TagFunc; - readonly thead: TagFunc; - readonly tr: TagFunc; - - // Forms - readonly button: TagFunc; - readonly datalist: TagFunc; - readonly fieldset: TagFunc; - readonly form: TagFunc; - readonly input: TagFunc; - readonly label: TagFunc; - readonly legend: TagFunc; - readonly meter: TagFunc; - readonly optgroup: TagFunc; - readonly option: TagFunc; - readonly output: TagFunc; - readonly progress: TagFunc; - readonly select: TagFunc; - readonly textarea: TagFunc; - - // Interactive elements - readonly details: TagFunc; - readonly dialog: TagFunc; - - // Web Components - readonly slot: TagFunc; - readonly template: TagFunc; -} +type Tags = Readonly>> & { + [K in keyof HTMLElementTagNameMap]: TagFunc; +}; declare function state(initVal: T): State; -declare function tagsNS(namespaceURI: string): TagsBase; +declare function tagsNS(namespaceURI: string): Tags; declare function bind(input: BindInput): HTMLElement; declare function derive(computed: () => T): ReadonlyState; declare function loop( diff --git a/examples/bento-grid/.gitignore b/examples/bento-grid/.gitignore new file mode 100644 index 00000000..a547bf36 --- /dev/null +++ b/examples/bento-grid/.gitignore @@ -0,0 +1,24 @@ +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +pnpm-debug.log* +lerna-debug.log* + +node_modules +dist +dist-ssr +*.local + +# Editor directories and files +.vscode/* +!.vscode/extensions.json +.idea +.DS_Store +*.suo +*.ntvs* +*.njsproj +*.sln +*.sw? diff --git a/examples/bento-grid/.npmrc b/examples/bento-grid/.npmrc new file mode 100644 index 00000000..6b5f38e8 --- /dev/null +++ b/examples/bento-grid/.npmrc @@ -0,0 +1,2 @@ +save-exact = true +package-lock = false diff --git a/examples/bento-grid/README.md b/examples/bento-grid/README.md new file mode 100644 index 00000000..5d31be75 --- /dev/null +++ b/examples/bento-grid/README.md @@ -0,0 +1,23 @@ +# FrontendMentor Bento Grid + +Here is the implementation in _Bau.js_ of the [Frontend Mentor Bento Grid code challenge](https://www.frontendmentor.io/challenges/bento-grid-RMydElrlOj) + +## Workflow + +Install the dependencies: + +```sh +npm install +``` + +Start a development server: + +```sh +npm run dev +``` + +Build a production version: + +```sh +npm run build +``` diff --git a/examples/bento-grid/bentoGrid.js b/examples/bento-grid/bentoGrid.js new file mode 100644 index 00000000..cbc13c3c --- /dev/null +++ b/examples/bento-grid/bentoGrid.js @@ -0,0 +1,211 @@ +export default function (context) { + const { bau, css } = context; + const { h1, picture, em, img, p, i, strong, article, section } = bau.tags; + + const className = css` + min-height: 95vh; + max-width: 900px; + display: grid; + gap: 1rem; + margin: 1rem; + grid-template-columns: 1fr 1fr 1fr 1fr; + grid-template-areas: + "section7 section1 section1 section4" + "section7 section2 section3 section4" + "section8 section2 section3 section4" + "section8 section6 section5 section5"; + + @media (max-width: 640px) { + grid-template-columns: 1fr; + grid-template-rows: auto; + grid-template-areas: "section1" "section2" "section3" "section4" "section5" "section6" "section7" "section8"; + } + + section { + background-color: var(--clr-white); + min-height: 100px; + min-width: 100px; + border-radius: 0.8rem; + padding: 1rem; + display: flex; + flex-direction: column; + gap: 1rem; + overflow: hidden; + h1 { + } + &.section1 { + grid-area: section1; + text-align: center; + background-color: var(--clr-primary-500); + color: var(--clr-white); + align-items: center; + h1 { + font-size: 2rem; + strong { + color: var(--clr-secondary-500); + } + } + img { + max-width: 200px; + } + } + &.section2 { + grid-area: section2; + } + + &.section3 { + background-color: var(--clr-secondary-500); + grid-area: section3; + padding-bottom: 0; + justify-content: space-between; + picture { + max-height: 100px; + overflow: hidden; + } + img { + max-width: 250px; + } + } + + &.section4 { + grid-area: section4; + background-color: var(--clr-primary-100); + display: flex; + justify-content: center; + align-items: flex-start; + @media (max-width: 640px) { + align-items: center; + } + + img { + max-height: 200px; + } + p { + font-size: smaller; + } + } + &.section5 { + grid-area: section5; + background-color: var(--clr-primary-500); + color: var(--clr-white); + display: flex; + align-items: center; + flex-direction: row; + @media (max-width: 640px) { + flex-direction: column; + } + img { + max-width: 200px; + max-height: 200px; + } + h1 { + text-align: center; + } + } + + &.section6 { + grid-area: section6; + h1 { + font-size: xx-large; + } + img { + max-width: 300px; + } + } + + &.section7 { + grid-area: section7; + background-color: var(--clr-secondary-100); + align-items: center; + h1 { + font-size: 1.7rem; + font-weight: 400; + } + img { + max-width: 150px; + } + em { + color: var(--clr-primary-500); + } + } + + &.section8 { + grid-area: section8; + background-color: var(--clr-secondary-500); + h1 { + font-size: 1.7rem; + font-weight: 400; + } + } + } + `; + + return function bentoGrid() { + return article( + { class: className }, + section( + { class: "section1" }, + h1("Social Media ", strong("10x"), i(" Faster"), " with AI"), + img({ + src: "./assets/images/illustration-five-stars.webp", + }), + p("Over 4,000 5-star reviews") + ), + section( + { class: "section2" }, + img({ + src: "./assets/images/illustration-multiple-platforms.webp", + }), + h1("Manage multiple accounts and platforms.") + ), + section( + { class: "section3" }, + h1("Maintain a consistent posting schedule."), + picture( + img({ + src: "./assets/images/illustration-consistent-schedule.webp", + }) + ) + ), + section( + { class: "section4" }, + h1("Schedule to social media."), + img({ + src: "./assets/images/illustration-schedule-posts.webp", + }), + p( + "Optimize post timings to publish content at the perfect time for your audience." + ) + ), + section( + { class: "section5" }, + img({ + src: "./assets/images/illustration-grow-followers.webp", + }), + h1("Grow followers with non-stop content.") + ), + section( + { class: "section6" }, + h1("> 56%"), + p("faster audience growth"), + img({ + src: "./assets/images/illustration-audience-growth.webp", + }) + ), + section( + { class: "section7" }, + h1("Create and schedule content ", em("quicker"), "."), + img({ + src: "./assets/images/illustration-create-post.webp", + }) + ), + section( + { class: "section8" }, + h1("Write your content using AI."), + img({ + src: "./assets/images/illustration-ai-content.webp", + }) + ) + ); + }; +} diff --git a/examples/bento-grid/index.html b/examples/bento-grid/index.html new file mode 100644 index 00000000..4343cd6e --- /dev/null +++ b/examples/bento-grid/index.html @@ -0,0 +1,23 @@ + + + + + + + Frontend Mentor Bento Grid + + + + + +
+ + + diff --git a/examples/bento-grid/main.js b/examples/bento-grid/main.js new file mode 100644 index 00000000..c44debfe --- /dev/null +++ b/examples/bento-grid/main.js @@ -0,0 +1,24 @@ +import Bau from "@grucloud/bau"; +import BauCss from "@grucloud/bau-css"; +import bentoGrid from "./bentoGrid"; + +import "./style.css"; + +const context = { + bau: Bau(), + ...BauCss(), +}; + +const app = (context) => { + const { bau, css } = context; + const { main } = bau.tags; + + const BentoGrid = bentoGrid(context); + + return function () { + return main(BentoGrid()); + }; +}; + +const App = app(context); +document.getElementById("app").replaceChildren(App()); diff --git a/examples/bento-grid/package.json b/examples/bento-grid/package.json new file mode 100644 index 00000000..d03f01dc --- /dev/null +++ b/examples/bento-grid/package.json @@ -0,0 +1,18 @@ +{ + "name": "frontendmentor-bentogrid", + "private": true, + "version": "0.85.0", + "type": "module", + "scripts": { + "dev": "vite", + "build": "vite build", + "preview": "vite preview" + }, + "devDependencies": { + "vite": "^5.2.11" + }, + "dependencies": { + "@grucloud/bau": "^0.85.0", + "@grucloud/bau-css": "^0.85.0" + } +} diff --git a/examples/bento-grid/public/assets/images/favicon-32x32.png b/examples/bento-grid/public/assets/images/favicon-32x32.png new file mode 100644 index 00000000..1e2df7f0 Binary files /dev/null and b/examples/bento-grid/public/assets/images/favicon-32x32.png differ diff --git a/examples/bento-grid/public/assets/images/illustration-ai-content.webp b/examples/bento-grid/public/assets/images/illustration-ai-content.webp new file mode 100644 index 00000000..4c35d530 Binary files /dev/null and b/examples/bento-grid/public/assets/images/illustration-ai-content.webp differ diff --git a/examples/bento-grid/public/assets/images/illustration-audience-growth.webp b/examples/bento-grid/public/assets/images/illustration-audience-growth.webp new file mode 100644 index 00000000..77d4600e Binary files /dev/null and b/examples/bento-grid/public/assets/images/illustration-audience-growth.webp differ diff --git a/examples/bento-grid/public/assets/images/illustration-consistent-schedule.webp b/examples/bento-grid/public/assets/images/illustration-consistent-schedule.webp new file mode 100644 index 00000000..9af8e3d1 Binary files /dev/null and b/examples/bento-grid/public/assets/images/illustration-consistent-schedule.webp differ diff --git a/examples/bento-grid/public/assets/images/illustration-create-post.webp b/examples/bento-grid/public/assets/images/illustration-create-post.webp new file mode 100644 index 00000000..227b1801 Binary files /dev/null and b/examples/bento-grid/public/assets/images/illustration-create-post.webp differ diff --git a/examples/bento-grid/public/assets/images/illustration-five-stars.webp b/examples/bento-grid/public/assets/images/illustration-five-stars.webp new file mode 100644 index 00000000..fe5a2fca Binary files /dev/null and b/examples/bento-grid/public/assets/images/illustration-five-stars.webp differ diff --git a/examples/bento-grid/public/assets/images/illustration-grow-followers.webp b/examples/bento-grid/public/assets/images/illustration-grow-followers.webp new file mode 100644 index 00000000..79ba6b05 Binary files /dev/null and b/examples/bento-grid/public/assets/images/illustration-grow-followers.webp differ diff --git a/examples/bento-grid/public/assets/images/illustration-multiple-platforms.webp b/examples/bento-grid/public/assets/images/illustration-multiple-platforms.webp new file mode 100644 index 00000000..0886632e Binary files /dev/null and b/examples/bento-grid/public/assets/images/illustration-multiple-platforms.webp differ diff --git a/examples/bento-grid/public/assets/images/illustration-schedule-posts.webp b/examples/bento-grid/public/assets/images/illustration-schedule-posts.webp new file mode 100644 index 00000000..27ed427c Binary files /dev/null and b/examples/bento-grid/public/assets/images/illustration-schedule-posts.webp differ diff --git a/examples/bento-grid/style.css b/examples/bento-grid/style.css new file mode 100644 index 00000000..2e1e32dc --- /dev/null +++ b/examples/bento-grid/style.css @@ -0,0 +1,24 @@ +* { + margin: 0; + box-sizing: border-box; +} + +:root { + font-family: "DM Sans", sans-serif; + --clr-background: hsl(0, 0%, 95%); + --clr-primary-100: hsl(254, 88%, 90%); + --clr-primary-500: hsl(256, 67%, 59%); + --clr-secondary-100: hsl(31, 66%, 93%); + --clr-secondary-500: hsl(39, 100%, 71%); + --clr-white: hsl(0, 0%, 100%); + --clr-black: hsl(0, 0%, 7%); +} + +body { + background-color: var(--clr-background); +} + +main { + display: grid; + place-items: center; +} diff --git a/examples/bento-grid/vite.config.js b/examples/bento-grid/vite.config.js new file mode 100644 index 00000000..41713bec --- /dev/null +++ b/examples/bento-grid/vite.config.js @@ -0,0 +1,9 @@ +import { defineConfig } from "vite"; + +export default defineConfig(({ command, mode, ssrBuild }) => { + return { + server: { + open: true, + }, + }; +});