@markdy/renderer-dom 1.0.11 → 1.0.12

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.
Files changed (2) hide show
  1. package/dist/index.js +194 -26
  2. package/package.json +3 -3
package/dist/index.js CHANGED
@@ -2494,24 +2494,178 @@ function ensureSceneStyles(doc) {
2494
2494
  }
2495
2495
  .markdy-footer {
2496
2496
  font-family: system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
2497
+ width: 100%;
2498
+ box-sizing: border-box;
2499
+ }
2500
+ .markdy-controls {
2501
+ display: flex;
2502
+ align-items: center;
2503
+ flex-wrap: nowrap;
2504
+ gap: 2.5px;
2505
+ max-width: 100%;
2506
+ overflow-x: auto;
2507
+ scrollbar-width: none;
2508
+ }
2509
+ .markdy-controls::-webkit-scrollbar {
2510
+ display: none;
2511
+ }
2512
+ @media (max-width: 640px) {
2513
+ .markdy-controls {
2514
+ flex-wrap: wrap;
2515
+ justify-content: center;
2516
+ gap: 3px;
2517
+ }
2497
2518
  }
2498
2519
  .markdy-controls button {
2520
+ appearance: none;
2499
2521
  touch-action: manipulation;
2500
2522
  user-select: none;
2501
2523
  -webkit-user-select: none;
2502
- transition: background 0.15s ease, border-color 0.15s ease, color 0.15s ease, transform 0.05s ease;
2524
+ border: 1px solid var(--md-control-border, rgba(148, 163, 184, 0.45));
2525
+ border-radius: 5px;
2526
+ background: var(--md-control-bg, rgba(248, 250, 252, 0.92));
2527
+ color: var(--md-control-text, #334155);
2528
+ cursor: pointer;
2529
+ font: 600 10px/1.2 system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
2530
+ padding: 2.5px 5.5px;
2531
+ min-height: 23px;
2532
+ min-width: 22px;
2533
+ display: inline-flex;
2534
+ align-items: center;
2535
+ justify-content: center;
2536
+ gap: 2px;
2537
+ white-space: nowrap;
2538
+ box-shadow: 0 1px 2px rgba(0, 0, 0, 0.03);
2539
+ transition: all 0.15s cubic-bezier(0.4, 0, 0.2, 1);
2503
2540
  }
2504
2541
  .markdy-controls button:hover:not([aria-pressed="true"]) {
2505
- background: rgba(241, 245, 249, 1);
2506
- color: #1e293b;
2507
- border-color: rgba(100, 116, 139, 0.6);
2542
+ background: var(--md-control-hover-bg, #ffffff);
2543
+ color: var(--md-control-hover-text, #0f172a);
2544
+ border-color: var(--md-control-hover-border, #94a3b8);
2545
+ box-shadow: 0 2px 4px rgba(0, 0, 0, 0.08);
2546
+ }
2547
+ .markdy-controls button[aria-pressed="true"] {
2548
+ background: #0f172a !important;
2549
+ color: #ffffff !important;
2550
+ border-color: #0f172a !important;
2551
+ box-shadow: 0 1px 3px rgba(15, 23, 42, 0.25) !important;
2508
2552
  }
2509
2553
  .markdy-controls button:focus-visible {
2510
2554
  outline: 2px solid #3b82f6;
2511
2555
  outline-offset: 1px;
2512
2556
  }
2513
2557
  .markdy-controls button:active {
2514
- transform: scale(0.96);
2558
+ transform: scale(0.95);
2559
+ }
2560
+ .markdy-control-play::before { content: "\u25B6"; font-size: 7.5px; margin-right: 1px; }
2561
+ .markdy-control-play[aria-label*="Pause"]::before,
2562
+ .markdy-control-play[title*="Pause"]::before { content: "\u23F8"; font-size: 7.5px; margin-right: 1px; }
2563
+ .markdy-control-restart::before { content: "\u21BA"; font-size: 10px; font-weight: 700; margin-right: 1px; }
2564
+ .markdy-control-prev-beat::before { content: "\u23EE"; font-size: 7.5px; margin-right: 1px; }
2565
+ .markdy-control-next-beat::before { content: "\u23ED"; font-size: 7.5px; margin-right: 1px; }
2566
+ .markdy-control-fit::before { content: "\u26F6"; font-size: 8.5px; margin-right: 1px; }
2567
+ .markdy-control-reset-view::before { content: "\u2299"; font-size: 8.5px; margin-right: 1px; }
2568
+ .markdy-control-fullscreen::before { content: "\u26F6"; font-size: 8.5px; margin-right: 1px; }
2569
+ .markdy-control-svg::before { content: "\u{1F4E5}"; font-size: 8.5px; margin-right: 1px; }
2570
+ .markdy-control-share::before { content: "\u{1F517}"; font-size: 8.5px; margin-right: 1px; }
2571
+ .markdy-control-rate {
2572
+ font-family: "JetBrains Mono", monospace, system-ui;
2573
+ font-size: 9px;
2574
+ font-weight: 600;
2575
+ padding: 2px 4.5px;
2576
+ min-width: 18px;
2577
+ min-height: 21px;
2578
+ }
2579
+ .markdy-control-seek {
2580
+ appearance: none;
2581
+ -webkit-appearance: none;
2582
+ background: transparent;
2583
+ cursor: pointer;
2584
+ height: 20px;
2585
+ width: clamp(35px, 5vw, 65px);
2586
+ min-width: 35px;
2587
+ max-width: 70px;
2588
+ margin: 0 1px;
2589
+ }
2590
+ .markdy-control-seek:focus {
2591
+ outline: none;
2592
+ }
2593
+ .markdy-control-seek::-webkit-slider-runnable-track {
2594
+ width: 100%;
2595
+ height: 4.5px;
2596
+ background: rgba(148, 163, 184, 0.35);
2597
+ border-radius: 9999px;
2598
+ transition: background 0.15s ease;
2599
+ }
2600
+ .markdy-control-seek:hover::-webkit-slider-runnable-track {
2601
+ background: rgba(148, 163, 184, 0.55);
2602
+ }
2603
+ .markdy-control-seek::-webkit-slider-thumb {
2604
+ -webkit-appearance: none;
2605
+ height: 13px;
2606
+ width: 13px;
2607
+ border-radius: 50%;
2608
+ background: #2563eb;
2609
+ border: 2px solid #ffffff;
2610
+ box-shadow: 0 1px 3px rgba(0, 0, 0, 0.3);
2611
+ margin-top: -4.25px;
2612
+ cursor: grab;
2613
+ transition: transform 0.1s ease, background 0.15s ease;
2614
+ }
2615
+ .markdy-control-seek:active::-webkit-slider-thumb {
2616
+ cursor: grabbing;
2617
+ transform: scale(1.2);
2618
+ background: #1d4ed8;
2619
+ }
2620
+ .markdy-control-seek::-moz-range-track {
2621
+ width: 100%;
2622
+ height: 4.5px;
2623
+ background: rgba(148, 163, 184, 0.35);
2624
+ border-radius: 9999px;
2625
+ }
2626
+ .markdy-control-seek::-moz-range-thumb {
2627
+ height: 13px;
2628
+ width: 13px;
2629
+ border-radius: 50%;
2630
+ background: #2563eb;
2631
+ border: 2px solid #ffffff;
2632
+ box-shadow: 0 1px 3px rgba(0, 0, 0, 0.3);
2633
+ cursor: grab;
2634
+ }
2635
+
2636
+ [data-markdy-theme="midnight"] .markdy-controls button,
2637
+ [data-markdy-theme="blueprint"] .markdy-controls button,
2638
+ [data-markdy-theme="terminal"] .markdy-controls button,
2639
+ [data-markdy-theme="graphite"] .markdy-controls button,
2640
+ [data-markdy-theme="nebula"] .markdy-controls button,
2641
+ :root[data-theme="dark"] .markdy-controls button,
2642
+ .theme-dark .markdy-controls button {
2643
+ background: var(--md-control-bg, rgba(30, 41, 59, 0.85));
2644
+ border-color: var(--md-control-border, rgba(71, 85, 105, 0.55));
2645
+ color: var(--md-control-text, #cbd5e1);
2646
+ }
2647
+ [data-markdy-theme="midnight"] .markdy-controls button:hover:not([aria-pressed="true"]),
2648
+ [data-markdy-theme="blueprint"] .markdy-controls button:hover:not([aria-pressed="true"]),
2649
+ [data-markdy-theme="terminal"] .markdy-controls button:hover:not([aria-pressed="true"]),
2650
+ [data-markdy-theme="graphite"] .markdy-controls button:hover:not([aria-pressed="true"]),
2651
+ [data-markdy-theme="nebula"] .markdy-controls button:hover:not([aria-pressed="true"]),
2652
+ :root[data-theme="dark"] .markdy-controls button:hover:not([aria-pressed="true"]),
2653
+ .theme-dark .markdy-controls button:hover:not([aria-pressed="true"]) {
2654
+ background: rgba(51, 65, 85, 0.95);
2655
+ color: #f8fafc;
2656
+ border-color: #94a3b8;
2657
+ }
2658
+ [data-markdy-theme="midnight"] .markdy-controls button[aria-pressed="true"],
2659
+ [data-markdy-theme="blueprint"] .markdy-controls button[aria-pressed="true"],
2660
+ [data-markdy-theme="terminal"] .markdy-controls button[aria-pressed="true"],
2661
+ [data-markdy-theme="graphite"] .markdy-controls button[aria-pressed="true"],
2662
+ [data-markdy-theme="nebula"] .markdy-controls button[aria-pressed="true"],
2663
+ :root[data-theme="dark"] .markdy-controls button[aria-pressed="true"],
2664
+ .theme-dark .markdy-controls button[aria-pressed="true"] {
2665
+ background: #3b82f6 !important;
2666
+ color: #ffffff !important;
2667
+ border-color: #3b82f6 !important;
2668
+ box-shadow: 0 0 10px rgba(59, 130, 246, 0.5) !important;
2515
2669
  }
2516
2670
  .markdy-footer a {
2517
2671
  transition: opacity 0.15s ease, color 0.15s ease;
@@ -2683,6 +2837,7 @@ function createDiagram(opts) {
2683
2837
  speeds: speedOptions,
2684
2838
  fit: fitViewButton,
2685
2839
  resetView: resetViewButton,
2840
+ fullscreen: fullscreenButton,
2686
2841
  svg: svgButton,
2687
2842
  share: shareButton
2688
2843
  } = player.controls;
@@ -3101,16 +3256,10 @@ function createDiagram(opts) {
3101
3256
  const rate = Number(button.dataset.rate ?? "1");
3102
3257
  const active = Math.abs(rate - playbackRate) < 1e-3;
3103
3258
  button.setAttribute("aria-pressed", active ? "true" : "false");
3104
- button.style.background = active ? "#1e293b" : "rgba(248, 250, 252, 0.92)";
3105
- button.style.color = active ? "#ffffff" : "#475569";
3106
- button.style.borderColor = active ? "#0f172a" : "rgba(148, 163, 184, 0.55)";
3107
3259
  }
3108
3260
  if (controlsSeekBar) controlsSeekBar.value = String(sceneMs / 1e3);
3109
3261
  if (controlsFitButton) {
3110
3262
  controlsFitButton.setAttribute("aria-pressed", fitViewActive ? "true" : "false");
3111
- controlsFitButton.style.background = fitViewActive ? "#1e293b" : "rgba(248, 250, 252, 0.92)";
3112
- controlsFitButton.style.color = fitViewActive ? "#ffffff" : "#475569";
3113
- controlsFitButton.style.borderColor = fitViewActive ? "#0f172a" : "rgba(148, 163, 184, 0.55)";
3114
3263
  }
3115
3264
  }
3116
3265
  function emitPlayStateChange(playing) {
@@ -3224,19 +3373,6 @@ function createDiagram(opts) {
3224
3373
  button.textContent = label;
3225
3374
  button.setAttribute("aria-label", ariaLabel);
3226
3375
  button.title = ariaLabel;
3227
- Object.assign(button.style, {
3228
- appearance: "none",
3229
- border: "1px solid rgba(148, 163, 184, 0.55)",
3230
- borderRadius: "5px",
3231
- background: "rgba(248, 250, 252, 0.92)",
3232
- color: "#475569",
3233
- cursor: "pointer",
3234
- font: "600 10px/1.1 system-ui, sans-serif",
3235
- padding: "4px 6px",
3236
- minWidth: "28px",
3237
- whiteSpace: "nowrap",
3238
- boxShadow: "none"
3239
- });
3240
3376
  return button;
3241
3377
  }
3242
3378
  function mountPlayControl(toolbar) {
@@ -3365,6 +3501,39 @@ function createDiagram(opts) {
3365
3501
  button.addEventListener("click", resetViewportTransform);
3366
3502
  toolbar.appendChild(button);
3367
3503
  }
3504
+ function mountFullscreenControl(toolbar) {
3505
+ if (!fullscreenButton) return;
3506
+ const button = makeControlButton("Full", "Toggle fullscreen view");
3507
+ button.className = "markdy-control-fullscreen";
3508
+ button.setAttribute("aria-pressed", "false");
3509
+ const host = container.parentElement ?? container;
3510
+ function syncFullscreenState() {
3511
+ const isFull = document.fullscreenElement === host || document.fullscreenElement === container || document.fullscreenElement === viewport;
3512
+ button.setAttribute("aria-pressed", isFull ? "true" : "false");
3513
+ button.title = isFull ? "Exit fullscreen" : "Toggle fullscreen view";
3514
+ }
3515
+ button.addEventListener("click", async () => {
3516
+ try {
3517
+ if (!document.fullscreenElement) {
3518
+ if (host.requestFullscreen) {
3519
+ await host.requestFullscreen();
3520
+ } else if (host.webkitRequestFullscreen) {
3521
+ await host.webkitRequestFullscreen();
3522
+ }
3523
+ } else {
3524
+ if (document.exitFullscreen) {
3525
+ await document.exitFullscreen();
3526
+ } else if (document.webkitExitFullscreen) {
3527
+ await document.webkitExitFullscreen();
3528
+ }
3529
+ }
3530
+ } catch (err) {
3531
+ onWarning({ severity: "warning", message: `Fullscreen toggle failed: ${String(err)}`, line: 0 });
3532
+ }
3533
+ });
3534
+ document.addEventListener("fullscreenchange", syncFullscreenState);
3535
+ toolbar.appendChild(button);
3536
+ }
3368
3537
  function handleKeyDown(event) {
3369
3538
  const target = event.target;
3370
3539
  if (target instanceof HTMLInputElement || target instanceof HTMLTextAreaElement || target instanceof HTMLSelectElement || target?.isContentEditable) {
@@ -3402,8 +3571,6 @@ function createDiagram(opts) {
3402
3571
  display: "flex",
3403
3572
  alignItems: "center",
3404
3573
  justifyContent: "flex-start",
3405
- flexWrap: "wrap",
3406
- gap: "4px",
3407
3574
  maxWidth: "100%",
3408
3575
  padding: "0",
3409
3576
  border: "0",
@@ -3425,6 +3592,7 @@ function createDiagram(opts) {
3425
3592
  mountSpeedControls(toolbar);
3426
3593
  mountFitControl(toolbar);
3427
3594
  mountResetViewControl(toolbar);
3595
+ mountFullscreenControl(toolbar);
3428
3596
  mountSvgControl(toolbar);
3429
3597
  mountShareControl(toolbar);
3430
3598
  ensureFooter().insertBefore(toolbar, badge ?? null);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@markdy/renderer-dom",
3
- "version": "1.0.11",
3
+ "version": "1.0.12",
4
4
  "description": "Browser renderer for diagram-native animated MarkdyScript architecture diagrams, built on the Web Animations API.",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -45,14 +45,14 @@
45
45
  },
46
46
  "dependencies": {
47
47
  "html2canvas": "^1.4.1",
48
- "@markdy/core": "1.0.11"
48
+ "@markdy/core": "1.0.12"
49
49
  },
50
50
  "devDependencies": {
51
51
  "jsdom": "^29.1.1",
52
52
  "tsup": "^8.5.1",
53
53
  "typescript": "^5.9.3",
54
54
  "vitest": "^4.1.7",
55
- "@markdy/stdlib-systems": "1.0.11"
55
+ "@markdy/stdlib-systems": "1.0.12"
56
56
  },
57
57
  "scripts": {
58
58
  "build": "tsup",