@ethlete/agent-rules 0.1.0-next.2 → 0.1.0-next.20
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +269 -0
- package/README.md +350 -29
- package/THIRD-PARTY-LICENSES.md +35 -0
- package/content/git-hooks/post-checkout.sh +10 -0
- package/content/git-hooks/pre-push.sh +5 -0
- package/content/hooks/context-warning.py +766 -108
- package/content/hooks/subagent-model-policy.py +187 -0
- package/content/output-styles/ste-clarity.md +131 -0
- package/content/rules/app-styling.md +59 -0
- package/content/rules/comments.md +53 -20
- package/content/rules/lint-and-format.md +6 -5
- package/content/rules/nx-layout.md +47 -0
- package/content/rules/reactive-state.md +1 -1
- package/content/rules/styling.md +9 -7
- package/content/rules/subagent-models.md +29 -0
- package/content/skills/angular-patterns/SKILL.md +30 -7
- package/content/skills/api-source/SKILL.md +130 -0
- package/content/skills/app-testing/SKILL.md +141 -0
- package/content/skills/codex-subagent/SKILL.md +90 -0
- package/content/skills/codex-subagent/codex-agent.mjs +229 -0
- package/content/skills/design-exploration/SKILL.md +205 -0
- package/content/skills/design-exploration/check-story.mjs +139 -0
- package/content/skills/design-exploration/shoot-template.mjs +61 -0
- package/content/skills/domain-modeling/ADR-FORMAT.md +47 -0
- package/content/skills/domain-modeling/CONTEXT-FORMAT.md +60 -0
- package/content/skills/domain-modeling/SKILL.md +80 -0
- package/content/skills/figma-export/SKILL.md +191 -0
- package/content/skills/figma-export/dump-figma-layers.py +83 -0
- package/content/skills/figma-export/dump-figma-svg.py +235 -0
- package/content/skills/figma-export/measure-template.mjs +87 -0
- package/content/skills/git-commit/SKILL.md +6 -7
- package/content/skills/git-flow/SKILL.md +87 -0
- package/content/skills/grill-with-docs/SKILL.md +13 -0
- package/content/skills/grilling/SKILL.md +34 -0
- package/content/skills/handoff/SKILL.md +74 -4
- package/content/skills/query/SKILL.md +165 -64
- package/content/skills/rxjs-signals/SKILL.md +31 -4
- package/content/skills/sdk-docs/SKILL.md +50 -14
- package/content/skills/sdk-local-build/SKILL.md +30 -10
- package/content/skills/sdk-local-build/sdk-local-baseline.mjs +64 -0
- package/content/skills/sdk-source/SKILL.md +49 -21
- package/content/skills/sdk-update/SKILL.md +96 -0
- package/content/skills/story-styling/SKILL.md +10 -8
- package/content/skills/styleguide/SKILL.md +12 -7
- package/content/skills/styleguide/assets.md +54 -0
- package/content/skills/styleguide/changesets.md +17 -0
- package/content/skills/styleguide/file-structure.md +73 -0
- package/content/skills/styleguide/lint-rule-lookup.md +51 -0
- package/content/skills/styleguide/storybook-structure.md +25 -0
- package/content/skills/theming/SKILL.md +41 -28
- package/content/skills/timetrack/SKILL.md +397 -0
- package/content/skills/verify-in-app/SKILL.md +107 -0
- package/migrations/app-styling-utilities.md +63 -0
- package/migrations/list-state-query-form.md +20 -0
- package/migrations/nx-layout.md +29 -0
- package/migrations/sdk-components-over-hand-built-ui.md +27 -0
- package/migrations/search-query-field.md +52 -0
- package/migrations.json +48 -0
- package/package.json +16 -2
- package/src/index.js +63 -28
- package/src/index.js.map +1 -1
- package/src/lib/cli-args.d.ts +9 -0
- package/src/lib/cli-args.js +48 -0
- package/src/lib/cli-args.js.map +1 -0
- package/src/lib/commitlint.d.ts +10 -0
- package/src/lib/commitlint.js +51 -0
- package/src/lib/commitlint.js.map +1 -0
- package/src/lib/config.d.ts +38 -4
- package/src/lib/config.js +84 -8
- package/src/lib/config.js.map +1 -1
- package/src/lib/filter.d.ts +2 -0
- package/src/lib/filter.js +4 -4
- package/src/lib/filter.js.map +1 -1
- package/src/lib/frontmatter.d.ts +2 -0
- package/src/lib/frontmatter.js +33 -5
- package/src/lib/frontmatter.js.map +1 -1
- package/src/lib/git-flow/build.d.ts +35 -0
- package/src/lib/git-flow/build.js +24 -0
- package/src/lib/git-flow/build.js.map +1 -0
- package/src/lib/git-flow/config.d.ts +59 -0
- package/src/lib/git-flow/config.js +50 -0
- package/src/lib/git-flow/config.js.map +1 -0
- package/src/lib/git-flow/index.d.ts +6 -0
- package/src/lib/git-flow/index.js +10 -0
- package/src/lib/git-flow/index.js.map +1 -0
- package/src/lib/git-flow/parse.d.ts +49 -0
- package/src/lib/git-flow/parse.js +300 -0
- package/src/lib/git-flow/parse.js.map +1 -0
- package/src/lib/git-flow/rename.d.ts +24 -0
- package/src/lib/git-flow/rename.js +70 -0
- package/src/lib/git-flow/rename.js.map +1 -0
- package/src/lib/git-flow/start.d.ts +49 -0
- package/src/lib/git-flow/start.js +57 -0
- package/src/lib/git-flow/start.js.map +1 -0
- package/src/lib/git-flow/validate.d.ts +34 -0
- package/src/lib/git-flow/validate.js +72 -0
- package/src/lib/git-flow/validate.js.map +1 -0
- package/src/lib/git-flow-command.d.ts +4 -0
- package/src/lib/git-flow-command.js +157 -0
- package/src/lib/git-flow-command.js.map +1 -0
- package/src/lib/git-flow-repair.d.ts +17 -0
- package/src/lib/git-flow-repair.js +157 -0
- package/src/lib/git-flow-repair.js.map +1 -0
- package/src/lib/git-flow-start.d.ts +20 -0
- package/src/lib/git-flow-start.js +132 -0
- package/src/lib/git-flow-start.js.map +1 -0
- package/src/lib/git.d.ts +64 -0
- package/src/lib/git.js +131 -0
- package/src/lib/git.js.map +1 -0
- package/src/lib/gitlab.d.ts +35 -0
- package/src/lib/gitlab.js +108 -0
- package/src/lib/gitlab.js.map +1 -0
- package/src/lib/index.d.ts +2 -0
- package/src/lib/index.js +2 -0
- package/src/lib/index.js.map +1 -1
- package/src/lib/migrate.js +1 -1
- package/src/lib/migrate.js.map +1 -1
- package/src/lib/output-style-command.d.ts +3 -0
- package/src/lib/output-style-command.js +69 -0
- package/src/lib/output-style-command.js.map +1 -0
- package/src/lib/output-style.d.ts +38 -0
- package/src/lib/output-style.js +134 -0
- package/src/lib/output-style.js.map +1 -0
- package/src/lib/owned-paths.js +27 -3
- package/src/lib/owned-paths.js.map +1 -1
- package/src/lib/package-runner.d.ts +3 -0
- package/src/lib/package-runner.js +69 -0
- package/src/lib/package-runner.js.map +1 -0
- package/src/lib/plain-text.d.ts +9 -0
- package/src/lib/plain-text.js +22 -0
- package/src/lib/plain-text.js.map +1 -0
- package/src/lib/plan.d.ts +6 -6
- package/src/lib/plan.js +147 -40
- package/src/lib/plan.js.map +1 -1
- package/src/lib/prompt.d.ts +8 -0
- package/src/lib/prompt.js +27 -0
- package/src/lib/prompt.js.map +1 -0
- package/src/lib/render.d.ts +24 -2
- package/src/lib/render.js +39 -10
- package/src/lib/render.js.map +1 -1
- package/src/lib/sync.d.ts +0 -1
- package/src/lib/sync.js +23 -15
- package/src/lib/sync.js.map +1 -1
- package/src/lib/targets/agents-skills.js +1 -1
- package/src/lib/targets/agents-skills.js.map +1 -1
- package/src/lib/targets/claude-hooks.d.ts +1 -23
- package/src/lib/targets/claude-hooks.js +17 -85
- package/src/lib/targets/claude-hooks.js.map +1 -1
- package/src/lib/targets/claude.js +1 -2
- package/src/lib/targets/claude.js.map +1 -1
- package/src/lib/targets/codex-hooks.d.ts +12 -0
- package/src/lib/targets/codex-hooks.js +34 -0
- package/src/lib/targets/codex-hooks.js.map +1 -0
- package/src/lib/targets/codex.js +4 -4
- package/src/lib/targets/codex.js.map +1 -1
- package/src/lib/targets/copilot.js +3 -3
- package/src/lib/targets/copilot.js.map +1 -1
- package/src/lib/targets/cursor.js +2 -2
- package/src/lib/targets/cursor.js.map +1 -1
- package/src/lib/targets/git-hooks.d.ts +24 -0
- package/src/lib/targets/git-hooks.js +71 -0
- package/src/lib/targets/git-hooks.js.map +1 -0
- package/src/lib/targets/hooks-shared.d.ts +58 -0
- package/src/lib/targets/hooks-shared.js +128 -0
- package/src/lib/targets/hooks-shared.js.map +1 -0
- package/src/lib/targets/shared.d.ts +1 -9
- package/src/lib/targets/shared.js +4 -8
- package/src/lib/targets/shared.js.map +1 -1
- package/src/lib/timetrack-command.d.ts +11 -0
- package/src/lib/timetrack-command.js +1055 -0
- package/src/lib/timetrack-command.js.map +1 -0
- package/src/lib/timetrack-snapshot.d.ts +55 -0
- package/src/lib/timetrack-snapshot.js +120 -0
- package/src/lib/timetrack-snapshot.js.map +1 -0
- package/src/lib/timetrack.d.ts +561 -0
- package/src/lib/timetrack.js +271 -0
- package/src/lib/timetrack.js.map +1 -0
- package/content/skills/styleguide/STYLEGUIDE.md +0 -520
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
# File structure
|
|
2
|
+
|
|
3
|
+
Read this file when placing routes, views, components, providers, or local utilities.
|
|
4
|
+
|
|
5
|
+
Mirror the route tree in folders and suffix routing components with `-view`:
|
|
6
|
+
|
|
7
|
+
```ts
|
|
8
|
+
import { Routes } from '@angular/router';
|
|
9
|
+
|
|
10
|
+
export const SHOP_ROUTES: Routes = [
|
|
11
|
+
{
|
|
12
|
+
path: 'items',
|
|
13
|
+
loadComponent: () =>
|
|
14
|
+
import('./items-list-view/items-list-view.component').then((module) => module.ItemsListViewComponent),
|
|
15
|
+
},
|
|
16
|
+
{
|
|
17
|
+
path: 'items/:id',
|
|
18
|
+
loadComponent: () =>
|
|
19
|
+
import('./item-detail-host-view/item-detail-host-view.component').then(
|
|
20
|
+
(module) => module.ItemDetailHostViewComponent,
|
|
21
|
+
),
|
|
22
|
+
children: [
|
|
23
|
+
{
|
|
24
|
+
path: '',
|
|
25
|
+
loadComponent: () =>
|
|
26
|
+
import('./item-detail-host-view/item-detail-view/item-detail-view.component').then(
|
|
27
|
+
(module) => module.ItemDetailViewComponent,
|
|
28
|
+
),
|
|
29
|
+
},
|
|
30
|
+
{
|
|
31
|
+
path: 'reviews',
|
|
32
|
+
loadComponent: () =>
|
|
33
|
+
import('./item-detail-host-view/item-reviews-view/item-reviews-view.component').then(
|
|
34
|
+
(module) => module.ItemReviewsViewComponent,
|
|
35
|
+
),
|
|
36
|
+
},
|
|
37
|
+
],
|
|
38
|
+
},
|
|
39
|
+
];
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
Use these placement rules:
|
|
43
|
+
|
|
44
|
+
- Put reusable view-level pieces in `components/`.
|
|
45
|
+
- Put children used only by one parent in that parent's `partials/`.
|
|
46
|
+
- Put generic presentation-only pieces in `uikit/`.
|
|
47
|
+
- Put application-shell pieces in `shell/`.
|
|
48
|
+
- Keep a directive, pipe, provider, form configuration, or utility beside its narrowest
|
|
49
|
+
consumer. Move it upward only when more consumers appear.
|
|
50
|
+
- Use simple utility names such as `items-list-filter-form.ts`, not `.utils.ts`.
|
|
51
|
+
- Give exportable folders an `index.ts`, but import source files directly. Do not import
|
|
52
|
+
a parent barrel from its subdirectory.
|
|
53
|
+
- Keep application projects thin; move shared or domain logic into buildable libraries
|
|
54
|
+
with clear import paths.
|
|
55
|
+
|
|
56
|
+
```plaintext
|
|
57
|
+
shop/
|
|
58
|
+
├── items-list-view/
|
|
59
|
+
│ ├── components/
|
|
60
|
+
│ │ └── item-card/
|
|
61
|
+
│ │ ├── partials/
|
|
62
|
+
│ │ │ ├── item-image/
|
|
63
|
+
│ │ │ └── item-price/
|
|
64
|
+
│ │ ├── item-card.component.ts
|
|
65
|
+
│ │ └── item-card.component.html
|
|
66
|
+
│ ├── items-list-filter-form.ts
|
|
67
|
+
│ └── items-list-view.component.ts
|
|
68
|
+
└── item-detail-host-view/
|
|
69
|
+
├── item-detail-view/
|
|
70
|
+
├── item-reviews-view/
|
|
71
|
+
├── item-detail.provider.ts
|
|
72
|
+
└── item-detail-host-view.component.ts
|
|
73
|
+
```
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
# Lint rule lookup
|
|
2
|
+
|
|
3
|
+
Read this file only to explain a lint result or identify which rule owns a mechanical
|
|
4
|
+
convention. Run lint with `--fix`; do not hand-check this table before linting.
|
|
5
|
+
|
|
6
|
+
| Convention | Rule |
|
|
7
|
+
| -------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
8
|
+
| No `any` / `$any()`; narrow `unknown` | `@typescript-eslint/no-explicit-any`, `@angular-eslint/template/no-any` |
|
|
9
|
+
| Static strings and booleans use attributes | `@angular-eslint/template/prefer-static-string-properties`, `ethlete/prefer-static-boolean-properties` |
|
|
10
|
+
| `type`, not `interface` (module augmentations stay interfaces) | `ethlete/consistent-type-definitions` |
|
|
11
|
+
| No `enum` or `const enum` | `ethlete/no-enum` |
|
|
12
|
+
| `const` by default; one declaration per statement | `no-var`, `prefer-const`, `one-var` |
|
|
13
|
+
| Strict equality | `eqeqeq` |
|
|
14
|
+
| Maximum two positional parameters | `max-params` |
|
|
15
|
+
| No type-only imports | `ethlete/no-type-only-import` |
|
|
16
|
+
| Descriptive `T`-prefixed generic names | `@typescript-eslint/naming-convention` |
|
|
17
|
+
| No `async` / `await` | `ethlete/no-async-await` |
|
|
18
|
+
| Arrow functions standalone; methods in classes | `no-restricted-syntax` |
|
|
19
|
+
| Blank line before a multiline guard return | `ethlete/guard-return-newline` |
|
|
20
|
+
| No trivially inferable return type | `ethlete/no-trivial-return-type` |
|
|
21
|
+
| Member and local naming conventions | `@typescript-eslint/naming-convention`, `ethlete/no-leading-underscore-class-member`, `ethlete/no-screaming-case-local` |
|
|
22
|
+
| Class constants are `readonly` and upper case | `ethlete/class-constant-property` |
|
|
23
|
+
| No `readonly` on reactive members | `ethlete/no-readonly-signal` |
|
|
24
|
+
| Injected and template-visible member accessibility | `ethlete/inject-member-accessibility`, `ethlete/template-member-accessibility` |
|
|
25
|
+
| No inject chains, pure aliases, or trivial wrappers | `ethlete/no-inject-chain`, `ethlete/no-member-alias`, `ethlete/no-trivial-wrapper-method` |
|
|
26
|
+
| No unused private or protected members | `ethlete/no-unused-class-member` |
|
|
27
|
+
| Pure module-scope provider calls | `ethlete/no-impure-top-level-provider` |
|
|
28
|
+
| No redundant `@internal` | `ethlete/no-redundant-internal` |
|
|
29
|
+
| Observable names end in `$` | `ethlete/require-dollar-suffix` |
|
|
30
|
+
| No subscribe body, subscribe in pipe, or RxJS in signal derivations | `ethlete/no-subscribe-with-body`, `ethlete/no-subscribe-in-pipe`, `ethlete/no-rxjs-in-effect` |
|
|
31
|
+
| `takeUntilDestroyed()` is the last operator in its pipe | `ethlete/take-until-destroyed-last` |
|
|
32
|
+
| Effect teardown uses `onCleanup` or `DestroyRef` | `ethlete/no-effect-cleanup-return` |
|
|
33
|
+
| Prefer `linkedSignal` for writable derived state | `ethlete/prefer-linked-signal` |
|
|
34
|
+
| Global component CSS encapsulation | `ethlete/require-view-encapsulation-none` |
|
|
35
|
+
| Angular-version-correct change detection metadata | `ethlete/require-on-push-change-detection`, `ethlete/no-redundant-on-push-change-detection` |
|
|
36
|
+
| No redundant standalone flag or empty metadata arrays | `ethlete/no-standalone-flag`, `ethlete/no-empty-angular-metadata-arrays` |
|
|
37
|
+
| No legacy lifecycle hooks or decorators | `no-restricted-syntax`, `ethlete/no-legacy-angular-decorators` |
|
|
38
|
+
| No injectable services, guards, or resolvers | `no-restricted-syntax` |
|
|
39
|
+
| Output naming | `@angular-eslint/no-output-on-prefix`, `@angular-eslint/no-output-native`, `ethlete/prefer-present-tense-output` |
|
|
40
|
+
| Inputs do not collide with global HTML attributes | `ethlete/no-native-html-input-name` |
|
|
41
|
+
| No pipe logic | `ethlete/no-pipe-logic` |
|
|
42
|
+
| Class members and decorator metadata stay ordered | `ethlete/class-member-order`, `ethlete/angular-decorator-property-order` |
|
|
43
|
+
| Routing views use `-view` / `ViewComponent` | `ethlete/enforce-routing-view-naming` |
|
|
44
|
+
| No direct browser globals, DOM queries, native observers, or cookies | `no-restricted-globals`, `ethlete/no-direct-dom-manipulation`, `ethlete/no-dom-query`, `ethlete/no-native-observers`, `ethlete/no-document-cookie` |
|
|
45
|
+
| No barrel imports | `no-restricted-syntax` |
|
|
46
|
+
| Prefer the SDK wrappers for platform utilities | `ethlete/prefer-clone-equal`, `ethlete/prefer-rxjs-timer`, `ethlete/prefer-match-media`, `ethlete/prefer-viewport-size`, `ethlete/no-angular-seo-services`, `ethlete/no-locale-id`, `ethlete/no-angular-router-api` |
|
|
47
|
+
|
|
48
|
+
Judgment still belongs outside lint: name things after their behavior, use an object
|
|
49
|
+
parameter after two positional parameters, expose injected members directly instead of
|
|
50
|
+
aliasing them, and use `/** @internal */` only on technically public library API that
|
|
51
|
+
must be stripped from declarations.
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# Storybook structure
|
|
2
|
+
|
|
3
|
+
Read this file when placing a `*.stories.ts` file or code used only to render stories.
|
|
4
|
+
|
|
5
|
+
- Keep the `*.stories.ts` file beside the component it documents.
|
|
6
|
+
- Put private host components, dummy data, and story-only helpers in `storybook/`.
|
|
7
|
+
- Never export Storybook-only code from the component's public barrel.
|
|
8
|
+
- A private `storybook/index.ts` may simplify imports into the adjacent story, but no
|
|
9
|
+
production source may import it.
|
|
10
|
+
|
|
11
|
+
```plaintext
|
|
12
|
+
settings-form/
|
|
13
|
+
├── storybook/
|
|
14
|
+
│ ├── settings-form-storybook.component.ts
|
|
15
|
+
│ ├── settings-form-storybook.component.html
|
|
16
|
+
│ ├── settings-form-dummy-data.ts
|
|
17
|
+
│ └── index.ts
|
|
18
|
+
├── settings-form.component.ts
|
|
19
|
+
├── settings-form.component.html
|
|
20
|
+
├── settings-form.component.stories.ts
|
|
21
|
+
└── index.ts
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
The story file stays at the component root; only its private support code goes into
|
|
25
|
+
`storybook/`.
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: theming
|
|
3
|
-
description: The two runtime theming systems in @ethlete/core - surface theming (elevation-aware neutrals) and color theming (semantic accent palettes)
|
|
3
|
+
description: The two runtime theming systems in @ethlete/core - surface theming (elevation-aware neutrals) and color theming (semantic accent palettes). Read BEFORE writing or reviewing CSS involving color, background, border, or interaction state, and when wiring theme context across overlay/portal boundaries.
|
|
4
4
|
kind: skill
|
|
5
5
|
scope: consumer
|
|
6
6
|
requires: ['@ethlete/core']
|
|
@@ -37,16 +37,16 @@ The generated CSS defines the raw vars on `.et-surface--<name>` / `.et-color--<n
|
|
|
37
37
|
classes (plus `:root` defaults) and derives the public tokens below on `:root` **and**
|
|
38
38
|
every scope class - so the tokens are always resolvable and components just read them.
|
|
39
39
|
|
|
40
|
-
**Theme names are yours.**
|
|
41
|
-
|
|
42
|
-
The portable handle is the theme **`type`**: `
|
|
43
|
-
the app registered with `type: 'error'`.
|
|
40
|
+
**Theme names are yours.** Never hardcode them as an SDK-defined union or reusable API
|
|
41
|
+
contract. App-specific docs may name their own themes when they label them as app values.
|
|
42
|
+
The portable handle is the theme **`type`**: `injectSemanticColorTheme('error')` finds
|
|
43
|
+
whichever theme the app registered with `type: 'error'`.
|
|
44
44
|
|
|
45
45
|
## Tokens components may consume
|
|
46
46
|
|
|
47
47
|
Use these **derived** tokens - never the raw `--et-surface-background` /
|
|
48
|
-
`--et-color-primary` channel triplets
|
|
49
|
-
|
|
48
|
+
`--et-color-primary` channel triplets. Never use a hardcoded color as the primary value.
|
|
49
|
+
A static fallback inside `var(--token, <fallback>)` is permitted, but not required.
|
|
50
50
|
|
|
51
51
|
Surface (each exists as `-solid` = usable color, `-rgb` = `R G B` channels):
|
|
52
52
|
|
|
@@ -61,12 +61,12 @@ Surface (each exists as `-solid` = usable color, `-rgb` = `R G B` channels):
|
|
|
61
61
|
|
|
62
62
|
Color (from the nearest `[etProvideColor]` scope):
|
|
63
63
|
|
|
64
|
-
| Token | Use for
|
|
65
|
-
| -------------------------------- |
|
|
66
|
-
| `--et-theme-color-primary` | filled backgrounds
|
|
67
|
-
| `--et-theme-color-primary-solid` | accents at full strength: focus borders, selected marks, spinners
|
|
68
|
-
| `--et-theme-color-on-primary` | text/icons on a primary-filled background
|
|
69
|
-
| `--et-theme-color-ink-solid` | primary-tinted text/border on transparent/tonal fills
|
|
64
|
+
| Token | Use for |
|
|
65
|
+
| -------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
66
|
+
| `--et-theme-color-primary` | filled backgrounds on an element you do **not** tint. To tint per state, set `--et-theme-color-primary-opacity: 0.16` and compose the color yourself: `rgb(var(--et-theme-color-primary-rgb) / var(--et-theme-color-primary-opacity))`. The alias is substituted at the `et-color--*` scope, so an inherited value carries the scope's opacity, never the element's |
|
|
67
|
+
| `--et-theme-color-primary-solid` | accents at full strength: focus borders, selected marks, spinners |
|
|
68
|
+
| `--et-theme-color-on-primary` | text/icons on a primary-filled background |
|
|
69
|
+
| `--et-theme-color-ink-solid` | primary-tinted text/border on transparent/tonal fills |
|
|
70
70
|
|
|
71
71
|
Interaction-state variants (`--et-surface-interaction-{hover,focus,active,disabled}-solid`)
|
|
72
72
|
resolve automatically per CSS state when the element has `[etSurfaceInteractive]`;
|
|
@@ -75,8 +75,8 @@ the interactive element itself, never on a wrapper.
|
|
|
75
75
|
|
|
76
76
|
## Providing context
|
|
77
77
|
|
|
78
|
-
- `[etProvideSurface]="
|
|
79
|
-
elevation) set the surface scope; `[etProvideColor]="
|
|
78
|
+
- `[etProvideSurface]="surfaceThemeName"` / `[etAutoSurface]` (auto-picks the next
|
|
79
|
+
elevation) set the surface scope; `[etProvideColor]="colorThemeName"` sets the color scope.
|
|
80
80
|
A component that owns a themed region usually adds `ProvideColorDirective` /
|
|
81
81
|
`ProvideSurfaceDirective` as `hostDirectives`.
|
|
82
82
|
- **Detached overlay panes (menu, dialog, tooltip…) do not inherit DOM context.**
|
|
@@ -85,10 +85,17 @@ the interactive element itself, never on a wrapper.
|
|
|
85
85
|
color and `resolveSurfaceByElevation(themes, type, elevation + 1)` for the surface.
|
|
86
86
|
- **Semantic colors come through DI, not CSS.** There is no global "error color"
|
|
87
87
|
variable - error/warning/success are just color themes. To render something in the
|
|
88
|
-
error color, `
|
|
89
|
-
theme) and either bind it
|
|
90
|
-
|
|
91
|
-
|
|
88
|
+
error color, `injectSemanticColorTheme('error')` (reading it throws if the app
|
|
89
|
+
registered no `type: 'error'` theme) and either bind it
|
|
90
|
+
(`[etProvideColor]="errorColorTheme()"`) or force it programmatically
|
|
91
|
+
(`provideColor.forceColor(theme)` / `clearForcedColor()`). Inside that scope,
|
|
92
|
+
`--et-theme-color-primary-*` _is_ the error color.
|
|
93
|
+
- **`injectSemanticColorTheme(type)` follows the surface**: it is a signal of the theme
|
|
94
|
+
the nearest surface names in `SurfaceTheme.semanticColorThemes` (e.g.
|
|
95
|
+
`{ success: 'success-on-light' }`, an extra theme registered without a `type`), else
|
|
96
|
+
the theme of that `type`. Never add per-surface logic to a color theme or new CSS vars
|
|
97
|
+
for it. `injectErrorTheme()`, `injectWarningTheme()` and `injectSuccessTheme()` are
|
|
98
|
+
deprecated: they ignore the surface.
|
|
92
99
|
|
|
93
100
|
## Pitfalls
|
|
94
101
|
|
|
@@ -96,15 +103,21 @@ the interactive element itself, never on a wrapper.
|
|
|
96
103
|
declared via `@property` can never default to a theme token. If the default should
|
|
97
104
|
come from the theme, don't declare an `@property` - consume the theme token directly
|
|
98
105
|
(optionally behind a `--_et-*` indirection var).
|
|
106
|
+
- `@property` `initial-value` also cannot use a **font-relative or container unit**
|
|
107
|
+
(`em`, `rem`, `ex`, `ch`, `lh`, `cap`, `ic`, `cq*`). The value must be computationally
|
|
108
|
+
independent, so the browser drops the whole rule and leaves the token unregistered -
|
|
109
|
+
with no error. Percentages and viewport units (`vh`, `vw`, `dvh`) are fine. When the
|
|
110
|
+
default has to be relative, use `syntax: '*'` with no `initial-value` and put the
|
|
111
|
+
default in a fallback at each use site: `var(--et-skeleton-size, 1em)`.
|
|
99
112
|
- `--et-theme-color-primary-*` always resolves to the **nearest color scope**. A
|
|
100
113
|
hardcoded semantic color in CSS can't be replaced by it unless the right theme is
|
|
101
114
|
provided on that element.
|
|
102
|
-
-
|
|
103
|
-
|
|
104
|
-
a hard requirement wherever it is
|
|
105
|
-
- **Cascade layers, not `:where()`,
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
Styling a **story** file rather than a component? The colour rule is the same
|
|
110
|
-
|
|
115
|
+
- A static fallback (`var(--et-surface-border-solid, rgb(255 255 255 / 0.1))`) is
|
|
116
|
+
permitted for theme-less setups, but themes make it unnecessary. `injectSemanticColorTheme()`
|
|
117
|
+
is a hard requirement wherever it is read.
|
|
118
|
+
- **Cascade layers, not `:where()`, decide who wins against SDK component CSS.** SDK
|
|
119
|
+
styles live in `@layer components`, so a utility or unlayered app CSS overrides them.
|
|
120
|
+
An app rule inside `@layer components` loses. See the `app-styling` rule.
|
|
121
|
+
|
|
122
|
+
Styling a **story** file rather than a component? The colour rule is the same. Check the
|
|
123
|
+
repository's Storybook guidance before assuming a Tailwind utility exists.
|