/* teach - herbruikbare plaatjeskiezer (emoji / ARASAAC-zoeken / eigen upload). Bouwt voort op dezelfde bouwstenen als de woordkaart-editor in letters.js (EMOJI_CATS, arasaacSearch/arasaacUrl, setPic, dezelfde CSS-klassen) i.p.v. een tweede plaatjessysteem te maken. Gebruikt door widgets die snel een los plaatje willen laten kiezen zonder de volledige woordkaart-editor te openen (bv. Ankerwoorden, als snelkoppeling vanaf een woord zonder automatisch plaatje). */ "use strict"; let pickerWrap = null, pickerCat = 0, pickerOnSelect = null; function choosePic(pic){ if(pickerOnSelect) pickerOnSelect(pic); closePicPicker(); } function closePicPicker(){ if(pickerWrap) pickerWrap.classList.remove("open"); pickerOnSelect = null; } function ensurePicPicker(){ if(pickerWrap) return pickerWrap; const wrap = document.createElement("div"); wrap.className = "modalwrap"; wrap.innerHTML = ` `; document.body.appendChild(wrap); pickerWrap = wrap; const q = s => wrap.querySelector(s); wrap.addEventListener("click", e=>{ if(e.target===wrap) closePicPicker(); }); q(".pp-close").addEventListener("click", closePicPicker); let tab = "emoji"; function setTab(t){ tab = t; refreshTabs(); } function applyLabels(){ q(".ed-uplbl").textContent = T("upload"); q(".ed-uphint").textContent = T("upHint"); q(".ed-credit").innerHTML = T("pictoCredit"); q(".ed-pgo").textContent = T("pictoSearch"); q(".ed-psearch").placeholder = T("pictoPh"); q(".pp-close").title = T("close"); refreshTabs(); } function refreshTabs(){ wrap.querySelectorAll(".ed-tabs button").forEach(b=>{ b.textContent = T("tab"+b.dataset.t[0].toUpperCase()+b.dataset.t.slice(1)); b.classList.toggle("active", b.dataset.t===tab); }); q(".ed-p-emoji").style.display = tab==="emoji" ? "block" : "none"; q(".ed-p-picto").style.display = tab==="picto" ? "block" : "none"; q(".ed-p-upload").style.display = tab==="upload" ? "block" : "none"; } wrap.querySelectorAll(".ed-tabs button").forEach(b=>{ b.addEventListener("click", ()=>{ tab = b.dataset.t; refreshTabs(); }); }); function renderCats(){ const cats = q(".ed-cats"); cats.innerHTML = ""; T("cats").forEach((name,i)=>{ const b = document.createElement("button"); b.type = "button"; b.textContent = name; b.classList.toggle("active", i===pickerCat); b.addEventListener("click", ()=>{ pickerCat=i; renderCats(); }); cats.appendChild(b); }); const grid = q(".ed-grid"); grid.innerHTML = ""; EMOJI_CATS[pickerCat].forEach(em=>{ const b = document.createElement("button"); b.type = "button"; b.textContent = em; b.addEventListener("click", ()=>choosePic(em)); grid.appendChild(b); }); } async function searchPictos(){ const term = q(".ed-psearch").value.trim(); if(!term) return; q(".ed-status").textContent = T("pictoLoad"); q(".ed-pgrid").innerHTML = ""; try{ const arr = await arasaacSearch(term, LANG); if(!arr.length){ q(".ed-status").textContent = T("pictoNone"); return; } q(".ed-status").textContent = ""; arr.slice(0,12).forEach(p=>{ const url = arasaacUrl(p._id); const b = document.createElement("button"); b.type = "button"; const im = document.createElement("img"); im.src = url; im.loading = "lazy"; im.alt = term; b.appendChild(im); b.addEventListener("click", ()=>choosePic(url)); q(".ed-pgrid").appendChild(b); }); }catch(e){ q(".ed-status").textContent = T("pictoErr"); } } q(".ed-pgo").addEventListener("click", searchPictos); q(".ed-psearch").addEventListener("keydown", e=>{ if(e.key==="Enter") searchPictos(); }); q(".ed-p-upload input").addEventListener("change", e=>{ const f = e.target.files[0]; if(!f) return; const img = new Image(); img.onload = ()=>{ const c = document.createElement("canvas"); const s = Math.min(1, 128/Math.max(img.width, img.height)); c.width = Math.round(img.width*s); c.height = Math.round(img.height*s); c.getContext("2d").drawImage(img, 0, 0, c.width, c.height); choosePic(c.toDataURL("image/png")); URL.revokeObjectURL(img.src); }; img.src = URL.createObjectURL(f); e.target.value = ""; }); wrap.__applyLabels = applyLabels; wrap.__renderCats = renderCats; wrap.__searchPictos = searchPictos; wrap.__setTab = setTab; return wrap; } function openPicPicker(word, onSelect){ const wrap = ensurePicPicker(); pickerOnSelect = onSelect; wrap.__applyLabels(); wrap.__renderCats(); wrap.querySelector(".ed-psearch").value = word || ""; /* met een woord starten we meteen op het picto-zoekresultaat i.p.v. het emoji-tabblad, anders lijkt de vooraf ingevulde zoekopdracht nergens naartoe te leiden */ wrap.__setTab(word ? "picto" : "emoji"); wrap.classList.add("open"); if(word) wrap.__searchPictos(); }