Klikkaa nimeä
Etunimi
Sukunimi
CSS
label { display: block; } fieldset { display: none; } #luvut { display: block; } .koodi { width: 98%; max-width: 98%; }
HTML
Javascript
// tietorakenteeseen on lisätty taulukko. Muokkaaminen osaa dynaamisesti // hallita erimittaiset taulukot. Käytetään jo uudelleen aiemmin luotuja // rakenteita eli ei turhaan poisteta ja luoda uudelleen input-kenttiä. //Klikkaa nimeä //
//
Etunimi
//
Sukunimi
//
//
//
//
//
// nämä ovat nyt globaaleja muuttujia, mutta koko sovellus voitaisiin // tehdä omaksi luokaksi tai nämä muuttujat tallentaa esim. lomakkeen // attribuuteiksi. Vaihtoehtoja on monia let listaus = document.getElementById("listaus"); let lomake = document.forms[0]; let fieldset = document.getElementById("luvut"); let muokattava_henkilo = {}; let alkuperainen_henkilo = muokattava_henkilo; // alustetaan henkilölistaus. Pyritään rakentamaan // viitteiden avulla siten, että minimoidaan turhat ja toistuvat haut DOM-puusta // samoin minimoidaan tietorakenteen läpikäyminen for(let henkilo of henkilot) { let li = document.createElement("li"); let etunimi = document.createTextNode( henkilo["etunimi"] ); let sukunimi = document.createTextNode( henkilo["sukunimi"] ); li.appendChild ( etunimi ); li.appendChild ( document.createTextNode(" ") ); li.appendChild ( sukunimi ); // sisempi lista lukuja varten let luvut = document.createElement("ul"); li.appendChild(luvut); for( let luku of henkilo.luvut ) { let lukuli = document.createElement("li"); lukuli.textContent = luku; luvut.appendChild(lukuli); } // tallennetaan li-objektiin viite tietorakenteessa olevaan objektiin li.henkilo = henkilo; // tallennetaan objektin sisältöä listauksessa vastaavien dom-nodejen viitteet myös objektiin // jos alkuperäistä objektia ei saa muuttaa niin pitää tehdä tätä varten oma // tietorakenne ja tallentaa vastaavat tiedot sinne henkilo["listaus"] = { "etunimi": etunimi, "sukunimi": sukunimi, "luvut": luvut }; li.addEventListener("click", muokkaa); listaus.appendChild(li); } function muokkaa(e) { // huomaa ero currentTarget vs target // currentTarget on elementti, joka käsittelee tapahtuman // target on elementti, jota klikattiin let henkilo = e.currentTarget.henkilo; // tehdään kopio muokattavista tiedoista // muokkaus on aina syytä tehdä kopioon ja muutokset päivitetään // tietorakenteeseen vasta, kun ne hyväksytään painikkeella // älä koskaan muokkaa suoraan alkuperäistä rakennetta, koska virheiden // peruminen tulee mahdottomaksi muokattava_henkilo["etunimi"] = henkilo["etunimi"]; muokattava_henkilo["sukunimi"] = henkilo["sukunimi"]; // tehdään kopio luvut-taulukosta. Huom! pelkkä sijoitus ei tässä riitä, koska // se tallentaisi vain viitteen samaan taulukkoon! // jos taulukko sisältäisi objekteja tai muita taulukoita niin ne pitää // vielä erikseen kopioida // https://medium.com/javascript-in-plain-english/how-to-deep-copy-objects-and-arrays-in-javascript-7c911359b089 muokattava_henkilo["luvut"] = Array.from( henkilo["luvut"] ); // tallennetaan alkuperäisen henkilön viite alkuperainen_henkilo = henkilo; // hyödynnetään lomakkeen ominaisuutta jossa lomake-elementit näkyvät suoraan lomakkeen attribuutteina // elementin name on sama kuin attribuutin name // tässä on varottava käyttämästä samoja nimiä kuin form-objektin olemassa olevilla attribuuteilla ja funktioilla on lomake["etunimi"].value = muokattava_henkilo["etunimi"]; lomake.sukunimi.value = muokattava_henkilo["sukunimi"]; // luodaan lukuja varten omat input-elementit // jos inputeja on jo olemassa niin käytetään niitä fieldset.style.display = "block"; // laitetaan fieldsetiin talteen viite luvut-taulukkoon fieldset.luvut = henkilo.luvut; let i = 0; for(; i
Konsoli