The import was unused — resolveIcon is never called in this file. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
57 lines
2.2 KiB
JavaScript
57 lines
2.2 KiB
JavaScript
// public/views/icon_picker.js — inline picker with Type + Brand tabs.
|
|
import { el, mount, clear } from '../dom.js';
|
|
import { api } from '../api.js';
|
|
|
|
// onPick(ref) called with 'set:<set>:<name>' or 'brand:<slug>'. Returns an element.
|
|
export function iconPicker(currentRef, onPick) {
|
|
const box = el('div', { class: 'icon-picker' });
|
|
const tabs = el('div', { class: 'ip-tabs' });
|
|
const body = el('div', { class: 'ip-body' });
|
|
const typeTab = el('button', { class: 'ip-tab active' }, 'Type');
|
|
const brandTab = el('button', { class: 'ip-tab' }, 'Brand');
|
|
typeTab.onclick = () => { typeTab.classList.add('active'); brandTab.classList.remove('active'); showType(); };
|
|
brandTab.onclick = () => { brandTab.classList.add('active'); typeTab.classList.remove('active'); showBrand(); };
|
|
|
|
async function showType() {
|
|
clear(body);
|
|
body.append(el('div', { class: 'muted' }, 'Loading…'));
|
|
let list = [];
|
|
try { list = await api.get('/api/icon-sets'); } catch { /* ignore */ }
|
|
clear(body);
|
|
for (const s of list) {
|
|
const grid = el('div', { class: 'ip-grid' }, s.icons.map(file => {
|
|
const name = file.replace(/\.[a-z]+$/, '');
|
|
const ref = `set:${s.set}:${name}`;
|
|
const b = el('button', { class: 'ip-icon', title: name },
|
|
el('img', { src: `/api/icon-sets/${s.set}/${file}` }));
|
|
b.onclick = () => onPick(ref);
|
|
return b;
|
|
}));
|
|
body.append(el('div', { class: 'ip-set' },
|
|
el('div', { class: 'ip-set-hd' }, s.set + (s.readonly ? '' : ' ·')),
|
|
grid));
|
|
}
|
|
}
|
|
|
|
function showBrand() {
|
|
clear(body);
|
|
const inp = el('input', { class: 'dv-edit-name', placeholder: 'brand slug e.g. apple, google-nest' });
|
|
const prev = el('div', { class: 'ip-grid' });
|
|
inp.oninput = () => {
|
|
const slug = inp.value.trim().toLowerCase().replace(/[^a-z0-9-]/g, '');
|
|
clear(prev);
|
|
if (!slug) return;
|
|
const b = el('button', { class: 'ip-icon' },
|
|
el('img', { src: `/api/icons/${slug}.png` }));
|
|
b.onclick = () => onPick(`brand:${slug}`);
|
|
prev.append(b);
|
|
};
|
|
body.append(inp, prev);
|
|
}
|
|
|
|
mount(tabs, typeTab, brandTab);
|
|
mount(box, tabs, body);
|
|
showType();
|
|
return box;
|
|
}
|