@sveltejs/vite-plugin-svelte 6.2.4 → 7.0.0-next.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/package.json CHANGED
@@ -1,8 +1,7 @@
1
1
  {
2
2
  "name": "@sveltejs/vite-plugin-svelte",
3
- "version": "6.2.4",
3
+ "version": "7.0.0-next.1",
4
4
  "license": "MIT",
5
- "author": "dominikg",
6
5
  "files": [
7
6
  "src",
8
7
  "types"
@@ -34,21 +33,20 @@
34
33
  },
35
34
  "homepage": "https://github.com/sveltejs/vite-plugin-svelte#readme",
36
35
  "dependencies": {
37
- "@sveltejs/vite-plugin-svelte-inspector": "^5.0.0",
38
36
  "deepmerge": "^4.3.1",
39
37
  "magic-string": "^0.30.21",
40
38
  "obug": "^2.1.0",
41
- "vitefu": "^1.1.1"
39
+ "vitefu": "^1.1.2"
42
40
  },
43
41
  "peerDependencies": {
44
- "svelte": "^5.0.0",
45
- "vite": "^6.3.0 || ^7.0.0"
42
+ "svelte": "^5.46.4",
43
+ "vite": "^8.0.0-beta.7 || ^8.0.0"
46
44
  },
47
45
  "devDependencies": {
48
46
  "@types/debug": "^4.1.12",
49
47
  "sass": "^1.94.2",
50
48
  "svelte": "^5.45.4",
51
- "vite": "^7.2.6"
49
+ "vite": "^8.0.0-beta.7"
52
50
  },
53
51
  "scripts": {
54
52
  "check:publint": "publint --strict",
package/src/index.js CHANGED
@@ -6,7 +6,7 @@ import { compile } from './plugins/compile.js';
6
6
  import { loadCompiledCss } from './plugins/load-compiled-css.js';
7
7
  import { setupOptimizer } from './plugins/setup-optimizer.js';
8
8
  import { compileModule } from './plugins/compile-module.js';
9
- import { svelteInspector } from '@sveltejs/vite-plugin-svelte-inspector';
9
+ import { svelteInspector } from './plugins/inspector/index.js';
10
10
  import { loadCustom } from './plugins/load-custom.js';
11
11
  import { hotUpdate } from './plugins/hot-update.js';
12
12
 
@@ -34,7 +34,7 @@ export function svelte(inlineOptions) {
34
34
  compile(api),
35
35
  compileModule(api),
36
36
  hotUpdate(api),
37
- svelteInspector()
37
+ svelteInspector(api)
38
38
  ];
39
39
  }
40
40
 
@@ -1,6 +1,5 @@
1
1
  import process from 'node:process';
2
2
  import { isDebugNamespaceEnabled, log } from '../utils/log.js';
3
- import * as vite from 'vite';
4
3
  import { VitePluginSvelteStats } from '../utils/vite-plugin-svelte-stats.js';
5
4
  import {
6
5
  buildExtraViteConfig,
@@ -13,25 +12,12 @@ import {
13
12
  import { buildIdFilter, buildIdParser } from '../utils/id.js';
14
13
  import { createCompileSvelte } from '../utils/compile.js';
15
14
 
16
- // @ts-ignore rolldownVersion
17
- const { version: viteVersion, rolldownVersion } = vite;
18
-
19
15
  /**
20
16
  * @param {Partial<import('../public.d.ts').Options>} [inlineOptions]
21
17
  * @param {import('../types/plugin-api.d.ts').PluginAPI} api
22
18
  * @returns {import('vite').Plugin}
23
19
  */
24
20
  export function configure(api, inlineOptions) {
25
- if (rolldownVersion) {
26
- log.warn.once(
27
- `!!! Support for vite 8 beta in vite-plugin-svelte is experimental (rolldown: ${rolldownVersion}, vite: ${viteVersion}) !!!
28
- See https://github.com/sveltejs/vite-plugin-svelte/issues/1143 for a list of known issues and to report feedback.`.replace(
29
- /\t+/g,
30
- '\t'
31
- )
32
- );
33
- }
34
-
35
21
  validateInlineOptions(inlineOptions);
36
22
 
37
23
  /**
@@ -72,7 +58,6 @@ export function configure(api, inlineOptions) {
72
58
  }
73
59
 
74
60
  api.filter = buildIdFilter(options);
75
- api.idFilter = api.filter;
76
61
  api.idParser = buildIdParser(options);
77
62
  api.compileSvelte = createCompileSvelte();
78
63
  log.debug('resolved options', api.options, 'config');
@@ -0,0 +1,123 @@
1
+ import { normalizePath } from 'vite';
2
+ import fs from 'node:fs';
3
+ import path from 'node:path';
4
+ import { fileURLToPath } from 'node:url';
5
+ import { defaultInspectorOptions, parseEnvironmentOptions } from './options.js';
6
+ import { log } from '../../utils/log.js';
7
+
8
+ /**
9
+ * @param {string} url
10
+ * @returns {string} url without query params or hash
11
+ */
12
+ function cleanUrl(url) {
13
+ return url.replace(/[?#].*$/s, '');
14
+ }
15
+
16
+ function getInspectorPath() {
17
+ const pluginPath = normalizePath(path.dirname(fileURLToPath(import.meta.url)));
18
+ return pluginPath.replace(
19
+ /\/vite-plugin-svelte\/src\/plugins\/inspector$/,
20
+ '/vite-plugin-svelte/src/plugins/inspector/runtime/'
21
+ );
22
+ }
23
+
24
+ /**
25
+ * @param {import('../../types/plugin-api.d.ts').PluginAPI} api
26
+ * @returns {import('vite').Plugin}
27
+ */
28
+ export function svelteInspector(api) {
29
+ const inspectorPath = getInspectorPath();
30
+ log.debug(`svelte inspector path: ${inspectorPath}`, null, 'inspector');
31
+
32
+ /** @type {import('../../public.d.ts').InspectorOptions} */
33
+ let inspectorOptions;
34
+ let disabled = false;
35
+
36
+ return {
37
+ name: 'vite-plugin-svelte-inspector',
38
+ apply: 'serve',
39
+ enforce: 'pre',
40
+
41
+ applyToEnvironment(env) {
42
+ return !disabled && env.config.consumer === 'client';
43
+ },
44
+
45
+ configResolved(config) {
46
+ const environmentOptions = parseEnvironmentOptions(config);
47
+ if (environmentOptions === false) {
48
+ log.debug('environment options set to false, inspector disabled', null, 'inspector');
49
+ disabled = true;
50
+ return;
51
+ }
52
+ const configFileOptions = api.options?.inspector;
53
+
54
+ if (!configFileOptions && !environmentOptions) {
55
+ log.debug('no inspector options found, inspector disabled', null, 'inspector');
56
+ disabled = true;
57
+ return;
58
+ }
59
+
60
+ if (environmentOptions === true) {
61
+ inspectorOptions = defaultInspectorOptions;
62
+ } else {
63
+ inspectorOptions = {
64
+ ...defaultInspectorOptions,
65
+ ...(typeof configFileOptions === 'object' ? configFileOptions : {}),
66
+ ...(environmentOptions || {})
67
+ };
68
+ }
69
+
70
+ inspectorOptions.__internal = {
71
+ base: config.base?.replace(/\/$/, '') || ''
72
+ };
73
+ },
74
+ resolveId: {
75
+ filter: {
76
+ id: /^virtual:svelte-inspector-/
77
+ },
78
+ async handler(id) {
79
+ if (disabled) {
80
+ return;
81
+ }
82
+ if (id === 'virtual:svelte-inspector-options') {
83
+ return id;
84
+ } else if (id.startsWith('virtual:svelte-inspector-path:') && !id.includes('..')) {
85
+ return id.replace('virtual:svelte-inspector-path:', inspectorPath);
86
+ }
87
+ }
88
+ },
89
+ load: {
90
+ filter: {
91
+ id: {
92
+ include: [`${inspectorPath}/**`, /^virtual:svelte-inspector-options$/],
93
+ exclude: [/style&lang\.css$/]
94
+ }
95
+ },
96
+ async handler(id) {
97
+ if (disabled) {
98
+ return;
99
+ }
100
+ if (id === 'virtual:svelte-inspector-options') {
101
+ return `export default ${JSON.stringify(inspectorOptions ?? {})}`;
102
+ } else if (id.startsWith(inspectorPath)) {
103
+ // read file ourselves to avoid getting shut out by vites fs.allow check
104
+ const file = cleanUrl(id);
105
+ if (fs.existsSync(file)) {
106
+ return await fs.promises.readFile(file, 'utf-8');
107
+ } else {
108
+ log.error(`failed to find svelte-inspector: ${id}`, null, 'inspector');
109
+ }
110
+ }
111
+ }
112
+ },
113
+ transform: {
114
+ filter: { id: /vite\/dist\/client\/client\.mjs(?:\?|$)/ },
115
+ handler(code) {
116
+ if (disabled) {
117
+ return;
118
+ }
119
+ return { code: `${code}\nimport('virtual:svelte-inspector-path:load-inspector.js')` };
120
+ }
121
+ }
122
+ };
123
+ }
@@ -0,0 +1,65 @@
1
+ import process from 'node:process';
2
+ import { loadEnv } from 'vite';
3
+ import { log } from '../../utils/log.js';
4
+
5
+ /** @type {import('../../public.d.ts').InspectorOptions} */
6
+ export const defaultInspectorOptions = {
7
+ toggleKeyCombo: 'alt-x',
8
+ navKeys: { parent: 'ArrowUp', child: 'ArrowDown', next: 'ArrowRight', prev: 'ArrowLeft' },
9
+ escapeKeys: ['Backspace', 'Escape'],
10
+ openKey: 'Enter',
11
+ holdMode: true,
12
+ showToggleButton: 'active',
13
+ toggleButtonPos: 'top-right',
14
+ customStyles: true
15
+ };
16
+
17
+ /**
18
+ * @param {import('vite').ResolvedConfig} config
19
+ * @returns {Partial<import('../../public.d.ts').InspectorOptions> | boolean | void}
20
+ */
21
+ export function parseEnvironmentOptions(config) {
22
+ const env = loadEnv(config.mode, config.envDir ?? process.cwd(), 'SVELTE_INSPECTOR');
23
+ const options = env?.SVELTE_INSPECTOR_OPTIONS;
24
+ const toggle = env?.SVELTE_INSPECTOR_TOGGLE;
25
+ if (options) {
26
+ try {
27
+ const parsed = JSON.parse(options);
28
+ const parsedType = typeof parsed;
29
+ if (parsedType === 'boolean') {
30
+ return parsed;
31
+ } else if (parsedType === 'object') {
32
+ if (Array.isArray(parsed)) {
33
+ throw new Error('invalid type, expected object map but got array');
34
+ }
35
+ const parsedKeys = Object.keys(parsed);
36
+ const defaultKeys = Object.keys(defaultInspectorOptions);
37
+ const unknownKeys = parsedKeys.filter((k) => !defaultKeys.includes(k));
38
+ if (unknownKeys.length) {
39
+ log.warn(
40
+ `[vite-plugin-svelte-inspector] ignoring unknown options in environment SVELTE_INSPECTOR_OPTIONS: ${unknownKeys.join(
41
+ ', '
42
+ )}`,
43
+ null,
44
+ 'inspector'
45
+ );
46
+ for (const key of unknownKeys) {
47
+ delete parsed[key];
48
+ }
49
+ }
50
+ log.debug('loaded environment config', parsed, 'inspector');
51
+ return parsed;
52
+ }
53
+ } catch (e) {
54
+ config.logger.error(
55
+ `[vite-plugin-svelte-inspector] failed to parse inspector options from environment SVELTE_INSPECTOR_OPTIONS="${options}"\n${e}`
56
+ );
57
+ }
58
+ } else if (toggle) {
59
+ const keyConfig = {
60
+ toggleKeyCombo: toggle
61
+ };
62
+ log.debug('loaded environment config', keyConfig, 'inspector');
63
+ return keyConfig;
64
+ }
65
+ }
@@ -0,0 +1,411 @@
1
+ <svelte:options runes={true} />
2
+
3
+ <script>
4
+ // do not use TS here so that this component works in non-ts projects too
5
+ import { onMount } from 'svelte';
6
+
7
+ import options from 'virtual:svelte-inspector-options';
8
+ const toggle_combo = options.toggleKeyCombo?.toLowerCase().split('-');
9
+ const escape_keys = options.escapeKeys?.map((k) => k.toLowerCase());
10
+ const nav_keys = Object.values(options.navKeys).map((k) => k?.toLowerCase());
11
+ const open_key = options.openKey?.toLowerCase();
12
+
13
+ let enabled = $state(false);
14
+ let has_opened = $state(false);
15
+
16
+ const icon = `data:image/svg+xml;base64,${btoa(
17
+ `
18
+ <svg xmlns="http://www.w3.org/2000/svg" width="21" height="25" viewBox="0 0 107 128">
19
+ <title>svelte-inspector-logo</title>
20
+ <path d="M94.1566,22.8189c-10.4-14.8851-30.94-19.2971-45.7914-9.8348L22.2825,29.6078A29.9234,29.9234,0,0,0,8.7639,49.6506a31.5136,31.5136,0,0,0,3.1076,20.2318A30.0061,30.0061,0,0,0,7.3953,81.0653a31.8886,31.8886,0,0,0,5.4473,24.1157c10.4022,14.8865,30.9423,19.2966,45.7914,9.8348L84.7167,98.3921A29.9177,29.9177,0,0,0,98.2353,78.3493,31.5263,31.5263,0,0,0,95.13,58.117a30,30,0,0,0,4.4743-11.1824,31.88,31.88,0,0,0-5.4473-24.1157" style="fill:#ff3e00"/><path d="M45.8171,106.5815A20.7182,20.7182,0,0,1,23.58,98.3389a19.1739,19.1739,0,0,1-3.2766-14.5025,18.1886,18.1886,0,0,1,.6233-2.4357l.4912-1.4978,1.3363.9815a33.6443,33.6443,0,0,0,10.203,5.0978l.9694.2941-.0893.9675a5.8474,5.8474,0,0,0,1.052,3.8781,6.2389,6.2389,0,0,0,6.6952,2.485,5.7449,5.7449,0,0,0,1.6021-.7041L69.27,76.281a5.4306,5.4306,0,0,0,2.4506-3.631,5.7948,5.7948,0,0,0-.9875-4.3712,6.2436,6.2436,0,0,0-6.6978-2.4864,5.7427,5.7427,0,0,0-1.6.7036l-9.9532,6.3449a19.0329,19.0329,0,0,1-5.2965,2.3259,20.7181,20.7181,0,0,1-22.2368-8.2427,19.1725,19.1725,0,0,1-3.2766-14.5024,17.9885,17.9885,0,0,1,8.13-12.0513L55.8833,23.7472a19.0038,19.0038,0,0,1,5.3-2.3287A20.7182,20.7182,0,0,1,83.42,29.6611a19.1739,19.1739,0,0,1,3.2766,14.5025,18.4,18.4,0,0,1-.6233,2.4357l-.4912,1.4978-1.3356-.98a33.6175,33.6175,0,0,0-10.2037-5.1l-.9694-.2942.0893-.9675a5.8588,5.8588,0,0,0-1.052-3.878,6.2389,6.2389,0,0,0-6.6952-2.485,5.7449,5.7449,0,0,0-1.6021.7041L37.73,51.719a5.4218,5.4218,0,0,0-2.4487,3.63,5.7862,5.7862,0,0,0,.9856,4.3717,6.2437,6.2437,0,0,0,6.6978,2.4864,5.7652,5.7652,0,0,0,1.602-.7041l9.9519-6.3425a18.978,18.978,0,0,1,5.2959-2.3278,20.7181,20.7181,0,0,1,22.2368,8.2427,19.1725,19.1725,0,0,1,3.2766,14.5024,17.9977,17.9977,0,0,1-8.13,12.0532L51.1167,104.2528a19.0038,19.0038,0,0,1-5.3,2.3287" style="fill:#fff"/>
21
+ <polygon points="0,0 15,40 40,20" stroke="#ff3e00" fill="#ff3e00"></polygon>
22
+ </svg>
23
+ `
24
+ .replace(/[\n\r\t\s]+/g, ' ')
25
+ .trim()
26
+ )}`;
27
+
28
+ // location of code in file
29
+ let file_loc = $state();
30
+ // cursor pos and width for file_loc overlay positioning
31
+ let x = $state(),
32
+ y = $state(),
33
+ w = $state();
34
+
35
+ let active_el = $state();
36
+
37
+ let hold_start_ts = $state();
38
+
39
+ let show_toggle = $derived(
40
+ options.showToggleButton === 'always' || (options.showToggleButton === 'active' && enabled)
41
+ );
42
+
43
+ function mousemove(e) {
44
+ x = e.x;
45
+ y = e.y;
46
+ }
47
+
48
+ function find_selectable_parent(el, include_self = false) {
49
+ if (!include_self) {
50
+ el = el.parentNode;
51
+ }
52
+ while (el) {
53
+ if (is_selectable(el)) {
54
+ return el;
55
+ }
56
+ el = el.parentNode;
57
+ }
58
+ }
59
+
60
+ function find_selectable_child(el) {
61
+ return [...el.querySelectorAll('*')].find(is_selectable);
62
+ }
63
+
64
+ function find_selectable_sibling(el, prev = false) {
65
+ do {
66
+ el = prev ? el.previousElementSibling : el.nextElementSibling;
67
+ if (is_selectable(el)) {
68
+ return el;
69
+ }
70
+ } while (el);
71
+ }
72
+
73
+ function find_selectable_for_nav(key) {
74
+ const el = active_el;
75
+ if (!el) {
76
+ return find_selectable_child(document?.body);
77
+ }
78
+ switch (key) {
79
+ case options.navKeys.parent:
80
+ return find_selectable_parent(el);
81
+ case options.navKeys.child:
82
+ return find_selectable_child(el);
83
+ case options.navKeys.next:
84
+ return find_selectable_sibling(el) || find_selectable_parent(el);
85
+ case options.navKeys.prev:
86
+ return find_selectable_sibling(el, true) || find_selectable_parent(el);
87
+ default:
88
+ return;
89
+ }
90
+ }
91
+
92
+ function is_selectable(el) {
93
+ const file = el?.__svelte_meta?.loc?.file;
94
+ if (!file || file.includes('node_modules/')) {
95
+ return false; // no file or 3rd party
96
+ }
97
+ const id = el.getAttribute('id');
98
+ if (id === 'svelte-announcer' || id?.startsWith('svelte-inspector-')) {
99
+ return false; // ignore some elements by id that would be selectable from keyboard nav otherwise
100
+ }
101
+ return true;
102
+ }
103
+
104
+ function mouseover({ target }) {
105
+ const el = find_selectable_parent(target, true);
106
+ activate(el, false);
107
+ }
108
+
109
+ function activate(el, set_bubble_pos = true) {
110
+ if (options.customStyles && el !== active_el) {
111
+ if (active_el) {
112
+ active_el.classList.remove('svelte-inspector-active-target');
113
+ }
114
+ if (el) {
115
+ el.classList.add('svelte-inspector-active-target');
116
+ }
117
+ }
118
+ if (el) {
119
+ const { file, line, column } = el.__svelte_meta.loc;
120
+ file_loc = `${file}:${line + 1}:${column + 1}`;
121
+ } else {
122
+ file_loc = null;
123
+ }
124
+ active_el = el;
125
+ if (set_bubble_pos) {
126
+ const pos = el.getBoundingClientRect();
127
+ x = Math.ceil(pos.left);
128
+ y = Math.ceil(pos.bottom - 20);
129
+ }
130
+ }
131
+
132
+ function open_editor(e) {
133
+ if (file_loc) {
134
+ stop(e);
135
+ fetch(`${options.__internal.base}/__open-in-editor?file=${encodeURIComponent(file_loc)}`);
136
+ has_opened = true;
137
+ if (options.holdMode && is_holding()) {
138
+ disable();
139
+ }
140
+ }
141
+ }
142
+
143
+ function is_active(key, e) {
144
+ switch (key) {
145
+ case 'shift':
146
+ case 'control':
147
+ case 'alt':
148
+ case 'meta':
149
+ return e.getModifierState(key.charAt(0).toUpperCase() + key.slice(1));
150
+ default:
151
+ return key === e.code.replace(/^Key/, '').toLowerCase() || key === e.key.toLowerCase();
152
+ }
153
+ }
154
+
155
+ function is_combo(e) {
156
+ return toggle_combo?.every((k) => is_active(k, e));
157
+ }
158
+
159
+ function is_escape(e) {
160
+ return escape_keys?.some((k) => is_active(k, e));
161
+ }
162
+
163
+ function is_toggle(e) {
164
+ return toggle_combo?.some((k) => is_active(k, e));
165
+ }
166
+
167
+ function is_nav(e) {
168
+ return nav_keys?.some((k) => is_active(k, e));
169
+ }
170
+
171
+ function is_open(e) {
172
+ return open_key && is_active(open_key, e);
173
+ }
174
+
175
+ function is_holding() {
176
+ return hold_start_ts && Date.now() - hold_start_ts > 250;
177
+ }
178
+
179
+ function stop(e) {
180
+ e.preventDefault();
181
+ e.stopPropagation();
182
+ e.stopImmediatePropagation();
183
+ }
184
+
185
+ function keydown(e) {
186
+ if (e.repeat || e.key == null || (!enabled && !is_toggle(e))) {
187
+ return;
188
+ }
189
+ if (is_combo(e)) {
190
+ toggle();
191
+ if (options.holdMode && enabled) {
192
+ hold_start_ts = Date.now();
193
+ }
194
+ } else if (enabled) {
195
+ if (is_nav(e)) {
196
+ const el = find_selectable_for_nav(e.key);
197
+ if (el) {
198
+ activate(el);
199
+ stop(e);
200
+ }
201
+ } else if (is_open(e)) {
202
+ open_editor(e);
203
+ } else if (is_holding() || is_escape(e)) {
204
+ // is_holding() checks for unhandled additional key pressed
205
+ // while holding the toggle keys, which is possibly another
206
+ // shortcut (e.g. 'meta-shift-x'), so disable again.
207
+
208
+ disable();
209
+ }
210
+ }
211
+ }
212
+
213
+ function keyup(e) {
214
+ if (e.repeat || e.key == null || !enabled) {
215
+ return;
216
+ }
217
+ if (is_toggle(e)) {
218
+ if (is_holding()) {
219
+ disable();
220
+ } else {
221
+ hold_start_ts = null;
222
+ }
223
+ }
224
+ }
225
+
226
+ function toggle() {
227
+ if (enabled) {
228
+ disable();
229
+ } else {
230
+ enable();
231
+ }
232
+ }
233
+
234
+ function listeners(body, enabled) {
235
+ const l = enabled ? body.addEventListener : body.removeEventListener;
236
+ l('mousemove', mousemove);
237
+ l('mouseover', mouseover);
238
+ l('click', open_editor, true);
239
+ }
240
+
241
+ function enable() {
242
+ enabled = true;
243
+ const b = document.body;
244
+ if (options.customStyles) {
245
+ b.classList.add('svelte-inspector-enabled');
246
+ }
247
+ listeners(b, enabled);
248
+ activate_initial_el();
249
+ }
250
+
251
+ function activate_initial_el() {
252
+ const hov = innermost_hover_el();
253
+ let el = find_selectable_parent(hov, true);
254
+ if (!el) {
255
+ const act = document.activeElement;
256
+ el = find_selectable_parent(act, true);
257
+ }
258
+ if (!el) {
259
+ el = find_selectable_child(document.body);
260
+ }
261
+ if (el) {
262
+ activate(el);
263
+ }
264
+ }
265
+
266
+ function innermost_hover_el() {
267
+ let e = document.body.querySelector(':hover');
268
+ let result;
269
+ while (e) {
270
+ result = e;
271
+ e = e.querySelector(':hover');
272
+ }
273
+ return result;
274
+ }
275
+
276
+ function disable() {
277
+ enabled = false;
278
+ has_opened = false;
279
+ hold_start_ts = null;
280
+ const b = document.body;
281
+ listeners(b, enabled);
282
+ if (options.customStyles) {
283
+ b.classList.remove('svelte-inspector-enabled');
284
+ active_el?.classList.remove('svelte-inspector-active-target');
285
+ }
286
+ active_el = null;
287
+ }
288
+
289
+ function visibilityChange() {
290
+ if (document.visibilityState === 'hidden') {
291
+ onLeave();
292
+ }
293
+ }
294
+
295
+ function onLeave() {
296
+ // disable if a file has been opened or combo is held
297
+ if (enabled && (has_opened || hold_start_ts)) {
298
+ disable();
299
+ }
300
+ }
301
+
302
+ onMount(() => {
303
+ const s = document.createElement('style');
304
+ s.setAttribute('type', 'text/css');
305
+ s.setAttribute('id', 'svelte-inspector-style');
306
+ s.textContent = `:root { --svelte-inspector-icon: url(${icon})};`;
307
+ document.head.append(s);
308
+ if (toggle_combo) {
309
+ document.body.addEventListener('keydown', keydown);
310
+ if (options.holdMode) {
311
+ document.body.addEventListener('keyup', keyup);
312
+ }
313
+ }
314
+ document.addEventListener('visibilitychange', visibilityChange);
315
+ document.documentElement.addEventListener('mouseleave', onLeave);
316
+ return () => {
317
+ // make sure we get rid of everything
318
+ disable();
319
+ const s = document.head.querySelector('#svelte-inspector-style');
320
+ if (s) {
321
+ document.head.removeChild(s);
322
+ }
323
+ if (toggle_combo) {
324
+ document.body.removeEventListener('keydown', keydown);
325
+ if (options.holdMode) {
326
+ document.body.removeEventListener('keyup', keyup);
327
+ }
328
+ }
329
+ document.removeEventListener('visibilitychange', visibilityChange);
330
+ document.documentElement.removeEventListener('mouseleave', onLeave);
331
+ };
332
+ });
333
+ </script>
334
+
335
+ {#if show_toggle}
336
+ <button
337
+ id="svelte-inspector-toggle"
338
+ class:enabled
339
+ style={`background-image: var(--svelte-inspector-icon);${options.toggleButtonPos
340
+ .split('-')
341
+ .map((p) => `${p}: 8px;`)
342
+ .join('')}`}
343
+ onclick={() => toggle()}
344
+ aria-label={`${enabled ? 'disable' : 'enable'} svelte-inspector`}
345
+ ></button>
346
+ {/if}
347
+ {#if enabled && active_el && file_loc}
348
+ {@const loc = active_el.__svelte_meta.loc}
349
+ <div
350
+ id="svelte-inspector-overlay"
351
+ style:left="{Math.min(x + 3, document.documentElement.clientWidth - w - 10)}px"
352
+ style:top="{document.documentElement.clientHeight < y + 50 ? y - 30 : y + 30}px"
353
+ bind:offsetWidth={w}
354
+ >
355
+ &lt;{active_el.tagName.toLowerCase()}&gt;&nbsp;{file_loc}
356
+ </div>
357
+ <div id="svelte-inspector-announcer" aria-live="assertive" aria-atomic="true">
358
+ {active_el.tagName.toLowerCase()} in file {loc.file} on line {loc.line} column {loc.column}
359
+ </div>
360
+ {/if}
361
+
362
+ <style>
363
+ :global(body.svelte-inspector-enabled *) {
364
+ cursor: var(--svelte-inspector-icon), crosshair !important;
365
+ }
366
+ :global(.svelte-inspector-active-target) {
367
+ outline: 2px dashed #ff3e00 !important;
368
+ }
369
+
370
+ #svelte-inspector-overlay {
371
+ position: fixed;
372
+ background-color: rgba(0, 0, 0, 0.8);
373
+ color: #fff;
374
+ padding: 2px 4px;
375
+ border-radius: 5px;
376
+ z-index: 999999;
377
+ pointer-events: none;
378
+ }
379
+
380
+ #svelte-inspector-toggle {
381
+ all: unset;
382
+ border: 1px solid #ff3e00;
383
+ border-radius: 8px;
384
+ position: fixed;
385
+ height: 32px;
386
+ width: 32px;
387
+ background-color: white;
388
+ background-position: center;
389
+ background-repeat: no-repeat;
390
+ cursor: pointer;
391
+ }
392
+
393
+ #svelte-inspector-announcer {
394
+ position: absolute;
395
+ left: 0px;
396
+ top: 0px;
397
+ clip: rect(0px, 0px, 0px, 0px);
398
+ clip-path: inset(50%);
399
+ overflow: hidden;
400
+ white-space: nowrap;
401
+ width: 1px;
402
+ height: 1px;
403
+ }
404
+
405
+ #svelte-inspector-toggle:not(.enabled) {
406
+ filter: grayscale(1);
407
+ }
408
+ #svelte-inspector-toggle:hover {
409
+ background-color: #facece;
410
+ }
411
+ </style>