@qodalis/cli 2.2.0 → 2.4.0

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.
@@ -16,7 +16,8 @@
16
16
  * --cli-panel-danger destructive items and errors
17
17
  * --cli-panel-shadow shadow color of the panel, menus and hide tab
18
18
  * --cli-panel-font font of the chrome (not the terminal)
19
- * --cli-panel-radius corner radius of buttons, tabs and menus (6px)
19
+ * --cli-panel-radius corner radius of buttons, tabs and menus (8px)
20
+ * --cli-panel-header-size height of the header (its width when docked left or right)
20
21
  */
21
22
 
22
23
  /* ─── Wrapper ────────────────────────────────────────────── */
@@ -27,6 +28,7 @@
27
28
  * --cli-panel-keyboard-inset and --cli-panel-visible-height from the visual
28
29
  * viewport), and is never taller than the space above it. */
29
30
  .cli-panel-wrapper {
31
+ --cli-panel-header-size: 48px;
30
32
  --cli-panel-bottom: max(
31
33
  var(--cli-panel-bottom-offset, 0px),
32
34
  var(--cli-panel-keyboard-inset, 0px)
@@ -60,11 +62,13 @@
60
62
  Arial,
61
63
  sans-serif
62
64
  );
63
- box-shadow: 0 -4px 20px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
65
+ box-shadow: 0 -8px 32px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
66
+ /* rounded on the edge facing the page; the header follows the corners */
67
+ border-radius: 12px 12px 0 0;
64
68
  }
65
69
 
66
70
  .cli-panel-wrapper.collapsed {
67
- transform: translateY(calc(100% - 60px));
71
+ transform: translateY(calc(100% - var(--cli-panel-header-size)));
68
72
  }
69
73
 
70
74
  .cli-panel-wrapper.resizing {
@@ -75,6 +79,7 @@
75
79
  /* ─── Header ─────────────────────────────────────────────── */
76
80
 
77
81
  .cli-panel-header {
82
+ border-radius: inherit;
78
83
  background-color: var(--cli-panel-header-bg, #0f1623);
79
84
  display: flex;
80
85
  flex-direction: column;
@@ -109,21 +114,21 @@
109
114
  }
110
115
 
111
116
  .cli-panel-header-content {
112
- height: 60px;
117
+ height: var(--cli-panel-header-size);
113
118
  display: flex;
114
119
  flex-direction: row;
115
- gap: 1rem;
120
+ gap: 12px;
116
121
  align-items: center;
117
- border-bottom: 1px solid var(--cli-panel-border, #1e293b);
118
- padding: 0 1rem;
122
+ padding: 0 8px 0 12px;
119
123
  }
120
124
 
121
125
  .cli-panel-title {
122
- font-size: 0.95rem;
126
+ font-size: 0.875rem;
127
+ letter-spacing: -0.01em;
123
128
  white-space: nowrap;
124
129
  min-width: 0;
125
130
  display: flex;
126
- gap: 0.5rem;
131
+ gap: 10px;
127
132
  justify-content: center;
128
133
  align-items: center;
129
134
  margin: 0;
@@ -131,10 +136,22 @@
131
136
  color: var(--cli-panel-text, #e2e8f0);
132
137
  }
133
138
 
139
+ /* The terminal glyph sits on a tile of the accent color */
134
140
  .cli-panel-title-icon {
135
141
  color: var(--cli-panel-accent, #818cf8);
142
+ background: color-mix(in srgb, var(--cli-panel-accent, #818cf8) 16%, transparent);
143
+ border-radius: var(--cli-panel-radius, 8px);
144
+ width: 28px;
145
+ height: 28px;
146
+ flex-shrink: 0;
136
147
  display: flex;
137
148
  align-items: center;
149
+ justify-content: center;
150
+ }
151
+
152
+ .cli-panel-title-icon svg {
153
+ width: 16px;
154
+ height: 16px;
138
155
  }
139
156
 
140
157
  /* An application's own icon (options.branding.icon) instead of the terminal glyph */
@@ -148,7 +165,7 @@
148
165
  .cli-panel-action-buttons {
149
166
  display: flex;
150
167
  flex-direction: row;
151
- gap: 0.35rem;
168
+ gap: 2px;
152
169
  margin-left: auto;
153
170
  }
154
171
 
@@ -158,9 +175,9 @@
158
175
  border: none;
159
176
  color: var(--cli-panel-text-secondary, #94a3b8);
160
177
  cursor: pointer;
161
- width: 40px;
162
- height: 40px;
163
- border-radius: 50%;
178
+ width: 32px;
179
+ height: 32px;
180
+ border-radius: var(--cli-panel-radius, 8px);
164
181
  display: inline-flex;
165
182
  align-items: center;
166
183
  justify-content: center;
@@ -172,6 +189,16 @@
172
189
 
173
190
  .cli-panel-btn svg {
174
191
  flex-shrink: 0;
192
+ width: 18px;
193
+ height: 18px;
194
+ }
195
+
196
+ .cli-panel-btn:focus-visible,
197
+ .cli-panel-tab:focus-visible,
198
+ .cli-panel-add-tab:focus-visible,
199
+ .cli-panel-hide-tab:focus-visible {
200
+ outline: 2px solid var(--cli-panel-accent, #818cf8);
201
+ outline-offset: 1px;
175
202
  }
176
203
 
177
204
  .cli-panel-btn:hover:not(:disabled) {
@@ -188,6 +215,11 @@
188
215
  cursor: not-allowed;
189
216
  }
190
217
 
218
+ .cli-panel-btn-close:hover:not(:disabled) {
219
+ color: var(--cli-panel-danger, #f87171);
220
+ background-color: color-mix(in srgb, var(--cli-panel-danger, #f87171) 14%, transparent);
221
+ }
222
+
191
223
  /* ─── Content ────────────────────────────────────────────── */
192
224
 
193
225
  .cli-panel-content {
@@ -204,23 +236,18 @@
204
236
  background-color: var(--cli-panel-header-bg, #0f1623);
205
237
  display: flex;
206
238
  align-items: center;
207
- height: 38px;
208
- padding: 0 8px;
209
- gap: 4px;
239
+ height: 40px;
240
+ padding: 0 8px 0 10px;
241
+ gap: 6px;
210
242
  border-bottom: 1px solid var(--cli-panel-border, #1e293b);
211
243
  overflow-x: auto;
212
244
  overflow-y: hidden;
213
245
  flex-shrink: 0;
214
- scrollbar-width: thin;
215
- scrollbar-color: var(--cli-panel-text-secondary, rgba(255, 255, 255, 0.3)) transparent;
246
+ scrollbar-width: none;
216
247
  }
217
248
 
218
249
  .cli-panel-tabs::-webkit-scrollbar {
219
- height: 2px;
220
- }
221
- .cli-panel-tabs::-webkit-scrollbar-thumb {
222
- background: var(--cli-panel-text-secondary, rgba(255, 255, 255, 0.3));
223
- border-radius: 1px;
250
+ display: none;
224
251
  }
225
252
 
226
253
  .cli-panel-tab-list {
@@ -228,29 +255,30 @@
228
255
  margin: 0;
229
256
  padding: 0;
230
257
  display: flex;
231
- gap: 2px;
232
- align-items: stretch;
258
+ gap: 4px;
259
+ align-items: center;
233
260
  height: 100%;
234
261
  }
235
262
 
263
+ /* Tabs are chips; the active one is cut from the terminal's own background */
236
264
  .cli-panel-tab {
237
265
  display: flex;
238
266
  align-items: center;
239
- gap: 6px;
240
- padding: 0 12px;
267
+ gap: 8px;
268
+ height: 28px;
269
+ padding: 0 6px 0 10px;
241
270
  cursor: pointer;
242
271
  background: transparent;
243
- border: none;
244
- border-top: 2px solid transparent;
272
+ border: 1px solid transparent;
273
+ border-radius: var(--cli-panel-radius, 8px);
245
274
  color: var(--cli-panel-text-secondary, #94a3b8);
246
- font-size: 0.8rem;
275
+ font-size: 0.8125rem;
247
276
  font-family: inherit;
248
277
  white-space: nowrap;
249
278
  transition:
250
279
  background-color 0.15s ease,
251
280
  color 0.15s ease,
252
281
  border-color 0.15s ease;
253
- height: 100%;
254
282
  }
255
283
 
256
284
  .cli-panel-tab:hover:not(.active) {
@@ -260,8 +288,10 @@
260
288
 
261
289
  .cli-panel-tab.active {
262
290
  background-color: var(--cli-panel-bg, #070b14);
291
+ border-color: var(--cli-panel-border, #1e293b);
263
292
  color: var(--cli-panel-text, #e2e8f0);
264
- border-top-color: var(--cli-panel-accent, #818cf8);
293
+ font-weight: 500;
294
+ box-shadow: 0 1px 2px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
265
295
  }
266
296
 
267
297
  .cli-panel-tab-title {
@@ -273,10 +303,10 @@
273
303
  background: var(--cli-panel-bg, #070b14);
274
304
  border: 1px solid var(--cli-panel-accent, #818cf8);
275
305
  color: var(--cli-panel-text, #e2e8f0);
276
- font-size: 0.8rem;
306
+ font-size: 0.8125rem;
277
307
  font-family: inherit;
278
308
  padding: 2px 6px;
279
- border-radius: var(--cli-panel-radius, 3px);
309
+ border-radius: calc(var(--cli-panel-radius, 8px) - 2px);
280
310
  outline: none;
281
311
  width: 120px;
282
312
  height: 22px;
@@ -288,15 +318,29 @@
288
318
  border: none;
289
319
  color: var(--cli-panel-text-secondary, rgba(255, 255, 255, 0.4));
290
320
  cursor: pointer;
291
- font-size: 1rem;
321
+ font-size: 0.95rem;
292
322
  line-height: 1;
293
- padding: 0 2px;
294
- border-radius: var(--cli-panel-radius, 3px);
323
+ width: 18px;
324
+ height: 18px;
325
+ padding: 0;
326
+ display: inline-flex;
327
+ align-items: center;
328
+ justify-content: center;
329
+ border-radius: calc(var(--cli-panel-radius, 8px) - 3px);
330
+ opacity: 0;
295
331
  transition:
332
+ opacity 0.15s ease,
296
333
  background-color 0.15s ease,
297
334
  color 0.15s ease;
298
335
  }
299
336
 
337
+ /* The close button shows on the active tab and under the pointer */
338
+ .cli-panel-tab.active .cli-panel-tab-close-btn,
339
+ .cli-panel-tab:hover .cli-panel-tab-close-btn,
340
+ .cli-panel-tab-close-btn:focus-visible {
341
+ opacity: 1;
342
+ }
343
+
300
344
  .cli-panel-tab-close-btn:hover {
301
345
  color: var(--cli-panel-text, #e2e8f0);
302
346
  background-color: var(--cli-btn-hover-bg, rgba(255, 255, 255, 0.1));
@@ -305,28 +349,27 @@
305
349
  .cli-panel-add-tab {
306
350
  appearance: none;
307
351
  background: transparent;
308
- border: 1px dashed var(--cli-panel-text-secondary, rgba(255, 255, 255, 0.3));
309
- color: var(--cli-panel-text-secondary, rgba(255, 255, 255, 0.5));
352
+ border: none;
353
+ color: var(--cli-panel-text-secondary, #94a3b8);
310
354
  cursor: pointer;
311
- font-size: 1rem;
355
+ font-size: 1.1rem;
356
+ font-family: inherit;
312
357
  line-height: 1;
313
358
  width: 28px;
314
- height: 24px;
315
- border-radius: var(--cli-panel-radius, 4px);
359
+ height: 28px;
360
+ border-radius: var(--cli-panel-radius, 8px);
316
361
  display: flex;
317
362
  align-items: center;
318
363
  justify-content: center;
319
364
  flex-shrink: 0;
320
365
  transition:
321
366
  background-color 0.15s ease,
322
- color 0.15s ease,
323
- border-color 0.15s ease;
367
+ color 0.15s ease;
324
368
  }
325
369
 
326
370
  .cli-panel-add-tab:hover {
327
371
  background-color: var(--cli-btn-hover-bg, rgba(129, 140, 248, 0.12));
328
372
  color: var(--cli-panel-text, #e2e8f0);
329
- border-color: var(--cli-panel-text, rgba(255, 255, 255, 0.5));
330
373
  }
331
374
 
332
375
  /* ─── Context menu ───────────────────────────────────────── */
@@ -419,9 +462,18 @@
419
462
  overflow: hidden;
420
463
  }
421
464
 
422
- .cli-panel-pane.active-pane {
423
- outline: 1px solid var(--cli-panel-accent, #818cf8);
424
- outline-offset: -1px;
465
+ .cli-panel-pane .xterm {
466
+ padding: 8px 4px 4px 14px;
467
+ }
468
+
469
+ /* xterm's viewport is black by default; the padding shows the theme's background instead */
470
+ .cli-panel-pane .xterm .xterm-viewport {
471
+ background-color: transparent !important;
472
+ }
473
+
474
+ /* Split panes: the active one is marked; a single pane needs no frame */
475
+ .cli-panel-pane.active-pane:not(:only-child) {
476
+ box-shadow: inset 0 2px 0 var(--cli-panel-accent, #818cf8);
425
477
  }
426
478
 
427
479
  .cli-panel-pane:hover .cli-panel-pane-close-btn {
@@ -498,12 +550,13 @@
498
550
  );
499
551
  border-top: none;
500
552
  border-bottom: 1px solid var(--cli-panel-border, #1e293b);
501
- box-shadow: 0 4px 20px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
553
+ box-shadow: 0 8px 32px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
554
+ border-radius: 0 0 12px 12px;
502
555
  flex-direction: column-reverse;
503
556
  }
504
557
 
505
558
  .cli-panel-wrapper[data-position="top"].collapsed {
506
- transform: translateY(calc(-100% + 60px));
559
+ transform: translateY(calc(-100% + var(--cli-panel-header-size)));
507
560
  }
508
561
 
509
562
  .cli-panel-wrapper[data-position="top"] .cli-panel-header-content {
@@ -529,16 +582,17 @@
529
582
  max-height: none;
530
583
  border-top: none;
531
584
  border-right: 1px solid var(--cli-panel-border, #1e293b);
532
- box-shadow: 4px 0 20px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
585
+ box-shadow: 8px 0 32px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
586
+ border-radius: 0 12px 12px 0;
533
587
  flex-direction: row-reverse;
534
588
  }
535
589
 
536
590
  .cli-panel-wrapper[data-position="left"].collapsed {
537
- transform: translateX(calc(-100% + 60px));
591
+ transform: translateX(calc(-100% + var(--cli-panel-header-size)));
538
592
  }
539
593
 
540
594
  .cli-panel-wrapper[data-position="left"] .cli-panel-header {
541
- width: 60px;
595
+ width: var(--cli-panel-header-size);
542
596
  flex-shrink: 0;
543
597
  flex-direction: column;
544
598
  }
@@ -596,16 +650,17 @@
596
650
  max-height: none;
597
651
  border-top: none;
598
652
  border-left: 1px solid var(--cli-panel-border, #1e293b);
599
- box-shadow: -4px 0 20px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
653
+ box-shadow: -8px 0 32px var(--cli-panel-shadow, rgba(0, 0, 0, 0.4));
654
+ border-radius: 12px 0 0 12px;
600
655
  flex-direction: row;
601
656
  }
602
657
 
603
658
  .cli-panel-wrapper[data-position="right"].collapsed {
604
- transform: translateX(calc(100% - 60px));
659
+ transform: translateX(calc(100% - var(--cli-panel-header-size)));
605
660
  }
606
661
 
607
662
  .cli-panel-wrapper[data-position="right"] .cli-panel-header {
608
- width: 60px;
663
+ width: var(--cli-panel-header-size);
609
664
  flex-shrink: 0;
610
665
  flex-direction: column;
611
666
  }
@@ -920,23 +975,34 @@
920
975
 
921
976
  /* ─── Status indicators ──────────────────────────────────── */
922
977
 
978
+ /* The status reads as one capsule, its items split by thin rules */
923
979
  .cli-panel-status-indicators {
924
980
  display: flex;
925
981
  align-items: center;
926
- gap: 14px;
927
- margin-left: 24px;
982
+ margin-left: 4px;
983
+ height: 26px;
984
+ padding: 0 4px;
985
+ border-radius: 999px;
986
+ border: 1px solid var(--cli-panel-border, #1e293b);
987
+ background: var(--cli-panel-bg, #070b14);
928
988
  font-size: 12px;
929
989
  overflow: hidden;
930
990
  white-space: nowrap;
991
+ min-width: 0;
931
992
  }
932
993
 
933
994
  .cli-panel-status-item {
934
995
  display: flex;
935
996
  align-items: center;
936
- gap: 5px;
997
+ gap: 6px;
998
+ padding: 0 8px;
937
999
  color: var(--cli-panel-text-secondary, #94a3b8);
938
1000
  }
939
1001
 
1002
+ .cli-panel-status-item + .cli-panel-status-item {
1003
+ border-left: 1px solid var(--cli-panel-border, #1e293b);
1004
+ }
1005
+
940
1006
  .cli-panel-status-dot {
941
1007
  width: 6px;
942
1008
  height: 6px;
@@ -1005,14 +1071,11 @@
1005
1071
 
1006
1072
  .cli-panel-status-item.status-clickable {
1007
1073
  cursor: pointer;
1008
- border-radius: var(--cli-panel-radius, 4px);
1009
- padding: 2px 6px;
1010
- margin: -2px -6px;
1011
- transition: background-color 0.15s ease;
1074
+ transition: color 0.15s ease;
1012
1075
  }
1013
1076
 
1014
1077
  .cli-panel-status-item.status-clickable:hover {
1015
- background-color: var(--cli-btn-hover-bg, rgba(129, 140, 248, 0.12));
1078
+ color: var(--cli-panel-text, #e2e8f0);
1016
1079
  }
1017
1080
 
1018
1081
  /* ─── Compact status indicators (vertical positions) ───── */
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@qodalis/cli",
3
- "version": "2.2.0",
3
+ "version": "2.4.0",
4
4
  "description": "Framework-agnostic CLI engine for @qodalis terminal applications.",
5
5
  "author": "Nicolae Lupei, Qodalis Solutions",
6
6
  "license": "MIT",
@@ -30,7 +30,7 @@
30
30
  "./assets/*": "./assets/*"
31
31
  },
32
32
  "dependencies": {
33
- "@qodalis/cli-core": "2.2.0",
33
+ "@qodalis/cli-core": "2.4.0",
34
34
  "@xterm/xterm": "^6.0.0",
35
35
  "@xterm/addon-fit": "^0.11.0",
36
36
  "@xterm/addon-web-links": "^0.12.0",
package/public-api.d.mts CHANGED
@@ -165,7 +165,7 @@ declare const CliKeyValueStore_TOKEN: any;
165
165
  */
166
166
  declare const SyntaxHighlighterRegistry_TOKEN: any;
167
167
 
168
- declare const LIBRARY_VERSION = "2.2.0";
168
+ declare const LIBRARY_VERSION = "2.4.0";
169
169
  declare const API_VERSION = 2;
170
170
 
171
171
  declare class CliAliasCommandProcessor implements ICliCommandProcessor {
@@ -789,14 +789,12 @@ declare class CliThemeCommandProcessor implements ICliCommandProcessor {
789
789
  metadata?: CliProcessorMetadata | undefined;
790
790
  stateConfiguration?: CliStateConfiguration | undefined;
791
791
  private themeOptions;
792
- private defaultTheme;
793
792
  constructor();
794
793
  initialize(context: ICliExecutionContext): Promise<void>;
795
794
  /** Apply the saved theme (or the default one when `reset` and none is saved). */
796
795
  private applySavedTheme;
797
796
  processCommand(command: CliProcessCommand, context: ICliExecutionContext): Promise<void>;
798
797
  private renderThemePreview;
799
- private applyStyles;
800
798
  private saveTheme;
801
799
  writeDescription?(context: ICliExecutionContext): void;
802
800
  }
@@ -946,8 +944,6 @@ declare class CliFontSizeCommandProcessor implements ICliCommandProcessor {
946
944
  metadata: CliProcessorMetadata;
947
945
  stateConfiguration: CliStateConfiguration;
948
946
  processors: ICliCommandProcessor[];
949
- /** The size the host configured (or the built-in default), restored by `font-size reset`. */
950
- private hostFontSize?;
951
947
  initialize(context: ICliExecutionContext): Promise<void>;
952
948
  processCommand(_: CliProcessCommand, context: ICliExecutionContext): Promise<void>;
953
949
  writeDescription(context: ICliExecutionContext): void;
@@ -2978,8 +2974,9 @@ declare class CliEngine {
2978
2974
  */
2979
2975
  focus(): void;
2980
2976
  /**
2981
- * Restyle the terminal: its colors and the background around it.
2982
- * The `theme` command can still change it afterwards.
2977
+ * The host's theme for this terminal: its colors and the background around it.
2978
+ * A theme the user chose with the `theme` command stays until `theme reset`,
2979
+ * which returns to this one.
2983
2980
  */
2984
2981
  setTheme(theme: ITheme): void;
2985
2982
  /**
@@ -3860,6 +3857,11 @@ declare class CliPanelController implements ICliPanelRef<CliEngine> {
3860
3857
  * `undefined` returns to the default palette and leaves the terminals' theme alone.
3861
3858
  */
3862
3859
  setTheme(theme: CliPanelThemeInput | undefined): void;
3860
+ /**
3861
+ * Whether the panel's colors follow its first terminal: with `syncTheme`, or
3862
+ * with a host theme so a theme the user applies restyles the panel too.
3863
+ */
3864
+ private get followsTerminalTheme();
3863
3865
  /** Replace the change callbacks (wrappers call this when their props change). */
3864
3866
  setCallbacks(callbacks: CliPanelCallbacks): void;
3865
3867
  /** Update host-controlled values. Unchanged values are ignored. */
@@ -3933,8 +3935,8 @@ declare class CliPanelController implements ICliPanelRef<CliEngine> {
3933
3935
  private readonly onDocumentKeydown;
3934
3936
  private syncDocumentListeners;
3935
3937
  private detachDocumentListeners;
3936
- /** Read the first terminal's theme and derive the panel colours from it. */
3937
- syncThemeFromEngine(): void;
3938
+ /** Read the first terminal's theme (or use `theme`) and derive the panel colours from it. */
3939
+ syncThemeFromEngine(theme?: ITheme): void;
3938
3940
  /**
3939
3941
  * Sync now and follow the first terminal's container: the `theme`
3940
3942
  * command restyles it, which re-derives the panel colours.
@@ -3945,6 +3947,8 @@ declare class CliPanelController implements ICliPanelRef<CliEngine> {
3945
3947
  /** Follow the system's light/dark setting while the theme is 'auto'. */
3946
3948
  private watchSystemScheme;
3947
3949
  private readonly onSystemSchemeChange;
3950
+ /** A terminal in the panel changed theme: follow the first one. */
3951
+ private readonly onTerminalTheme;
3948
3952
  /**
3949
3953
  * Phone browsers open the keyboard over the page and shrink only the visual
3950
3954
  * viewport; follow it so the panel stays above the keyboard.
package/public-api.d.ts CHANGED
@@ -165,7 +165,7 @@ declare const CliKeyValueStore_TOKEN: any;
165
165
  */
166
166
  declare const SyntaxHighlighterRegistry_TOKEN: any;
167
167
 
168
- declare const LIBRARY_VERSION = "2.2.0";
168
+ declare const LIBRARY_VERSION = "2.4.0";
169
169
  declare const API_VERSION = 2;
170
170
 
171
171
  declare class CliAliasCommandProcessor implements ICliCommandProcessor {
@@ -789,14 +789,12 @@ declare class CliThemeCommandProcessor implements ICliCommandProcessor {
789
789
  metadata?: CliProcessorMetadata | undefined;
790
790
  stateConfiguration?: CliStateConfiguration | undefined;
791
791
  private themeOptions;
792
- private defaultTheme;
793
792
  constructor();
794
793
  initialize(context: ICliExecutionContext): Promise<void>;
795
794
  /** Apply the saved theme (or the default one when `reset` and none is saved). */
796
795
  private applySavedTheme;
797
796
  processCommand(command: CliProcessCommand, context: ICliExecutionContext): Promise<void>;
798
797
  private renderThemePreview;
799
- private applyStyles;
800
798
  private saveTheme;
801
799
  writeDescription?(context: ICliExecutionContext): void;
802
800
  }
@@ -946,8 +944,6 @@ declare class CliFontSizeCommandProcessor implements ICliCommandProcessor {
946
944
  metadata: CliProcessorMetadata;
947
945
  stateConfiguration: CliStateConfiguration;
948
946
  processors: ICliCommandProcessor[];
949
- /** The size the host configured (or the built-in default), restored by `font-size reset`. */
950
- private hostFontSize?;
951
947
  initialize(context: ICliExecutionContext): Promise<void>;
952
948
  processCommand(_: CliProcessCommand, context: ICliExecutionContext): Promise<void>;
953
949
  writeDescription(context: ICliExecutionContext): void;
@@ -2978,8 +2974,9 @@ declare class CliEngine {
2978
2974
  */
2979
2975
  focus(): void;
2980
2976
  /**
2981
- * Restyle the terminal: its colors and the background around it.
2982
- * The `theme` command can still change it afterwards.
2977
+ * The host's theme for this terminal: its colors and the background around it.
2978
+ * A theme the user chose with the `theme` command stays until `theme reset`,
2979
+ * which returns to this one.
2983
2980
  */
2984
2981
  setTheme(theme: ITheme): void;
2985
2982
  /**
@@ -3860,6 +3857,11 @@ declare class CliPanelController implements ICliPanelRef<CliEngine> {
3860
3857
  * `undefined` returns to the default palette and leaves the terminals' theme alone.
3861
3858
  */
3862
3859
  setTheme(theme: CliPanelThemeInput | undefined): void;
3860
+ /**
3861
+ * Whether the panel's colors follow its first terminal: with `syncTheme`, or
3862
+ * with a host theme so a theme the user applies restyles the panel too.
3863
+ */
3864
+ private get followsTerminalTheme();
3863
3865
  /** Replace the change callbacks (wrappers call this when their props change). */
3864
3866
  setCallbacks(callbacks: CliPanelCallbacks): void;
3865
3867
  /** Update host-controlled values. Unchanged values are ignored. */
@@ -3933,8 +3935,8 @@ declare class CliPanelController implements ICliPanelRef<CliEngine> {
3933
3935
  private readonly onDocumentKeydown;
3934
3936
  private syncDocumentListeners;
3935
3937
  private detachDocumentListeners;
3936
- /** Read the first terminal's theme and derive the panel colours from it. */
3937
- syncThemeFromEngine(): void;
3938
+ /** Read the first terminal's theme (or use `theme`) and derive the panel colours from it. */
3939
+ syncThemeFromEngine(theme?: ITheme): void;
3938
3940
  /**
3939
3941
  * Sync now and follow the first terminal's container: the `theme`
3940
3942
  * command restyles it, which re-derives the panel colours.
@@ -3945,6 +3947,8 @@ declare class CliPanelController implements ICliPanelRef<CliEngine> {
3945
3947
  /** Follow the system's light/dark setting while the theme is 'auto'. */
3946
3948
  private watchSystemScheme;
3947
3949
  private readonly onSystemSchemeChange;
3950
+ /** A terminal in the panel changed theme: follow the first one. */
3951
+ private readonly onTerminalTheme;
3948
3952
  /**
3949
3953
  * Phone browsers open the keyboard over the page and shrink only the visual
3950
3954
  * viewport; follow it so the panel stays above the keyboard.