Toteuta tunnit ilman usean luokan tai opettajan tukea

This commit is contained in:
Juhani Krekelä 2023-08-08 19:08:44 +03:00
parent e617e76432
commit c7b7d726d9
3 changed files with 289 additions and 12 deletions

View File

@ -10,7 +10,7 @@ document.getElementById('tee-uudelleen').addEventListener('click', () => {
document.getElementById('lisää-luokka-aste').addEventListener('click', () => {
suorita(tapahtumaTyypit.lisääAste);
piirräLuokat();
piirräKaikki();
});
document.getElementById('lisää-opettaja').addEventListener('submit', (tapahtuma) => {
@ -34,7 +34,7 @@ document.getElementById('lisää-opettaja').addEventListener('submit', (tapahtum
lyhenneElementti.value = '';
lyhenneElementti.placeholder = '';
virheElementti.classList.add('piilotettu');
piirräOpettajat();
piirräKaikki();
} else if (toinenNimi === nimi) {
virheElementti.firstChild.textContent =
`Opettaja ${nimi} on jo listassa`;
@ -61,9 +61,31 @@ document.getElementById('opettaja-nimi').addEventListener('input', () => {
document.getElementById('opettaja-lyhenne').placeholder = lyhenne;
});
document.getElementById('lisää-tunti').addEventListener('submit', (tapahtuma) => {
tapahtuma.preventDefault();
let nimiElementti = document.getElementById('tunti-nimi');
let luokkaElementti = document.getElementById('tunti-luokka');
let opettajaElementti = document.getElementById('tunti-opettaja');
let kertaaViikossaElementti = document.getElementById('tunti-kertaa-viikossa');
let nimi = nimiElementti.value;
let luokka = luokkaElementti.value;
let opettajaLyhenne = opettajaElementti.value;
let kertaaViikossa = parseInt(kertaaViikossaElementti.value);
suorita(tapahtumaTyypit.lisääTunti, nimi, luokka, opettajaLyhenne, kertaaViikossa);
nimiElementti.value = '';
luokkaElementti.value = '';
opettajaElementti.value = '';
kertaaViikossaElementti.value = 1;
piirräKaikki();
});
function piirräKaikki() {
piirräLuokat();
piirräOpettajat();
piirräTunnit();
}
function piirräLuokat() {
@ -82,6 +104,7 @@ function piirräLuokat() {
valinta.appendChild(document.createTextNode(luokka));
tuntiLuokkaValinta.appendChild(valinta);
}
tuntiLuokkaValinta.value = '';
vanhaTuntiLuokkaValinta.parentNode.replaceChild(
tuntiLuokkaValinta,
vanhaTuntiLuokkaValinta
@ -108,7 +131,7 @@ function luoLuokkaAsteListassa(aste) {
luokkaAsteListassa.appendChild(luoPainike('+', () => {
suorita(tapahtumaTyypit.lisääLuokka, aste);
piirräLuokat();
piirräKaikki();
}));
luokkaAsteListassa.appendChild(luoPainike('-', () => {
if (luokkaAsteet.asteet[aste].luokat().length > 1) {
@ -116,7 +139,7 @@ function luoLuokkaAsteListassa(aste) {
} else {
suorita(tapahtumaTyypit.poistaAste, aste);
}
piirräLuokat();
piirräKaikki();
}));
luokkaAsteListassa.appendChild(luoLuokkaLista(aste));
@ -146,7 +169,7 @@ function luoLuokkaAsteListassa(aste) {
let uusiAste = parseInt(asteValitsin.value);
if (luokkaAsteet.asteet[uusiAste] === undefined || aste === uusiAste) {
suorita(tapahtumaTyypit.muutaAste, aste, uusiAste);
piirräLuokat();
piirräKaikki();
} else {
muokkausVirhe.firstChild.textContent =
`Luokka-aste ${uusiAste} on jo olemassa.`;
@ -194,6 +217,7 @@ function piirräOpettajat() {
valinta.value = lyhenne;
tuntiOpettajaValinta.appendChild(valinta);
}
tuntiOpettajaValinta.value = '';
vanhaTuntiOpettajaValinta.parentNode.replaceChild(
tuntiOpettajaValinta,
vanhaTuntiOpettajaValinta
@ -216,7 +240,7 @@ function luoOpettajaListassa(lyhenne, nimi) {
opettajaListassa.appendChild(luoPainike('-', () => {
suorita(tapahtumaTyypit.poistaOpettaja, lyhenne);
piirräOpettajat();
piirräKaikki();
}));
let opettajanNimi = document.createElement('span');
@ -226,6 +250,38 @@ function luoOpettajaListassa(lyhenne, nimi) {
return opettajaListassa;
}
function piirräTunnit() {
let vanhaTuntiLista = document.getElementById('tunnit');
let tuntiLista = luoTuntiLista();
vanhaTuntiLista.parentNode.replaceChild(
tuntiLista,
vanhaTuntiLista
);
}
function luoTuntiLista() {
let tuntiLista = document.createElement('ul');
tuntiLista.id = 'tunnit';
for (let [_, tunti] of tunnit.järjestyksessä()) {
let tuntiListassa = document.createElement('li');
let nimi = tunti.nimi;
let luokat = tunti.luokat.join(', ');
let opettajat = tunti.opettajaLyhenteet.join(', ');
let kertaaViikossa = tunti.kertaaViikossa;
let teksti;
if (kertaaViikossa === 1) {
teksti = `${nimi} ${luokat} ${opettajat}`;
} else {
teksti = `${nimi} ${luokat} ${opettajat} ×${kertaaViikossa}`;
}
tuntiListassa.appendChild(document.createTextNode(teksti));
tuntiLista.appendChild(tuntiListassa);
}
return tuntiLista;
}
function luoPainike(teksti, funktio) {
let painike = document.createElement('input');
painike.type = 'button';

View File

@ -9,6 +9,9 @@ const tapahtumaTyypit = {
lisääOpettaja: 'lisääOpettaja',
poistaOpettaja: 'poistaOpettaja',
lisääTunti: 'lisääTunti',
poistaTunti: 'poistaTunti',
};
class Tapahtuma {
@ -19,7 +22,7 @@ class Tapahtuma {
}
let historia, tulevaisuus;
let luokkaAsteet, opettajat;
let luokkaAsteet, opettajat, tunnit;
alustaMalli();
function alustaMalli() {
@ -27,6 +30,7 @@ function alustaMalli() {
tulevaisuus = [];
luokkaAsteet = new LuokkaAsteet();
opettajat = new Opettajat();
tunnit = new Tunnit();
}
function suorita(tyyppi, ...argumentit) {
@ -38,11 +42,38 @@ function suorita(tyyppi, ...argumentit) {
break;
case tapahtumaTyypit.poistaAste:
assertEq('poistaAste argumentit määrä', argumentit.length, 1);
paluuarvo = luokkaAsteet.poista(...argumentit)
let [poistettuAste] = argumentit;
luokkaAsteet.poista(poistettuAste);
// Poista poistettujen luokka-asteiden luokat tunneista
for (let [id, tunti] of tunnit.tunnit) {
let luokat = [];
for (let luokka of tunti.luokat) {
let luokanAste = parseInt(luokka[0]);
if (luokanAste !== poistettuAste) {
luokat.push(luokka);
}
}
tunnit.tunnit.get(id).luokat = luokat;
}
break;
case tapahtumaTyypit.muutaAste:
assertEq('muutaAste argumentit määrä', argumentit.length, 2);
luokkaAsteet.muuta(...argumentit)
let [vanhaAste, uusiAste] = argumentit;
luokkaAsteet.muuta(vanhaAste, uusiAste);
// Muuta muutetut luokka-asteet tunneissa
for (let [id, tunti] of tunnit.tunnit) {
let luokat = [];
for (let luokka of tunti.luokat) {
let luokanAste = parseInt(luokka[0]);
if (luokanAste === vanhaAste) {
let luokanLuokka = luokka.slice(1);
luokat.push(`${uusiAste}${luokanLuokka}`);
} else {
luokat.push(luokka);
}
}
tunnit.tunnit.get(id).luokat = luokat;
}
break;
case tapahtumaTyypit.lisääLuokka:
@ -51,16 +82,47 @@ function suorita(tyyppi, ...argumentit) {
break;
case tapahtumaTyypit.poistaLuokka:
assertEq('poistaLuokka argumentit määrä', argumentit.length, 1);
luokkaAsteet.asteet[argumentit[0]].poista();
let [aste] = argumentit;
luokkaAsteet.asteet[aste].poista();
// Poista luokka jota ei enää ole asteella tunneista
for (let [id, tunti] of tunnit.tunnit) {
let luokat = [];
for (let luokka of tunti.luokat) {
if (luokkaAsteet.luokat().indexOf(luokka) !== -1) {
luokat.push(luokka);
}
}
tunnit.tunnit.get(id).luokat = luokat;
}
break;
case tapahtumaTyypit.lisääOpettaja:
assertEq('lisääOpettaja argumentit määrä', argumentit.length, 2);
opettajat.lisää(argumentit[0], argumentit[1]);
opettajat.lisää(...argumentit);
break;
case tapahtumaTyypit.poistaOpettaja:
assertEq('poistaOpettaja argumentit määrä', argumentit.length, 1);
opettajat.poista(argumentit[0]);
let [poistettuOpettaja] = argumentit;
opettajat.poista(poistettuOpettaja);
// Poista opettaja joita ei enää ole tunneista
for (let [id, tunti] of tunnit.tunnit) {
let opettajaLyhenteet = [];
for (let opettajaLyhenne of tunti.opettajaLyhenteet) {
if (opettajaLyhenne !== poistettuOpettaja) {
opettajaLyhenteet.push(opettajaLyhenne);
}
}
tunnit.tunnit.get(id).opettajaLyhenteet = opettajaLyhenteet;
}
break;
case tapahtumaTyypit.lisääTunti:
assertEq('lisääTunti argumentit määrä', argumentit.length, 4);
paluuarvo = tunnit.lisää(...argumentit);
break;
case tapahtumaTyypit.poistaTunti:
assertEq('poistaTunti argumentit määrä', argumentit.length, 1);
tunnit.poista(...argumentit);
break;
default:
@ -105,11 +167,13 @@ testi('mallin alustaminen', () => {
tulevaisuus = undefined;
luokkaAsteet = undefined;
opettajat = undefined;
tunnit = undefined;
alustaMalli();
assertNe('historia', historia, undefined);
assertNe('tulevaisuus', tulevaisuus, undefined);
assertNe('luokkaAsteet', luokkaAsteet, undefined);
assertNe('opettajat', opettajat, undefined);
assertNe('tunnit', tunnit, undefined);
});
testi('tapahtumahistoria', () => {
@ -210,3 +274,54 @@ testi('opettajien käsittely', () => {
suorita(tapahtumaTyypit.poistaOpettaja, 'MM');
assertEq('poistettua', opettajat.opettajat(), []);
});
testi('tuntien käsittely', () => {
alustaMalli();
suorita(tapahtumaTyypit.lisääAste);
suorita(tapahtumaTyypit.lisääAste, 5);
suorita(tapahtumaTyypit.lisääLuokka, 5);
suorita(tapahtumaTyypit.lisääOpettaja, 'KV', 'Kari Virtanen');
suorita(tapahtumaTyypit.lisääOpettaja, 'AS', 'Aili Savolainen');
suorita(tapahtumaTyypit.lisääOpettaja, 'MM', 'Maija Meikäläinen');
assertEq('aluksi', tunnit.järjestyksessä(), []);
assertEq('historia',
suorita(tapahtumaTyypit.lisääTunti, 'Historia', '5B', 'KV', 1),
0
);
assertEq('äidinkieli',
suorita(tapahtumaTyypit.lisääTunti, 'Äidinkieli', '1A', 'AS', 3),
1
);
assertEq('kuvataide',
suorita(tapahtumaTyypit.lisääTunti, 'Kuvataide', '5A', 'MM', 1),
2
);
assertEq('lisättyä pituus', tunnit.järjestyksessä().length, 3);
suorita(tapahtumaTyypit.poistaAste, 1);
assertEq('aste poistettua 0', tunnit.järjestyksessä()[0][1].luokat, ['5B']);
assertEq('aste poistettua 1', tunnit.järjestyksessä()[1][1].luokat, ['5A']);
assertEq('aste poistettua 2', tunnit.järjestyksessä()[2][1].luokat, []);
suorita(tapahtumaTyypit.muutaAste, 5, 6);
assertEq('aste muutettua 0', tunnit.järjestyksessä()[0][1].luokat, ['6B']);
assertEq('aste muutettua 1', tunnit.järjestyksessä()[1][1].luokat, ['6A']);
assertEq('aste muutettua 2', tunnit.järjestyksessä()[2][1].luokat, []);
suorita(tapahtumaTyypit.poistaLuokka, 6);
assertEq('luokka poistettua 0', tunnit.järjestyksessä()[0][1].luokat, []);
assertEq('luokka poistettua 1', tunnit.järjestyksessä()[1][1].luokat, ['6A']);
assertEq('luokka poistettua 1', tunnit.järjestyksessä()[2][1].luokat, []);
suorita(tapahtumaTyypit.poistaOpettaja, 'KV');
assertEq('opettaja poistettua 0', tunnit.järjestyksessä()[0][1].opettajaLyhenteet, []);
assertEq('opettaja poistettua 1', tunnit.järjestyksessä()[1][1].opettajaLyhenteet, ['MM']);
assertEq('opettaja poistettua 2', tunnit.järjestyksessä()[2][1].opettajaLyhenteet, ['AS']);
suorita(tapahtumaTyypit.poistaTunti, 0);
assertEq('poistettua pituus', tunnit.järjestyksessä().length, 2);
alustaMalli();
// TODO: Luokkien ja opettajien listojen päivitys
});

View File

@ -109,6 +109,71 @@ class Opettajat {
}
}
class Tunti {
constructor(nimi, luokat, opettajaLyhenteet, kertaaViikossa) {
this.nimi = nimi;
this.luokat = luokat;
this.opettajaLyhenteet = opettajaLyhenteet;
this.kertaaViikossa = kertaaViikossa;
}
}
class Tunnit {
tunnit = new Map();
#seuraavaId = 0;
lisää(nimi, luokka, opettajaLyhenne, kertaaViikossa) {
let id = this.#seuraavaId++;
this.tunnit.set(
id,
new Tunti(nimi, [luokka], [opettajaLyhenne], kertaaViikossa)
);
return id;
}
poista(id) {
if (!this.tunnit.delete(id)) {
throw new Error(`ei tuntia ID:llä ${id}`);
}
}
järjestyksessä() {
let tunnit = [];
for (let [id, tunti] of this.tunnit) {
tunnit.push([id, tunti]);
}
tunnit.sort((a, b) => {
let tulos = vertaa(a[1].nimi, b[1].nimi);
// TODO: Korjaa niin, että osaa verrata okein listoja
if (tulos === 0) {
tulos = vertaa(a[1].luokat, b[1].luokat);
}
// TODO: Korjaa niin, että osaa verrata okein listoja
if (tulos === 0) {
tulos = vertaa(a[1].opettajaLyhenteet, b[1].opettajaLyhenteet);
}
if (tulos === 0) {
tulos = vertaa(a[1].kertaaViikossa, b[1].kertaaViikossa);
}
if (tulos === 0) {
tulos = vertaa(a[0], b[0]);
}
return tulos;
});
return tunnit;
}
}
function vertaa(a, b) {
if (a < b) {
return -1;
} else if (a > b) {
return 1;
} else {
return 0;
}
}
testi('seuraava aste', () => {
let luokkaAsteet = new LuokkaAsteet();
assertEq('aluksi', luokkaAsteet.seuraavaAste(), 1);
@ -228,3 +293,44 @@ testi('opettajien lyhenteen', () => {
assertEq('MaM', opettajat.lyhenne('MaM'), 'Matti Meikäläinen');
assertEq('ZZ', opettajat.lyhenne('ZZ'), undefined);
});
testi('tuntien lisääminen', () => {
let tunnit = new Tunnit();
assertEq('historia', tunnit.lisää('Historia', '5B', 'KV', 1), 0);
assertEq('äidinkieli', tunnit.lisää('Äidinkieli', '1A', 'AS', 3), 1);
assertEq('historia nimi', tunnit.tunnit.get(0).nimi, 'Historia');
assertEq('historia luokat', tunnit.tunnit.get(0).luokat, ['5B']);
assertEq('historia opettajat', tunnit.tunnit.get(0).opettajaLyhenteet, ['KV']);
assertEq('historia viikossa', tunnit.tunnit.get(0).kertaaViikossa, 1);
assertEq('äidinkieli nimi', tunnit.tunnit.get(1).nimi, 'Äidinkieli');
assertEq('äidinkieli luokat', tunnit.tunnit.get(1).luokat, ['1A']);
assertEq('äidinkieli opettajat', tunnit.tunnit.get(1).opettajaLyhenteet, ['AS']);
assertEq('äidinkieli viikossa', tunnit.tunnit.get(1).kertaaViikossa, 3);
});
testi('tuntien poistaminen', () => {
let tunnit = new Tunnit();
tunnit.lisää('Historia', '5B', 'KV', 1);
tunnit.lisää('Äidinkieli', '1B', 'AS', 3);
tunnit.poista(0);
tunnit.poista(1);
assertThrow('jo poistettu', 'ei tuntia ID:llä 1', () => {
tunnit.poista(1);
});
assertEq('kuvataide', tunnit.lisää('Kuvataide', '6A', 'MM', 1), 2);
});
testi('tuntien järjestys', () => {
let tunnit = new Tunnit();
tunnit.lisää('Historia', '5B', 'KV', 1);
tunnit.lisää('Äidinkieli', '1B', 'AS', 3);
assertEq('aluksi', tunnit.järjestyksessä()[0][1].nimi, 'Historia');
tunnit.tunnit.get(1).nimi = 'Historia';
assertEq('sama nimi', tunnit.järjestyksessä()[0][1].luokat, ['1B']);
tunnit.tunnit.get(0).luokat = ['1B'];
assertEq('sama luokka', tunnit.järjestyksessä()[0][1].opettajaLyhenteet, ['AS']);
tunnit.tunnit.get(0).opettajaLyhenteet = ['AS'];
assertEq('sama opettaja', tunnit.järjestyksessä()[0][1].kertaaViikossa, 1);
tunnit.tunnit.get(1).kertaaViikossa = 1;
assertEq('yhtä monta kertaa viikossa', tunnit.järjestyksessä()[0][0], 0);
});