@openpresentation/opf-editor 0.29.1 → 0.31.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.
package/dist/styles.css CHANGED
@@ -39,6 +39,20 @@
39
39
  --opf-ui-shadow-pop: 0 8px 24px rgba(0, 0, 0, 0.1);
40
40
  --opf-ui-ease: 120ms ease;
41
41
 
42
+ /* Component tokens (CE-29). The defaults derive from the tokens above, so they follow the scheme and a host's theme; set one to restyle
43
+ the bar, the deck title or the expanded editor's layer without touching a component. docs/styling.md says where each is read. */
44
+ --opf-ui-bar-bg: var(--opf-ui-surface);
45
+ --opf-ui-bar-fg: var(--opf-ui-fg);
46
+ --opf-ui-bar-border: var(--opf-ui-border);
47
+ --opf-ui-bar-gap: 8px;
48
+ --opf-ui-bar-padding: 6px 12px;
49
+ --opf-ui-bar-height: 0px;
50
+ --opf-ui-title-font: var(--opf-ui-font);
51
+ --opf-ui-title-size: 15px;
52
+ --opf-ui-title-weight: 600;
53
+ --opf-ui-title-fg: var(--opf-ui-fg);
54
+ --opf-ui-z-overlay: 1000;
55
+
42
56
  color-scheme: light;
43
57
  }
44
58
 
@@ -163,6 +177,330 @@
163
177
  }
164
178
  }
165
179
 
180
+ /* deck-title.css */
181
+ /* Deck title (CE-28). Uses only --opf-ui-* tokens. */
182
+ .opf-title {
183
+ display: inline-flex;
184
+ align-items: center;
185
+ box-sizing: border-box;
186
+ min-width: 0;
187
+ max-width: 100%;
188
+ font-family: var(--opf-ui-font);
189
+ }
190
+ .opf-title-input {
191
+ box-sizing: border-box;
192
+ field-sizing: content;
193
+ min-width: 6ch;
194
+ max-width: 100%;
195
+ height: var(--opf-ui-control-h);
196
+ margin: 0;
197
+ padding: 0 8px;
198
+ border: 1px solid transparent;
199
+ border-radius: var(--opf-ui-radius);
200
+ background: transparent;
201
+ color: var(--opf-ui-title-fg);
202
+ font: var(--opf-ui-title-weight) var(--opf-ui-title-size)/1.2 var(--opf-ui-title-font);
203
+ text-overflow: ellipsis;
204
+ transition: border-color var(--opf-ui-ease), background-color var(--opf-ui-ease);
205
+ }
206
+ .opf-title[data-density="touch"] .opf-title-input {
207
+ height: 40px;
208
+ }
209
+ .opf-title-input::placeholder {
210
+ color: var(--opf-ui-muted-fg);
211
+ font-weight: 500;
212
+ opacity: 1;
213
+ }
214
+ .opf-title-input:hover:not([readonly]) {
215
+ border-color: var(--opf-ui-border);
216
+ }
217
+ .opf-title-input:focus {
218
+ border-color: var(--opf-ui-ring);
219
+ background: var(--opf-ui-surface);
220
+ outline: 2px solid var(--opf-ui-ring);
221
+ outline-offset: 1px;
222
+ text-overflow: clip;
223
+ }
224
+ .opf-title-input[readonly] {
225
+ cursor: default;
226
+ }
227
+ .opf-title-input[readonly]:focus {
228
+ background: transparent;
229
+ border-color: transparent;
230
+ }
231
+ .opf-title-input[aria-disabled="true"] {
232
+ color: var(--opf-ui-muted-fg);
233
+ }
234
+ @media (prefers-reduced-motion: reduce) {
235
+ .opf-title-input {
236
+ transition: none;
237
+ }
238
+ }
239
+
240
+ /* design-menu.css */
241
+ /* CE-29: the Design quick menu (src/design-menu.js). Only --opf-ui-* tokens, no color literals (test/styles.mjs). */
242
+ .opf-design-menu,
243
+ .opf-design-menu *,
244
+ .opf-design-menu *::before,
245
+ .opf-design-menu *::after { box-sizing: border-box; }
246
+ .opf-design-menu [hidden] { display: none !important; }
247
+
248
+ .opf-design-menu {
249
+ --opf-design-menu-row: 32px;
250
+ position: relative;
251
+ display: inline-flex;
252
+ font-family: var(--opf-ui-font);
253
+ font-size: 13px;
254
+ line-height: 1.4;
255
+ color: var(--opf-ui-fg);
256
+ }
257
+ .opf-design-menu[data-density="touch"] { --opf-design-menu-row: 40px; }
258
+ :where(.opf-design-menu button) { font: inherit; color: inherit; margin: 0; }
259
+ .opf-design-menu .opf-icon { flex: none; }
260
+ .opf-design-menu button:focus-visible {
261
+ outline: 2px solid var(--opf-ui-ring);
262
+ outline-offset: -2px;
263
+ }
264
+
265
+ /* ---- the toolbar button ------------------------------------------------------------------------------------------------------------- */
266
+ .opf-design-menu .opf-design-menu-trigger {
267
+ display: inline-flex;
268
+ align-items: center;
269
+ gap: 6px;
270
+ height: var(--opf-ui-control-h);
271
+ padding: 0 10px;
272
+ border: 1px solid var(--opf-ui-border);
273
+ border-radius: var(--opf-ui-radius);
274
+ background: var(--opf-ui-surface);
275
+ white-space: nowrap;
276
+ cursor: pointer;
277
+ transition: background-color var(--opf-ui-ease), border-color var(--opf-ui-ease);
278
+ }
279
+ .opf-design-menu .opf-design-menu-trigger:hover { background: var(--opf-ui-muted-2); border-color: var(--opf-ui-border-strong); }
280
+ .opf-design-menu .opf-design-menu-trigger[aria-expanded="true"] { background: var(--opf-ui-muted); }
281
+ .opf-design-menu .opf-design-menu-trigger:focus-visible { outline-offset: 2px; }
282
+ .opf-design-menu .opf-design-menu-trigger:disabled { opacity: 0.5; cursor: not-allowed; }
283
+ .opf-design-menu[data-density="touch"] .opf-design-menu-trigger { height: max(var(--opf-ui-control-h), 40px); }
284
+
285
+ /* ---- the popover ---------------------------------------------------------------------------------------------------------------------- */
286
+ .opf-design-menu .opf-design-menu-popover {
287
+ position: fixed;
288
+ z-index: 40;
289
+ display: flex;
290
+ flex-direction: column;
291
+ width: 296px;
292
+ max-width: calc(100vw - 16px);
293
+ background: var(--opf-ui-surface);
294
+ border: 1px solid var(--opf-ui-border);
295
+ border-radius: var(--opf-ui-radius-md);
296
+ box-shadow: var(--opf-ui-shadow-pop);
297
+ overflow: hidden;
298
+ }
299
+ .opf-design-menu .opf-design-menu-handle,
300
+ .opf-design-menu .opf-design-menu-head { display: none; }
301
+ .opf-design-menu .opf-design-menu-menu {
302
+ flex: 1 1 auto;
303
+ min-height: 0;
304
+ padding: 4px;
305
+ overflow-y: auto;
306
+ overscroll-behavior: contain;
307
+ }
308
+ .opf-design-menu .opf-design-menu-group + .opf-design-menu-group {
309
+ margin-top: 4px;
310
+ padding-top: 4px;
311
+ border-top: 1px solid var(--opf-ui-border);
312
+ }
313
+ .opf-design-menu .opf-design-menu-group-label {
314
+ padding: 6px 8px 4px;
315
+ font-size: 11px;
316
+ font-weight: 600;
317
+ letter-spacing: 0.04em;
318
+ text-transform: uppercase;
319
+ color: var(--opf-ui-muted-fg);
320
+ }
321
+ .opf-design-menu .opf-design-menu-list {
322
+ max-height: calc(var(--opf-design-menu-row) * 5.5);
323
+ overflow-y: auto;
324
+ overscroll-behavior: contain;
325
+ }
326
+ .opf-design-menu .opf-design-menu-empty { margin: 0; padding: 12px 8px; color: var(--opf-ui-muted-fg); }
327
+
328
+ .opf-design-menu .opf-design-menu-item {
329
+ display: flex;
330
+ align-items: center;
331
+ gap: 8px;
332
+ width: 100%;
333
+ min-height: var(--opf-design-menu-row);
334
+ padding: 0 8px;
335
+ border: 0;
336
+ border-radius: var(--opf-ui-radius);
337
+ background: transparent;
338
+ text-align: start;
339
+ cursor: pointer;
340
+ transition: background-color var(--opf-ui-ease);
341
+ }
342
+ .opf-design-menu .opf-design-menu-item:hover { background: var(--opf-ui-muted-2); }
343
+ .opf-design-menu .opf-design-menu-item:focus-visible { background: var(--opf-ui-muted); }
344
+ .opf-design-menu .opf-design-menu-item[aria-checked="true"] { background: var(--opf-ui-muted); font-weight: 600; }
345
+ .opf-design-menu .opf-design-menu-label { flex: 1 1 auto; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
346
+ .opf-design-menu .opf-design-menu-check { display: inline-flex; flex: none; width: 14px; color: var(--opf-ui-accent-strong); }
347
+ .opf-design-menu .opf-design-menu-item[aria-checked="false"] .opf-design-menu-check { visibility: hidden; }
348
+ .opf-design-menu .opf-design-menu-more {
349
+ margin-top: 4px;
350
+ border-top: 1px solid var(--opf-ui-border);
351
+ border-radius: 0 0 var(--opf-ui-radius) var(--opf-ui-radius);
352
+ color: var(--opf-ui-accent-strong);
353
+ }
354
+
355
+ .opf-design-menu .opf-design-menu-swatches { display: inline-flex; flex: none; gap: 2px; }
356
+ .opf-design-menu .opf-design-menu-swatch {
357
+ width: 12px;
358
+ height: 12px;
359
+ border-radius: var(--opf-ui-radius-sm);
360
+ border: 1px solid var(--opf-ui-border-strong);
361
+ }
362
+
363
+ /* Screen-reader only. */
364
+ .opf-design-menu .opf-design-menu-live {
365
+ position: absolute;
366
+ width: 1px;
367
+ height: 1px;
368
+ margin: -1px;
369
+ padding: 0;
370
+ overflow: hidden;
371
+ clip-path: inset(50%);
372
+ white-space: nowrap;
373
+ border: 0;
374
+ }
375
+
376
+ /* ---- the bottom sheet (a phone, or a button that is not on screen) --------------------------------------------------------------------- */
377
+ .opf-design-menu .opf-design-menu-scrim {
378
+ position: fixed;
379
+ inset: 0;
380
+ z-index: 50;
381
+ background: color-mix(in srgb, var(--opf-ui-fg) 32%, transparent);
382
+ }
383
+ .opf-design-menu[data-mode="sheet"] .opf-design-menu-popover {
384
+ z-index: 51;
385
+ inset: auto 0 0 0;
386
+ width: auto;
387
+ max-width: 560px;
388
+ max-height: 85vh;
389
+ max-height: 85dvh;
390
+ margin-inline: auto;
391
+ padding-bottom: max(12px, env(safe-area-inset-bottom));
392
+ border-width: 1px 0 0;
393
+ border-radius: var(--opf-ui-radius-lg) var(--opf-ui-radius-lg) 0 0;
394
+ }
395
+ .opf-design-menu[data-mode="sheet"] .opf-design-menu-handle {
396
+ display: block;
397
+ flex: none;
398
+ width: 36px;
399
+ height: 4px;
400
+ margin: 8px auto 4px;
401
+ border-radius: 2px;
402
+ background: var(--opf-ui-border-strong);
403
+ }
404
+ .opf-design-menu[data-mode="sheet"] .opf-design-menu-head {
405
+ display: flex;
406
+ flex: none;
407
+ align-items: center;
408
+ padding: 0 8px 0 16px;
409
+ }
410
+ .opf-design-menu .opf-design-menu-title { font-size: 15px; font-weight: 600; }
411
+ .opf-design-menu .opf-design-menu-close {
412
+ display: grid;
413
+ place-items: center;
414
+ width: 40px;
415
+ height: 40px;
416
+ margin-inline-start: auto;
417
+ border: 0;
418
+ border-radius: var(--opf-ui-radius);
419
+ background: transparent;
420
+ color: var(--opf-ui-muted-fg);
421
+ cursor: pointer;
422
+ }
423
+ .opf-design-menu .opf-design-menu-close:hover { background: var(--opf-ui-muted-2); color: var(--opf-ui-fg); }
424
+ .opf-design-menu[data-mode="sheet"] .opf-design-menu-item { padding: 0 12px; font-size: 14px; }
425
+ .opf-design-menu[data-mode="sheet"] .opf-design-menu-list { max-height: calc(var(--opf-design-menu-row) * 4.5); }
426
+
427
+ @media (prefers-reduced-motion: reduce) {
428
+ .opf-design-menu *,
429
+ .opf-design-menu *::before,
430
+ .opf-design-menu *::after { transition: none !important; }
431
+ }
432
+
433
+ /* expand.css */
434
+ /* CE-28: the expand-editor part (src/editor-expand.js). Only --opf-ui-* tokens, no color literals (test/styles.mjs). */
435
+
436
+ /* ---- the expanded editor -------------------------------------------------------------------------------------------------------------- */
437
+ /* The editor's host element becomes a fixed overlay over the viewport; it stays where it is in the DOM. !important beats the sizes a host sets
438
+ inline or by class on the element. A host can raise or lower the overlay with --opf-ui-z-overlay (default 1000: above page chrome, below the
439
+ presenter at 2000); --opf-expand-z is the older name and still wins when set. An ancestor with a transform, filter or containment would make "fixed" relative to itself; the host owns that. */
440
+ [data-opf-expanded] {
441
+ position: fixed !important;
442
+ inset: 0 !important;
443
+ z-index: var(--opf-expand-z, var(--opf-ui-z-overlay)) !important;
444
+ box-sizing: border-box !important;
445
+ width: auto !important;
446
+ height: auto !important;
447
+ min-width: 0 !important;
448
+ min-height: 0 !important;
449
+ max-width: none !important;
450
+ max-height: none !important;
451
+ margin: 0 !important;
452
+ border-radius: 0 !important;
453
+ background: var(--opf-ui-bg);
454
+ color: var(--opf-ui-fg);
455
+ overscroll-behavior: contain;
456
+ }
457
+ /* The target takes the focus when it expands; the whole viewport must not wear a ring. */
458
+ [data-opf-expanded]:focus,
459
+ [data-opf-expanded]:focus-visible { outline: none; }
460
+
461
+ /* ---- the button ----------------------------------------------------------------------------------------------------------------------- */
462
+ .opf-expand-button,
463
+ .opf-expand-button *,
464
+ .opf-expand-button *::before,
465
+ .opf-expand-button *::after { box-sizing: border-box; }
466
+ .opf-expand-button {
467
+ display: inline-flex;
468
+ align-items: center;
469
+ justify-content: center;
470
+ flex: none;
471
+ width: var(--opf-ui-control-h);
472
+ height: var(--opf-ui-control-h);
473
+ margin: 0;
474
+ padding: 0;
475
+ border: 1px solid transparent;
476
+ border-radius: var(--opf-ui-radius);
477
+ background: transparent;
478
+ color: var(--opf-ui-muted-fg);
479
+ font: inherit;
480
+ cursor: pointer;
481
+ transition: color var(--opf-ui-ease), background-color var(--opf-ui-ease);
482
+ }
483
+ .opf-expand-button[data-density="touch"] {
484
+ width: 40px;
485
+ height: 40px;
486
+ }
487
+ .opf-expand-button:hover { background: var(--opf-ui-muted); color: var(--opf-ui-fg); }
488
+ .opf-expand-button[aria-pressed="true"] { color: var(--opf-ui-fg); }
489
+ .opf-expand-button:focus-visible {
490
+ outline: 2px solid var(--opf-ui-ring);
491
+ outline-offset: 2px;
492
+ }
493
+ .opf-expand-button[aria-disabled="true"] {
494
+ opacity: 0.5;
495
+ cursor: not-allowed;
496
+ }
497
+ .opf-expand-button[aria-disabled="true"]:hover { background: transparent; color: var(--opf-ui-muted-fg); }
498
+ .opf-expand-button .opf-expand-icon { flex: none; }
499
+
500
+ @media (prefers-reduced-motion: reduce) {
501
+ .opf-expand-button { transition: none; }
502
+ }
503
+
166
504
  /* export-menu.css */
167
505
  /* RR-98: the Export menu (src/export-menu.js). Only --opf-ui-* tokens, no color literals (test/styles.mjs). */
168
506
  .opf-export,
@@ -4287,6 +4625,84 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
4287
4625
  .opf-present-button { transition: none; }
4288
4626
  }
4289
4627
 
4628
+ /* review-pill.css */
4629
+ /* The review pill (src/review-pill.js). Uses only --opf-ui-* tokens. State is never color alone: every state has a glyph and words. */
4630
+ .opf-review-pill {
4631
+ display: inline-flex;
4632
+ align-items: center;
4633
+ gap: 6px;
4634
+ box-sizing: border-box;
4635
+ height: var(--opf-ui-control-h);
4636
+ min-height: 0;
4637
+ max-width: 100%;
4638
+ padding: 0 10px;
4639
+ border: 1px solid var(--opf-ui-border);
4640
+ border-radius: calc(var(--opf-ui-control-h) / 2);
4641
+ background: var(--opf-ui-surface);
4642
+ color: var(--opf-ui-fg);
4643
+ font: 500 12px/1 var(--opf-ui-font);
4644
+ white-space: nowrap;
4645
+ cursor: pointer;
4646
+ transition: color var(--opf-ui-ease), background-color var(--opf-ui-ease), border-color var(--opf-ui-ease);
4647
+ }
4648
+ .opf-review-pill[data-density="touch"] { height: 40px; }
4649
+ .opf-review-pill:hover:not(:disabled) { background: var(--opf-ui-muted); border-color: var(--opf-ui-border-strong); }
4650
+ .opf-review-pill:focus-visible { outline: 2px solid var(--opf-ui-ring); outline-offset: 2px; }
4651
+ .opf-review-pill:disabled { cursor: default; }
4652
+ .opf-review-pill-icon { flex: none; width: 14px; height: 14px; }
4653
+ .opf-review-pill[data-density="touch"] .opf-review-pill-icon { width: 16px; height: 16px; }
4654
+ .opf-review-pill-text { overflow: hidden; text-overflow: ellipsis; }
4655
+
4656
+ .opf-review-pill[data-state="valid"] .opf-review-pill-icon { color: var(--opf-ui-success); }
4657
+ .opf-review-pill[data-state="checking"],
4658
+ .opf-review-pill[data-state="unavailable"] { color: var(--opf-ui-muted-fg); }
4659
+ .opf-review-pill[data-state="unavailable"] { border-style: dashed; opacity: 0.8; }
4660
+ .opf-review-pill[data-severity="error"] { border-color: var(--opf-ui-danger); }
4661
+ .opf-review-pill[data-severity="error"] .opf-review-pill-icon { color: var(--opf-ui-danger); }
4662
+ .opf-review-pill[data-severity="warning"] { border-color: var(--opf-ui-warn); }
4663
+ .opf-review-pill[data-severity="warning"] .opf-review-pill-icon { color: var(--opf-ui-warn); }
4664
+ .opf-review-pill[data-severity="info"] .opf-review-pill-icon { color: var(--opf-ui-accent-strong); }
4665
+
4666
+ @media (prefers-reduced-motion: reduce) {
4667
+ .opf-review-pill { transition: none; }
4668
+ }
4669
+ @media (forced-colors: active) {
4670
+ .opf-review-pill { border-color: ButtonText; }
4671
+ .opf-review-pill:disabled { border-color: GrayText; color: GrayText; }
4672
+ }
4673
+
4674
+ /* shortcuts-sheet.css */
4675
+ /* The help item (src/shortcuts-sheet.js). The sheet itself reuses the source pane's shortcuts dialog styles (shortcuts.css: .opf-shortcuts*).
4676
+ Uses only --opf-ui-* tokens. */
4677
+ .opf-help-button {
4678
+ display: inline-grid;
4679
+ place-items: center;
4680
+ box-sizing: border-box;
4681
+ width: var(--opf-ui-control-h);
4682
+ height: var(--opf-ui-control-h);
4683
+ min-height: 0;
4684
+ padding: 0;
4685
+ border: 0;
4686
+ border-radius: var(--opf-ui-radius);
4687
+ background: transparent;
4688
+ color: var(--opf-ui-muted-fg);
4689
+ font: inherit;
4690
+ cursor: pointer;
4691
+ transition: color var(--opf-ui-ease), background-color var(--opf-ui-ease);
4692
+ }
4693
+ .opf-help-button[data-density="touch"] { width: 40px; height: 40px; }
4694
+ .opf-help-button:hover:not(:disabled),
4695
+ .opf-help-button[aria-expanded="true"] { background: var(--opf-ui-muted); color: var(--opf-ui-fg); }
4696
+ .opf-help-button:disabled { opacity: 0.4; cursor: default; }
4697
+ .opf-help-button:focus-visible { outline: 2px solid var(--opf-ui-ring); outline-offset: 2px; }
4698
+ .opf-help-icon { width: 18px; height: 18px; }
4699
+ .opf-help-button[data-density="touch"] .opf-help-icon { width: 20px; height: 20px; }
4700
+ .opf-help-sheet { z-index: 80; }
4701
+ .opf-help-close-icon { width: 16px; height: 16px; flex: none; }
4702
+ @media (prefers-reduced-motion: reduce) {
4703
+ .opf-help-button { transition: none; }
4704
+ }
4705
+
4290
4706
  /* shortcuts.css */
4291
4707
  /* The keyboard shortcuts dialog (src/source-shortcuts.js). Only --opf-ui-* tokens, no color literals (test/styles.mjs). */
4292
4708
  .opf-shortcuts,
@@ -4954,22 +5370,19 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
4954
5370
  opacity: 0.45;
4955
5371
  cursor: default;
4956
5372
  }
4957
- .opf-studio-name {
5373
+ /* CE-28: the deck title part (src/deck-title.js) and the expand button in the bar. */
5374
+ .opf-studio-title {
5375
+ display: flex;
4958
5376
  flex: 0 1 200px;
4959
5377
  min-width: 80px;
4960
- height: 28px;
4961
- padding: 0 8px;
4962
- border: 1px solid transparent;
4963
- border-radius: var(--opf-ui-radius-sm);
4964
- background: transparent;
4965
- color: var(--opf-ui-fg);
4966
- font: 600 13px var(--opf-ui-font);
4967
- text-overflow: ellipsis;
4968
5378
  }
4969
- .opf-studio-name:hover,
4970
- .opf-studio-name:focus {
4971
- border-color: var(--opf-ui-border);
4972
- background: var(--opf-ui-surface);
5379
+ .opf-studio-title:empty,
5380
+ .opf-studio-expand:empty {
5381
+ display: none;
5382
+ }
5383
+ .opf-studio-expand {
5384
+ display: inline-flex;
5385
+ flex: none;
4973
5386
  }
4974
5387
  .opf-studio-views {
4975
5388
  padding: 2px;
@@ -6061,7 +6474,7 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
6061
6474
  .opf-studio[data-width="narrow"][data-preset="studio"] .opf-studio-sheetbar {
6062
6475
  display: inline-flex;
6063
6476
  }
6064
- .opf-studio[data-width="narrow"] :is(.opf-studio-format, .opf-studio-counter, .opf-studio-zoombar, .opf-studio-name) {
6477
+ .opf-studio[data-width="narrow"] :is(.opf-studio-format, .opf-studio-counter, .opf-studio-zoombar, .opf-studio-title) {
6065
6478
  display: none;
6066
6479
  }
6067
6480
  .opf-studio[data-width="narrow"][data-sheet="slides"] .opf-studio-left,
@@ -6111,7 +6524,7 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
6111
6524
  .opf-studio .opf-studio-design-advanced > summary {
6112
6525
  padding-block: calc((44px - 1lh) / 2);
6113
6526
  }
6114
- .opf-studio :is(.opf-studio-number, .opf-studio-input, .opf-studio-name) {
6527
+ .opf-studio :is(.opf-studio-number, .opf-studio-input) {
6115
6528
  min-height: 44px;
6116
6529
  font-size: 16px;
6117
6530
  }
@@ -6297,18 +6710,344 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
6297
6710
  }
6298
6711
  @media (prefers-reduced-motion: reduce) {
6299
6712
  .opf-thumbs-item,
6300
- .opf-thumbs-frame {
6713
+ .opf-thumbs-frame,
6714
+ .opf-thumbs-add,
6715
+ .opf-thumbs-menu-item {
6301
6716
  transition: none;
6302
6717
  }
6303
6718
  }
6304
6719
 
6305
- /* touch.css */
6306
- /*
6307
- * Touch: a coarse pointer (a finger) gets a 44px hit area on every control, and the text in a field is 16px so iOS Safari does not
6308
- * zoom the page when the field gets focus. tokens.css already raises --opf-ui-control-h to 44px under `(pointer: coarse)`, which lifts every
6309
- * control that is sized by it; this file lifts the ones that size themselves (compact buttons, rows, menu items, completion items) and
6310
- * keeps the visual look: the padding grows, the type does not. The code in an editor stays at its own size: it is not a field.
6311
- * Tokens only, no color literals (test/styles.mjs).
6720
+ /* Slide management (CE-29): the trailing "+" button, the context and layout menus and the status line. Only with actions: true. */
6721
+ .opf-thumbs-add-slot {
6722
+ flex: none;
6723
+ list-style: none;
6724
+ }
6725
+ .opf-thumbs[data-orientation="horizontal"] .opf-thumbs-add-slot {
6726
+ align-self: stretch;
6727
+ }
6728
+ .opf-thumbs-add {
6729
+ display: flex;
6730
+ align-items: center;
6731
+ justify-content: center;
6732
+ box-sizing: border-box;
6733
+ width: 40px;
6734
+ height: 100%;
6735
+ min-height: 40px;
6736
+ margin: 0;
6737
+ padding: 0;
6738
+ color: var(--opf-ui-muted-fg);
6739
+ background: transparent;
6740
+ border: 1px dashed var(--opf-ui-border-strong);
6741
+ border-radius: var(--opf-ui-radius-sm);
6742
+ cursor: pointer;
6743
+ transition: color var(--opf-ui-ease), border-color var(--opf-ui-ease), background-color var(--opf-ui-ease);
6744
+ }
6745
+ .opf-thumbs[data-orientation="vertical"] .opf-thumbs-add {
6746
+ width: 100%;
6747
+ height: 40px;
6748
+ }
6749
+ .opf-thumbs-add:hover,
6750
+ .opf-thumbs-add[aria-expanded="true"] {
6751
+ color: var(--opf-ui-accent-strong);
6752
+ border-color: var(--opf-ui-accent);
6753
+ background: var(--opf-ui-muted-2);
6754
+ }
6755
+ .opf-thumbs-add:focus-visible {
6756
+ outline: 2px solid var(--opf-ui-ring);
6757
+ outline-offset: 2px;
6758
+ }
6759
+ .opf-thumbs-add-icon {
6760
+ width: 20px;
6761
+ height: 20px;
6762
+ fill: none;
6763
+ stroke: currentColor;
6764
+ stroke-width: 2;
6765
+ stroke-linecap: round;
6766
+ stroke-linejoin: round;
6767
+ }
6768
+ .opf-thumbs-status {
6769
+ position: absolute;
6770
+ width: 1px;
6771
+ height: 1px;
6772
+ margin: -1px;
6773
+ padding: 0;
6774
+ overflow: hidden;
6775
+ clip: rect(0, 0, 0, 0);
6776
+ white-space: nowrap;
6777
+ border: 0;
6778
+ }
6779
+ .opf-thumbs-menu {
6780
+ position: fixed;
6781
+ z-index: 1000;
6782
+ box-sizing: border-box;
6783
+ min-width: 200px;
6784
+ max-width: min(320px, 92vw);
6785
+ max-height: min(420px, 80dvh);
6786
+ padding: 4px;
6787
+ overflow: auto;
6788
+ font-family: var(--opf-ui-font);
6789
+ color: var(--opf-ui-fg);
6790
+ background: var(--opf-ui-surface);
6791
+ border: 1px solid var(--opf-ui-border);
6792
+ border-radius: var(--opf-ui-radius-md);
6793
+ box-shadow: var(--opf-ui-shadow-pop);
6794
+ }
6795
+ .opf-thumbs-menu:focus {
6796
+ outline: none;
6797
+ }
6798
+ .opf-thumbs-menu-item {
6799
+ display: flex;
6800
+ align-items: center;
6801
+ justify-content: space-between;
6802
+ gap: 18px;
6803
+ box-sizing: border-box;
6804
+ width: 100%;
6805
+ margin: 0;
6806
+ padding: 6px 10px;
6807
+ font: 13px/1.4 var(--opf-ui-font);
6808
+ text-align: start;
6809
+ color: var(--opf-ui-fg);
6810
+ background: transparent;
6811
+ border: 0;
6812
+ border-radius: var(--opf-ui-radius-sm);
6813
+ cursor: pointer;
6814
+ transition: background-color var(--opf-ui-ease);
6815
+ }
6816
+ .opf-thumbs-menu-item kbd {
6817
+ font: 11px var(--opf-ui-mono);
6818
+ color: var(--opf-ui-muted-fg);
6819
+ }
6820
+ .opf-thumbs-menu-item:hover:not(:disabled),
6821
+ .opf-thumbs-menu-item:focus-visible {
6822
+ background: var(--opf-ui-muted);
6823
+ outline: none;
6824
+ }
6825
+ .opf-thumbs-menu-item:focus-visible {
6826
+ box-shadow: inset 0 0 0 2px var(--opf-ui-ring);
6827
+ }
6828
+ .opf-thumbs-menu-item:disabled {
6829
+ opacity: 0.45;
6830
+ cursor: default;
6831
+ }
6832
+ .opf-thumbs-menu-separator {
6833
+ height: 1px;
6834
+ margin: 4px 2px;
6835
+ background: var(--opf-ui-border);
6836
+ }
6837
+ .opf-thumbs-menu-heading {
6838
+ padding: 6px 10px 2px;
6839
+ font: 600 11px/1.4 var(--opf-ui-font);
6840
+ color: var(--opf-ui-muted-fg);
6841
+ }
6842
+ .opf-thumbs-menu-group + .opf-thumbs-menu-group {
6843
+ margin-top: 4px;
6844
+ border-top: 1px solid var(--opf-ui-border);
6845
+ }
6846
+
6847
+ /* toolbar-actions.css */
6848
+ /* Toolbar actions (src/toolbar-actions.js): the host's own buttons. Uses only --opf-ui-* tokens. */
6849
+ .opf-actions {
6850
+ display: inline-flex;
6851
+ align-items: center;
6852
+ gap: 6px;
6853
+ font-family: var(--opf-ui-font);
6854
+ }
6855
+ .opf-actions[hidden] { display: none; }
6856
+ .opf-actions-button {
6857
+ display: inline-flex;
6858
+ align-items: center;
6859
+ gap: 6px;
6860
+ box-sizing: border-box;
6861
+ height: var(--opf-ui-control-h);
6862
+ min-height: 0;
6863
+ padding: 0 12px;
6864
+ border: 1px solid var(--opf-ui-border);
6865
+ border-radius: var(--opf-ui-radius);
6866
+ background: var(--opf-ui-surface);
6867
+ color: var(--opf-ui-fg);
6868
+ font: 500 13px/1 var(--opf-ui-font);
6869
+ white-space: nowrap;
6870
+ cursor: pointer;
6871
+ transition: color var(--opf-ui-ease), background-color var(--opf-ui-ease), border-color var(--opf-ui-ease);
6872
+ }
6873
+ .opf-actions[data-density="touch"] .opf-actions-button { height: 40px; }
6874
+ .opf-actions-button:hover:not(:disabled) { background: var(--opf-ui-muted); border-color: var(--opf-ui-border-strong); }
6875
+ .opf-actions-button[aria-pressed="true"] { background: var(--opf-ui-muted); border-color: var(--opf-ui-border-strong); box-shadow: inset 0 -2px 0 var(--opf-ui-accent); }
6876
+ .opf-actions-button.is-primary { background: var(--opf-ui-accent); border-color: var(--opf-ui-accent); color: var(--opf-ui-accent-fg); }
6877
+ .opf-actions-button.is-primary:hover:not(:disabled) { background: var(--opf-ui-accent-strong); border-color: var(--opf-ui-accent-strong); }
6878
+ .opf-actions-button:disabled { opacity: 0.45; cursor: default; }
6879
+ .opf-actions-button:focus-visible { outline: 2px solid var(--opf-ui-ring); outline-offset: 2px; }
6880
+ .opf-actions-icon { flex: none; width: 16px; height: 16px; }
6881
+ .opf-actions-label { overflow: hidden; text-overflow: ellipsis; }
6882
+ @media (prefers-reduced-motion: reduce) {
6883
+ .opf-actions-button { transition: none; }
6884
+ }
6885
+ @media (forced-colors: active) {
6886
+ .opf-actions-button { border-color: ButtonText; }
6887
+ .opf-actions-button:disabled { border-color: GrayText; color: GrayText; }
6888
+ .opf-actions-button[aria-pressed="true"] { outline: 2px solid Highlight; }
6889
+ }
6890
+
6891
+ /* toolbar.css */
6892
+ /* CE-28: the editor's title bar (src/toolbar.js). One row that never wraps: the items that do not fit move into the ⋯ menu. Tokens only. */
6893
+ .opf-tb {
6894
+ position: relative;
6895
+ display: flex;
6896
+ flex-wrap: nowrap;
6897
+ align-items: center;
6898
+ gap: var(--opf-ui-bar-gap);
6899
+ box-sizing: border-box;
6900
+ width: 100%;
6901
+ min-width: 0;
6902
+ color: var(--opf-ui-bar-fg);
6903
+ font-family: var(--opf-ui-font);
6904
+ }
6905
+ .opf-tb > .opf-tb-item {
6906
+ display: inline-flex;
6907
+ flex: 0 0 auto;
6908
+ align-items: center;
6909
+ gap: 4px;
6910
+ min-width: 0;
6911
+ }
6912
+ /* The deck title shrinks before anything collapses below its wish; while the row is measured it asks for its wish. */
6913
+ .opf-tb > .opf-tb-item[data-opf-toolbar-item="title"] {
6914
+ flex: 0 1 auto;
6915
+ max-width: 28rem;
6916
+ }
6917
+ .opf-tb[data-measuring] > .opf-tb-item[data-opf-toolbar-item="title"] {
6918
+ flex: 0 0 auto;
6919
+ width: 8rem;
6920
+ max-width: none;
6921
+ }
6922
+ .opf-tb > .opf-tb-item:empty,
6923
+ .opf-tb > [data-collapsed],
6924
+ .opf-tb > [hidden],
6925
+ .opf-tb .opf-tb-menu[hidden] {
6926
+ display: none;
6927
+ }
6928
+ .opf-tb > .opf-tb-spacer {
6929
+ flex: 1 1 0;
6930
+ min-width: 0;
6931
+ }
6932
+ .opf-tb[data-measuring] > .opf-tb-spacer {
6933
+ flex: 0 0 0;
6934
+ }
6935
+ .opf-tb > .opf-tb-divider {
6936
+ flex: none;
6937
+ align-self: stretch;
6938
+ width: 1px;
6939
+ margin: 4px 0;
6940
+ background: var(--opf-ui-border);
6941
+ }
6942
+ .opf-tb .opf-tb-more {
6943
+ position: relative;
6944
+ }
6945
+ .opf-tb .opf-tb-more-button {
6946
+ display: inline-flex;
6947
+ align-items: center;
6948
+ justify-content: center;
6949
+ box-sizing: border-box;
6950
+ min-width: var(--opf-ui-control-h);
6951
+ height: var(--opf-ui-control-h);
6952
+ padding: 0 8px;
6953
+ border: 1px solid var(--opf-ui-border);
6954
+ border-radius: var(--opf-ui-radius);
6955
+ background: var(--opf-ui-surface);
6956
+ color: var(--opf-ui-fg);
6957
+ cursor: pointer;
6958
+ transition: background-color var(--opf-ui-ease), border-color var(--opf-ui-ease);
6959
+ }
6960
+ .opf-tb .opf-tb-more-button:hover {
6961
+ background: var(--opf-ui-muted);
6962
+ }
6963
+ .opf-tb .opf-tb-more-button[aria-expanded="true"] {
6964
+ border-color: var(--opf-ui-accent);
6965
+ background: var(--opf-ui-muted);
6966
+ color: var(--opf-ui-accent-strong);
6967
+ }
6968
+ .opf-tb .opf-tb-more-button:focus-visible,
6969
+ .opf-tb .opf-tb-menu-item:focus-visible {
6970
+ outline: 2px solid var(--opf-ui-ring);
6971
+ outline-offset: 1px;
6972
+ }
6973
+ .opf-tb .opf-tb-menu {
6974
+ position: absolute;
6975
+ top: calc(100% + 4px);
6976
+ right: 0;
6977
+ z-index: 40;
6978
+ display: flex;
6979
+ flex-direction: column;
6980
+ box-sizing: border-box;
6981
+ min-width: 200px;
6982
+ max-width: min(320px, calc(100vw - 16px));
6983
+ padding: 4px;
6984
+ border: 1px solid var(--opf-ui-border);
6985
+ border-radius: var(--opf-ui-radius-md);
6986
+ background: var(--opf-ui-surface);
6987
+ box-shadow: var(--opf-ui-shadow-pop);
6988
+ }
6989
+ .opf-tb .opf-tb-menu-item {
6990
+ display: flex;
6991
+ align-items: center;
6992
+ gap: 8px;
6993
+ box-sizing: border-box;
6994
+ width: 100%;
6995
+ min-height: var(--opf-ui-control-h);
6996
+ padding: 0 10px;
6997
+ border: 0;
6998
+ border-radius: var(--opf-ui-radius-sm);
6999
+ background: transparent;
7000
+ color: var(--opf-ui-fg);
7001
+ font: 500 13px/1.2 var(--opf-ui-font);
7002
+ text-align: left;
7003
+ cursor: pointer;
7004
+ }
7005
+ .opf-tb .opf-tb-menu-item:hover:not([aria-disabled="true"]),
7006
+ .opf-tb .opf-tb-menu-item:focus {
7007
+ background: var(--opf-ui-muted);
7008
+ }
7009
+ .opf-tb .opf-tb-menu-item[aria-disabled="true"] {
7010
+ color: var(--opf-ui-muted-fg);
7011
+ cursor: default;
7012
+ }
7013
+ .opf-tb .opf-tb-menu-item[aria-checked="true"] {
7014
+ color: var(--opf-ui-accent-strong);
7015
+ }
7016
+ .opf-tb .opf-tb-menu-item[role="menuitemcheckbox"]::before {
7017
+ content: "";
7018
+ flex: none;
7019
+ width: 6px;
7020
+ height: 6px;
7021
+ border-radius: 50%;
7022
+ }
7023
+ .opf-tb .opf-tb-menu-item[aria-checked="true"]::before {
7024
+ background: var(--opf-ui-accent-strong);
7025
+ }
7026
+ .opf-tb .opf-tb-menu-separator {
7027
+ height: 1px;
7028
+ margin: 4px 0;
7029
+ background: var(--opf-ui-border);
7030
+ }
7031
+ .opf-tb[data-density="touch"] .opf-tb-more-button {
7032
+ min-width: max(var(--opf-ui-control-h), 40px);
7033
+ height: max(var(--opf-ui-control-h), 40px);
7034
+ }
7035
+ .opf-tb[data-density="touch"] .opf-tb-menu-item {
7036
+ min-height: max(var(--opf-ui-control-h), 40px);
7037
+ }
7038
+ @media (prefers-reduced-motion: reduce) {
7039
+ .opf-tb .opf-tb-more-button {
7040
+ transition: none;
7041
+ }
7042
+ }
7043
+
7044
+ /* touch.css */
7045
+ /*
7046
+ * Touch: a coarse pointer (a finger) gets a 44px hit area on every control, and the text in a field is 16px so iOS Safari does not
7047
+ * zoom the page when the field gets focus. tokens.css already raises --opf-ui-control-h to 44px under `(pointer: coarse)`, which lifts every
7048
+ * control that is sized by it; this file lifts the ones that size themselves (compact buttons, rows, menu items, completion items) and
7049
+ * keeps the visual look: the padding grows, the type does not. The code in an editor stays at its own size: it is not a field.
7050
+ * Tokens only, no color literals (test/styles.mjs).
6312
7051
  */
6313
7052
  @media (pointer: coarse) {
6314
7053
  /* ---- fields: 16px, 44px ------------------------------------------------------------------------------------------------------ */
@@ -6522,6 +7261,90 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
6522
7261
  }
6523
7262
  }
6524
7263
 
7264
+ /* ---- deck title (CE-28): the presentation name field ---------------------------------------------------------------------------- */
7265
+ @media (pointer: coarse) {
7266
+ .opf-title-input,
7267
+ .opf-title[data-density="touch"] .opf-title-input {
7268
+ height: auto;
7269
+ min-height: 44px;
7270
+ font-size: 16px;
7271
+ }
7272
+ }
7273
+
7274
+ /* ---- toolbar (CE-28): the ⋯ button and its menu ----------------------------------------------------------------------------------- */
7275
+ @media (pointer: coarse) {
7276
+ .opf-tb .opf-tb-more-button,
7277
+ .opf-tb[data-density="touch"] .opf-tb-more-button {
7278
+ min-width: 44px;
7279
+ height: 44px;
7280
+ }
7281
+ .opf-tb .opf-tb-menu-item,
7282
+ .opf-tb[data-density="touch"] .opf-tb-menu-item {
7283
+ min-height: 44px;
7284
+ }
7285
+ }
7286
+
7287
+ /* ---- CE-28: the expand-editor button (src/editor-expand.js) ---------------------------------------------------------------------- */
7288
+ @media (pointer: coarse) {
7289
+ .opf-expand-button,
7290
+ .opf-expand-button[data-density="touch"] {
7291
+ width: 44px;
7292
+ height: 44px;
7293
+ }
7294
+ }
7295
+
7296
+ /* CE-29: the Design quick menu (src/design-menu.js). */
7297
+ @media (pointer: coarse) {
7298
+ .opf-design-menu,
7299
+ .opf-design-menu[data-density="touch"] {
7300
+ --opf-design-menu-row: 44px;
7301
+ }
7302
+ .opf-design-menu .opf-design-menu-trigger,
7303
+ .opf-design-menu[data-density="touch"] .opf-design-menu-trigger {
7304
+ min-width: 44px;
7305
+ min-height: 44px;
7306
+ }
7307
+ .opf-design-menu .opf-design-menu-close {
7308
+ width: 44px;
7309
+ height: 44px;
7310
+ }
7311
+ }
7312
+
7313
+ /* ---- CE-29 toolbar parts: the review pill (review-pill.js), the help button and its sheet (shortcuts-sheet.js), the host's action buttons (toolbar-actions.js) -- */
7314
+ @media (pointer: coarse) {
7315
+ .opf-review-pill,
7316
+ .opf-review-pill[data-density="touch"] {
7317
+ min-height: 44px;
7318
+ min-width: 44px;
7319
+ padding-inline: 14px;
7320
+ }
7321
+ .opf-help-button,
7322
+ .opf-help-button[data-density="touch"] {
7323
+ min-width: 44px;
7324
+ min-height: 44px;
7325
+ }
7326
+ .opf-actions-button,
7327
+ .opf-actions[data-density="touch"] .opf-actions-button {
7328
+ min-height: 44px;
7329
+ min-width: 44px;
7330
+ padding-inline: 14px;
7331
+ }
7332
+ }
7333
+
7334
+ /* Thumbnail strip slide management (CE-29): the "+" button and the context and layout menu items. */
7335
+ @media (pointer: coarse) {
7336
+ .opf-thumbs .opf-thumbs-add {
7337
+ min-width: 44px;
7338
+ min-height: 44px;
7339
+ }
7340
+ .opf-thumbs[data-orientation="vertical"] .opf-thumbs-add {
7341
+ height: 44px;
7342
+ }
7343
+ .opf-thumbs-menu .opf-thumbs-menu-item {
7344
+ min-height: 44px;
7345
+ }
7346
+ }
7347
+
6525
7348
  /* workspace.css */
6526
7349
  /* The embeddable editor (CE-06): the default arrangement `createOpfEditor` builds for `layout: "full" | "canvas" | "source"`.
6527
7350
  Uses only --opf-ui-* tokens. A host that passes its own `slots` ignores all of this except the `data-` attributes. */
@@ -6540,15 +7363,50 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
6540
7363
  .opf-workspace[data-opf-layout="slots"] {
6541
7364
  display: contents;
6542
7365
  }
7366
+ /* CE-28: the bar holds the toolbar (src/styles/toolbar.css), one row whose items move into its ⋯ menu when they do not fit. */
6543
7367
  .opf-ws-bar {
6544
- display: flex;
7368
+ display: block;
6545
7369
  flex: none;
6546
- align-items: center;
6547
- flex-wrap: wrap;
6548
- gap: 8px;
6549
- padding: 6px 12px;
6550
- border-bottom: 1px solid var(--opf-ui-border);
6551
- background: var(--opf-ui-surface);
7370
+ min-width: 0;
7371
+ min-height: var(--opf-ui-bar-height);
7372
+ padding: var(--opf-ui-bar-padding);
7373
+ border-bottom: 1px solid var(--opf-ui-bar-border);
7374
+ background: var(--opf-ui-bar-bg);
7375
+ color: var(--opf-ui-bar-fg);
7376
+ }
7377
+ /* CE-28 wave 2: Export collapsed into the ⋯ menu stays in the page, out of sight and out of the row, so the sheet it opens from there (fixed on
7378
+ screen) and its progress and result are visible. */
7379
+ .opf-tb > .opf-ws-export[data-collapsed] {
7380
+ display: block;
7381
+ position: absolute;
7382
+ width: 0;
7383
+ height: 0;
7384
+ overflow: hidden;
7385
+ visibility: hidden;
7386
+ }
7387
+ .opf-tb > .opf-ws-export[data-collapsed] :is(.opf-export-sheet, .opf-export-scrim, .opf-export-status) {
7388
+ visibility: visible;
7389
+ }
7390
+ /* CE-28, `layout: "embed"`: the slide alone under a compact bar, for a page that shows a deck. The status line is read, not shown. */
7391
+ /* The compact bar is the embed default of --opf-ui-bar-padding; a host sets the token with a selector as specific as this one, or in `theme.tokens`. */
7392
+ .opf-workspace[data-opf-layout="embed"] {
7393
+ --opf-ui-bar-padding: 4px 8px;
7394
+ }
7395
+ .opf-workspace[data-opf-layout="embed"] .opf-ws-stage {
7396
+ padding: 8px;
7397
+ }
7398
+ .opf-workspace[data-opf-layout="embed"] .opf-ws-main {
7399
+ position: relative;
7400
+ }
7401
+ .opf-workspace[data-opf-layout="embed"] .opf-ws-status {
7402
+ position: absolute;
7403
+ width: 1px;
7404
+ height: 1px;
7405
+ margin: -1px;
7406
+ padding: 0;
7407
+ overflow: hidden;
7408
+ clip-path: inset(50%);
7409
+ white-space: nowrap;
6552
7410
  }
6553
7411
  .opf-ws-group,
6554
7412
  .opf-ws-views {
@@ -6673,6 +7531,11 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
6673
7531
  gap: 4px;
6674
7532
  padding: 0 12px 8px;
6675
7533
  }
7534
+ /* CE-30: the slide row is no wider than the editor; the thumbnail strip scrolls inside it (a narrow box, a phone). */
7535
+ .opf-ws-dock > .opf-ws-navigator,
7536
+ .opf-ws-dock > .opf-ws-thumbnails {
7537
+ max-width: 100%;
7538
+ }
6676
7539
  .opf-ws-status {
6677
7540
  flex: none;
6678
7541
  margin: 0;
@@ -6760,27 +7623,29 @@ input.opf-lx-input[data-field="max"] { font-family: var(--opf-ui-mono); font-siz
6760
7623
  flex: 1 1 0;
6761
7624
  min-height: 0;
6762
7625
  }
6763
- /* A phone: the parts stack, the source above the slide, the side panel below. */
7626
+ /* A phone: the parts stack, the source above the slide, the side panel below. CE-30: only in the layouts that have several parts to stack;
7627
+ `embed`, `viewer` and `canvas` are the slide alone and fit it to their box at any width (a stage of 40vh made a short embed overflow).
7628
+ `:where()` keeps the specificity of the plain class. */
6764
7629
  @media (max-width: 760px) {
6765
- .opf-ws-body {
7630
+ :where(.opf-workspace:not([data-opf-layout="embed"], [data-opf-layout="viewer"], [data-opf-layout="canvas"])) .opf-ws-body {
6766
7631
  flex-direction: column;
6767
7632
  overflow: auto;
6768
7633
  }
6769
- .opf-ws-source {
7634
+ :where(.opf-workspace:not([data-opf-layout="embed"], [data-opf-layout="viewer"], [data-opf-layout="canvas"])) .opf-ws-source {
6770
7635
  flex: none;
6771
7636
  min-width: 0;
6772
7637
  height: 40vh;
6773
7638
  border-right: 0;
6774
7639
  border-bottom: 1px solid var(--opf-ui-border);
6775
7640
  }
6776
- .opf-ws-main {
7641
+ :where(.opf-workspace:not([data-opf-layout="embed"], [data-opf-layout="viewer"], [data-opf-layout="canvas"])) .opf-ws-main {
6777
7642
  flex: none;
6778
7643
  }
6779
- .opf-ws-stage {
7644
+ :where(.opf-workspace:not([data-opf-layout="embed"], [data-opf-layout="viewer"], [data-opf-layout="canvas"])) .opf-ws-stage {
6780
7645
  flex: none;
6781
7646
  min-height: 40vh;
6782
7647
  }
6783
- .opf-ws-side {
7648
+ :where(.opf-workspace:not([data-opf-layout="embed"], [data-opf-layout="viewer"], [data-opf-layout="canvas"])) .opf-ws-side {
6784
7649
  flex: none;
6785
7650
  border-left: 0;
6786
7651
  border-top: 1px solid var(--opf-ui-border);