Panel frontend
The control panel is server-rendered Blade with Livewire 3 components and Alpine.js, built with Vite from core/assets/ and shipped as a committed dist that projects publish with evolve.assets.
Build
core/assets/package.json has one script, vite build, with laravel-vite-plugin, Tailwind (plus container queries), sass and the Alpine and TipTap dependencies. The output is core/assets/public/build/, committed, and published to public/vendor/evolve of a project. Rebuild after changing anything under core/assets and commit the dist. Gotcha from the repo's CLAUDE.md: the Tailwind content glob loops through the Testbench skeleton's vendor symlink; remove vendor/orchestra/testbench-core/laravel/vendor before building.
Since 2.13 the bundle is split (core/assets/scripts/lazy.ts): app.ts carries Alpine, the plugins, dropdowns, prefetch, tooltips, the command palette and the progress indicator; charts, the TipTap rich text editor, the tree, selects and date pickers load on first use and window.makeChart, makeEditor, editorAi, makeTree, makeSelect, makeDatePicker return Promises. No web font is loaded; the system stack is used.
Scripts
core/assets/scripts/: app.ts (entry), alpine-plugins.ts, command-palette.ts (Cmd-K, filters views and actions in the browser from the server-rendered registry), dropdown.ts (the registered Alpine component dropdown(alignment), popper created on first open), custom-confirm.ts and custom-prompt.ts (window.betterPrompt, used by the editor's link, image and AI prompt dialogs), prefetch.ts (data-prefetch links), progressIndicator.ts, richtext.ts (TipTap with the AI menu), select.ts, datepicker.ts, tree.ts (page tree), sortable.ts, tooltips.ts, charts.ts, theme.ts (light and dark mode), definitions/ (TypeScript typings), frontend/ (scripts the frontend info bar needs).
Icons
core/assets/icons/ holds the Nucleo set (licence in LICENSE.md, panel only) and aliases.php, which maps the old Font Awesome names that blueprints, sidebar entries and stored activity names still use. <x-evolve::icon name="..." /> renders <svg><use href="/evolve/icons.svg?v=<hash>#name">; the sprite route is cached immutably by hash. evolve:icons:sync (workbench only) regenerates the sprite and fails above the 250 icon budget; IconsTest guards the manifest.
Layouts and components
core/views/app.blade.php, guest.blade.php, blank.blade.php are the three layouts; Support\PanelTheme sets the CSS variables (evolve.theme-color feeds only the accent). Shared components under core/views/components/: layout/sidebar, layout/header (renders layout.command-palette), layout/drawer (records, with the close-modal contract and sizes xs to lg), layout/modal (tasks), action-bar (sticky, submits through the form attribute, unsaved guard), segmented and segmented.item, resource/list and resource/list-item (48 px rows, hairlines), dropdown, card, tabs, toggle, form/* (field types), icon.
Livewire conventions: legacy_model_binding must be true in the project's config/livewire.php (a documented v2 breaking change); components under core/src/Http/Livewire and <module>/src/Http/Livewire, loaded by LivewireComponentLoader; ResourceComponent is the base for list managers with create, edit, delete, search and sorting, ResourceController for the classic create and edit screens.
Overrides
Projects may copy panel views into resources/views/vendor/evolve or theme/views/vendor/evolve. Support\ViewOverrides holds CHANGES (per version, which view changed and what a copy must follow) and REMOVED; evolve:view-overrides {--since=} {--strict} compares a project's copies against it and also matches content patterns (Font Awesome tags, synchronous makeEditor, white text on bg-primary). Every PR that changes a view a project might have copied adds an entry.