Málokto nemá rád rámce, ale aj keď ste jedným z nich, mali by ste si to všimnúť a osvojiť si vlastnosti, ktoré trochu uľahčujú život.
Bol som proti použitiu rámcov v minulosti . V poslednej dobe som však mal skúsenosti s prácou Reagovať a Uhlové v niektorých mojich projektoch. Prvýkrát som otvoril editor kódu a začal písať kód v Angular, čo mi prišlo čudné a neprirodzené; najmä po viac ako desiatich rokoch programovania bez použitia akýchkoľvek rámcov. Po chvíli som sa rozhodol zaviazať sa učeniu týchto technológií. Veľmi rýchlo sa ukázal jeden veľký rozdiel: manipulácia s DOMom bola taká ľahká, také ľahké bolo podľa potreby upraviť poradie uzlov a na vytvorenie používateľského rozhrania nebolo potrebné stránky a stránky kódu.
Aj keď stále preferujem slobodu nebyť pripútaný k rámcu alebo architektúre, nemohol som ignorovať skutočnosť, že vytváranie prvkov DOM v jednom je oveľa pohodlnejšie. Začal som teda hľadať spôsoby, ako napodobniť zážitok vo vanilkovej JS. Mojím cieľom je extrahovať niektoré z týchto nápadov z Reactu a demonštrovať, ako je možné implementovať rovnaké princípy v obyčajnom JavaScripte (často označovanom ako vanilla JS), aby sa vývojárom trochu uľahčil život. Aby sme to dosiahli, vytvorme si jednoduchú aplikáciu na prehliadanie projektov GitHub.
Bez ohľadu na to, ako budujeme klientske rozhranie pomocou JavaScriptu, budeme mať prístup k DOM a manipuláciu s ním. Pre našu aplikáciu budeme musieť vytvoriť reprezentáciu každého úložiska (miniatúra, názov a popis) a pridať ju do DOM ako prvok zoznamu. Budeme používať GitHub Search API na získanie našich výsledkov. A keďže hovoríme o JavaScripte, poďme prehľadať archívy JavaScriptu. Keď sa pýtame na POŽIAR , dostaneme nasledujúcu odpoveď JSON:
{ 'total_count': 398819, 'incomplete_results': false, 'items': [ { 'id': 28457823, 'name': 'freeCodeCamp', 'full_name': 'freeCodeCamp/freeCodeCamp', 'owner': { 'login': 'freeCodeCamp', 'id': 9892522, 'avatar_url': 'https://avatars0.githubusercontent.com/u/9892522?v=4', 'gravatar_id': '', 'url': 'https://api.github.com/users/freeCodeCamp', 'site_admin': false }, 'private': false, 'html_url': 'https://github.com/freeCodeCamp/freeCodeCamp', 'description': 'The https://freeCodeCamp.org open source codebase '+ 'and curriculum. Learn to code and help nonprofits.', // more omitted information }, //... ] }
Vďaka funkcii React je veľmi jednoduché zapisovať na stránku prvky HTML a je jednou z funkcií, ktoré som vždy chcel mať pri písaní komponentov v čistom jazyku JavaScript. React používa JSX , ktorý je veľmi podobný bežnému HTML.
To však prehliadač nečíta.
Pod kapotou React transformuje JSX na množstvo hovorov na React.createElement
funkcia. Pozrime sa na príklad JSX, ktorý používa jednu položku z GitHub API, a pozrime sa, na čo sa prekladá.
{item.name} {item.description}
;
; React.createElement( 'div', { className: 'repository' }, React.createElement( 'div', null, item.name ), React.createElement( 'p', null, item.description ), React.createElement( 'img', { src: item.owner.avatar_url } ) );
JSX je veľmi jednoduchý. Píšete bežný kód HTML a vkladáte údaje z objektu pridaním zložených zátvoriek. Spustí sa kód JavaScript v zátvorkách a hodnota sa vloží do výsledného modelu DOM. Jednou z výhod JSX je, že React vytvára virtuálny DOM (virtuálne znázornenie stránky) na sledovanie zmien a aktualizácií. Namiesto prepisovania celého HTML upravuje React DOM stránky vždy, keď sú informácie aktualizované. Toto je jeden z hlavných problémov, ktoré boli vytvorené na vyriešenie.
Vývojári často používali jQuery. Chcel by som to tu spomenúť, pretože je stále populárny, a tiež preto, že je veľmi blízky riešeniu v čistom jazyku JavaScript. jQuery získa odkaz na uzol DOM (alebo kolekciu DOM uzlov) dotazom na DOM. Zahŕňa tiež tento odkaz rôznymi funkciami na úpravu jeho obsahu.
Zatiaľ čo jQuery má svoje vlastné stavebné nástroje DOM, najbežnejšie vidím veci iba v spojení HTML. Napríklad môžeme vložiť HTML kód do vybraných uzlov volaním html()
funkcia. Podľa jQuery dokumentácia , ak chceme zmeniť obsah a div
uzol s triedou demo-container
môžeme to urobiť takto:
$( 'div.demo-container' ).html( 'All new content. You bet!
' );
Tento prístup uľahčuje vytváranie prvkov DOM; keď však potrebujeme aktualizovať uzly, musíme vyhľadať uzly, ktoré potrebujeme, alebo (častejšie) ustúpiť a znovu vytvoriť celý úryvok, kedykoľvek je aktualizácia potrebná.
JavaScript v prehliadačoch má zabudovanú funkciu DOM API ktorá nám poskytuje priamy prístup k vytváraniu, úpravám a mazaniu uzlov na stránke. To sa odráža v prístupe spoločnosti React a používaním rozhrania DOM API sa dostávame o krok bližšie k výhodám tohto prístupu. Upravujeme iba tie prvky stránky, ktoré je skutočne potrebné zmeniť. React však sleduje aj samostatný virtuálny DOM. Porovnaním rozdielov medzi virtuálnym a skutočným DOM potom dokáže React identifikovať, ktoré časti si vyžadujú úpravu.
Tieto kroky navyše sú niekedy užitočné, ale nie vždy, a priama manipulácia s DOM môže byť efektívnejšia. Nové uzly DOM môžeme vytvoriť pomocou _document.createElement_
funkcia, ktorá vráti odkaz na vytvorený uzol. Sledovanie týchto odkazov nám umožňuje ľahký spôsob úpravy iba uzlov obsahujúcich časť, ktorú je potrebné aktualizovať.
Použitím rovnakej štruktúry a zdroja údajov ako v príklade JSX môžeme DOM skonštruovať nasledujúcim spôsobom:
var item = document.createElement('div'); item.className = 'repository'; var nameNode = document.createElement('div'); nameNode.innerHTML = item.name item.appendChild(nameNode); var description = document.createElement('p'); description.innerHTML = item.description; item.appendChild(description ); var image = new Image(); Image.src = item.owner.avatar_url; item.appendChild(image); document.body.appendChild(item);
Ak vám záleží iba na efektívnosti vykonávania kódu, potom je tento prístup veľmi dobrý. Účinnosť sa však nemeria iba v rýchlosti vykonania, ale aj v ľahkosti údržby, škálovateľnosti a plasticity. Problém tohto prístupu spočíva v tom, že je veľmi podrobný a niekedy komplikovaný. Musíme napísať veľa funkčných volaní, aj keď konštruujeme iba základnú štruktúru. Druhou veľkou nevýhodou je samotný počet vytvorených a sledovaných premenných. Povedzme, že komponent, ktorý pracujete, obsahuje svojich 30 elementov DOM, budete musieť vytvoriť a použiť 30 rôznych elementov DOM a premenných. Niektoré z nich môžete znova použiť a žonglovať na úkor udržiavateľnosti a plasticity, ale môže to byť skutočne nepríjemné, skutočne rýchle.
Ďalšou významnou nevýhodou je počet riadkov kódu, ktoré musíte napísať. Postupom času je čoraz ťažšie presúvať prvky z jedného rodiča do druhého. To je jedna vec, ktorú si veľmi vážim od React. Dokážem zobraziť syntax JSX a za pár sekúnd dostať, ktorý uzol je kde obsiahnutý, a podľa potreby ho zmeniť. Aj keď by sa zo začiatku mohlo zdať, že nejde o veľký problém, väčšina projektov má neustále zmeny, vďaka ktorým budete hľadať lepšiu cestu.
Práca priamo s DOM funguje a prácu dokončí, ale umožňuje tiež veľmi podrobné zostavenie stránky, najmä keď potrebujeme pridať atribúty HTML a vnoriť uzly. Myšlienkou by teda bolo zachytiť niektoré výhody práce s technológiami ako JSX a zjednodušiť nám život. Výhody, ktoré sa snažíme replikovať, sú nasledujúce:
Tu je jednoduchá funkcia, ktorá by to dosiahla pomocou útržku kódu HTML.
Browser.DOM = function (html, scope) { // Creates empty node and injects html string using .innerHTML // in case the variable isn't a string we assume is already a node var node; if (html.constructor === String) { var node = document.createElement('div'); node.innerHTML = html; } else { node = html; } // Creates of uses and object to which we will create variables // that will point to the created nodes var _scope = scope || {}; // Recursive function that will read every node and when a node // contains the var attribute add a reference in the scope object function toScope(node, scope) { var children = node.children; for (var iChild = 0; iChild 0) { var _property = names.shift(); if (names.length == 0) { obj[_property] = children[iChild]; } else { if (!obj.hasOwnProperty(_property)){ obj[_property] = {}; } obj = obj[_property]; } } } toScope(children[iChild], scope); } } toScope(node, _scope); if (html.constructor != String) { return html; } // If the node in the highest hierarchy is one return it if (node.childNodes.length == 1) { // if a scope to add node variables is not set // attach the object we created into the highest hierarchy node // by adding the nodes property. if (!scope) { node.childNodes[0].nodes = _scope; } return node.childNodes[0]; } // if the node in highest hierarchy is more than one return a fragment var fragment = document.createDocumentFragment(); var children = node.childNodes; // add notes into DocumentFragment while (children.length > 0) { if (fragment.append){ fragment.append(children[0]); }else{ fragment.appendChild(children[0]); } } fragment.nodes = _scope; return fragment; }
Myšlienka je jednoduchá, ale účinná; funkcii HTML, ktorú chceme vytvoriť, pošleme ako reťazec, v reťazci HTML pridáme atribút var do uzlov, pre ktoré chceme mať vytvorené referencie. Druhým parametrom je objekt, v ktorom budú uložené tieto referencie. Pokiaľ nebude zadané, vytvoríme vlastnosť „uzly“ na vrátenom uzle alebo fragmente dokumentu (v prípade, že uzol s najvyššou hierarchiou je viac ako jeden). Všetko je dosiahnuté za menej ako 60 riadkov kódu.
Funkcia funguje v troch krokoch:
Ako teda vyzerá náš kód na vykreslenie príkladu?
var UI = {}; var template = ''; template += ' ' template += ' '; template += ' ' template += '
' template += ' '; var item = Browser.DOM(template, UI); UI.name.innerHTML = data.name; UI.text.innerHTML = data.description; UI.image.src = data.owner.avatar_url;
Najskôr definujeme objekt (UI), kde budeme ukladať odkazy na vytvorené uzly. Potom zostavíme šablónu HTML, ktorú budeme používať, ako reťazec a označíme cieľové uzly atribútom „var“. Potom zavoláme funkciu Browser.DOM so šablónou a prázdnym objektom, ktorý uloží odkazy. Nakoniec použijeme uložené odkazy na umiestnenie údajov do uzlov.
Tento prístup tiež oddeľuje budovanie štruktúry DOM a vkladanie údajov do samostatných krokov, čo pomáha udržiavať kód organizovaný a dobre štruktúrovaný. To nám umožňuje samostatne vytvoriť štruktúru modelu DOM a vyplniť (alebo aktualizovať) údaje, keď budú k dispozícii.
Aj keď sa niektorým z nás nepáči myšlienka prechodu na rámce a odovzdania kontroly, je dôležité, aby sme si uvedomili výhody, ktoré tieto rámce prinášajú. Existuje dôvod, prečo sú také populárne.
Aj keď rámec nemusí vždy vyhovovať vášmu štýlu alebo potrebám, niektoré funkcie a techniky je možné prijať, napodobniť alebo niekedy dokonca oddeliť od rámca. Niektoré veci sa pri preklade vždy stratia, ale veľa sa dá získať a použiť za malý zlomok nákladov, ktoré rámec nesie.
JSX je komponenta React, ktorá zjednodušuje syntax a proces vytvárania šablón HTML a prvkov DOM. JSX je napísaný ako vložený HTML v zdrojovom kóde, ale prepisuje sa na pokyny JavaScriptu pre stavbu DOM, čím získava to najlepšie z oboch svetov.
Virtuálny DOM je reprezentáciou DOMu spoločnosti React. Porovnaním so stránkou DOM je možné sledovať zmeny a modifikovať iba tie časti stránky, ktoré je skutočne potrebné upraviť, a nie radiť veľké časti stránky na analýzu a opätovné vykreslenie.