1
Fork 0
This repository has been archived on 2025-06-02. You can view files and clone it, but you cannot make any changes to it's state, such as pushing and creating new issues, pull requests or comments.
2022ST-project-Phikipathia/index.js
2022-05-19 21:50:37 +02:00

138 lines
4 KiB
JavaScript

// TODO Optimalisatie: De huidige lijst meegeven en controleren tijdens het opstellen zodat er gestopt wordt vanaf er een titel gevonden is
// Initialiseer de webpagina
const taal = document.getElementById('taal');
const start = document.getElementById('start');
const einde = document.getElementById('einde');
const toevoegKnop = document.getElementById('toevoegKnop');
const visualisatie = document.getElementById('visualisatie');
const logo = document.getElementById('logo');
const waarschuwing = document.getElementById('waarschuwing');
let huidigeTaal;
let huidigeDoel;
let timer;
let rotatie;
refreshTree();
/**
* Zoek een pad met python backend en voeg deze toe in de lijst.
*/
function zoek() {
// Schakel de knop 'toevoegen' uit zolang het zoekproces bezig is, zodat er geen meerdere
// paden tegelijk toegevoegd kunnen worden.
toggleZoeken(false);
refreshTree();
const verzoek = { // Standaardwaarden gebruiken indien het veld leeg is.
taal: getOrDefault(taal),
start: getOrDefault(start),
einde: getOrDefault(einde)
};
fetch(`cgi-bin/init.py?data=${JSON.stringify(verzoek)}`)
.then(antwoord => antwoord.json())
.then(data => voegToe(data))
.catch(reason => alert('‼ ' + reason))
.finally(() => toggleZoeken()); // Herstel de knop. Ook als er ondertussen iets mis ging.
}
function voegToe(data) {
if (data.hasOwnProperty('error')) {
alert('↯ ' + data.error);
} else {
let pad = data.pad;
// Locatie van invoegen bepalen.
let moeder = visualisatie;
let kinderen = visualisatie.getElementsByTagName('li');
let kindernamen = Array.from(kinderen).map(item => item.getAttribute('item'));
let i = 0;
while (moeder === visualisatie && i < pad.length) {
if (kindernamen.indexOf(pad[i]) !== -1) {
moeder = kinderen[kindernamen.indexOf(pad[i])];
}
i += 1;
}
// Alleen nog die elementen toevoegen die nog niet op het pad staan.
pad = pad.slice(0, i - 1);
// Nieuw element creëren (zonder toe te voegen aan het DOM).
for (let item of pad.reverse()) {
moeder = maakIn(item, moeder);
}
}
}
/**
* Maakt een element aan binnen een ander element, en geeft het nieuwste (diepste) element terug.
*/
function maakIn(titel, moeder, id) {
let wrap = document.createElement('ul');
let nieuw = document.createElement('li');
nieuw.innerHTML = titel;
nieuw.setAttribute('item', titel);
wrap.appendChild(nieuw);
if (id !== undefined) {
wrap.id = id;
}
moeder.appendChild(wrap);
return nieuw;
}
/**
* Probeer of de huidige boom verwijderd moet worden en voeg de bestemming reeds toe aan de nieuwe boom.
*/
function refreshTree() {
if (huidigeDoel !== getOrDefault(einde) || huidigeTaal !== getOrDefault(taal)) {
huidigeTaal = getOrDefault(taal);
huidigeDoel = getOrDefault(einde);
visualisatie.innerHTML = '';
maakIn(huidigeDoel, visualisatie, 'wortel');
inputWaarschuwing();
}
}
/**
* Toon of verberg een speciale waarschuwing die zegt of de huidige boom verwijderd zal worden
* bij een nieuwe toevoeging.
*/
function inputWaarschuwing() {
waarschuwing.hidden = (huidigeTaal === getOrDefault(taal) && huidigeDoel === getOrDefault(einde));
}
function getOrDefault(element) {
return element.value === '' ? element.getAttribute('placeholder') : element.value;
}
/**
* Toggle tussen de zoek-status en de wacht-op-input-status. Dit heeft invloed op zowel de indienkop als op het
* roterende logo. Standaardaanroep zal alles stoppen, om überveel animaties te vermijden bij fout gebruik.
*/
function toggleZoeken(stop = true) {
toevoegKnop.disabled = !stop;
rotatie = 0;
if (stop) {
clearInterval(timer);
logo.style.transform = 'rotate(0)';
} else {
timer = setInterval(draai, 24);
}
}
function draai() {
rotatie += 5;
logo.style.transform = `rotate(${rotatie % 360}deg`;
}