# Design System The Design System tool extracts the colours, typography, spacing and component styles out of a Bubble app and documents them in a form you can hand to a designer, a developer, or an AI. ## What to upload A full Bubble application export. The upload itself only needs `pages` or `element_definitions`. `styles` and `settings` are what make the output worth reading rather than what makes the file load. If the file has neither `pages` nor `element_definitions` you get *"Invalid Bubble JSON format. Expected pages or element_definitions with styles."* The message names `styles`, but the check does not: a file without `styles` or `settings` still loads, it just comes back with no named styles, no resolved style properties and no colour or font tokens. See [get your app export out of Bubble](/docs/export-your-bubble-app). ## Do not sanitize this one first The [JSON Sanitizer](/docs/json-sanitizer) deliberately preserves the design-related keys it finds under `settings.client_safe` — colour tokens, font tokens, colour swatches, default styles and responsive breakpoints — precisely so a sanitized export still works here. That said, if you are troubleshooting a design system that looks empty, check that you uploaded a file that still has its `settings` block. ## What it extracts - **Colour tokens and swatches**, including the app's defined palette rather than just the colours that happen to be used. - **Typography**: font families, sizes, weights and the styles they are attached to. - **Spacing and layout**, including responsive breakpoints. - **Element styles**: Bubble's named styles and the properties on them. - **Default styles**, so you can see what a new element of each type will look like. ## The views The **element tree** runs down the left: every page and reusable, expandable to the individual groups and elements inside. Click the arrow to open a branch, click the name to select it. On anything larger than a toy app you will want the search box above it instead, which is covered in [finding an element](#finding-an-element). [[img:design-system/01-loaded.png|The element tree: every page and reusable, expandable down to the individual groups and elements inside.]] Selecting an element fills three places at once: - **Preview** renders the element on its own, at whatever zoom and background you pick. - **HTML** is the generated markup for it. - The panel on the right carries **Bubble Properties**, the resolved values, and **CSS Output**, the same values as CSS. That right-hand panel starts collapsed, so selecting something in the tree does not open it for you. Open it with the thin vertical strip on the right edge of the screen, or click an element inside the Preview, which opens the panel and inspects the element you clicked at the same time. Two details in that panel are worth knowing. It names the **Bubble style** the element is attached to, which is the thing to search for in the editor when you want to change every element like it. And every property row is tagged with where its value came from, `element` for something set on this element alone or `style` for something inherited from the named style. That distinction is exactly what the [Limits](#limits) note below is about, and the badges answer it per property. [[img:design-system/02-element-preview.png|One button selected. It renders in the Preview pane, and the panel gives its Bubble style name, every resolved property tagged element or style, and the design tokens it uses.]] Container elements preview as an empty box, which is correct rather than broken: a group with no background of its own has nothing to draw. Drill down to a Text, Button, Input or Icon to see something. ## Finding an element On a real app the tree runs to thousands of elements across dozens of pages and reusables, and the one you want is usually four levels down inside a group whose name you would have to guess. The search box above the tree exists for that. Type two characters or more and it searches element names across **every page and reusable**, including the ones you have never opened. They are parsed on demand the moment you search, so nothing needs expanding first. [[img:design-system/03-search.png|Searching "group responsive" across a whole app. Every hit names the page or reusable it belongs to, and the pink badge marks the ones inside a reusable. Long trails truncate, so identically named elements can still look alike in the list; click one to land on it in the tree and see where it really sits.]] Results are ordered by how well they match: exact names first, then names that begin with what you typed, then names that merely contain it. Each row carries its path, the owning page or reusable followed by the groups in between. Clicking a result does the navigating for you. It opens the owning page, expands every ancestor down to the match, then selects it and scrolls it into view. If the element is one Bubble hides by default, a Popup for instance, it is force-shown too, so the preview is not just an empty box. The list stops at 50 matches and tells you when there are more. Narrow the query rather than scrolling. ## Exports The tool produces three files, dated by export: a markdown document, a JSON file and a CSS variables file. They are saved as three separate downloads a fraction of a second apart, so your browser may ask whether to allow multiple files. Those exports are the input to the `bubble-design-system` skill, which turns them into a full design-system presentation with element-generation metadata. That in turn feeds `bubble-element`, which generates pasteable Bubble UI. If you are using LumiDevKit as part of that toolchain, this is where the chain starts. Select a reusable in the tree and you get a second, narrower export. The panel header for that reusable carries a copy button and a download button that produce just that one reusable as JSON, with an **Include workflows** toggle beside them showing how many workflows would come with it. That toggle is on by default. Use it when you want one component rather than the whole app. ## Limits The tool reads what Bubble records in the export. Styling applied inline on a single element in ways Bubble does not record as a style will not appear as a token, though it will show up on the element itself in the tree.