@ogygia/devtools 0.0.0 → 0.11.1
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/LICENSE +21 -0
- package/README.md +24 -1
- package/dist/client.d.ts +3 -0
- package/dist/client.js +24 -0
- package/dist/devtools/BoundaryOverlay.svelte +396 -0
- package/dist/devtools/BoundaryOverlay.svelte.d.ts +19 -0
- package/dist/devtools/Devtools.svelte +663 -0
- package/dist/devtools/Devtools.svelte.d.ts +15 -0
- package/dist/devtools/HubTab.svelte +206 -0
- package/dist/devtools/HubTab.svelte.d.ts +11 -0
- package/dist/devtools/HydrationTab.svelte +237 -0
- package/dist/devtools/HydrationTab.svelte.d.ts +13 -0
- package/dist/devtools/IslandDetail.svelte +615 -0
- package/dist/devtools/IslandDetail.svelte.d.ts +15 -0
- package/dist/devtools/LedgerTab.svelte +287 -0
- package/dist/devtools/LedgerTab.svelte.d.ts +11 -0
- package/dist/devtools/LensTab.svelte +290 -0
- package/dist/devtools/LensTab.svelte.d.ts +19 -0
- package/dist/devtools/NavTab.svelte +229 -0
- package/dist/devtools/NavTab.svelte.d.ts +11 -0
- package/dist/devtools/PageTab.svelte +1122 -0
- package/dist/devtools/PageTab.svelte.d.ts +15 -0
- package/dist/devtools/ProfilerTab.svelte +755 -0
- package/dist/devtools/ProfilerTab.svelte.d.ts +15 -0
- package/dist/devtools/PropsTree.svelte +155 -0
- package/dist/devtools/PropsTree.svelte.d.ts +15 -0
- package/dist/devtools/SessionTab.svelte +796 -0
- package/dist/devtools/SessionTab.svelte.d.ts +11 -0
- package/dist/devtools/TimelineTab.svelte +267 -0
- package/dist/devtools/TimelineTab.svelte.d.ts +11 -0
- package/dist/devtools/WireTab.svelte +149 -0
- package/dist/devtools/WireTab.svelte.d.ts +11 -0
- package/dist/devtools/bytes.d.ts +70 -0
- package/dist/devtools/bytes.js +82 -0
- package/dist/devtools/cache-headers.d.ts +20 -0
- package/dist/devtools/cache-headers.js +81 -0
- package/dist/devtools/highlight.d.ts +7 -0
- package/dist/devtools/highlight.js +83 -0
- package/dist/devtools/hydration.d.ts +48 -0
- package/dist/devtools/hydration.js +93 -0
- package/dist/devtools/index.d.ts +3 -0
- package/dist/devtools/index.js +3 -0
- package/dist/devtools/ledger-dom.d.ts +7 -0
- package/dist/devtools/ledger-dom.js +151 -0
- package/dist/devtools/leftovers.d.ts +77 -0
- package/dist/devtools/leftovers.js +319 -0
- package/dist/devtools/names.d.ts +1 -0
- package/dist/devtools/names.js +34 -0
- package/dist/devtools/page.d.ts +96 -0
- package/dist/devtools/page.js +957 -0
- package/dist/devtools/profile-anchors.d.ts +22 -0
- package/dist/devtools/profile-anchors.js +135 -0
- package/dist/devtools/profile-store.d.ts +175 -0
- package/dist/devtools/profile-store.js +239 -0
- package/dist/devtools/regions.d.ts +77 -0
- package/dist/devtools/regions.js +132 -0
- package/dist/devtools/session.d.ts +31 -0
- package/dist/devtools/session.js +455 -0
- package/dist/devtools/since-load.d.ts +50 -0
- package/dist/devtools/since-load.js +89 -0
- package/dist/devtools/source-lines.d.ts +24 -0
- package/dist/devtools/source-lines.js +106 -0
- package/dist/devtools/styles.d.ts +52 -0
- package/dist/devtools/styles.js +248 -0
- package/dist/devtools/testing-engine.d.ts +83 -0
- package/dist/devtools/testing-engine.js +220 -0
- package/dist/devtools/ui-app.d.ts +5 -0
- package/dist/devtools/ui-app.js +69 -0
- package/dist/devtools/ui.d.ts +50 -0
- package/dist/devtools/ui.js +175 -0
- package/dist/profiler/alloc.d.ts +75 -0
- package/dist/profiler/alloc.js +76 -0
- package/dist/profiler/analyze.d.ts +437 -0
- package/dist/profiler/analyze.js +1941 -0
- package/dist/profiler/app-path.d.ts +7 -0
- package/dist/profiler/app-path.js +26 -0
- package/dist/profiler/async-io.d.ts +58 -0
- package/dist/profiler/async-io.js +187 -0
- package/dist/profiler/beacon-standalone.d.ts +4 -0
- package/dist/profiler/beacon-standalone.js +409 -0
- package/dist/profiler/browser-findings.d.ts +25 -0
- package/dist/profiler/browser-findings.js +260 -0
- package/dist/profiler/byte-strip.d.ts +58 -0
- package/dist/profiler/byte-strip.js +228 -0
- package/dist/profiler/client-files.d.ts +16 -0
- package/dist/profiler/client-files.js +60 -0
- package/dist/profiler/client-windows.d.ts +49 -0
- package/dist/profiler/client-windows.js +95 -0
- package/dist/profiler/client.d.ts +40 -0
- package/dist/profiler/client.js +82 -0
- package/dist/profiler/compare.d.ts +308 -0
- package/dist/profiler/compare.js +733 -0
- package/dist/profiler/compress.d.ts +10 -0
- package/dist/profiler/compress.js +36 -0
- package/dist/profiler/contention.d.ts +60 -0
- package/dist/profiler/contention.js +86 -0
- package/dist/profiler/crypto.d.ts +19 -0
- package/dist/profiler/crypto.js +101 -0
- package/dist/profiler/doc-diff.d.ts +47 -0
- package/dist/profiler/doc-diff.js +214 -0
- package/dist/profiler/dom-diff.d.ts +43 -0
- package/dist/profiler/dom-diff.js +121 -0
- package/dist/profiler/drill.d.ts +89 -0
- package/dist/profiler/drill.js +553 -0
- package/dist/profiler/embedded-maps.d.ts +37 -0
- package/dist/profiler/embedded-maps.js +135 -0
- package/dist/profiler/env.d.ts +6 -0
- package/dist/profiler/env.js +10 -0
- package/dist/profiler/forecast.d.ts +76 -0
- package/dist/profiler/forecast.js +225 -0
- package/dist/profiler/frames.d.ts +11 -0
- package/dist/profiler/frames.js +42 -0
- package/dist/profiler/gc.d.ts +144 -0
- package/dist/profiler/gc.js +271 -0
- package/dist/profiler/hole-slots.d.ts +31 -0
- package/dist/profiler/hole-slots.js +90 -0
- package/dist/profiler/index.d.ts +288 -0
- package/dist/profiler/index.js +4921 -0
- package/dist/profiler/insights.d.ts +96 -0
- package/dist/profiler/insights.js +239 -0
- package/dist/profiler/ledger.d.ts +121 -0
- package/dist/profiler/ledger.js +440 -0
- package/dist/profiler/lineage.d.ts +81 -0
- package/dist/profiler/lineage.js +359 -0
- package/dist/profiler/module-map.d.ts +12 -0
- package/dist/profiler/module-map.js +94 -0
- package/dist/profiler/net.d.ts +169 -0
- package/dist/profiler/net.js +586 -0
- package/dist/profiler/on-demand.d.ts +11 -0
- package/dist/profiler/on-demand.js +15 -0
- package/dist/profiler/own-requests.d.ts +9 -0
- package/dist/profiler/own-requests.js +17 -0
- package/dist/profiler/patterns.d.ts +476 -0
- package/dist/profiler/patterns.js +2203 -0
- package/dist/profiler/profiler-router.d.ts +245 -0
- package/dist/profiler/profiler-router.js +113 -0
- package/dist/profiler/refresh-stub.d.ts +2 -0
- package/dist/profiler/refresh-stub.js +37 -0
- package/dist/profiler/report.d.ts +1404 -0
- package/dist/profiler/report.js +2638 -0
- package/dist/profiler/river.d.ts +65 -0
- package/dist/profiler/river.js +298 -0
- package/dist/profiler/route-files.d.ts +22 -0
- package/dist/profiler/route-files.js +55 -0
- package/dist/profiler/route-imports.d.ts +14 -0
- package/dist/profiler/route-imports.js +83 -0
- package/dist/profiler/saving.d.ts +22 -0
- package/dist/profiler/saving.js +42 -0
- package/dist/profiler/score.d.ts +109 -0
- package/dist/profiler/score.js +261 -0
- package/dist/profiler/session-cookie.d.ts +28 -0
- package/dist/profiler/session-cookie.js +45 -0
- package/dist/profiler/sink.d.ts +81 -0
- package/dist/profiler/sink.js +124 -0
- package/dist/profiler/site-fixes.d.ts +25 -0
- package/dist/profiler/site-fixes.js +62 -0
- package/dist/profiler/source-scan.d.ts +210 -0
- package/dist/profiler/source-scan.js +1724 -0
- package/dist/profiler/span.d.ts +90 -0
- package/dist/profiler/span.js +109 -0
- package/dist/profiler/stacks.d.ts +43 -0
- package/dist/profiler/stacks.js +107 -0
- package/dist/profiler/standalone.d.ts +27 -0
- package/dist/profiler/standalone.js +98 -0
- package/dist/profiler/steps.d.ts +39 -0
- package/dist/profiler/steps.js +74 -0
- package/dist/profiler/storage/index.d.ts +87 -0
- package/dist/profiler/storage/index.js +76 -0
- package/dist/profiler/storage/postgres.d.ts +12 -0
- package/dist/profiler/storage/postgres.js +94 -0
- package/dist/profiler/storage/redis.d.ts +19 -0
- package/dist/profiler/storage/redis.js +148 -0
- package/dist/profiler/storage/sqlite.d.ts +2 -0
- package/dist/profiler/storage/sqlite.js +85 -0
- package/dist/profiler/storage/visits.d.ts +4 -0
- package/dist/profiler/storage/visits.js +6 -0
- package/dist/profiler/stream-tail.d.ts +26 -0
- package/dist/profiler/stream-tail.js +74 -0
- package/dist/profiler/timeline.d.ts +279 -0
- package/dist/profiler/timeline.js +690 -0
- package/dist/profiler/ui/AllocStrip.svelte +146 -0
- package/dist/profiler/ui/AllocStrip.svelte.d.ts +17 -0
- package/dist/profiler/ui/Awaits.svelte +363 -0
- package/dist/profiler/ui/Awaits.svelte.d.ts +16 -0
- package/dist/profiler/ui/ByteStrip.svelte +182 -0
- package/dist/profiler/ui/ByteStrip.svelte.d.ts +18 -0
- package/dist/profiler/ui/Compare.svelte +24 -0
- package/dist/profiler/ui/Compare.svelte.d.ts +16 -0
- package/dist/profiler/ui/CompareBody.svelte +429 -0
- package/dist/profiler/ui/CompareBody.svelte.d.ts +8 -0
- package/dist/profiler/ui/ComponentsTable.svelte +265 -0
- package/dist/profiler/ui/ComponentsTable.svelte.d.ts +20 -0
- package/dist/profiler/ui/Dashboard.svelte +492 -0
- package/dist/profiler/ui/Dashboard.svelte.d.ts +31 -0
- package/dist/profiler/ui/DataRiver.svelte +206 -0
- package/dist/profiler/ui/DataRiver.svelte.d.ts +13 -0
- package/dist/profiler/ui/DomTravel.svelte +207 -0
- package/dist/profiler/ui/DomTravel.svelte.d.ts +9 -0
- package/dist/profiler/ui/DownloadHtml.svelte +52 -0
- package/dist/profiler/ui/DownloadHtml.svelte.d.ts +10 -0
- package/dist/profiler/ui/Drill.svelte +276 -0
- package/dist/profiler/ui/Drill.svelte.d.ts +12 -0
- package/dist/profiler/ui/ExportButton.svelte +59 -0
- package/dist/profiler/ui/ExportButton.svelte.d.ts +8 -0
- package/dist/profiler/ui/Flame.svelte +222 -0
- package/dist/profiler/ui/Flame.svelte.d.ts +12 -0
- package/dist/profiler/ui/FrameDetails.svelte +308 -0
- package/dist/profiler/ui/FrameDetails.svelte.d.ts +16 -0
- package/dist/profiler/ui/FunctionsTable.svelte +156 -0
- package/dist/profiler/ui/FunctionsTable.svelte.d.ts +17 -0
- package/dist/profiler/ui/IslandHeatmap.svelte +151 -0
- package/dist/profiler/ui/IslandHeatmap.svelte.d.ts +16 -0
- package/dist/profiler/ui/IslandsTable.svelte +448 -0
- package/dist/profiler/ui/IslandsTable.svelte.d.ts +16 -0
- package/dist/profiler/ui/KeepLocal.svelte +46 -0
- package/dist/profiler/ui/KeepLocal.svelte.d.ts +8 -0
- package/dist/profiler/ui/Ledger.svelte +196 -0
- package/dist/profiler/ui/Ledger.svelte.d.ts +18 -0
- package/dist/profiler/ui/LocalCompare.svelte +48 -0
- package/dist/profiler/ui/LocalCompare.svelte.d.ts +8 -0
- package/dist/profiler/ui/LocalReports.svelte +68 -0
- package/dist/profiler/ui/LocalReports.svelte.d.ts +7 -0
- package/dist/profiler/ui/Login.svelte +13 -0
- package/dist/profiler/ui/Login.svelte.d.ts +12 -0
- package/dist/profiler/ui/LoginForm.svelte +42 -0
- package/dist/profiler/ui/LoginForm.svelte.d.ts +7 -0
- package/dist/profiler/ui/Message.svelte +10 -0
- package/dist/profiler/ui/Message.svelte.d.ts +12 -0
- package/dist/profiler/ui/OnThisPage.svelte +137 -0
- package/dist/profiler/ui/OnThisPage.svelte.d.ts +3 -0
- package/dist/profiler/ui/OneClock.svelte +297 -0
- package/dist/profiler/ui/OneClock.svelte.d.ts +27 -0
- package/dist/profiler/ui/Panel.svelte +10 -0
- package/dist/profiler/ui/Panel.svelte.d.ts +16 -0
- package/dist/profiler/ui/Paths.svelte +269 -0
- package/dist/profiler/ui/Paths.svelte.d.ts +15 -0
- package/dist/profiler/ui/Patterns.svelte +364 -0
- package/dist/profiler/ui/Patterns.svelte.d.ts +15 -0
- package/dist/profiler/ui/PermalinkGate.svelte +143 -0
- package/dist/profiler/ui/PermalinkGate.svelte.d.ts +10 -0
- package/dist/profiler/ui/RenderSteps.svelte +218 -0
- package/dist/profiler/ui/RenderSteps.svelte.d.ts +13 -0
- package/dist/profiler/ui/Report.svelte +28 -0
- package/dist/profiler/ui/Report.svelte.d.ts +20 -0
- package/dist/profiler/ui/ReportBody.svelte +2592 -0
- package/dist/profiler/ui/ReportBody.svelte.d.ts +21 -0
- package/dist/profiler/ui/Run.svelte +17 -0
- package/dist/profiler/ui/Run.svelte.d.ts +14 -0
- package/dist/profiler/ui/RunView.svelte +146 -0
- package/dist/profiler/ui/RunView.svelte.d.ts +10 -0
- package/dist/profiler/ui/ScoreCard.svelte +197 -0
- package/dist/profiler/ui/ScoreCard.svelte.d.ts +7 -0
- package/dist/profiler/ui/Scrub.svelte +293 -0
- package/dist/profiler/ui/Scrub.svelte.d.ts +18 -0
- package/dist/profiler/ui/SeedExplainer.svelte +193 -0
- package/dist/profiler/ui/SeedExplainer.svelte.d.ts +16 -0
- package/dist/profiler/ui/ShareLink.svelte +148 -0
- package/dist/profiler/ui/ShareLink.svelte.d.ts +8 -0
- package/dist/profiler/ui/Shell.svelte +50 -0
- package/dist/profiler/ui/Shell.svelte.d.ts +27 -0
- package/dist/profiler/ui/Sidebar.svelte +312 -0
- package/dist/profiler/ui/Sidebar.svelte.d.ts +7 -0
- package/dist/profiler/ui/Site.svelte +20 -0
- package/dist/profiler/ui/Site.svelte.d.ts +23 -0
- package/dist/profiler/ui/SiteView.svelte +385 -0
- package/dist/profiler/ui/SiteView.svelte.d.ts +27 -0
- package/dist/profiler/ui/ThemeSwitch.svelte +78 -0
- package/dist/profiler/ui/ThemeSwitch.svelte.d.ts +3 -0
- package/dist/profiler/ui/Timeline.svelte +672 -0
- package/dist/profiler/ui/Timeline.svelte.d.ts +22 -0
- package/dist/profiler/ui/Treemap.svelte +278 -0
- package/dist/profiler/ui/Treemap.svelte.d.ts +20 -0
- package/dist/profiler/ui/Upload.svelte +19 -0
- package/dist/profiler/ui/Upload.svelte.d.ts +10 -0
- package/dist/profiler/ui/UploadForm.svelte +59 -0
- package/dist/profiler/ui/UploadForm.svelte.d.ts +6 -0
- package/dist/profiler/ui/WaitingTable.svelte +55 -0
- package/dist/profiler/ui/WaitingTable.svelte.d.ts +14 -0
- package/dist/profiler/ui/Waterfall.svelte +371 -0
- package/dist/profiler/ui/Waterfall.svelte.d.ts +7 -0
- package/dist/profiler/ui/WhatIf.svelte +87 -0
- package/dist/profiler/ui/WhatIf.svelte.d.ts +18 -0
- package/dist/profiler/ui/fake-progress.svelte.d.ts +15 -0
- package/dist/profiler/ui/fake-progress.svelte.js +38 -0
- package/dist/profiler/ui/format.d.ts +20 -0
- package/dist/profiler/ui/format.js +71 -0
- package/dist/profiler/ui/permalink.d.ts +9 -0
- package/dist/profiler/ui/permalink.js +108 -0
- package/dist/profiler/ui/press.d.ts +5 -0
- package/dist/profiler/ui/press.js +19 -0
- package/dist/profiler/ui/profiler.css +650 -0
- package/dist/profiler/ui/report-data.d.ts +189 -0
- package/dist/profiler/ui/report-data.js +393 -0
- package/dist/profiler/ui/report-request.d.ts +6 -0
- package/dist/profiler/ui/report-request.js +50 -0
- package/dist/profiler/ui/row-anchor.svelte.d.ts +12 -0
- package/dist/profiler/ui/row-anchor.svelte.js +44 -0
- package/dist/profiler/ui/sort.svelte.d.ts +14 -0
- package/dist/profiler/ui/sort.svelte.js +37 -0
- package/dist/profiler/ui/store.d.ts +45 -0
- package/dist/profiler/ui/store.js +92 -0
- package/dist/profiler/visit.d.ts +389 -0
- package/dist/profiler/visit.js +1002 -0
- package/dist/report.d.ts +5 -0
- package/dist/report.js +4 -0
- package/dist/server.d.ts +11 -0
- package/dist/server.js +38 -0
- package/dist/vite.d.ts +12 -0
- package/dist/vite.js +78 -0
- package/package.json +99 -6
|
@@ -0,0 +1,287 @@
|
|
|
1
|
+
<!-- (its CSS injected into the dock's shadow root: see Devtools.svelte) -->
|
|
2
|
+
<svelte:options css="injected" />
|
|
3
|
+
|
|
4
|
+
<script>
|
|
5
|
+
/**
|
|
6
|
+
* The Bytes tab (byte ledger): real over-the-wire JS per island entry chunk + the shared runtime
|
|
7
|
+
* chunk, from PerformanceResourceTiming. Cold islands show `cold` and fill in live as the panel
|
|
8
|
+
* ticks. Measures each island's OWN chunk (not transitive deps); dev sizes are flagged.
|
|
9
|
+
*/
|
|
10
|
+
import {
|
|
11
|
+
all_regions,
|
|
12
|
+
chunk_bytes,
|
|
13
|
+
basename,
|
|
14
|
+
kb,
|
|
15
|
+
region_name,
|
|
16
|
+
region_transitive
|
|
17
|
+
} from './regions.js';
|
|
18
|
+
|
|
19
|
+
import { page_ledger } from './ledger-dom.js';
|
|
20
|
+
import { profile_for, profiles_version } from './profile-store.js';
|
|
21
|
+
|
|
22
|
+
let { tick = 0 } = $props();
|
|
23
|
+
const IS_DEV = !!(import.meta.env && import.meta.env.DEV);
|
|
24
|
+
|
|
25
|
+
// THE EXACT LEDGER (a build): the page's island graph names every file each island needs, the
|
|
26
|
+
// browser says what each file weighed — each file counted once, and per island what only it needs
|
|
27
|
+
const exact = $derived.by(() => {
|
|
28
|
+
void tick;
|
|
29
|
+
return page_ledger();
|
|
30
|
+
});
|
|
31
|
+
// the modules the build shipped twice that this page loads both copies of (the last profile's)
|
|
32
|
+
const twice = $derived.by(() => {
|
|
33
|
+
void tick;
|
|
34
|
+
profiles_version();
|
|
35
|
+
return profile_for(location.pathname)?.assets?.twice ?? [];
|
|
36
|
+
});
|
|
37
|
+
|
|
38
|
+
const model = $derived.by(() => {
|
|
39
|
+
void tick; // refresh with the panel tick
|
|
40
|
+
|
|
41
|
+
// Group regions by entry chunk (dedupe: same component + strategy = ONE chunk, N instances).
|
|
42
|
+
const groups = new Map();
|
|
43
|
+
for (const r of all_regions()) {
|
|
44
|
+
if (!r.entry) continue;
|
|
45
|
+
const key = basename(r.entry);
|
|
46
|
+
const g = groups.get(key);
|
|
47
|
+
if (g) g.count++;
|
|
48
|
+
else groups.set(key, { entry: r.entry, kind: r.kind, wake: r.wake, count: 1 });
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
const rows = [...groups.values()]
|
|
52
|
+
.map((g) => {
|
|
53
|
+
const t = region_transitive(g.entry);
|
|
54
|
+
return {
|
|
55
|
+
...g,
|
|
56
|
+
...chunk_bytes(g.entry),
|
|
57
|
+
name: region_name(g.entry),
|
|
58
|
+
transitive: t ? t.bytes : 0,
|
|
59
|
+
modules: t ? t.modules : 0
|
|
60
|
+
};
|
|
61
|
+
})
|
|
62
|
+
// Sort by the real (transitive) cost when we have it, else by the entry-chunk wire size.
|
|
63
|
+
.sort((a, b) => b.transitive - a.transitive || b.wire - a.wire);
|
|
64
|
+
|
|
65
|
+
const runtimeSrc =
|
|
66
|
+
document.querySelector('script[data-ogygia-runtime]')?.getAttribute('src') || '';
|
|
67
|
+
const runtime = runtimeSrc ? { src: runtimeSrc, ...chunk_bytes(runtimeSrc) } : null;
|
|
68
|
+
|
|
69
|
+
// Page total over UNIQUE chunks (rows are already one-per-island). `wire` = wrapper chunks;
|
|
70
|
+
// `transitive` = each island's whole subgraph (the real-cost column).
|
|
71
|
+
const counted = new Set();
|
|
72
|
+
let wire = 0;
|
|
73
|
+
let transitive = 0;
|
|
74
|
+
for (const row of rows) {
|
|
75
|
+
const key = basename(row.entry);
|
|
76
|
+
if (counted.has(key)) continue;
|
|
77
|
+
counted.add(key);
|
|
78
|
+
if (row.loaded) wire += row.wire;
|
|
79
|
+
transitive += row.transitive;
|
|
80
|
+
}
|
|
81
|
+
if (runtime?.loaded && !counted.has(basename(runtime.src))) wire += runtime.wire;
|
|
82
|
+
return { rows, runtime, totalWire: wire, totalTransitive: transitive };
|
|
83
|
+
});
|
|
84
|
+
</script>
|
|
85
|
+
|
|
86
|
+
<h3>byte ledger — JavaScript per island</h3>
|
|
87
|
+
{#if exact}
|
|
88
|
+
<div class="note" data-og-ledger-exact>
|
|
89
|
+
Every file each island needs, from the page's island graph, weighed by the browser (over the
|
|
90
|
+
wire).
|
|
91
|
+
<b>only it</b> is what that island alone needs: what removing it would save. <b>shared</b> it shares
|
|
92
|
+
with other islands. The page total counts each file once.
|
|
93
|
+
</div>
|
|
94
|
+
<table>
|
|
95
|
+
<thead>
|
|
96
|
+
<tr
|
|
97
|
+
><th>island</th><th>kind</th><th>files</th><th>loaded</th><th>only it</th><th>shared</th
|
|
98
|
+
></tr
|
|
99
|
+
>
|
|
100
|
+
</thead>
|
|
101
|
+
<tbody>
|
|
102
|
+
{#each exact.rows as row (row.entry)}
|
|
103
|
+
<tr>
|
|
104
|
+
<td title={row.entry}
|
|
105
|
+
><span class="nm">{row.name}</span>{#if row.count > 1}<span class="muted">
|
|
106
|
+
×{row.count}</span
|
|
107
|
+
>{/if}</td
|
|
108
|
+
>
|
|
109
|
+
<td>{row.kind}{row.kind === 'island' ? ' · ' + row.wake : ''}</td>
|
|
110
|
+
<td
|
|
111
|
+
>{row.files}{#if row.cold}<span class="muted"> · {row.cold} cold</span>{/if}</td
|
|
112
|
+
>
|
|
113
|
+
<td
|
|
114
|
+
>{#if row.files > row.cold}{kb(row.wire)}{:else}<span class="muted">cold</span>{/if}</td
|
|
115
|
+
>
|
|
116
|
+
<td><span class="strong">{kb(row.unique)}</span></td>
|
|
117
|
+
<td class="muted">{kb(row.shared)}</td>
|
|
118
|
+
</tr>
|
|
119
|
+
{/each}
|
|
120
|
+
<tr>
|
|
121
|
+
<td>ogygia runtime</td>
|
|
122
|
+
<td class="muted">every island</td>
|
|
123
|
+
<td>{exact.runtime.files}</td>
|
|
124
|
+
<td>{kb(exact.runtime.wire)}</td>
|
|
125
|
+
<td class="muted">—</td>
|
|
126
|
+
<td class="muted">—</td>
|
|
127
|
+
</tr>
|
|
128
|
+
</tbody>
|
|
129
|
+
<tfoot>
|
|
130
|
+
<tr>
|
|
131
|
+
<td>page</td>
|
|
132
|
+
<td class="muted">each file once</td>
|
|
133
|
+
<td
|
|
134
|
+
>{exact.page.files}{#if exact.page.cold}<span class="muted">
|
|
135
|
+
· {exact.page.cold} cold</span
|
|
136
|
+
>{/if}</td
|
|
137
|
+
>
|
|
138
|
+
<td>{kb(exact.page.wire)}</td>
|
|
139
|
+
<td colspan="2" class="muted">{kb(exact.page.raw)} decoded</td>
|
|
140
|
+
</tr>
|
|
141
|
+
</tfoot>
|
|
142
|
+
</table>
|
|
143
|
+
{#if exact.shared.length}
|
|
144
|
+
<h3 class="sub">shared files</h3>
|
|
145
|
+
<table data-og-ledger-shared>
|
|
146
|
+
<tbody>
|
|
147
|
+
{#each exact.shared.slice(0, 8) as s (s.url)}
|
|
148
|
+
<tr>
|
|
149
|
+
<td title={s.url}>{basename(s.url)}</td>
|
|
150
|
+
<td>{kb(s.wire)}</td>
|
|
151
|
+
<td class="muted"
|
|
152
|
+
>{s.users.length > 4
|
|
153
|
+
? `${s.users.slice(0, 3).join(', ')} and ${s.users.length - 3} more`
|
|
154
|
+
: s.users.join(', ')}</td
|
|
155
|
+
>
|
|
156
|
+
</tr>
|
|
157
|
+
{/each}
|
|
158
|
+
</tbody>
|
|
159
|
+
</table>
|
|
160
|
+
{/if}
|
|
161
|
+
{#if twice.length}
|
|
162
|
+
<!-- the last profile of this page: modules the build shipped twice, both copies loaded here -->
|
|
163
|
+
<h3 class="sub">loaded twice</h3>
|
|
164
|
+
<div class="note" data-og-ledger-twice>
|
|
165
|
+
One module reached by two paths (a package's source and its build, or two of its versions)
|
|
166
|
+
ships as two copies, and this page loads both: {kb(twice.reduce((s, d) => s + d.extra, 0))} of code
|
|
167
|
+
its browser downloads, parses and runs a second time. From the last profile.
|
|
168
|
+
</div>
|
|
169
|
+
<table>
|
|
170
|
+
<tbody>
|
|
171
|
+
{#each twice.slice(0, 8) as d (d.name)}
|
|
172
|
+
<tr>
|
|
173
|
+
<td>{d.name}</td>
|
|
174
|
+
<td>{kb(d.extra)}</td>
|
|
175
|
+
<td class="muted"
|
|
176
|
+
>{d.copies
|
|
177
|
+
.map((c) => `${basename(c.file)}${c.from ? ` (${c.from})` : ''}`)
|
|
178
|
+
.join(' · ')}</td
|
|
179
|
+
>
|
|
180
|
+
</tr>
|
|
181
|
+
{/each}
|
|
182
|
+
</tbody>
|
|
183
|
+
</table>
|
|
184
|
+
{/if}
|
|
185
|
+
{:else}
|
|
186
|
+
<div class="note">
|
|
187
|
+
Each <b>+deps</b> figure is that island's <b>whole bundle</b> — the component plus every shared
|
|
188
|
+
function and utility it imports. Shared code is therefore counted in <em>every</em> island that
|
|
189
|
+
uses it, so the figures overlap and the page total over-counts code that actually ships once.{#if IS_DEV}
|
|
190
|
+
Dev estimate: sizes are unbundled/unminified — build + preview for shipped numbers.{/if} A cold
|
|
191
|
+
island (not yet woken) shows <b>—</b> until it loads.
|
|
192
|
+
</div>
|
|
193
|
+
|
|
194
|
+
<table>
|
|
195
|
+
<thead>
|
|
196
|
+
<tr><th>island</th><th>kind</th><th>wrapper</th><th>+deps</th></tr>
|
|
197
|
+
</thead>
|
|
198
|
+
<tbody>
|
|
199
|
+
{#each model.rows as row (row.entry)}
|
|
200
|
+
<tr>
|
|
201
|
+
<td title={row.entry}>
|
|
202
|
+
<span class="nm">{row.name}</span>{#if row.count > 1}<span class="muted">
|
|
203
|
+
×{row.count}</span
|
|
204
|
+
>{/if}
|
|
205
|
+
</td>
|
|
206
|
+
<td>{row.kind}{row.kind === 'island' ? ' · ' + row.wake : ''}</td>
|
|
207
|
+
<td
|
|
208
|
+
>{#if row.loaded}{kb(row.wire)}{:else}<span class="muted">cold</span>{/if}</td
|
|
209
|
+
>
|
|
210
|
+
<td>
|
|
211
|
+
{#if row.transitive}
|
|
212
|
+
<span class="strong">{kb(row.transitive)}</span><span class="muted">
|
|
213
|
+
· {row.modules} mod</span
|
|
214
|
+
>
|
|
215
|
+
{:else}<span class="muted">—</span>{/if}
|
|
216
|
+
</td>
|
|
217
|
+
</tr>
|
|
218
|
+
{:else}
|
|
219
|
+
<tr><td colspan="4" class="muted">no island chunks on this page</td></tr>
|
|
220
|
+
{/each}
|
|
221
|
+
{#if model.runtime}
|
|
222
|
+
<tr>
|
|
223
|
+
<td>ogygia runtime</td>
|
|
224
|
+
<td class="muted">shared</td>
|
|
225
|
+
<td>{model.runtime.loaded ? kb(model.runtime.wire) : '—'}</td>
|
|
226
|
+
<td class="muted">—</td>
|
|
227
|
+
</tr>
|
|
228
|
+
{/if}
|
|
229
|
+
</tbody>
|
|
230
|
+
<tfoot>
|
|
231
|
+
<tr>
|
|
232
|
+
<td>page total</td><td class="muted">unique · +deps</td>
|
|
233
|
+
<td>{kb(model.totalWire)}</td><td>{kb(model.totalTransitive)}</td>
|
|
234
|
+
</tr>
|
|
235
|
+
</tfoot>
|
|
236
|
+
</table>
|
|
237
|
+
{/if}
|
|
238
|
+
|
|
239
|
+
<style>
|
|
240
|
+
h3 {
|
|
241
|
+
margin: 0 0 8px;
|
|
242
|
+
font-size: 12px;
|
|
243
|
+
color: #5eead4;
|
|
244
|
+
}
|
|
245
|
+
h3.sub {
|
|
246
|
+
margin-top: 12px;
|
|
247
|
+
}
|
|
248
|
+
.note {
|
|
249
|
+
color: #94a3b8;
|
|
250
|
+
margin-bottom: 6px;
|
|
251
|
+
}
|
|
252
|
+
table {
|
|
253
|
+
border-collapse: collapse;
|
|
254
|
+
width: 100%;
|
|
255
|
+
}
|
|
256
|
+
th,
|
|
257
|
+
td {
|
|
258
|
+
text-align: right;
|
|
259
|
+
padding: 2px 8px;
|
|
260
|
+
white-space: nowrap;
|
|
261
|
+
}
|
|
262
|
+
th:first-child,
|
|
263
|
+
td:first-child,
|
|
264
|
+
th:nth-child(2),
|
|
265
|
+
td:nth-child(2) {
|
|
266
|
+
text-align: left;
|
|
267
|
+
}
|
|
268
|
+
thead th {
|
|
269
|
+
color: #94a3b8;
|
|
270
|
+
border-bottom: 1px solid rgba(148, 163, 184, 0.2);
|
|
271
|
+
}
|
|
272
|
+
tfoot td {
|
|
273
|
+
border-top: 1px solid rgba(148, 163, 184, 0.2);
|
|
274
|
+
color: #5eead4;
|
|
275
|
+
font-weight: 600;
|
|
276
|
+
}
|
|
277
|
+
.muted {
|
|
278
|
+
color: #94a3b8;
|
|
279
|
+
}
|
|
280
|
+
.nm {
|
|
281
|
+
color: #e2e8f0;
|
|
282
|
+
font-weight: 600;
|
|
283
|
+
}
|
|
284
|
+
.strong {
|
|
285
|
+
color: #e2e8f0;
|
|
286
|
+
}
|
|
287
|
+
</style>
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export default LedgerTab;
|
|
2
|
+
type LedgerTab = {
|
|
3
|
+
$on?(type: string, callback: (e: any) => void): () => void;
|
|
4
|
+
$set?(props: Partial<$$ComponentProps>): void;
|
|
5
|
+
};
|
|
6
|
+
declare const LedgerTab: import("svelte").Component<{
|
|
7
|
+
tick?: number;
|
|
8
|
+
}, {}, "">;
|
|
9
|
+
type $$ComponentProps = {
|
|
10
|
+
tick?: number;
|
|
11
|
+
};
|
|
@@ -0,0 +1,290 @@
|
|
|
1
|
+
<!-- (its CSS injected into the dock's shadow root: see Devtools.svelte) -->
|
|
2
|
+
<svelte:options css="injected" />
|
|
3
|
+
|
|
4
|
+
<script>
|
|
5
|
+
/**
|
|
6
|
+
* The Lens tab: toggles the page-tinting {@link ./BoundaryOverlay.svelte overlay} and lists every
|
|
7
|
+
* region by NAME with its kind / schedule / JS cost / hydration state. Hovering a row lights up the
|
|
8
|
+
* matching box on the page (shared `focus`), and clicking a row smooth-scrolls that region into
|
|
9
|
+
* view — so the roster is a live index into the page, not just a static table. The overlay itself is
|
|
10
|
+
* drawn by BoundaryOverlay (a sibling under the root app); this tab controls it and mirrors it.
|
|
11
|
+
*/
|
|
12
|
+
import { all_regions, region_name, region_transitive } from './regions.js';
|
|
13
|
+
|
|
14
|
+
let {
|
|
15
|
+
tick = 0,
|
|
16
|
+
overlay = $bindable(false),
|
|
17
|
+
focus = $bindable(null),
|
|
18
|
+
selected = $bindable(null),
|
|
19
|
+
picking = $bindable(false)
|
|
20
|
+
} = $props();
|
|
21
|
+
|
|
22
|
+
const kb = (n) => (n < 1024 ? n + ' B' : (n / 1024).toFixed(1) + ' KB');
|
|
23
|
+
|
|
24
|
+
const regions = $derived.by(() => {
|
|
25
|
+
void tick; // refresh with the panel tick
|
|
26
|
+
return all_regions().map((r) => ({
|
|
27
|
+
r,
|
|
28
|
+
name: region_name(r.entry),
|
|
29
|
+
js: r.kind === 'island' ? region_transitive(r.entry) : null
|
|
30
|
+
}));
|
|
31
|
+
});
|
|
32
|
+
const summary = $derived.by(() => {
|
|
33
|
+
const c = { island: 0, lake: 0, hole: 0 };
|
|
34
|
+
let js = 0;
|
|
35
|
+
let cold = 0;
|
|
36
|
+
for (const { r, js: t } of regions) {
|
|
37
|
+
c[r.kind]++;
|
|
38
|
+
if (t) js += t.bytes;
|
|
39
|
+
if (r.kind === 'island' && !r.hydrated) cold++;
|
|
40
|
+
}
|
|
41
|
+
return { ...c, js, cold };
|
|
42
|
+
});
|
|
43
|
+
|
|
44
|
+
function state_of(r) {
|
|
45
|
+
// (a nested island rides the island around it: awake with it, never on its own)
|
|
46
|
+
if (r.kind === 'island' && r.rides)
|
|
47
|
+
return r.hydrated ? 'rides its parent' : 'cold (with its parent)';
|
|
48
|
+
if (r.kind === 'island') return r.hydrated ? 'hydrated' : 'cold';
|
|
49
|
+
return r.hydrated ? 'filled' : 'pending';
|
|
50
|
+
}
|
|
51
|
+
function toggle_pick() {
|
|
52
|
+
picking = !picking;
|
|
53
|
+
if (picking) overlay = true; // need the boxes visible to pick one on the page
|
|
54
|
+
}
|
|
55
|
+
</script>
|
|
56
|
+
|
|
57
|
+
<div class="cap">
|
|
58
|
+
boundary lens <span class="muted">· every region on the page, x-rayed</span>
|
|
59
|
+
</div>
|
|
60
|
+
|
|
61
|
+
<div class="controls">
|
|
62
|
+
<button
|
|
63
|
+
class="btn"
|
|
64
|
+
data-og-overlay-toggle
|
|
65
|
+
class:on={overlay}
|
|
66
|
+
onclick={() => (overlay = !overlay)}
|
|
67
|
+
>
|
|
68
|
+
<span class="eye"></span>{overlay ? 'hide overlay' : 'show overlay'}
|
|
69
|
+
</button>
|
|
70
|
+
<button
|
|
71
|
+
class="btn pick"
|
|
72
|
+
data-og-pick
|
|
73
|
+
class:on={picking}
|
|
74
|
+
onclick={toggle_pick}
|
|
75
|
+
title="then click an island on the page"
|
|
76
|
+
>
|
|
77
|
+
<span class="target"></span>{picking ? 'click an island…' : 'pick on page'}
|
|
78
|
+
</button>
|
|
79
|
+
<span class="legend">
|
|
80
|
+
<span class="sw og-island"></span>{summary.island}
|
|
81
|
+
<span class="sw og-lake"></span>{summary.lake}
|
|
82
|
+
<span class="sw og-hole"></span>{summary.hole}
|
|
83
|
+
</span>
|
|
84
|
+
{#if summary.js > 0}<span class="tot"
|
|
85
|
+
>{kb(summary.js)} JS{#if summary.cold}<span class="muted">
|
|
86
|
+
· {summary.cold} cold</span
|
|
87
|
+
>{/if}</span
|
|
88
|
+
>{/if}
|
|
89
|
+
</div>
|
|
90
|
+
|
|
91
|
+
<table>
|
|
92
|
+
<thead>
|
|
93
|
+
<tr><th>island</th><th>wake</th><th>js + deps</th><th>state</th></tr>
|
|
94
|
+
</thead>
|
|
95
|
+
<tbody>
|
|
96
|
+
{#each regions as { r, name, js } (r.el)}
|
|
97
|
+
<tr
|
|
98
|
+
class:on={focus === r.el}
|
|
99
|
+
class:cold={r.kind === 'island' && !r.hydrated}
|
|
100
|
+
onmouseenter={() => (focus = r.el)}
|
|
101
|
+
onmouseleave={() => (focus = null)}
|
|
102
|
+
onclick={() => {
|
|
103
|
+
selected = r.el;
|
|
104
|
+
picking = false;
|
|
105
|
+
}}
|
|
106
|
+
title="inspect this region"
|
|
107
|
+
>
|
|
108
|
+
<!-- the name is a button: Tab reaches the row, Enter opens it (the press bubbles to the row) -->
|
|
109
|
+
<td
|
|
110
|
+
><span class="dot og-{r.kind}"></span><button
|
|
111
|
+
class="nm rowbtn"
|
|
112
|
+
onfocus={() => (focus = r.el)}
|
|
113
|
+
onblur={() => (focus = null)}>{name}</button
|
|
114
|
+
></td
|
|
115
|
+
>
|
|
116
|
+
<td>{r.kind === 'island' ? r.wake : r.kind}</td>
|
|
117
|
+
<td class="mono">
|
|
118
|
+
{#if r.kind !== 'island'}<span class="muted">0 B</span>
|
|
119
|
+
{:else if js}{kb(js.bytes)}
|
|
120
|
+
{:else}<span class="muted">—</span>{/if}
|
|
121
|
+
</td>
|
|
122
|
+
<td class:coldstate={r.kind === 'island' && !r.hydrated}>{state_of(r)}</td>
|
|
123
|
+
</tr>
|
|
124
|
+
{:else}
|
|
125
|
+
<tr><td colspan="4" class="muted">no regions on this page</td></tr>
|
|
126
|
+
{/each}
|
|
127
|
+
</tbody>
|
|
128
|
+
</table>
|
|
129
|
+
|
|
130
|
+
<style>
|
|
131
|
+
.cap {
|
|
132
|
+
font-size: 12px;
|
|
133
|
+
color: #5eead4;
|
|
134
|
+
margin-bottom: 8px;
|
|
135
|
+
}
|
|
136
|
+
.controls {
|
|
137
|
+
display: flex;
|
|
138
|
+
align-items: center;
|
|
139
|
+
gap: 12px;
|
|
140
|
+
margin-bottom: 10px;
|
|
141
|
+
}
|
|
142
|
+
.btn {
|
|
143
|
+
display: inline-flex;
|
|
144
|
+
align-items: center;
|
|
145
|
+
gap: 7px;
|
|
146
|
+
padding: 5px 11px;
|
|
147
|
+
border-radius: 7px;
|
|
148
|
+
border: 1px solid rgba(148, 163, 184, 0.3);
|
|
149
|
+
background: #0d1526;
|
|
150
|
+
color: #e2e8f0;
|
|
151
|
+
cursor: pointer;
|
|
152
|
+
font: inherit;
|
|
153
|
+
}
|
|
154
|
+
.btn .eye {
|
|
155
|
+
width: 9px;
|
|
156
|
+
height: 9px;
|
|
157
|
+
border-radius: 50%;
|
|
158
|
+
border: 1.5px solid currentColor;
|
|
159
|
+
opacity: 0.7;
|
|
160
|
+
}
|
|
161
|
+
.btn.on {
|
|
162
|
+
background: #14b8a6;
|
|
163
|
+
color: #022;
|
|
164
|
+
border-color: #0d9488;
|
|
165
|
+
}
|
|
166
|
+
.btn.on .eye {
|
|
167
|
+
opacity: 1;
|
|
168
|
+
background: currentColor;
|
|
169
|
+
}
|
|
170
|
+
.btn.pick .target {
|
|
171
|
+
width: 10px;
|
|
172
|
+
height: 10px;
|
|
173
|
+
border-radius: 50%;
|
|
174
|
+
border: 1.5px solid currentColor;
|
|
175
|
+
position: relative;
|
|
176
|
+
opacity: 0.75;
|
|
177
|
+
}
|
|
178
|
+
.btn.pick .target::after {
|
|
179
|
+
content: '';
|
|
180
|
+
position: absolute;
|
|
181
|
+
inset: 3px;
|
|
182
|
+
border-radius: 50%;
|
|
183
|
+
background: currentColor;
|
|
184
|
+
}
|
|
185
|
+
.btn.pick.on {
|
|
186
|
+
background: #f59e0b;
|
|
187
|
+
color: #201400;
|
|
188
|
+
border-color: #d97706;
|
|
189
|
+
}
|
|
190
|
+
.btn.pick.on .target {
|
|
191
|
+
opacity: 1;
|
|
192
|
+
}
|
|
193
|
+
.legend {
|
|
194
|
+
color: #94a3b8;
|
|
195
|
+
display: flex;
|
|
196
|
+
align-items: center;
|
|
197
|
+
gap: 5px;
|
|
198
|
+
}
|
|
199
|
+
.tot {
|
|
200
|
+
margin-left: auto;
|
|
201
|
+
color: #5eead4;
|
|
202
|
+
font-weight: 600;
|
|
203
|
+
}
|
|
204
|
+
.sw {
|
|
205
|
+
display: inline-block;
|
|
206
|
+
width: 10px;
|
|
207
|
+
height: 10px;
|
|
208
|
+
border-radius: 3px;
|
|
209
|
+
margin-left: 6px;
|
|
210
|
+
}
|
|
211
|
+
.sw.og-island,
|
|
212
|
+
.dot.og-island {
|
|
213
|
+
background: #14b8a6;
|
|
214
|
+
}
|
|
215
|
+
.sw.og-lake,
|
|
216
|
+
.dot.og-lake {
|
|
217
|
+
background: #f59e0b;
|
|
218
|
+
}
|
|
219
|
+
.sw.og-hole,
|
|
220
|
+
.dot.og-hole {
|
|
221
|
+
background: #8b5cf6;
|
|
222
|
+
}
|
|
223
|
+
.dot {
|
|
224
|
+
display: inline-block;
|
|
225
|
+
width: 8px;
|
|
226
|
+
height: 8px;
|
|
227
|
+
border-radius: 50%;
|
|
228
|
+
margin-right: 7px;
|
|
229
|
+
vertical-align: 0;
|
|
230
|
+
}
|
|
231
|
+
.nm {
|
|
232
|
+
color: #e2e8f0;
|
|
233
|
+
font-weight: 600;
|
|
234
|
+
}
|
|
235
|
+
/* a button that reads as the name it was */
|
|
236
|
+
.rowbtn {
|
|
237
|
+
all: unset;
|
|
238
|
+
cursor: pointer;
|
|
239
|
+
}
|
|
240
|
+
/* (after the reset: the name's own look) */
|
|
241
|
+
.rowbtn.nm {
|
|
242
|
+
color: #e2e8f0;
|
|
243
|
+
font-weight: 600;
|
|
244
|
+
}
|
|
245
|
+
.rowbtn:focus-visible {
|
|
246
|
+
outline: 2px solid rgba(94, 234, 212, 0.7);
|
|
247
|
+
outline-offset: 2px;
|
|
248
|
+
border-radius: 3px;
|
|
249
|
+
}
|
|
250
|
+
table {
|
|
251
|
+
border-collapse: collapse;
|
|
252
|
+
width: 100%;
|
|
253
|
+
}
|
|
254
|
+
th,
|
|
255
|
+
td {
|
|
256
|
+
text-align: right;
|
|
257
|
+
padding: 3px 8px;
|
|
258
|
+
white-space: nowrap;
|
|
259
|
+
}
|
|
260
|
+
th:first-child,
|
|
261
|
+
td:first-child,
|
|
262
|
+
th:nth-child(2),
|
|
263
|
+
td:nth-child(2) {
|
|
264
|
+
text-align: left;
|
|
265
|
+
}
|
|
266
|
+
thead th {
|
|
267
|
+
color: #94a3b8;
|
|
268
|
+
border-bottom: 1px solid rgba(148, 163, 184, 0.2);
|
|
269
|
+
}
|
|
270
|
+
tbody tr {
|
|
271
|
+
cursor: pointer;
|
|
272
|
+
border-radius: 5px;
|
|
273
|
+
}
|
|
274
|
+
tbody tr:hover,
|
|
275
|
+
tbody tr.on {
|
|
276
|
+
background: rgba(94, 234, 212, 0.12);
|
|
277
|
+
}
|
|
278
|
+
tbody tr.on {
|
|
279
|
+
box-shadow: inset 2px 0 0 #5eead4;
|
|
280
|
+
}
|
|
281
|
+
.muted {
|
|
282
|
+
color: #94a3b8;
|
|
283
|
+
}
|
|
284
|
+
.mono {
|
|
285
|
+
font-variant-numeric: tabular-nums;
|
|
286
|
+
}
|
|
287
|
+
.coldstate {
|
|
288
|
+
color: #94a3b8;
|
|
289
|
+
}
|
|
290
|
+
</style>
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
export default LensTab;
|
|
2
|
+
type LensTab = {
|
|
3
|
+
$on?(type: string, callback: (e: any) => void): () => void;
|
|
4
|
+
$set?(props: Partial<$$ComponentProps>): void;
|
|
5
|
+
};
|
|
6
|
+
declare const LensTab: import("svelte").Component<{
|
|
7
|
+
tick?: number;
|
|
8
|
+
overlay?: boolean;
|
|
9
|
+
focus?: any;
|
|
10
|
+
selected?: any;
|
|
11
|
+
picking?: boolean;
|
|
12
|
+
}, {}, "focus" | "overlay" | "selected" | "picking">;
|
|
13
|
+
type $$ComponentProps = {
|
|
14
|
+
tick?: number;
|
|
15
|
+
overlay?: boolean;
|
|
16
|
+
focus?: any;
|
|
17
|
+
selected?: any;
|
|
18
|
+
picking?: boolean;
|
|
19
|
+
};
|