docs: add nodedc ui guideline registry

This commit is contained in:
DCCONSTRUCTIONS 2026-05-01 22:28:34 +03:00
parent 85aa322990
commit c99c91c826
26 changed files with 1209 additions and 0 deletions

20
dc-ui-guideline/README.md Normal file
View File

@ -0,0 +1,20 @@
# NODE.DC UI Guideline
This folder is the first local source of truth for reusable NODE.DC UI components.
It is intentionally MCP-friendly:
- `registry.json` lists every known component contract.
- `tokens/nodedc.tokens.json` contains machine-readable design tokens.
- `tokens/nodedc.tokens.css` mirrors runtime CSS variables.
- `components/*.json` describe component anatomy, states, rules, and source references.
- `recipes/*.json` describe larger UI compositions.
- `sources/source-map.json` links this launcher and NODEDC Task Manager implementation files.
The codebase remains the source of truth for implementation. This folder is the index and contract layer that an MCP server or coding agent can read before generating UI.
## Operating Rule
Before creating a new NODE.DC UI element, check `registry.json`.
If a matching component exists, use or extend it. Do not create a local one-off dropdown, modal, button, status pill, table, calendar, or navigation panel.

View File

@ -0,0 +1,41 @@
{
"id": "action-dropdown",
"name": "ActionDropdown",
"kind": "component",
"status": "stable-reference",
"summary": "Shared action menu for ellipsis buttons and command lists. Used instead of local card menus.",
"sourceRefs": [
{
"project": "nodedc_taskmanager",
"file": "plane-src/packages/ui/src/dropdowns/action-dropdown.tsx",
"exports": ["ActionDropdown"]
},
{
"project": "nodedc_taskmanager",
"file": "HDROPDOWN-CANON.md",
"section": "Action dropdown"
}
],
"propsContract": {
"items": "Array of action menu items with key, icon, title, description, disabled, action, nestedMenuItems.",
"button": "Optional custom trigger.",
"buttonAsChild": "Allows using the provided trigger element as anchor.",
"placement": "Popper placement.",
"portalElement": "Defaults to document.body.",
"menuClassName": "Optional width/padding adjustment."
},
"behaviorContract": [
"Uses real trigger element.",
"Uses fixed Popper strategy.",
"Uses offset [0, 8].",
"Uses flip and preventOverflow.",
"Uses portal to document.body by default.",
"Stops trigger event propagation so cards do not open when the menu opens."
],
"rules": [
"Do not build card ellipsis menus with local isOpen and absolute positioning.",
"Menu item visual rendering lives inside ActionDropdown.",
"Nested items are allowed, but still use the same dropdown shell."
]
}

View File

@ -0,0 +1,45 @@
{
"id": "admin-side-nav",
"name": "AdminSideNav",
"kind": "component",
"status": "draft-stable",
"summary": "Left admin panel navigation with full-width rounded rows, circular icons, client selector, close button, and role footer.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/widgets/admin-overlay/AdminOverlay.tsx",
"classes": ["admin-panel-nav", "admin-panel-client-select", "admin-panel-nav-item", "admin-panel-role"]
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["admin-panel-nav", "admin-panel-nav-item", "admin-panel-nav-item__icon", "admin-panel-close"]
}
],
"anatomy": [
"panel shell",
"head: eyebrow, title, close action",
"client selector row",
"nav list",
"role footer"
],
"geometry": {
"width": "clamp(20.75rem, 19.5vw, 22rem)",
"panelPadding": "1.1rem",
"rowHeight": "controlRing + 2 * controlInset",
"iconSize": "controlRing",
"edgeInset": "5px"
},
"states": {
"inactive": "muted text, darker icon circle, partial opacity",
"active": "white icon circle and brighter row surface",
"hover": "slightly brighter row surface"
},
"rules": [
"Rows stretch to panel edges by counteracting panel padding.",
"Active nav icon is white, not green.",
"Close button is anchored at panel radius with 5px inset.",
"Client selector uses the same row/circle geometry as nav rows."
]
}

View File

@ -0,0 +1,43 @@
{
"id": "admin-table",
"name": "AdminTable",
"kind": "component",
"status": "draft-stable",
"summary": "Admin data table shell used for services, clients, users, groups, invites, sync, and audit.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/widgets/admin-overlay/AdminOverlay.tsx",
"functions": ["ServicesSection", "ClientsSection", "UsersSection", "GroupsSection", "InvitesSection", "SyncSection", "AuditSection"]
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["table-shell", "admin-data-table", "services-admin-table", "admin-table-input"]
}
],
"anatomy": [
"table-shell glass surface",
"table-toolbar",
"thead labels",
"tbody rows",
"inline editable cells",
"StatusControl cells",
"DateField cells",
"CircleActionButton action cells"
],
"visualContract": {
"background": "same family as inactive admin nav row, not a foreign panel",
"fontSize": "0.82rem table; compact labels 0.66rem",
"cellVerticalAlign": "middle",
"rowAction": "circular edit button at right"
},
"rules": [
"Create action is a solid circular plus, not a wide text CTA.",
"Inline editable cells use transparent input surfaces that brighten on hover/focus.",
"Status cells use StatusControl.",
"Date cells use CalendarPopover/DateField.",
"Drag handles move full rows, not detached ghosts."
]
}

View File

@ -0,0 +1,40 @@
{
"id": "app-header",
"name": "NodeDcAppHeader",
"kind": "component",
"status": "draft-stable",
"summary": "Top application header with logo, centered navigation group, workspace mark, and profile cluster.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/widgets/top-bar/TopBar.tsx"
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["nodedc-expanded-toolbar", "nodedc-expanded-nav-group", "nodedc-expanded-nav-button", "nodedc-expanded-user-group"]
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/core/components/core/app-header.tsx"
}
],
"anatomy": [
"left brand logo",
"center workspace mark",
"center segmented nav",
"right profile pill with optional notification icon and avatar"
],
"geometry": {
"shellPadding": "1.25rem top/right/left in launcher",
"pillHeight": "3rem in launcher expanded toolbar",
"brandLogo": "visual size follows Task Manager reference, not text-only brand"
},
"rules": [
"Header is monocolor black/dark, not gradient decoration.",
"Active top nav segment is white filled pill.",
"Profile avatar diameter must match reference topbar avatar.",
"Launcher and Task Manager headers must remain visually identical where routes overlap."
]
}

View File

@ -0,0 +1,47 @@
{
"id": "calendar-popover",
"name": "CalendarPopover",
"kind": "component",
"status": "stable-reference",
"summary": "Date picker popover based on Task Manager DateDropdown and nodedc-calendar-shell styling.",
"sourceRefs": [
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/core/components/dropdowns/date.tsx",
"exports": ["DateDropdown"]
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/styles/globals.css",
"classes": ["nodedc-calendar-shell"]
},
{
"project": "nodedc_launcher",
"file": "src/widgets/admin-overlay/AdminOverlay.tsx",
"functions": ["DateField"]
}
],
"anatomy": [
"date trigger button",
"portal dropdown surface",
"calendar shell",
"month/year controls",
"day buttons",
"single or range mode"
],
"visualContract": {
"surface": "DropdownSurface",
"calendarRadius": "1.1rem",
"dayButtonRadius": "999px",
"selectedRangeFill": "accentRgb with high contrast dark text",
"outsideDays": "muted"
},
"behaviorContract": [
"Default placement bottom-start.",
"Render through portal.",
"Support minDate, maxDate, clearable value, start-of-week preference.",
"Close on select when closeOnSelect is true."
],
"nextImplementationStep": "Replace launcher native input date fallback with this shared calendar component."
}

View File

@ -0,0 +1,53 @@
{
"id": "circle-action-button",
"name": "CircleActionButton",
"kind": "primitive",
"status": "draft-stable",
"summary": "Icon-only circular action control for close, add, edit, refresh, search, copy, drag-adjacent actions, and toolbar icon actions.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/shared/ui/Button.tsx",
"exports": ["IconButton"]
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["admin-circle-action", "admin-panel-close", "services-admin-table__edit"]
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/styles/globals.css",
"classes": ["nodedc-external-icon-button", "nodedc-toolbar-icon-button"]
}
],
"anatomy": [
"button element",
"single centered icon",
"aria-label/title",
"optional solid active/primary variant"
],
"geometry": {
"size": "tokens.size.controlRing",
"shape": "circle",
"insetToHostEdge": "tokens.size.controlInset when anchored in a rounded container"
},
"variants": {
"ghost": {
"background": "transparent",
"border": "soft white alpha only if needed",
"hover": "white alpha surface"
},
"solid": {
"background": "rgba(247, 248, 244, 0.96)",
"color": "onAccentRgb"
}
},
"rules": [
"Do not replace with text pill when action is clear by icon.",
"Close button starts transparent with only soft circular boundary.",
"Hover may add subtle surface fill.",
"All icon-only admin actions share the same diameter."
]
}

View File

@ -0,0 +1,48 @@
{
"id": "dropdown-surface",
"name": "DropdownSurface",
"kind": "primitive",
"status": "stable-reference",
"summary": "Canonical dark floating surface for selection dropdowns, action dropdowns, filters, and profile menu popovers.",
"sourceRefs": [
{
"project": "nodedc_taskmanager",
"file": "HDROPDOWN-CANON.md"
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/styles/globals.css",
"classes": ["nodedc-dropdown-surface", "nodedc-dropdown-search", "nodedc-dropdown-option"]
},
{
"project": "nodedc_launcher",
"file": "src/shared/ui/PortalDropdown.tsx"
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["portal-dropdown", "nodedc-dropdown-surface"]
}
],
"visualContract": {
"background": "linear-gradient(180deg, rgba(255,255,255,0.025), rgba(255,255,255,0.01)) over rgba(8,8,11,0.9)",
"radius": "1.25rem",
"padding": "0.75rem",
"blur": "44px",
"shadow": "tokens.shadow.dropdown",
"border": "0"
},
"behaviorContract": [
"Render on fixed/portal layer when inside cards, sidebars, tables, sticky headers, or scroll containers.",
"Close on outside pointer and Escape.",
"Use Popper or equivalent fixed-position placement.",
"Default selection placement is bottom-start.",
"Default action placement for card quick actions is bottom-start or bottom-end depending on anchor edge."
],
"optionContract": {
"radius": "0.9rem",
"hover": "rgba(255,255,255,0.06)",
"outline": "none"
}
}

View File

@ -0,0 +1,47 @@
{
"id": "entity-modal",
"name": "EntityModal",
"kind": "component",
"status": "draft-stable",
"summary": "Dark glass edit/create modal used for services, clients, users, and groups.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/widgets/admin-overlay/AdminOverlay.tsx",
"functions": ["ServiceContentModal", "ClientEditorModal", "UserEditorModal", "GroupEditorModal", "EntityModalHead", "EntityModalFoot"]
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["service-content-modal-layer", "service-content-modal", "service-content-field"]
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/styles/globals.css",
"classes": ["nodedc-glass-modal", "nodedc-modal-input", "nodedc-modal-editor", "nodedc-modal-primary-button"]
}
],
"anatomy": [
"fixed overlay layer",
"modal shell",
"head with eyebrow/title/close circle",
"scrollable responsive grid",
"fields",
"footer with cancel, optional delete, save"
],
"visualContract": {
"shellWidth": "min(58rem, viewport - 2.8rem)",
"radius": "modal",
"background": "dark matte glass",
"blur": "modal",
"fieldRadius": "1rem to 1.25rem",
"footerButtonHeight": "2.75rem"
},
"rules": [
"Delete is left of Save inside the right footer action group.",
"Cancel stays on the left.",
"Close action is circular and transparent until hover.",
"Fields/selects/textareas share the same glass family."
]
}

View File

@ -0,0 +1,36 @@
{
"id": "glass-panel",
"name": "GlassPanel",
"kind": "surface",
"status": "draft-stable",
"summary": "Dark matte glass container used for panels, cards, modal shells, dropdown shells, and admin content blocks.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/shared/ui/Glass.tsx"
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["glass-surface", "admin-panel-nav", "admin-panel-content", "service-content-modal"]
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/styles/globals.css",
"classes": ["nodedc-dropdown-surface", "nodedc-modal-field", "nodedc-settings-card"]
}
],
"tokens": {
"radius": "card | modal | control depending on scale",
"blur": "panel | modal | dropdown",
"background": "dark matte glass gradient over rgba black",
"border": "none or transparent soft glass only"
},
"rules": [
"Never use hard outline as the main visual boundary.",
"Use background opacity and blur to separate layers.",
"For major shells use radius.card or radius.modal.",
"For controls inside shells use radius.control."
]
}

View File

@ -0,0 +1,33 @@
{
"id": "launcher-showcase-stage",
"name": "LauncherShowcaseStage",
"kind": "recipe-component",
"status": "draft-stable",
"summary": "Large showcase stage with looping ambient media, selected service media square, and glass description square.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/widgets/service-stage/ServiceStage.tsx"
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["service-stage", "stage-service-overlay", "stage-media-card", "stage-description-card", "stage-video-controls"]
}
],
"anatomy": [
"stage container",
"ambient background media",
"topline back/title",
"left side controls",
"two centered equal squares: media and description",
"bottom center previous/next controls"
],
"rules": [
"The media card and description card have equal width and height.",
"Cards are separated by a small gap and each has four rounded corners.",
"Ambient media fills the stage and clips to radius.card.",
"When admin panel content is open, stage content controls are hidden and media becomes decorative."
]
}

View File

@ -0,0 +1,40 @@
{
"id": "media-source-field",
"name": "MediaSourceField",
"kind": "component",
"status": "draft-stable",
"summary": "Media input field that switches between local storage upload and external URL for card and background content.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/widgets/admin-overlay/AdminOverlay.tsx",
"functions": ["MediaSourceField", "MediaPreview"]
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["service-media-control", "service-media-file-button", "service-media-source-button"]
}
],
"anatomy": [
"label with icon",
"rounded input/control shell",
"file chooser button",
"selected filename",
"URL input",
"two circular source buttons: file, url",
"preview surface"
],
"behaviorContract": [
"Local file upload persists to public storage and returns stable URL.",
"Source switch decides whether field uses stored file URL or external URL.",
"Accepts images, gifs, videos, and common video extensions.",
"Preview renders video when mediaKind or extension indicates video."
],
"rules": [
"The file chooser is a single rounded button, never browser default file input UI.",
"The source buttons are circular and attached to the field right side.",
"Background content and card content both accept the same media categories."
]
}

View File

@ -0,0 +1,41 @@
{
"id": "profile-menu",
"name": "ProfileMenu",
"kind": "component",
"status": "stable-reference",
"summary": "User profile popover opened from the top toolbar avatar. Uses ActionDropdown shell with custom menu content.",
"sourceRefs": [
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/core/components/workspace/sidebar/user-menu-root.tsx",
"exports": ["UserMenuRoot"]
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/packages/ui/src/dropdowns/action-dropdown.tsx",
"exports": ["ActionDropdown"]
}
],
"anatomy": [
"toolbar avatar trigger",
"cover image header",
"centered circular avatar",
"user name and email",
"action rows: settings, sign out",
"optional admin-only action"
],
"visualContract": {
"menuWidth": "18rem",
"menuPadding": "0.75rem",
"coverHeight": "7.25rem",
"coverRadius": "0.5rem in task manager reference; can be upgraded to token radius.control",
"rowRadius": "0.9rem",
"rowHover": "rgba(255,255,255,0.06)"
},
"rules": [
"Profile popover is an ActionDropdown menuContent variant, not a separate dropdown engine.",
"Avatar trigger stays circular and borderless.",
"Menu uses DropdownSurface/ActionDropdown stacking rules."
]
}

View File

@ -0,0 +1,34 @@
{
"id": "segmented-nav",
"name": "SegmentedNav",
"kind": "component",
"status": "draft-stable",
"summary": "Rounded grouped navigation control used in topbars and mode switchers.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["nodedc-expanded-nav-group", "nodedc-expanded-nav-button"]
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/styles/globals.css",
"classes": ["nodedc-toolbar-group", "nodedc-toolbar-pill", "nodedc-toolbar-primary"]
}
],
"visualContract": {
"groupRadius": "999px",
"groupPadding": "0.25rem",
"buttonRadius": "999px",
"buttonHeight": "2.5rem to 3rem depending on header scale",
"activeFill": "white or accent depending on context",
"inactiveFill": "transparent or dark group surface"
},
"rules": [
"No outlines.",
"All items share height.",
"Active segment does not resize the group.",
"Use text labels only for route/mode tabs; icon-only actions use CircleActionButton."
]
}

View File

@ -0,0 +1,39 @@
{
"id": "service-rail-card",
"name": "ServiceRailCard",
"kind": "component",
"status": "draft-stable",
"summary": "Bottom launcher rail item made from a square media tile and separate glass description tile with an attached circular arrow action.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/widgets/service-rail/ServiceRail.tsx"
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["service-rail", "service-rail-card", "service-rail-card__media", "service-rail-card__body"]
}
],
"anatomy": [
"rail glass strip with ambient media under blur",
"service card group",
"square media tile",
"separate square body tile",
"status pill",
"circular arrow action"
],
"layoutContract": [
"One service centers in the rail.",
"Two services divide available rail into three equal gaps.",
"Three services divide into five equal gaps.",
"When gaps would become smaller than one tile size, horizontal scroll starts."
],
"rules": [
"Media and body tiles are separated by a small seam gap.",
"Both tiles have four rounded corners.",
"Tiles touch rail vertical bounds from top to bottom after rail padding rules.",
"The arrow action can select/open the service card."
]
}

View File

@ -0,0 +1,33 @@
{
"id": "status-control",
"name": "StatusControl",
"kind": "component",
"status": "draft-stable",
"summary": "Status pill and status dropdown for service/client/user/invite/sync/audit states.",
"sourceRefs": [
{
"project": "nodedc_launcher",
"file": "src/widgets/admin-overlay/AdminOverlay.tsx",
"functions": ["ServiceStatusDropdown", "AdminStatusDropdown", "AdminStatusPill"]
},
{
"project": "nodedc_launcher",
"file": "src/styles/globals.css",
"classes": ["service-status-trigger", "admin-status-trigger", "admin-status-menu"]
}
],
"geometry": {
"width": "8.65rem for admin status, 7.45rem for compact service status",
"height": "2.08rem",
"radius": "999px",
"labelAlignment": "center"
},
"tones": ["green", "yellow", "violet", "red", "muted"],
"rules": [
"No outline and no select browser arrow inside status pills.",
"Clickable status opens DropdownSurface menu.",
"Static status uses the same pill geometry but pointer-events none.",
"Color opacity must stay restrained; status cannot become a bright visual hotspot."
]
}

View File

@ -0,0 +1,42 @@
{
"id": "work-item-card",
"name": "WorkItemCard",
"kind": "component",
"status": "stable-reference",
"summary": "Task Manager kanban work item card with avatar header, centered title, progress, footer metadata, and ellipsis action dropdown.",
"sourceRefs": [
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/core/components/issues/issue-layouts/shared/nodedc-work-item-card.tsx",
"exports": ["NodedcWorkItemCard", "NodedcWorkItemProgress", "getNodedcWorkItemCardAppearance"]
},
{
"project": "nodedc_taskmanager",
"file": "plane-src/apps/web/styles/globals.css",
"classes": ["nodedc-work-item-card"]
}
],
"anatomy": [
"rounded card surface",
"header",
"optional subtitle",
"center title area",
"segmented progress",
"footer"
],
"geometry": {
"radius": "28px in reference",
"padding": "1rem",
"minContentHeight": "220px"
},
"states": {
"passive": "cardPassive surface with muted foreground",
"active": "cardActive accent surface with on-card-active foreground"
},
"rules": [
"Kanban card ellipsis uses ActionDropdown.",
"Card click must not intercept dropdown trigger clicks.",
"Progress segments use three equal tracks and accent fill when passive."
]
}

View File

@ -0,0 +1,33 @@
{
"schemaVersion": "0.1.0",
"serverName": "nodedc-ui-guideline",
"recommendedResources": [
{
"uri": "nodedc-ui://registry",
"file": "registry.json",
"description": "Top-level component registry."
},
{
"uri": "nodedc-ui://tokens",
"file": "tokens/nodedc.tokens.json",
"description": "Machine-readable design tokens."
},
{
"uri": "nodedc-ui://rules",
"file": "rules/ui-rules.json",
"description": "Global UI rules and forbidden patterns."
},
{
"uri": "nodedc-ui://sources",
"file": "sources/source-map.json",
"description": "Source implementation map across launcher and task manager."
}
],
"toolingNotes": [
"Expose each components/*.json file as a read-only resource.",
"Expose recipes/*.json as composition examples.",
"When generating UI, load registry, tokens, rules, then the specific component specs.",
"Prefer source references over re-inventing markup."
]
}

View File

@ -0,0 +1,47 @@
{
"id": "admin-catalog",
"name": "AdminCatalogRecipe",
"summary": "Composition for launcher admin panel and catalog-style admin sections.",
"components": [
"admin-side-nav",
"admin-table",
"status-control",
"calendar-popover",
"circle-action-button",
"entity-modal",
"media-source-field",
"dropdown-surface",
"action-dropdown"
],
"layout": {
"base": "left AdminSideNav + optional AdminTable content + decorative compressed stage media",
"navOnly": "stage squeezes but keeps showcase controls",
"contentOpen": "content table opens next to nav; stage becomes narrow decorative media"
},
"compositionRules": [
"Admin nav buttons use the same row geometry as project quick-select buttons.",
"Table create actions are circular plus buttons.",
"Inline status fields use StatusControl, not native select UI.",
"Dates use CalendarPopover, with Task Manager calendar as reference.",
"Edit opens EntityModal; content/media uses MediaSourceField.",
"All dropdowns use portal/fixed layer."
],
"sourceRefs": [
{
"project": "nodedc_launcher",
"files": [
"src/widgets/admin-overlay/AdminOverlay.tsx",
"src/styles/globals.css"
]
},
{
"project": "nodedc_taskmanager",
"files": [
"plane-src/apps/web/core/components/dropdowns/date.tsx",
"plane-src/packages/ui/src/dropdowns/action-dropdown.tsx",
"plane-src/apps/web/styles/globals.css"
]
}
]
}

View File

@ -0,0 +1,39 @@
{
"id": "launcher-shell",
"name": "LauncherShellRecipe",
"summary": "Composition for NODE.DC launcher main screen.",
"components": [
"app-header",
"segmented-nav",
"launcher-showcase-stage",
"service-rail-card",
"circle-action-button",
"status-control",
"glass-panel"
],
"layout": {
"root": "dark monocolor app background",
"top": "NodeDcAppHeader",
"center": "LauncherShowcaseStage",
"bottom": "ServiceRailCard collection in rail strip"
},
"compositionRules": [
"Header stays visually identical to Task Manager header where possible.",
"Stage and rail respect pagePad and panelGap tokens.",
"Selected service opens the stage detail; repeat click can close detail where the screen supports collapsed state.",
"Rail uses ambient media under glass, clipped to the strip."
],
"sourceRefs": [
{
"project": "nodedc_launcher",
"files": [
"src/app/LauncherApp.tsx",
"src/widgets/top-bar/TopBar.tsx",
"src/widgets/service-stage/ServiceStage.tsx",
"src/widgets/service-rail/ServiceRail.tsx",
"src/styles/globals.css"
]
}
]
}

View File

@ -0,0 +1,40 @@
{
"id": "task-manager-board",
"name": "TaskManagerBoardRecipe",
"summary": "Composition for Task Manager project board, including kanban cards, action dropdowns, profile menu, and calendar.",
"components": [
"app-header",
"segmented-nav",
"work-item-card",
"action-dropdown",
"dropdown-surface",
"calendar-popover",
"profile-menu",
"circle-action-button"
],
"layout": {
"top": "Task Manager header with active route segmented nav and profile cluster",
"board": "kanban columns with WorkItemCard items",
"floatingMenus": "ActionDropdown and selection dropdowns on portal layer",
"date": "CalendarPopover for task start/target dates"
},
"compositionRules": [
"Card ellipsis uses ActionDropdown.",
"Date chips open CalendarPopover.",
"Profile avatar opens ProfileMenu through ActionDropdown menuContent.",
"All popovers use DropdownSurface and never render inline inside cards."
],
"sourceRefs": [
{
"project": "nodedc_taskmanager",
"files": [
"plane-src/apps/web/core/components/issues/issue-layouts/shared/nodedc-work-item-card.tsx",
"plane-src/apps/web/core/components/workspace/sidebar/user-menu-root.tsx",
"plane-src/apps/web/core/components/dropdowns/date.tsx",
"plane-src/packages/ui/src/dropdowns/action-dropdown.tsx",
"plane-src/apps/web/styles/globals.css"
]
}
]
}

View File

@ -0,0 +1,128 @@
{
"schemaVersion": "0.1.0",
"name": "NODE.DC UI Guideline",
"purpose": "Component registry for NODE.DC launcher, task manager, future apps, and MCP-backed UI generation.",
"sourceProjects": [
{
"id": "nodedc_launcher",
"root": "/Users/dcconstructions/Downloads/mnt/data/nodedc_launcher",
"role": "current launcher implementation and first MCP guideline host"
},
{
"id": "nodedc_taskmanager",
"root": "/Users/dcconstructions/Downloads/mnt/data/dc_taskmanager/NODEDC_TASKMANAGER",
"role": "reference implementation for app header, work item cards, action dropdowns, profile menu, and calendar"
}
],
"tokens": {
"json": "tokens/nodedc.tokens.json",
"css": "tokens/nodedc.tokens.css"
},
"components": [
{
"id": "app-header",
"spec": "components/app-header.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher",
"taskManagerReference": true
},
{
"id": "segmented-nav",
"spec": "components/segmented-nav.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "circle-action-button",
"spec": "components/circle-action-button.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "glass-panel",
"spec": "components/glass-panel.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "dropdown-surface",
"spec": "components/dropdown-surface.json",
"status": "stable-reference",
"primarySource": "nodedc_taskmanager"
},
{
"id": "action-dropdown",
"spec": "components/action-dropdown.json",
"status": "stable-reference",
"primarySource": "nodedc_taskmanager"
},
{
"id": "status-control",
"spec": "components/status-control.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "calendar-popover",
"spec": "components/calendar-popover.json",
"status": "stable-reference",
"primarySource": "nodedc_taskmanager"
},
{
"id": "profile-menu",
"spec": "components/profile-menu.json",
"status": "stable-reference",
"primarySource": "nodedc_taskmanager"
},
{
"id": "admin-side-nav",
"spec": "components/admin-side-nav.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "admin-table",
"spec": "components/admin-table.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "entity-modal",
"spec": "components/entity-modal.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "media-source-field",
"spec": "components/media-source-field.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "launcher-showcase-stage",
"spec": "components/launcher-showcase-stage.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "service-rail-card",
"spec": "components/service-rail-card.json",
"status": "draft-stable",
"primarySource": "nodedc_launcher"
},
{
"id": "work-item-card",
"spec": "components/work-item-card.json",
"status": "stable-reference",
"primarySource": "nodedc_taskmanager"
}
],
"recipes": [
"recipes/launcher-shell.recipe.json",
"recipes/admin-catalog.recipe.json",
"recipes/task-manager-board.recipe.json"
],
"globalRules": "rules/ui-rules.json",
"sourceMap": "sources/source-map.json"
}

View File

@ -0,0 +1,51 @@
{
"schemaVersion": "0.1.0",
"rules": [
{
"id": "no-random-local-ui",
"severity": "error",
"text": "Do not create a local one-off UI element when a registry component exists."
},
{
"id": "no-outlines",
"severity": "error",
"text": "Visible browser outlines and hard colored outlines are forbidden. Use surface hover/focus states."
},
{
"id": "circle-actions",
"severity": "error",
"text": "Icon-only actions are circular controls. They use the shared control-ring size and 5px inset rules."
},
{
"id": "dropdowns-portal",
"severity": "error",
"text": "Dropdowns inside cards, tables, sidebars, sticky headers, and scroll containers render through a portal/fixed layer."
},
{
"id": "dropdowns-shared-engine",
"severity": "error",
"text": "Selection dropdowns and action dropdowns use the shared dropdown engine. Do not implement local outside-click and absolute inline menus."
},
{
"id": "matte-glass",
"severity": "error",
"text": "Popup, dropdown, modal, sidebar, and settings surfaces use dark matte glass with blur, not plain transparency or light foreign backgrounds."
},
{
"id": "status-pills",
"severity": "error",
"text": "Statuses use the shared status-tone palette, centered label, no outline, and fixed status control geometry."
},
{
"id": "admin-tables",
"severity": "warning",
"text": "Admin data screens use AdminTable anatomy: table-shell, toolbar, editable cells, circular actions, and shared status/date controls."
},
{
"id": "taskmanager-calendar",
"severity": "warning",
"text": "Calendar popovers must follow the Task Manager nodedc-calendar-shell and portal dropdown pattern."
}
]
}

View File

@ -0,0 +1,86 @@
{
"schemaVersion": "0.1.0",
"projects": {
"nodedc_launcher": {
"root": "/Users/dcconstructions/Downloads/mnt/data/nodedc_launcher",
"sources": {
"tokensAndCss": [
"src/styles/globals.css"
],
"topBar": [
"src/widgets/top-bar/TopBar.tsx"
],
"launcherStage": [
"src/widgets/service-stage/ServiceStage.tsx"
],
"serviceRail": [
"src/widgets/service-rail/ServiceRail.tsx"
],
"adminOverlay": [
"src/widgets/admin-overlay/AdminOverlay.tsx"
],
"primitiveUi": [
"src/shared/ui/Button.tsx",
"src/shared/ui/Glass.tsx",
"src/shared/ui/PortalDropdown.tsx"
],
"storage": [
"src/shared/api/storageApi.ts"
]
}
},
"nodedc_taskmanager": {
"root": "/Users/dcconstructions/Downloads/mnt/data/dc_taskmanager/NODEDC_TASKMANAGER",
"sources": {
"existingDocs": [
"HDESIGN-CODE.md",
"HDROPDOWN-CANON.md",
"HUI-CANON-AUDIT.md",
"design.config.json"
],
"tokensAndCss": [
"plane-src/apps/web/styles/globals.css"
],
"actionDropdown": [
"plane-src/packages/ui/src/dropdowns/action-dropdown.tsx"
],
"dateDropdown": [
"plane-src/apps/web/core/components/dropdowns/date.tsx"
],
"profileMenu": [
"plane-src/apps/web/core/components/workspace/sidebar/user-menu-root.tsx"
],
"workItemCard": [
"plane-src/apps/web/core/components/issues/issue-layouts/shared/nodedc-work-item-card.tsx"
],
"appHeader": [
"plane-src/apps/web/core/components/core/app-header.tsx",
"plane-src/apps/web/ce/components/common/extended-app-header.tsx"
]
}
}
},
"crossProjectMapping": [
{
"component": "dropdown-surface",
"launcher": ["portal-dropdown", "nodedc-dropdown-surface"],
"taskManager": ["nodedc-dropdown-surface", "nodedc-dropdown-option"]
},
{
"component": "calendar-popover",
"launcher": ["DateField", "nodedc-calendar-shell placeholder"],
"taskManager": ["DateDropdown", "nodedc-calendar-shell"]
},
{
"component": "profile-menu",
"launcher": ["topbar profile cluster needs implementation"],
"taskManager": ["UserMenuRoot"]
},
{
"component": "admin-table",
"launcher": ["ServicesSection", "ClientsSection", "UsersSection", "GroupsSection"],
"taskManager": ["settings tables and external contour settings classes"]
}
]
}

View File

@ -0,0 +1,24 @@
:root {
--nodedc-accent-rgb: 195 255 102;
--nodedc-card-passive-rgb: 42 43 46;
--nodedc-card-active-rgb: 195 255 102;
--nodedc-on-accent-rgb: 11 17 23;
--nodedc-radius-modal: 1.75rem;
--nodedc-radius-card: 1.35rem;
--nodedc-radius-control: 1.25rem;
--nodedc-radius-option: 0.9rem;
--nodedc-radius-calendar: 1.1rem;
--nodedc-radius-circle: 999px;
--nodedc-toolbar-pill-height: 2.5rem;
--nodedc-control-ring: 2.92rem;
--nodedc-control-inset: 5px;
--nodedc-status-width: 8.65rem;
--nodedc-status-height: 2.08rem;
--nodedc-page-pad: 1.25rem;
--nodedc-panel-gap: 1.25rem;
--nodedc-panel-pad: 1rem;
--nodedc-dropdown-blur: 44px;
--nodedc-panel-blur: 28px;
--nodedc-modal-blur: 34px;
}

View File

@ -0,0 +1,79 @@
{
"schemaVersion": "0.1.0",
"name": "NODE.DC Design Tokens",
"color": {
"accentRgb": [195, 255, 102],
"onAccentRgb": [11, 17, 23],
"cardPassiveRgb": [42, 43, 46],
"cardActiveRgb": [195, 255, 102],
"surfaceBlack": "rgba(8, 8, 11, 0.9)",
"surfacePanel": "rgba(10, 10, 13, 0.88)",
"surfaceControl": "rgba(255, 255, 255, 0.06)",
"surfaceControlHover": "rgba(255, 255, 255, 0.10)",
"textPrimary": "rgba(255, 255, 255, 0.94)",
"textSecondary": "rgba(255, 255, 255, 0.74)",
"textMuted": "rgba(255, 255, 255, 0.54)"
},
"radius": {
"modal": "1.75rem",
"card": "1.35rem",
"control": "1.25rem",
"dropdownOption": "0.9rem",
"calendar": "1.1rem",
"circle": "999px"
},
"size": {
"toolbarHeight": "3rem",
"toolbarPillHeight": "2.5rem",
"controlRing": "2.92rem",
"controlInset": "5px",
"statusWidth": "8.65rem",
"statusHeight": "2.08rem",
"modalButtonHeight": "2.75rem",
"launcherRailHeight": "9.2rem"
},
"space": {
"pagePad": "1.25rem",
"panelGap": "1.25rem",
"panelPad": "1rem",
"controlGap": "0.65rem",
"dropdownPad": "0.75rem",
"tableCellX": "0.75rem",
"tableCellY": "0.48rem"
},
"blur": {
"dropdown": "44px",
"panel": "28px",
"modal": "34px",
"control": "18px"
},
"shadow": {
"dropdown": "0 22px 60px rgba(0, 0, 0, 0.36), 0 6px 18px rgba(0, 0, 0, 0.2)",
"panel": "0 34px 110px rgba(0, 0, 0, 0.52)",
"modal": "0 34px 120px rgba(0, 0, 0, 0.62)",
"workItem": "0 14px 34px rgba(0, 0, 0, 0.24), inset 0 1px 0 rgba(255, 255, 255, 0.035)"
},
"statusTone": {
"green": {
"background": "rgba(181, 255, 90, 0.075)",
"color": "rgba(226, 255, 190, 0.94)"
},
"yellow": {
"background": "rgba(246, 201, 95, 0.075)",
"color": "rgba(255, 232, 178, 0.94)"
},
"violet": {
"background": "rgba(210, 197, 255, 0.07)",
"color": "rgba(232, 225, 255, 0.92)"
},
"red": {
"background": "rgba(255, 120, 120, 0.07)",
"color": "rgba(255, 216, 216, 0.92)"
},
"muted": {
"background": "rgba(255, 255, 255, 0.075)",
"color": "rgba(255, 255, 255, 0.78)"
}
}
}