UNPKG

@thebase/ui

Version:

CDN-installable Owl and Bootstrap 5 UI component library.

106 lines (78 loc) • 8.23 kB
# Pure Owl Components See the [Usage Guide](usage-guide.md) for when to reach for this API versus the static `b-ui` one. This page covers the pure Owl API only. BaseUI ships a second, additive public API alongside the static `b-ui` markers: real Owl component classes you import, compose with `static components`, and mount as part of your own Owl app. This page covers how to load and use it; see [Component Authoring](component-authoring.md) for how components implement both APIs from one source folder. As of 1.1.0, every component in the registry (all 65) has a pure Owl export — there are no static-only components left. Compound components export a root class plus sub-components (e.g. `Dialog`/`DialogTrigger`/`DialogContent`/...); check a component's `owlComponents` entry in `dist/baseui.registry.json`, or its doc page under [`docs/components/`](components/), for the exact export list. A few components have a deliberately reshaped pure Owl API versus their static markup-scanning adapter — see [Registry](registry.md#component-export-policy) for which ones and why. ## What you need to load Everything — the static `b-ui` runtime, the Owl framework, every pure Owl component class, and the theme helper — is one file: `dist/baseui.esm.js` (or `dist/baseui.min.js` as a classic script). There is no separate `baseui.owl.*`/`baseui.components.esm.js`/`baseui.theme.esm.js` to load. | File | Purpose | | --- | --- | | `dist/baseui.min.css` | Bootstrap + BaseUI styling, shared by both APIs. | | `@base/owl` (`dist/baseui.esm.js`) | The Owl framework — `Component`, `mount`, `xml`, `useState`, etc. Pinned to Owl `2.8.3`, embedded directly in this file. Import your app's own Owl usage from here too, not `@odoo/owl`. | | `@base/component` (`dist/baseui.esm.js`) | The pure Owl component classes — same file as `@base/owl` above, just a different import-map key for readability. | | `@base/theme` (`dist/baseui.esm.js`) | Same file again — the theme helper for persisted light/dark toggles, URL overrides, button-label sync, and iframe preview sync. | | `@base/templates` (`dist/baseui.templates.xml`) | The Owl templates the component classes reference (`static template = "baseui.Button"`, etc). Must be loaded and passed to `mount()` before any BaseUI component tag renders — a component class alone does not carry its template. | ## Browser (import map) usage ```html <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@thebase/ui@latest/dist/baseui.min.css"> <script type="importmap"> { "imports": { "@base/owl": "https://cdn.jsdelivr.net/npm/@thebase/ui@latest/dist/baseui.esm.js", "@base/component": "https://cdn.jsdelivr.net/npm/@thebase/ui@latest/dist/baseui.esm.js", "@base/theme": "https://cdn.jsdelivr.net/npm/@thebase/ui@latest/dist/baseui.esm.js", "@base/templates": "https://cdn.jsdelivr.net/npm/@thebase/ui@latest/dist/baseui.templates.xml" } } </script> <script type="module"> import { Component, mount, xml } from "@base/owl"; import { Button, Card, CardBody, CardHeader, CardTitle } from "@base/component"; // "@base/templates" is an import-map entry, not a JS module — resolve it // to its mapped URL and fetch the text. const templates = await fetch(import.meta.resolve("@base/templates")).then((r) => r.text()); class Root extends Component { static components = { Button, Card, CardBody, CardHeader, CardTitle }; static template = xml` <Card> <CardHeader><CardTitle>Hello</CardTitle></CardHeader> <CardBody> <Button variant="'default'" label="'Save'" onClick="() => console.log('saved')"/> </CardBody> </Card>`; } await mount(Root, document.getElementById("app"), { templates }); </script> ``` `https://unpkg.com/@thebase/ui@latest/dist/...` mirrors the same files as an alternative CDN if jsDelivr is unreachable — swap the host in each URL above. For a self-hosted build, replace the CDN host with your own served path (e.g. `/dist/baseui.esm.js`). These snippets use `@latest` for readability; pin an exact version (e.g. `@0.0.4`) in production so a new release can't change what your page loads. No `@odoo/owl` import appears anywhere in that snippet — `@base/owl` is the only Owl entry point BaseUI components and consumer apps need. Because `@base/owl`, `@base/component`, and `@base/theme` all point at the exact same `dist/baseui.esm.js` URL, the browser fetches and evaluates it once and every key shares the same module instance — no separate classic `<script>` needs to load first to set up a shared global. ## npm / bundler usage ```sh npm install @thebase/ui ``` ```js import { Component, mount, xml, Button, Card } from "@thebase/ui"; import baseuiTemplates from "@thebase/ui/dist/baseui.templates.xml?raw"; // exact loader syntax depends on your bundler class Root extends Component { static components = { Button, Card }; static template = "Root"; } ``` There's only one package entry now — `@thebase/ui` exports the Owl framework (built from the exact `@odoo/owl@2.8.3` this BaseUI release vendors; you do not need to install `@odoo/owl` yourself), every pure Owl component class, and the theme helper together. Browser import-map examples above still use the `@base/owl`/`@base/component`/`@base/theme` keys for readability, but they're just local aliases to the same file. When a bundler cannot import XML with `?raw`, load `dist/baseui.templates.xml` as a served asset and pass the fetched string to `mount(Root, target, { templates })`. The template file is part of the runtime contract, not optional documentation. ## Mixing with the static API Both APIs come from the exact same bundle now, so there's nothing extra to load — just be clear about which mechanism owns which markup: - `BaseUI.mountAll(root)` enhances static `[b-ui]` and `[b-icon]` markers. - Owl `mount(Root, target, { templates })` renders component tags such as `<Button/>`. - Importing the package always also runs `autoMount()` (its `[b-ui]`/`[b-icon]` DOM scan on `DOMContentLoaded`) — harmless if your page has none, but means there's no side-effect-free way to import just the component classes anymore. - Both APIs share `dist/baseui.min.css`, `@base/theme`, and the same `b-theme` / `data-bs-theme` root attributes. ## Props, events, slots - Props are camelCase (`variant`, `label`, `disabled`, `className`). - Almost every component that renders its own root element also accepts `style` (a string or a plain object of CSS properties) alongside `className`. Components that only forward a default slot with no wrapping element of their own (`AlertDialog`, `Pwa`, `Sheet`, `ContextMenu`, `Drawer`) have neither prop. A handful of components that already compute an internal style (`Icon`, `AspectRatio`, `Progress`, `ContextMenuContent`, `SidebarMenuSkeleton`) merge your `style` with their own computed value instead of one overwriting the other. - Events are callback props (`onClick`, `onChange`, `onOpenChange`), not DOM `CustomEvent`s — that's the static API's contract, not this one. - Default slot content works as normal Owl children (`<Badge>Draft</Badge>`); compound components use named slots/sub-tags (`<CardHeader>`, `<DialogFooter>`). See each component's page under [`docs/components/`](components/) for its specific props table and an Owl usage example alongside the static `b-ui` one. ## Common mistakes - **Rendering a bare `<Button/>` with no template loaded.** `mount(Root, target)` without `{ templates }` (or `app.addTemplates(...)`) throws — the `.xml` file is a real build/runtime input, not documentation. - **Registering `Button` under the wrong tag name.** `static components = { Button }` must match the tag used in the template (`<Button/>`), same as any other Owl component. - **Importing from `@odoo/owl`.** Always import from `@base/owl` instead, even in your own app code — it keeps your app on the exact Owl version this BaseUI release was tested against. - **Adding a `baseui.owl.min.js`/`baseui.owl.esm.js`/`baseui.components.esm.js` script or import-map entry.** None of those files are published anymore — point `@base/owl`/`@base/component`/`@base/theme` all at `dist/baseui.esm.js` instead.