jupyterlab_vscode_icons_extension 1.0.37

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/lib/index.js ADDED
@@ -0,0 +1,666 @@
1
+ import { ISettingRegistry } from '@jupyterlab/settingregistry';
2
+ import { LabIcon, markdownIcon } from '@jupyterlab/ui-components';
3
+ import { getIconSVG } from './icons';
4
+ const PLUGIN_ID = 'jupyterlab_vscode_icons_extension:plugin';
5
+ /**
6
+ * Create a LabIcon from vscode-icons SVG data
7
+ */
8
+ function createLabIcon(iconName) {
9
+ const svgBody = getIconSVG(iconName);
10
+ const svgStr = `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">${svgBody}</svg>`;
11
+ return new LabIcon({
12
+ name: `vscode-icons:${iconName}`,
13
+ svgstr: svgStr
14
+ });
15
+ }
16
+ // Comprehensive file type configurations grouped by category
17
+ const fileTypeConfigs = [
18
+ // Programming Languages
19
+ {
20
+ extensions: ['.js', '.mjs', '.cjs'],
21
+ iconName: 'file-type-js-official',
22
+ group: 'enableLanguageIcons'
23
+ },
24
+ {
25
+ extensions: ['.jsx'],
26
+ iconName: 'file-type-reactjs',
27
+ group: 'enableLanguageIcons'
28
+ },
29
+ {
30
+ extensions: ['.ts', '.mts', '.cts'],
31
+ iconName: 'file-type-typescript-official',
32
+ group: 'enableLanguageIcons'
33
+ },
34
+ {
35
+ extensions: ['.tsx'],
36
+ iconName: 'file-type-reactts',
37
+ group: 'enableLanguageIcons'
38
+ },
39
+ {
40
+ extensions: ['.py', '.pyw', '.pyx'],
41
+ iconName: 'file-type-python',
42
+ group: 'enableLanguageIcons'
43
+ },
44
+ {
45
+ extensions: ['.ipynb'],
46
+ iconName: 'file-type-jupyter',
47
+ group: 'enableLanguageIcons'
48
+ },
49
+ {
50
+ extensions: ['.java'],
51
+ iconName: 'file-type-java',
52
+ group: 'enableLanguageIcons'
53
+ },
54
+ {
55
+ extensions: ['.c'],
56
+ iconName: 'file-type-c',
57
+ group: 'enableLanguageIcons'
58
+ },
59
+ {
60
+ extensions: ['.cpp', '.cc', '.cxx'],
61
+ iconName: 'file-type-cpp',
62
+ group: 'enableLanguageIcons'
63
+ },
64
+ {
65
+ extensions: ['.h', '.hpp'],
66
+ iconName: 'file-type-c',
67
+ group: 'enableLanguageIcons'
68
+ },
69
+ {
70
+ extensions: ['.cs'],
71
+ iconName: 'file-type-csharp',
72
+ group: 'enableLanguageIcons'
73
+ },
74
+ {
75
+ extensions: ['.go'],
76
+ iconName: 'file-type-go',
77
+ group: 'enableLanguageIcons'
78
+ },
79
+ {
80
+ extensions: ['.rs'],
81
+ iconName: 'file-type-rust',
82
+ group: 'enableLanguageIcons'
83
+ },
84
+ {
85
+ extensions: ['.rb'],
86
+ iconName: 'file-type-ruby',
87
+ group: 'enableLanguageIcons'
88
+ },
89
+ {
90
+ extensions: ['.php'],
91
+ iconName: 'file-type-php',
92
+ group: 'enableLanguageIcons'
93
+ },
94
+ {
95
+ extensions: ['.swift'],
96
+ iconName: 'file-type-swift',
97
+ group: 'enableLanguageIcons'
98
+ },
99
+ {
100
+ extensions: ['.kt', '.kts'],
101
+ iconName: 'file-type-kotlin',
102
+ group: 'enableLanguageIcons'
103
+ },
104
+ {
105
+ extensions: ['.r', '.R'],
106
+ iconName: 'file-type-r',
107
+ group: 'enableLanguageIcons'
108
+ },
109
+ {
110
+ extensions: ['.jl'],
111
+ iconName: 'file-type-julia',
112
+ group: 'enableLanguageIcons'
113
+ },
114
+ {
115
+ extensions: ['.scala'],
116
+ iconName: 'file-type-scala',
117
+ group: 'enableLanguageIcons'
118
+ },
119
+ {
120
+ extensions: ['.lua'],
121
+ iconName: 'file-type-lua',
122
+ group: 'enableLanguageIcons'
123
+ },
124
+ {
125
+ extensions: ['.pl', '.pm'],
126
+ iconName: 'file-type-perl',
127
+ group: 'enableLanguageIcons'
128
+ },
129
+ {
130
+ extensions: ['.sh', '.bash', '.zsh'],
131
+ iconName: 'file-type-shell',
132
+ group: 'enableLanguageIcons'
133
+ },
134
+ {
135
+ extensions: ['.bat', '.cmd'],
136
+ iconName: 'file-type-shell',
137
+ group: 'enableLanguageIcons'
138
+ },
139
+ {
140
+ extensions: ['.ps1'],
141
+ iconName: 'file-type-powershell',
142
+ group: 'enableLanguageIcons'
143
+ },
144
+ {
145
+ extensions: ['.vbs', '.vbe'],
146
+ iconName: 'file-type-vba',
147
+ group: 'enableLanguageIcons'
148
+ },
149
+ {
150
+ extensions: ['.sql'],
151
+ iconName: 'file-type-sql',
152
+ group: 'enableLanguageIcons'
153
+ },
154
+ // Web Development
155
+ {
156
+ extensions: ['.html', '.htm'],
157
+ iconName: 'file-type-html',
158
+ group: 'enableWebIcons'
159
+ },
160
+ {
161
+ extensions: ['.css'],
162
+ iconName: 'file-type-css',
163
+ group: 'enableWebIcons'
164
+ },
165
+ {
166
+ extensions: ['.scss'],
167
+ iconName: 'file-type-scss',
168
+ group: 'enableWebIcons'
169
+ },
170
+ {
171
+ extensions: ['.sass'],
172
+ iconName: 'file-type-sass',
173
+ group: 'enableWebIcons'
174
+ },
175
+ {
176
+ extensions: ['.less'],
177
+ iconName: 'file-type-less',
178
+ group: 'enableWebIcons'
179
+ },
180
+ {
181
+ extensions: ['.vue'],
182
+ iconName: 'file-type-vue',
183
+ group: 'enableWebIcons'
184
+ },
185
+ {
186
+ extensions: ['.svelte'],
187
+ iconName: 'file-type-svelte',
188
+ group: 'enableWebIcons'
189
+ },
190
+ // Data Formats
191
+ {
192
+ extensions: ['.toml'],
193
+ iconName: 'file-type-toml',
194
+ group: 'enableDataIcons'
195
+ },
196
+ {
197
+ extensions: ['.xml'],
198
+ iconName: 'file-type-xml',
199
+ group: 'enableDataIcons'
200
+ },
201
+ {
202
+ extensions: ['.csv', '.tsv'],
203
+ iconName: 'file-type-csv',
204
+ group: 'enableDataIcons'
205
+ },
206
+ // Documentation
207
+ {
208
+ extensions: ['.md'],
209
+ iconName: 'file-type-markdown',
210
+ group: 'enableDocIcons'
211
+ },
212
+ {
213
+ extensions: ['.mdx'],
214
+ iconName: 'file-type-mdx',
215
+ group: 'enableDocIcons'
216
+ },
217
+ {
218
+ extensions: ['.rst'],
219
+ iconName: 'file-type-rst',
220
+ group: 'enableDocIcons'
221
+ },
222
+ {
223
+ extensions: ['.txt'],
224
+ iconName: 'file-type-text',
225
+ group: 'enableDocIcons'
226
+ },
227
+ {
228
+ extensions: ['.pdf'],
229
+ iconName: 'file-type-pdf',
230
+ group: 'enableDocIcons'
231
+ },
232
+ // Config Files
233
+ {
234
+ extensions: ['.env'],
235
+ iconName: 'file-type-dotenv',
236
+ group: 'enableConfigIcons'
237
+ },
238
+ {
239
+ extensions: ['.ini'],
240
+ iconName: 'file-type-ini',
241
+ group: 'enableConfigIcons'
242
+ },
243
+ {
244
+ extensions: ['.cfg', '.conf'],
245
+ iconName: 'file-type-config',
246
+ group: 'enableConfigIcons'
247
+ },
248
+ {
249
+ pattern: '^(Dockerfile|dockerfile).*$',
250
+ extensions: [],
251
+ iconName: 'file-type-docker',
252
+ group: 'enableConfigIcons'
253
+ },
254
+ {
255
+ pattern: '^\\.git(ignore|modules|attributes)?$',
256
+ extensions: [],
257
+ iconName: 'file-type-git',
258
+ group: 'enableConfigIcons'
259
+ },
260
+ {
261
+ pattern: '^\\.dockerignore$',
262
+ extensions: [],
263
+ iconName: 'file-type-docker',
264
+ group: 'enableConfigIcons'
265
+ },
266
+ {
267
+ pattern: '^package\\.json$',
268
+ extensions: [],
269
+ iconName: 'file-type-npm',
270
+ group: 'enableConfigIcons'
271
+ },
272
+ {
273
+ pattern: '^package-lock\\.json$',
274
+ extensions: [],
275
+ iconName: 'file-type-npm',
276
+ group: 'enableConfigIcons'
277
+ },
278
+ {
279
+ pattern: '^yarn\\.lock$',
280
+ extensions: [],
281
+ iconName: 'file-type-yarn',
282
+ group: 'enableConfigIcons'
283
+ },
284
+ {
285
+ pattern: '^requirements\\.txt$',
286
+ extensions: [],
287
+ iconName: 'file-type-python',
288
+ group: 'enableConfigIcons'
289
+ },
290
+ {
291
+ pattern: '^pyproject\\.toml$',
292
+ extensions: [],
293
+ iconName: 'file-type-toml',
294
+ group: 'enableConfigIcons'
295
+ },
296
+ {
297
+ pattern: '^setup\\.py$',
298
+ extensions: [],
299
+ iconName: 'file-type-python',
300
+ group: 'enableConfigIcons'
301
+ },
302
+ {
303
+ pattern: '^Cargo\\.(toml|lock)$',
304
+ extensions: [],
305
+ iconName: 'file-type-rust',
306
+ group: 'enableConfigIcons'
307
+ },
308
+ {
309
+ pattern: '^Gemfile$',
310
+ extensions: [],
311
+ iconName: 'file-type-ruby',
312
+ group: 'enableConfigIcons'
313
+ },
314
+ {
315
+ extensions: ['.lnk'],
316
+ iconName: 'file-type-lnk',
317
+ group: 'enableConfigIcons'
318
+ },
319
+ // Images
320
+ {
321
+ extensions: ['.png', '.jpg', '.jpeg', '.gif', '.ico', '.webp', '.bmp'],
322
+ iconName: 'file-type-image',
323
+ group: 'enableImageIcons'
324
+ },
325
+ {
326
+ extensions: ['.svg'],
327
+ iconName: 'file-type-svg',
328
+ group: 'enableImageIcons'
329
+ }
330
+ ];
331
+ const plugin = {
332
+ id: PLUGIN_ID,
333
+ description: 'Jupyterlab extension with a shameless rip-off of the vscode-icons into our beloved environment',
334
+ autoStart: true,
335
+ optional: [ISettingRegistry],
336
+ activate: (app, settingRegistry) => {
337
+ const { docRegistry } = app;
338
+ // Function to inject CSS that overrides Jupytext icons
339
+ const injectIconOverrideCSS = () => {
340
+ // Get icons: Python (VSCode), Markdown (JupyterLab native), Claude (VSCode), README (custom)
341
+ const pythonIcon = createLabIcon('file-type-python');
342
+ const claudeIcon = createLabIcon('file-type-claude');
343
+ const markdownSvg = markdownIcon.svgstr;
344
+ // Custom README icon (purple filled circle with bold lowercase i - transparent cutout)
345
+ const readmeSvg = `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
346
+ <defs>
347
+ <mask id="readme-mask">
348
+ <circle cx="16" cy="16" r="12" fill="white"/>
349
+ <text x="16" y="22" font-size="20" font-weight="900" text-anchor="middle" fill="black" stroke="black" stroke-width="0.7" font-family="'Courier New', Courier, monospace">i</text>
350
+ </mask>
351
+ </defs>
352
+ <circle cx="16" cy="16" r="12" fill="#9826c8" mask="url(#readme-mask)"/>
353
+ </svg>`;
354
+ // Get SVG content
355
+ const pythonSvg = pythonIcon.svgstr;
356
+ const claudeSvg = claudeIcon.svgstr;
357
+ // Create base64 encoded data URIs
358
+ const pythonDataUri = `data:image/svg+xml;base64,${btoa(pythonSvg)}`;
359
+ const markdownDataUri = `data:image/svg+xml;base64,${btoa(markdownSvg)}`;
360
+ const claudeDataUri = `data:image/svg+xml;base64,${btoa(claudeSvg)}`;
361
+ const readmeDataUri = `data:image/svg+xml;base64,${btoa(readmeSvg)}`;
362
+ // Inject CSS that overrides icons for .py and .md files
363
+ // Note: Jupytext marks .py and .md files as type="notebook", so we need to
364
+ // use JavaScript to detect and mark these files for CSS targeting
365
+ const style = document.createElement('style');
366
+ style.id = 'vscode-icons-jupytext-override';
367
+ style.textContent = `
368
+ /* Override Python file icons (.py files shown as notebooks by Jupytext) */
369
+ .jp-DirListing-item[data-file-type="notebook"][data-jupytext-py] .jp-DirListing-itemIcon svg,
370
+ .jp-DirListing-item[data-file-type="notebook"][data-jupytext-py] .jp-DirListing-itemIcon img {
371
+ display: none !important;
372
+ }
373
+ .jp-DirListing-item[data-file-type="notebook"][data-jupytext-py] .jp-DirListing-itemIcon::before {
374
+ content: '';
375
+ display: inline-block;
376
+ width: 18px;
377
+ height: 18px;
378
+ background-image: url('${pythonDataUri}');
379
+ background-size: contain;
380
+ background-repeat: no-repeat;
381
+ background-position: center;
382
+ }
383
+
384
+ /* Override Markdown file icons (.md files shown as notebooks by Jupytext) with JupyterLab native markdown icon */
385
+ .jp-DirListing-item[data-file-type="notebook"][data-jupytext-md] .jp-DirListing-itemIcon svg,
386
+ .jp-DirListing-item[data-file-type="notebook"][data-jupytext-md] .jp-DirListing-itemIcon img {
387
+ display: none !important;
388
+ }
389
+ .jp-DirListing-item[data-file-type="notebook"][data-jupytext-md] .jp-DirListing-itemIcon::before {
390
+ content: '';
391
+ display: inline-block;
392
+ width: 18px;
393
+ height: 18px;
394
+ background-image: url('${markdownDataUri}');
395
+ background-size: contain;
396
+ background-repeat: no-repeat;
397
+ background-position: center;
398
+ }
399
+
400
+ /* Override CLAUDE.md file icon with VSCode Claude icon (purple tint) */
401
+ .jp-DirListing-item[data-file-type="notebook"][data-claude-md] .jp-DirListing-itemIcon svg,
402
+ .jp-DirListing-item[data-file-type="notebook"][data-claude-md] .jp-DirListing-itemIcon img {
403
+ display: none !important;
404
+ }
405
+ .jp-DirListing-item[data-file-type="notebook"][data-claude-md] .jp-DirListing-itemIcon::before {
406
+ content: '';
407
+ display: inline-block;
408
+ width: 18px;
409
+ height: 18px;
410
+ background-image: url('${claudeDataUri}');
411
+ background-size: contain;
412
+ background-repeat: no-repeat;
413
+ background-position: center;
414
+ filter: hue-rotate(270deg) saturate(1.5) brightness(1.1);
415
+ }
416
+
417
+ /* Override README.md file icon with custom info icon */
418
+ .jp-DirListing-item[data-file-type="notebook"][data-readme-md] .jp-DirListing-itemIcon svg,
419
+ .jp-DirListing-item[data-file-type="notebook"][data-readme-md] .jp-DirListing-itemIcon img {
420
+ display: none !important;
421
+ }
422
+ .jp-DirListing-item[data-file-type="notebook"][data-readme-md] .jp-DirListing-itemIcon::before {
423
+ content: '';
424
+ display: inline-block;
425
+ width: 20px;
426
+ height: 20px;
427
+ background-image: url('${readmeDataUri}');
428
+ background-size: contain;
429
+ background-repeat: no-repeat;
430
+ background-position: center;
431
+ }
432
+ `;
433
+ // Add CSS to make JavaScript icons less bright
434
+ style.textContent += `
435
+ /* Reduce brightness of JavaScript icons */
436
+ .jp-DirListing-item[data-file-type*="js"] .jp-DirListing-itemIcon svg,
437
+ .jp-DirListing-item[data-file-type="vscode-file-type-js-official"] .jp-DirListing-itemIcon svg {
438
+ filter: brightness(0.85) saturate(0.85);
439
+ }
440
+
441
+ /* Color shell script icons - pale red for Linux shells (.sh, .bash, .zsh) with inverted colors */
442
+ .jp-DirListing-item[data-shell-type="linux"] .jp-DirListing-itemIcon svg {
443
+ filter: invert(1) hue-rotate(130deg) saturate(0.8) brightness(0.9);
444
+ }
445
+
446
+ /* Color shell script icons - pale blue for Windows shells (.bat, .cmd) */
447
+ .jp-DirListing-item[data-shell-type="windows"] .jp-DirListing-itemIcon svg {
448
+ filter: hue-rotate(180deg) saturate(0.6) brightness(1.2);
449
+ }
450
+ `;
451
+ // Add a MutationObserver to mark special files in the file browser
452
+ const markSpecialFiles = () => {
453
+ // Mark Jupytext files (.py and .md notebooks) and CLAUDE.md
454
+ const notebookItems = document.querySelectorAll('.jp-DirListing-item[data-file-type="notebook"]');
455
+ notebookItems.forEach(item => {
456
+ const nameSpan = item.querySelector('.jp-DirListing-itemText');
457
+ if (nameSpan && nameSpan.textContent) {
458
+ const name = nameSpan.textContent.trim();
459
+ if (name === 'CLAUDE.md') {
460
+ item.setAttribute('data-claude-md', 'true');
461
+ }
462
+ else if (name === 'README.md') {
463
+ item.setAttribute('data-readme-md', 'true');
464
+ }
465
+ else if (name.endsWith('.py')) {
466
+ item.setAttribute('data-jupytext-py', 'true');
467
+ }
468
+ else if (name.endsWith('.md')) {
469
+ item.setAttribute('data-jupytext-md', 'true');
470
+ }
471
+ }
472
+ });
473
+ // Mark shell script files for different coloring
474
+ const shellItems = document.querySelectorAll('.jp-DirListing-item[data-file-type="vscode-file-type-shell"]');
475
+ shellItems.forEach(item => {
476
+ const nameSpan = item.querySelector('.jp-DirListing-itemText');
477
+ if (nameSpan && nameSpan.textContent) {
478
+ const name = nameSpan.textContent.trim();
479
+ if (name.endsWith('.sh') || name.endsWith('.bash') || name.endsWith('.zsh')) {
480
+ item.setAttribute('data-shell-type', 'linux');
481
+ }
482
+ else if (name.endsWith('.bat') || name.endsWith('.cmd')) {
483
+ item.setAttribute('data-shell-type', 'windows');
484
+ }
485
+ }
486
+ });
487
+ };
488
+ // Watch for changes in the file browser
489
+ const observer = new MutationObserver(() => {
490
+ markSpecialFiles();
491
+ });
492
+ // Start observing when the file browser is ready
493
+ setTimeout(() => {
494
+ const fileBrowser = document.querySelector('.jp-DirListing-content');
495
+ if (fileBrowser) {
496
+ observer.observe(fileBrowser, {
497
+ childList: true,
498
+ subtree: true
499
+ });
500
+ markSpecialFiles();
501
+ }
502
+ }, 1000);
503
+ // Remove existing override style if present
504
+ const existing = document.getElementById('vscode-icons-jupytext-override');
505
+ if (existing) {
506
+ existing.remove();
507
+ }
508
+ document.head.appendChild(style);
509
+ };
510
+ // Wait for DOM to be ready, then inject CSS
511
+ app.started.then(() => {
512
+ setTimeout(injectIconOverrideCSS, 500);
513
+ });
514
+ // Default settings
515
+ const settings = {
516
+ enableLanguageIcons: true,
517
+ enableWebIcons: true,
518
+ enableDataIcons: true,
519
+ enableConfigIcons: true,
520
+ enableDocIcons: true,
521
+ enableImageIcons: true
522
+ };
523
+ // Function to register file types based on settings
524
+ const registerFileTypes = () => {
525
+ var _a;
526
+ // Clear existing registrations by re-registering
527
+ fileTypeConfigs.forEach(config => {
528
+ // Check if this group is enabled
529
+ if (!settings[config.group]) {
530
+ return;
531
+ }
532
+ const icon = createLabIcon(config.iconName);
533
+ const fileTypeName = `vscode-${config.iconName}`;
534
+ // Register file type
535
+ const fileTypeOptions = {
536
+ name: fileTypeName,
537
+ icon: icon,
538
+ fileFormat: 'text',
539
+ contentType: 'file'
540
+ };
541
+ if (config.extensions.length > 0) {
542
+ fileTypeOptions.extensions = config.extensions;
543
+ }
544
+ if (config.pattern) {
545
+ fileTypeOptions.pattern = config.pattern;
546
+ }
547
+ docRegistry.addFileType(fileTypeOptions);
548
+ });
549
+ // Register Makefile with custom icon (separate from main icon loop)
550
+ const makefileSvg = `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24">
551
+ <text x="12" y="18" font-size="20" font-weight="900" text-anchor="middle" fill="#d84a4a" font-family="Arial, sans-serif">M</text>
552
+ </svg>`;
553
+ const makefileIcon = new LabIcon({
554
+ name: 'makefile-icon',
555
+ svgstr: makefileSvg
556
+ });
557
+ docRegistry.addFileType({
558
+ name: 'vscode-makefile',
559
+ displayName: 'Makefile',
560
+ mimeTypes: ['text/x-makefile'],
561
+ extensions: ['.mk', '.mak', '.make'],
562
+ pattern: '^(Makefile|makefile|GNUmakefile|makefile\\..*|Makefile\\..*)',
563
+ fileFormat: 'text',
564
+ contentType: 'file',
565
+ icon: makefileIcon
566
+ });
567
+ // Register LICENSE with custom copyright icon (C in circle)
568
+ const licenseSvg = `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
569
+ <circle cx="16" cy="16" r="11" fill="none" stroke="#4a90e2" stroke-width="3"/>
570
+ <path fill="#4a90e2" stroke="#4a90e2" stroke-width="0.5" d="M19 19.5c-0.8 0.8-2 1.3-3.2 1.3c-2.5 0-4.5-2-4.5-4.5s2-4.5 4.5-4.5c1.2 0 2.3 0.5 3.2 1.3l1.2-1.2c-1.1-1.1-2.6-1.8-4.3-1.8c-3.4 0-6.2 2.8-6.2 6.2s2.8 6.2 6.2 6.2c1.7 0 3.2-0.7 4.3-1.8L19 19.5z"/>
571
+ </svg>`;
572
+ const licenseIcon = new LabIcon({
573
+ name: 'license-icon',
574
+ svgstr: licenseSvg
575
+ });
576
+ docRegistry.addFileType({
577
+ name: 'vscode-license',
578
+ displayName: 'License',
579
+ pattern: '^(LICENSE|LICENCE|LICENSE\\..*|LICENCE\\..*)$',
580
+ fileFormat: 'text',
581
+ contentType: 'file',
582
+ icon: licenseIcon
583
+ });
584
+ // Register CLAUDE.md with Claude icon (always register, not conditional on settings)
585
+ const claudeIcon = createLabIcon('file-type-claude');
586
+ console.log('[VSCode Icons] CLAUDE.md icon created:', !!claudeIcon);
587
+ if (claudeIcon) {
588
+ console.log('[VSCode Icons] CLAUDE.md icon svgstr length:', ((_a = claudeIcon.svgstr) === null || _a === void 0 ? void 0 : _a.length) || 0);
589
+ docRegistry.addFileType({
590
+ name: 'vscode-claude-md',
591
+ displayName: 'Claude Configuration',
592
+ pattern: '^CLAUDE\\.md$',
593
+ fileFormat: 'text',
594
+ contentType: 'file',
595
+ icon: claudeIcon
596
+ });
597
+ console.log('[VSCode Icons] CLAUDE.md file type registered with pattern: ^CLAUDE\\.md$');
598
+ }
599
+ else {
600
+ console.error('[VSCode Icons] Failed to create CLAUDE.md icon');
601
+ }
602
+ // Register README.md with custom purple filled info icon
603
+ const readmeSvg = `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
604
+ <circle cx="16" cy="16" r="11" fill="#9826c8"/>
605
+ <text x="16" y="22" font-size="18" font-weight="bold" text-anchor="middle" fill="#ffffff" font-family="Arial, sans-serif">i</text>
606
+ </svg>`;
607
+ const readmeIcon = new LabIcon({
608
+ name: 'readme-icon',
609
+ svgstr: readmeSvg
610
+ });
611
+ docRegistry.addFileType({
612
+ name: 'vscode-readme',
613
+ displayName: 'README',
614
+ pattern: '^README\\.md$',
615
+ fileFormat: 'text',
616
+ contentType: 'file',
617
+ icon: readmeIcon
618
+ });
619
+ console.log('[VSCode Icons] README.md file type registered with pattern: ^README\\.md$');
620
+ };
621
+ // Debounce timer for settings change alert
622
+ let settingsChangeTimeout = null;
623
+ // Load settings
624
+ if (settingRegistry) {
625
+ settingRegistry
626
+ .load(PLUGIN_ID)
627
+ .then(loadedSettings => {
628
+ // Update settings from registry
629
+ Object.keys(settings).forEach(key => {
630
+ const value = loadedSettings.get(key).composite;
631
+ if (typeof value === 'boolean') {
632
+ settings[key] = value;
633
+ }
634
+ });
635
+ registerFileTypes();
636
+ // Listen for settings changes
637
+ loadedSettings.changed.connect(() => {
638
+ Object.keys(settings).forEach(key => {
639
+ const value = loadedSettings.get(key).composite;
640
+ if (typeof value === 'boolean') {
641
+ settings[key] = value;
642
+ }
643
+ });
644
+ // Debounce the alert to show only once when multiple settings change
645
+ if (settingsChangeTimeout) {
646
+ clearTimeout(settingsChangeTimeout);
647
+ }
648
+ settingsChangeTimeout = setTimeout(() => {
649
+ alert('VSCode Icons settings changed. Please refresh the page to apply changes.');
650
+ settingsChangeTimeout = null;
651
+ }, 500);
652
+ });
653
+ })
654
+ .catch(reason => {
655
+ console.error('Failed to load settings for jupyterlab_vscode_icons_extension.', reason);
656
+ // Register with default settings
657
+ registerFileTypes();
658
+ });
659
+ }
660
+ else {
661
+ // No settings registry, use defaults
662
+ registerFileTypes();
663
+ }
664
+ }
665
+ };
666
+ export default plugin;