From 7869a747bc46ebf9611a1717e576b803cacaa216 Mon Sep 17 00:00:00 2001 From: Your Name Date: Tue, 21 Jul 2026 20:49:27 -0400 Subject: [PATCH] feat(core): port FileIcon to Vue 3, replace require() with import.meta.glob 30 webpack require() calls replaced by a single eager import.meta.glob. The extension-to-icon mapping is preserved exactly, restructured from a switch chain into lookup tables. Fixes alt="name" rendering the literal string 'name'. --- n-link-core/components/FileIcon.vue | 242 ++++++++++------------------ 1 file changed, 89 insertions(+), 153 deletions(-) diff --git a/n-link-core/components/FileIcon.vue b/n-link-core/components/FileIcon.vue index ab0399f..e0dd9a1 100644 --- a/n-link-core/components/FileIcon.vue +++ b/n-link-core/components/FileIcon.vue @@ -1,161 +1,97 @@ - - +const FOLDER_ICONS: Record = { + games: 'games', + images: 'images', + photos: 'images', + music: 'music', + sound: 'music', + sounds: 'music', + script: 'scripts', + scripts: 'scripts', + program: 'scripts', + programs: 'scripts', + template: 'templates', + templates: 'templates', + video: 'video', + videos: 'video', +}; + +const EXT_ICONS: Record = { + bin: 'binary', + ical: 'calendar', ics: 'calendar', ifb: 'calendar', icalendar: 'calendar', + cfg: 'cfg', + vcf: 'contact', + csv: 'csv', log: 'csv', logs: 'csv', + sql: 'db', db: 'db', sqlite: 'db', + epub: 'epub', + eot: 'font', otf: 'font', ttf: 'font', woff: 'font', woff2: 'font', + png: 'image', bmp: 'image', jpg: 'image', jpeg: 'image', jpe: 'image', + jif: 'image', jfif: 'image', jfi: 'image', jp2: 'image', j2k: 'image', + jpf: 'image', jpx: 'image', jpm: 'image', mj2: 'image', gif: 'image', + tiff: 'image', tif: 'image', ppm: 'image', pgm: 'image', pbm: 'image', + pnm: 'image', webp: 'image', heif: 'image', heifs: 'image', heic: 'image', + heics: 'image', avci: 'image', avcs: 'image', avif: 'image', avifs: 'image', + ico: 'image', icon: 'image', icns: 'image', pcx: 'image', pgf: 'image', + tga: 'image', psd: 'image', xcf: 'image', + js: 'js', mjs: 'js', + json: 'json', json5: 'json', + lua: 'lua', + pdf: 'pdf', + py: 'python', + rom: 'rom', '89u': 'rom', smc: 'rom', sfc: 'rom', srm: 'rom', img: 'rom', + svg: 'svg', svgz: 'svg', + txt: 'txt', + mp4: 'video', + xml: 'xml', + zip: 'zip', tar: 'zip', gz: 'zip', +}; + +const name = computed(() => props.path.split('/').pop() as string); + +const ext = computed(() => { + const parts = name.value.split('.'); + if (parts[parts.length - 1] === 'tns') parts.pop(); + if (parts.length < 2) return ''; + return parts.pop() as string; +}); + +const icon = computed(() => { + if (props.dir) { + const key = FOLDER_ICONS[name.value.trim().toLowerCase()] ?? 'folder'; + return asset(`folders/${key}.svg`); + } + if (name.value === 'ndless_resources.tns') return asset('files/resources.svg'); + if (name.value.startsWith('ndless_installer')) return asset('files/installer.svg'); + return asset(`files/${EXT_ICONS[ext.value.toLowerCase()] ?? 'unknown'}.svg`); +}); +