Code editor
The editor surface, gutter, caret, current line, selection, bracket match and monochrome syntax roles that every code-editing or code-viewing host maps onto.
stable · light DOM · 4.0.0. Light DOM retains static content, native semantics, label relationships and host composition without duplicating controls.
Live variants
default
// Compose the window title of the focused container. import { Container } from "./tree.js"; const MAX_LENGTH = 48; export function title(container) { const name = container.name ?? "untitled…"; let label = `${name} (${container.children.length})`; if (label.length > MAX_LENGTH) { label = label.slice(0, MAX_LENGTH) + "…"; } return escape(label); /* escape() is deprecated */ } const broken = 0x1G;
<j3w1-code-editor id="example-code-editor-default"><div class="code-editor" role="textbox" aria-multiline="true" aria-readonly="true" aria-label="title.js, read-only" tabindex="0">
<pre class="code-editor-pre"><span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">1</span><span class="code-editor-text"><span class="code-editor-cm">// Compose the window title of the focused container.</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">2</span><span class="code-editor-text"><span class="code-editor-kw">import</span> <span class="code-editor-punct">{</span> <span class="code-editor-type">Container</span> <span class="code-editor-punct">}</span> <span class="code-editor-kw">from</span> <span class="code-editor-str">"./tree.js"</span><span class="code-editor-punct">;</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">3</span><span class="code-editor-text"><span class="code-editor-kw">const</span> <span class="code-editor-const">MAX_LENGTH</span> <span class="code-editor-op">=</span> <span class="code-editor-num">48</span><span class="code-editor-punct">;</span><span class="code-editor-ws" aria-hidden="true" data-whitespace="··"></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">4</span><span class="code-editor-text"><span class="code-editor-kw">export</span> <span class="code-editor-kw">function</span> <span class="code-editor-fn">title</span><span class="code-editor-punct code-editor-bracket">(</span><span class="code-editor-var">container</span><span class="code-editor-punct code-editor-bracket">)</span> <span class="code-editor-punct">{</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">5</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-kw">const</span> <span class="code-editor-var">name</span> <span class="code-editor-op">=</span> <span class="code-editor-var">container</span><span class="code-editor-punct">.</span><span class="code-editor-prop">name</span> <span class="code-editor-op">??</span> <span class="code-editor-str">"untitled<span class="code-editor-esc">…</span>"</span><span class="code-editor-punct">;</span></span></span>
<span class="code-editor-line code-editor-line-current"><span class="code-editor-ln" aria-hidden="true">6</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-kw">let</span> <span class="code-editor-var">label</span> <span class="code-editor-op">=</span> <span class="code-editor-str">`${</span><span class="code-editor-var">name</span><span class="code-editor-str">} (${</span><span class="code-editor-var">container</span><span class="code-editor-punct">.</span><span class="code-editor-prop">children</span><span class="code-editor-punct">.</span><span class="code-editor-prop">length</span><span class="code-editor-str">})`</span><span class="code-editor-punct">;</span><span class="code-editor-caret" aria-hidden="true"></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">7</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-kw">if</span> <span class="code-editor-punct">(</span><span class="code-editor-sel"><span class="code-editor-var">label</span><span class="code-editor-punct">.</span><span class="code-editor-prop">length</span> <span class="code-editor-op">></span> <span class="code-editor-const">MAX_LENGTH</span><span class="code-editor-punct">)</span> <span class="code-editor-punct">{</span></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">8</span><span class="code-editor-text"><span class="code-editor-sel"><span class="code-editor-indent"> </span><span class="code-editor-indent"> </span><span class="code-editor-var">label</span> <span class="code-editor-op">=</span> <span class="code-editor-var">label</span><span class="code-editor-punct">.</span><span class="code-editor-fn">slice</span><span class="code-editor-punct">(</span><span class="code-editor-num">0</span><span class="code-editor-punct">,</span> <span class="code-editor-const">MAX_LENGTH</span><span class="code-editor-punct">)</span></span> <span class="code-editor-op">+</span> <span class="code-editor-str">"…"</span><span class="code-editor-punct">;</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">9</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-punct">}</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">10</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-kw">return</span> <span class="code-editor-fn code-editor-deprecated">escape</span><span class="code-editor-punct">(</span><span class="code-editor-var">label</span><span class="code-editor-punct">);</span> <span class="code-editor-cm">/* escape() is deprecated */</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">11</span><span class="code-editor-text"><span class="code-editor-punct">}</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">12</span><span class="code-editor-text"><span class="code-editor-kw">const</span> <span class="code-editor-var">broken</span> <span class="code-editor-op">=</span> <span class="code-editor-num">0x1</span><span class="code-editor-invalid">G</span><span class="code-editor-punct">;</span></span></span></pre>
</div></j3w1-code-editor>markup
<!doctype html> <!-- window frame specimen --> <html lang="en"> <head> <title>j3w1 — theme</title> </head> <body class="frame" data-density="compact"> <h1>Window frame</h1> <marquee>obsolete</marquee> <p>Focus is a ring; selection is a fill.</p> </body> </html><
<j3w1-code-editor id="example-code-editor-markup"><div class="code-editor" role="textbox" aria-multiline="true" aria-readonly="true" aria-label="frame.html, read-only" tabindex="0">
<pre class="code-editor-pre"><span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">1</span><span class="code-editor-text"><span class="code-editor-punct"><!</span><span class="code-editor-kw">doctype</span> <span class="code-editor-attr">html</span><span class="code-editor-punct">></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">2</span><span class="code-editor-text"><span class="code-editor-cm"><!-- window frame specimen --></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">3</span><span class="code-editor-text"><span class="code-editor-punct"><</span><span class="code-editor-tag">html</span> <span class="code-editor-attr">lang</span><span class="code-editor-op">=</span><span class="code-editor-str">"en"</span><span class="code-editor-punct">></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">4</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-punct"><</span><span class="code-editor-tag">head</span><span class="code-editor-punct">></span></span></span>
<span class="code-editor-line code-editor-line-current"><span class="code-editor-ln" aria-hidden="true">5</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-indent"> </span><span class="code-editor-punct"><</span><span class="code-editor-tag">title</span><span class="code-editor-punct">></span>j3w1 <span class="code-editor-esc">&mdash;</span> theme<span class="code-editor-punct"></</span><span class="code-editor-tag">title</span><span class="code-editor-punct">></span><span class="code-editor-caret" aria-hidden="true"></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">6</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-punct"></</span><span class="code-editor-tag">head</span><span class="code-editor-punct">></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">7</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-punct"><</span><span class="code-editor-tag">body</span> <span class="code-editor-attr">class</span><span class="code-editor-op">=</span><span class="code-editor-str">"frame"</span> <span class="code-editor-attr">data-density</span><span class="code-editor-op">=</span><span class="code-editor-str">"compact"</span><span class="code-editor-punct">></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">8</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-indent"> </span><span class="code-editor-punct code-editor-bracket"><</span><span class="code-editor-tag">h1</span><span class="code-editor-punct code-editor-bracket">></span><span class="code-editor-heading">Window frame</span><span class="code-editor-punct"></</span><span class="code-editor-tag">h1</span><span class="code-editor-punct">></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">9</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-indent"> </span><span class="code-editor-punct"><</span><span class="code-editor-tag code-editor-deprecated">marquee</span><span class="code-editor-punct">></span>obsolete<span class="code-editor-punct"></</span><span class="code-editor-tag code-editor-deprecated">marquee</span><span class="code-editor-punct">></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">10</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-indent"> </span><span class="code-editor-punct"><</span><span class="code-editor-tag">p</span><span class="code-editor-punct">></span><span class="code-editor-sel">Focus is a ring; selection is a fill.</span><span class="code-editor-punct"></</span><span class="code-editor-tag">p</span><span class="code-editor-punct">></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">11</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-sel"><span class="code-editor-punct"></</span><span class="code-editor-tag">body</span><span class="code-editor-punct">></span></span><span class="code-editor-ws" aria-hidden="true" data-whitespace="·"></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">12</span><span class="code-editor-text"><span class="code-editor-punct"></</span><span class="code-editor-tag">html</span><span class="code-editor-punct">></span><span class="code-editor-invalid"><</span></span></span></pre>
</div></j3w1-code-editor>folded
export function title(container) { const name = container.name ?? "untitled"; if (label.length > MAX_LENGTH) { ⋯ } return escape(label); /* escape() is deprecated */ }
<j3w1-code-editor id="example-code-editor-folded"><div class="code-editor" role="textbox" aria-multiline="true" aria-readonly="true" aria-label="title.js with a folded region, read-only" tabindex="0">
<pre class="code-editor-pre"><span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">4</span><span class="code-editor-text"><span class="code-editor-kw">export</span> <span class="code-editor-kw">function</span> <span class="code-editor-fn">title</span><span class="code-editor-punct code-editor-bracket">(</span><span class="code-editor-var">container</span><span class="code-editor-punct code-editor-bracket">)</span> <span class="code-editor-punct">{</span></span></span>
<span class="code-editor-line code-editor-line-current"><span class="code-editor-ln" aria-hidden="true">5</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-kw">const</span> <span class="code-editor-var">name</span> <span class="code-editor-op">=</span> <span class="code-editor-var">container</span><span class="code-editor-punct">.</span><span class="code-editor-prop">name</span> <span class="code-editor-op">??</span> <span class="code-editor-str">"untitled"</span><span class="code-editor-punct">;</span><span class="code-editor-caret" aria-hidden="true"></span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true"><span class="code-editor-fold-gutter">›</span>7</span><span class="code-editor-text"><span class="code-editor-indent"> </span><span class="code-editor-kw">if</span> <span class="code-editor-punct">(</span><span class="code-editor-sel"><span class="code-editor-var">label</span><span class="code-editor-punct">.</span><span class="code-editor-prop">length</span> <span class="code-editor-op">></span> <span class="code-editor-const">MAX_LENGTH</span><span class="code-editor-punct">)</span> <span class="code-editor-punct">{</span></span> <span class="code-editor-fold" role="img" aria-label="3 folded lines">⋯</span> <span class="code-editor-punct">}</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">10</span><span class="code-editor-text"><span class="code-editor-sel"><span class="code-editor-indent"> </span><span class="code-editor-kw">return</span> <span class="code-editor-fn code-editor-deprecated">escape</span><span class="code-editor-punct">(</span><span class="code-editor-var">label</span><span class="code-editor-punct">);</span></span> <span class="code-editor-cm">/* escape() is deprecated */</span></span></span>
<span class="code-editor-line"><span class="code-editor-ln" aria-hidden="true">11</span><span class="code-editor-text"><span class="code-editor-punct">}</span><span class="code-editor-ws" aria-hidden="true" data-whitespace="·"></span></span></span></pre>
</div></j3w1-code-editor>Install and register
Use the exact version. If npm publication is pending, install the release tarball from the installation guide.
npm install --save-exact @j3w1/ui@4.0.0import '@j3w1/ui/tokens.css';
import '@j3w1/ui/styles/code-editor.css';
import '@j3w1/ui/register/code-editor';Insert the maintained markup above after loading these imports. Its native children provide accessible names and form behavior; the empty custom tag alone does not create a control.
Copy the complete implementation
npx --package=@j3w1/ui@4.0.0 j3w1-ui copy code-editor --out ./vendor/j3w1/code-editorThe CLI verifies every file before writing and refuses overwrites. Serve the output over HTTP and open index.html. Keep its modules, CSS, tokens and licence notices together.
Public API
attributes
| Name | Type / signature | Meaning |
|---|---|---|
disabled | CustomEvent | Disable the native controls owned by this instance. |
loading | CustomEvent | Mark the primary control busy and prevent duplicate activation. |
properties
| Name | Type / signature | Meaning |
|---|---|---|
disabled | boolean | Delegates disabled state to native children. |
name | string | Native control name; application form keys remain explicit. |
methods
| Name | Type / signature | Meaning |
|---|---|---|
refresh | (): void | Reconnect behavior after replacing native child structure. |
focus | (options?: FocusOptions): void | Focus the first usable native control. |
setText | (text: string): void | Replace the bounded read-only text view; no code or shell execution occurs. |
events
| Name | Type / signature | Meaning |
|---|---|---|
j3w1-action | CustomEvent | Request a developer-view action; editing and execution belong to the host. |
Dependencies and verification
Registered components: none. Style dependencies: none.
Package presence establishes an available implementation. Actual passes depend on the tested artifact and environment. Read specification execution evidence; read packed-consumer evidence; inspect the complete state matrix.
Full implementation manifest, API and token dependency closure
Canonical specification
Code editor code-editor
The editor surface, gutter, caret, current line, selection, bracket match and monochrome syntax roles that every code-editing or code-viewing host maps onto.
Report an issue with this component
Tokens
Focus a role to inspect its values; follow its link for persistent usage and source details.
| Part | Role | Value | Use |
|---|---|---|---|
root.bg | color.code.bgapproveduse | #000000 | D-041 code.bg: color.primitive.ink.0. |
root.border | color.border.controlapproveduse | #c81a1a | D-041 owner correction: red control and floating-frame borders, distinct from rose text. |
root.ring | color.interaction.focus.ring-containerobserveduse | #ffa2a7 | Focus colour for containers and explicitly mapped filled controls (D-015); component rules determine ring geometry. |
gutter.bg | color.code.gutter-bgapproveduse | #000000 | D-041 code.gutter-bg: color.primitive.ink.0. |
gutter.rule | color.code.gutter-ruleapproveduse | #482b2b | D-041 code.gutter-rule: color.primitive.modern.divider. |
gutter.bg-read-only | color.surface.sunkenapproveduse | #000000 | Reading and detail panes set below the canvas. |
line-number.text | color.code.line-numberapproveduse | #bd787d | D-041 owner correction: rose is the default UI and reading foreground; near-white is reserved for document headings, highlights and contrast-critical fills. |
line-number.text-active | color.code.line-number-activeapproveduse | #e99499 | D-041 owner correction: rose is the default UI and reading foreground; near-white is reserved for document headings, highlights and contrast-critical fills. |
line.bg-current | color.code.current-lineapproveduse | #0d0707 | D-041 code.current-line: color.primitive.modern.panel. |
caret.bg | color.code.caretapproveduse | #ffa2a7 | D-041 owner correction: rose is the default UI and reading foreground; near-white is reserved for document headings, highlights and contrast-critical fills. |
selection.bg | color.code.selection-bgobserveduse | #420f0c | Editor selection background (muted text stays 4.71:1). |
selection.bg-inactive | color.interaction.selection.inactive-bgobserveduse | #420f0c | Selection while the container is not focused. |
selection.text-inactive | color.interaction.selection.inactive-textapproveduse | #e99499 | D-041 owner correction: rose is the default UI and reading foreground; near-white is reserved for document headings, highlights and contrast-critical fills. |
bracket.outline | color.code.bracket-matchobserveduse | #e53935 | Matching bracket 1px border. |
indent.guide | color.code.indent-guideapproveduse | #482b2b | D-041 code.indent-guide: color.primitive.modern.divider. |
whitespace.text | color.code.whitespaceapproveduse | #986f72 | D-041 code.whitespace: color.primitive.modern.control. |
fold.text | color.text.mutedapproveduse | #d4868b | D-041 owner correction: rose is the default UI and reading foreground; near-white is reserved for document headings, highlights and contrast-critical fills. |
fold.border | color.border.controlapproveduse | #c81a1a | D-041 owner correction: red control and floating-frame borders, distinct from rose text. |
syntax.keyword | color.code.syntax.keywordapproveduse | #c7a0e8 | D-041 code.syntax.keyword: color.primitive.modern.violet. |
syntax.string | color.code.syntax.stringapproveduse | #82d9a0 | D-041 code.syntax.string: color.primitive.modern.green. |
syntax.comment | color.code.syntax.commentapproveduse | #bd787d | D-041 owner correction: rose is the default UI and reading foreground; near-white is reserved for document headings, highlights and contrast-critical fills. |
syntax.number | color.code.syntax.numberapproveduse | #e5c07b | D-041 code.syntax.number: color.primitive.modern.amber. |
syntax.constant | color.code.syntax.constantapproveduse | #e5c07b | D-041 code.syntax.constant: color.primitive.modern.amber. |
syntax.function | color.code.syntax.functionapproveduse | #82b4ff | D-041 code.syntax.function: color.primitive.modern.blue. |
syntax.variable | color.code.syntax.variableapproveduse | #e99499 | D-041 rose coding text reduces glare while syntax hues distinguish meaning. |
syntax.type | color.code.syntax.typeapproveduse | #78d4d4 | D-041 code.syntax.type: color.primitive.modern.cyan. |
syntax.operator | color.code.syntax.operatorapproveduse | #e99499 | D-041 rose coding text reduces glare while syntax hues distinguish meaning. |
syntax.punctuation | color.code.syntax.punctuationapproveduse | #d4868b | D-041 owner correction: rose is the default UI and reading foreground; near-white is reserved for document headings, highlights and contrast-critical fills. |
syntax.property | color.code.syntax.propertyapproveduse | #78d4d4 | D-041 code.syntax.property: color.primitive.modern.cyan. |
syntax.heading | color.code.syntax.headingapproveduse | #f4eeee | D-041 code.syntax.heading: color.primitive.modern.bright. |
syntax.tag | color.code.syntax.tagapproveduse | #f07178 | D-041 code.syntax.tag: color.primitive.modern.red. |
syntax.attribute | color.code.syntax.attributeapproveduse | #e5c07b | D-041 code.syntax.attribute: color.primitive.modern.amber. |
syntax.escape | color.code.syntax.escapeapproveduse | #e5c07b | D-041 code.syntax.escape: color.primitive.modern.amber. |
syntax.invalid | color.code.syntax.invalidapproveduse | #f07178 | D-041 code.syntax.invalid: color.primitive.modern.red. |
syntax.deprecated | color.code.syntax.deprecatedapproveduse | #bd787d | D-041 owner correction: rose is the default UI and reading foreground; near-white is reserved for document headings, highlights and contrast-critical fills. |
State matrix
Every declared state and combination, statically rendered; the default cell is live. Sizes: compact, comfortable (switch with the density control above).
| State | JavaScript | Markup | Folded region |
|---|---|---|---|
default | // Compose the window title of the focused container. import { Container } from "./tree.js"; const MAX_LENGTH = 48; export function title(container) { const name = container.name ?? "untitled…"; let label = `${name} (${container.children.length})`; if (label.length > MAX_LENGTH) { label = label.slice(0, MAX_LENGTH) + "…"; } return escape(label); /* escape() is deprecated */ } const broken = 0x1G; | <!doctype html> <!-- window frame specimen --> <html lang="en"> <head> <title>j3w1 — theme</title> </head> <body class="frame" data-density="compact"> <h1>Window frame</h1> <marquee>obsolete</marquee> <p>Focus is a ring; selection is a fill.</p> </body> </html>< | export function title(container) { const name = container.name ?? "untitled"; if (label.length > MAX_LENGTH) { ⋯ } return escape(label); /* escape() is deprecated */ } |
focus-visible | |||
selected | |||
selected+container-inactive | |||
current | |||
read-only |
Purpose
The reference rendering of source code: the contract a real editor’s theme API is mapped onto. It never edits.
Anatomy
Root .code-editor; parts .code-editor-<part>: -pre, -line, -ln
(line number), -text, -indent, -ws (rendered whitespace), -caret,
-sel (selection range), -bracket, -fold, -fold-gutter. Syntax spans
are .code-editor-<role>: -kw keyword, -str string, -cm comment,
-num number, -const constant, -fn function, -var variable, -type,
-op operator, -punct punctuation, -prop property, -heading, -tag,
-attr attribute, -esc escape, -invalid, -deprecated.
States
| State | Visual | Non-colour channel |
|---|---|---|
| default | code on color.code.bg; comments italic; invalid text wavy-underlined in color.code.syntax.invalid; deprecated text struck through | italic, wavy underline, line-through |
| focus-visible | 2px color.interaction.focus.ring-container ring at −3px; 1px color.code.caret bar; caret line filled color.code.current-line across gutter and text, its number color.code.line-number-active | the ring; the caret bar |
| selected | range filled color.code.selection-bg; syntax colours kept | the host’s selection is announced; the fill spans line ends |
| selected+container-inactive | same range in color.interaction.selection.inactive-bg with color.interaction.selection.inactive-text; no caret, no ring | lightness drop between the two fills |
| current | both characters of the matched pair outlined 1px solid color.code.bracket-match | an outline box, not a colour change |
| read-only | gutter on color.surface.sunken, same line numbers; dotted gutter rule; no caret | aria-readonly; dotted rule; no caret |
Precedence: selection under the text, current line under the selection, bracket outline and caret above everything. The caret never blinks in the reference; a host that blinks it follows the user’s cursor-blink setting and stops under reduced motion.
Keyboard
As in the key table. The theme only draws what the host’s keys produce; the read-only reference consumes no key. A host that captures Tab offers Escape, then Tab, and announces it.
Accessibility
Syntax colour is decoration; meaning never rides on colour alone (italic
comments, wavy-underlined invalid text, struck-through deprecated text).
Selection is a fill and focus a ring, drawn together, never substituting for
each other. Every syntax role meets 4.5:1 on color.code.bg. Inside
color.code.selection-bg, D-041 also keeps comments and types above 4.5:1.
The reference uses semantic syntax hues; the existing code.hued.* roles
alias those syntax roles for consumers using the earlier opt-in mapping.
Line numbers are text people read and meet the text floor; indent
guides, rendered whitespace and the gutter rule are decorative. In forced
colours the caret, selection and bracket outline take Highlight; syntax
spans keep their text styles.
Portability
The port maps these roles onto the host’s theme API without touching caret
behaviour, keyboard handling or selection semantics. No bracket-match
outline: bold weight, deviation recorded. No 1px caret: the host’s own caret
in color.code.caret. The heritage-ansi and extended profiles change
role values only, never the mapping.
Non-examples
Rainbow syntax in the reference, or any hue beyond the three bounded ones
(hosts opt into code.hued.*, D-030). A blinking or animated caret in the
reference. A selection that turns text white and drops the syntax roles. A
current line brighter than the selection. A bracket match as a background
fill, which reads as a selection. Line numbers in a decorative colour. A glow,
gradient or rounded corner on the box. Removing the host’s focus indicator
without drawing the container ring.
Contrast report
33 declared pairs measured on resolved sRGB values with the WCAG 2.x formula; 0 waived (decorative only), 0 failing. A pass is a design target for the named role, not an application-wide conformance claim.
| Pair | State | Kind | Foreground | Background | Ratio | Min | Result |
|---|---|---|---|---|---|---|---|
| code-editor default text | default | text | color.code.syntax.variable #e99499 | color.code.bg #000000 | 9.16 | 4.5 | pass |
| code-editor default border | default | ui | color.border.control #c81a1a | color.code.bg #000000 | 3.62 | 3 | pass |
| code-editor focus-visible text | focus-visible | text | color.code.syntax.variable #e99499 | color.code.current-line #0d0707 | 8.72 | 4.5 | pass |
| code-editor focus-visible outline | focus-visible | ui | color.interaction.focus.ring-container #ffa2a7 | color.code.current-line #0d0707 | 10.45 | 3 | pass |
| code-editor selected text | selected | text | color.code.syntax.variable #e99499 | color.code.selection-bg #420f0c | 7.02 | 4.5 | pass |
| code-editor selected+container-inactive text | selected+container-inactive | text | color.interaction.selection.inactive-text #e99499 | color.interaction.selection.inactive-bg #420f0c | 7.02 | 4.5 | pass |
| code-editor current text | current | text | color.code.syntax.variable #e99499 | color.code.bg #000000 | 9.16 | 4.5 | pass |
| code-editor current border | current | ui | color.code.bracket-match #e53935 | color.code.bg #000000 | 4.97 | 3 | pass |
| code-editor read-only text | read-only | text | color.code.line-number #bd787d | color.surface.sunken #000000 | 6.15 | 4.5 | pass |
| caret on the current line | focus-visible | ui | color.code.caret #ffa2a7 | color.code.current-line #0d0707 | 10.45 | 3 | pass |
| bracket-match outline on the editor surface | current | ui | color.code.bracket-match #e53935 | color.code.bg #000000 | 4.97 | 3 | pass |
| bracket-match outline on the current line | current | ui | color.code.bracket-match #e53935 | color.code.current-line #0d0707 | 4.73 | 3 | pass |
| line numbers in the gutter | — | text | color.code.line-number #bd787d | color.code.gutter-bg #000000 | 6.15 | 4.5 | pass |
| active line number | — | text | color.code.line-number-active #e99499 | color.code.current-line #0d0707 | 8.72 | 4.5 | pass |
| keyword | — | text | color.code.syntax.keyword #c7a0e8 | color.code.bg #000000 | 9.62 | 4.5 | pass |
| string | — | text | color.code.syntax.string #82d9a0 | color.code.bg #000000 | 12.38 | 4.5 | pass |
| comment | — | text | color.code.syntax.comment #bd787d | color.code.bg #000000 | 6.15 | 4.5 | pass |
| number and constant | — | text | color.code.syntax.number #e5c07b | color.code.bg #000000 | 12.16 | 4.5 | pass |
| function | — | text | color.code.syntax.function #82b4ff | color.code.bg #000000 | 9.92 | 4.5 | pass |
| type | — | text | color.code.syntax.type #78d4d4 | color.code.bg #000000 | 12.17 | 4.5 | pass |
| property, heading and invalid text | — | text | color.code.syntax.property #78d4d4 | color.code.bg #000000 | 12.17 | 4.5 | pass |
| tag | — | text | color.code.syntax.tag #f07178 | color.code.bg #000000 | 7.34 | 4.5 | pass |
| attribute and escape | — | text | color.code.syntax.attribute #e5c07b | color.code.bg #000000 | 12.16 | 4.5 | pass |
| deprecated text | — | text | color.code.syntax.deprecated #bd787d | color.code.bg #000000 | 6.15 | 4.5 | pass |
| comment syntax inside the selection | selected | text | color.code.syntax.comment #bd787d | color.code.selection-bg #420f0c | 4.71 | 4.5 | pass |
| type syntax inside the selection | selected | text | color.code.syntax.type #78d4d4 | color.code.selection-bg #420f0c | 9.32 | 4.5 | pass |
| muted string text inside the selection | selected | text | color.code.syntax.string #82d9a0 | color.code.selection-bg #420f0c | 9.49 | 4.5 | pass |
| keyword and tag text inside the selection (D-029) | selected | text | color.code.syntax.keyword #c7a0e8 | color.code.selection-bg #420f0c | 7.37 | 4.5 | pass |
| property, heading and invalid text inside the selection (D-029) | selected | text | color.code.syntax.property #78d4d4 | color.code.selection-bg #420f0c | 9.32 | 4.5 | pass |
| fold marker text | — | text | color.text.muted #d4868b | color.code.bg #000000 | 7.58 | 4.5 | pass |
| indent guide (decorative) | — | ui | color.code.indent-guide #482b2b | color.code.bg #000000 | 1.66 | 1 | pass |
| rendered whitespace (decorative) | — | ui | color.code.whitespace #986f72 | color.code.bg #000000 | 4.85 | 1 | pass |
| gutter rule (decorative) | — | ui | color.code.gutter-rule #482b2b | color.code.bg #000000 | 1.66 | 1 | pass |
Keys
| Key | Action |
|---|---|
| (host) | The host editor owns every key; the theme changes no binding, no caret behaviour and no selection model. |
| Tab | Reaches the editor as one stop in the reference; whether Tab inserts or moves focus is the host's rule and is announced by the host. |
| Escape | In hosts that trap Tab, Escape must release focus to the next stop; the theme does not provide it. |
For agents
Component JSON ·Implementation brief ·Build a task kit ·
Related: diagnostics diff-view terminal
Stress fixtures: FX-STATE-MATRIX FX-320 FX-ZOOM-200 FX-RM FX-HC FX-LONG FX-RTL