Witold Wrotek, „Javascript i jQuery. 131 praktycznych skryptów” – przykładowy rozdział

1 stycznia 2015 przez Comandeer | Opublikowany w Książki

Tagi: , ,

0

Dwóch rzeczy nienawidzę tak bardzo, że mnie aż skręca, gdy na nie natrafię: złych książek oraz szerzenia przestarzałych lub po prostu nieprawdziwych informacji o technologiach webowych. A już do prawdziwego szału doprowadzają mnie złe książki szerzące przestarzałe lub po prostu nieprawdziwe informacje o technologiach webowych. Oczywiście gromy mego gniewu (jak to drzewiej bywało) spadną na wydawnictwo Helion, jako de facto jedyne fachowe webmasterskie wydawnictwo w Polsce, a dokładniej na ich najnowszą propozycję (z tego roku – tak, mamy 1 stycznia) – Javascript i jQuery. 131 praktycznych skryptów, autorstwa Witolda Wrotka, której co prawda nie posiadam, lecz nieopatrznie spojrzałem do przykładowego rozdziału, przyciągnięty tytułem.

Zacznijmy od tego, że nie jestem fanem papierowych książek dotyczących programowania – zwłaszcza tego związanego z Siecią. Czemu? Bo książki są nieaktualne w dniu premiery. Raczej widziałbym całkowicie inny model wydawniczy: książki powstają jako Open Source (albo na licencji CC) i ich „kod” ląduje na GitHubie, gdzie każdy zaznajomiony z tematem może dowalić swoim pull requestem, naprawiając wyłapane błędy. A jeśli całość naskrobiemy np. w Markdown i wrzucimy do gałęzi gh-pages, mamy autopublikującą się pozycję, która może zostać uaktualniona w ciągu kilku chwil. Pomijam już dostępność przykładów kodu, które po prostu byłyby razem z książką. Open Source publishing! A dla tradycjonalistów możliwość wydrukowania sobie ładnie sformatowanej książki. Można? Można, ale przecież hajs się musi zgadzać. Kilku osobom ten pomysł już pokazałem i każda z nich pokiwała z powątpiewaniem głową i stwierdziła, że na tym się nie da zarobić… Cóż, wydaje mi się, że jeśli ktoś ma dostateczną wiedzę, żeby taką książkę napisać, nie musi zarabiać na swojej grafomanii, bo trzepie dużą kasę na czym innym. No ale koniec tego marudzenia, pomarudźmy o przykładowym rozdziale!

Oczywiście opierajac tę recenzję na przykładowym rozdziale, wychodzę z założenia, że skoro ten rozdział ma mnie zachęcić do kupna, to pokazuje to, co najlepsze w książce. Zasadnym jest zatem wyrobienie sobie zdania o całości (zasada koła hermeneutycznego: całość opisuje części, a części całość!), niemniej ostrze mej krytyki jest głównie wymierzone w to, co czytałem.

  • Na początek spis treści… Źle się dzieje, gdy błędy są już w nim. Tu niestety tak mamy (ba, błąd jest nawet na okładce! Ale o nim za chwilę). Pomijam już tutaj dość dziwną kolejność rozdziałów (najpierw uczymy się obliczać – gdzie też, nie wiem czemu, opisano typ logiczny zmiennych – a dopiero później zapoznajemy się z… liczbami w JS) czy szalenie niefortunny termin „witalizacji strony” (jakby ktoś miał wątpliwości – chodzi o ożywienie strony animacjami) – jest tutaj błąd, który dyskwalifikuje tę książkę jeszcze przed dotarciem do treści. Otóż widzimy tutaj… rozwinięcie „skrótu” jQuery. Problemem jest to, że jQuery to nie skrót. Ale ok, jeszcze bym to jakoś przecierpiał, gdyby to rozwinięcie nie było całkowicie bezsensowne. Bo kto normalny nazwałby helper DOM-owy, naskrobany w JS, JavaQuery? Owszem, coś takiego istnieje, ale jest zbiorem API dla Javy, a Java ma się do JS jak – parafrazując inny klasyk Heliona – szynka do hamburgera. Mylenie tych dwóch języków jest po prostu niewybaczalne i wręcz obraźliwe dla twórców tej biblioteki.
  • No właśnie – biblioteki. Powróćmy do okładki, gdzie znajdziemy taki passus:

    jQuery, czyli genialny framework pełen skryptowych gotowców

    Okładka prawdę mówiąca

    Otóż jQuery nie jest frameworkiem – to biblioteka (a jeszcze dokładniej można go nazwać helperem/wrapperem DOM-owym), której głównym zadaniem jest zapewnianie międzyprzeglądarkowej zgodności. Tyle i aż tyle. Poza tym – pojęcie frameworka z założenia wyklucza gotowce. Sam jQuery nazywa siebie biblioteką:

    jQuery is a fast, small, and feature-rich JavaScript library.

    jQuery we własnej osobie (chociaż mówi o sobie w 3. osobie)

    Czemu? Bo framework to jednak co innego i de facto każdy posiada IoC (Invertion of Control – Odwrócenie Sterowania) oraz służy za szkielet aplikacji. jQuery natomiast po prostu… pomaga nam operować na DOM. Nic więcej.

  • Ok, przejdźmy do przykładowego rozdziału, poświęconego zdarzeniom. Już 1. zdanie wprawiło mnie w zakłopotanie:

    Zdarzenia dzielą się na zdarzenia HTML i HTML DOM.

    Otóż nie. Coś takiego, jak zdarzenia HTML nie może istnieć z prostego powodu: HTML nie definiuje żadnych zdarzeń. Owszem, specyfikacja HTML5 definiuje atrybuty HTML, które jako swoją wartość biorą tekst mający się wykonać jako JS (który de facto zostaje przez przeglądarkę przepuszczony przez konstruktor Function, co jest zawoalowaną postacią eval), ale są to atrybuty, nie – zdarzenia. HTML jest wyłącznie tekstem, który trzeba sparsować, a tekstowi średnio są potrzebne jakiekolwiek zdarzenia. Wszystkie zdarzenia są częścią standardu DOM, czyli „przestrzennego” modelu, który powstaje po przetrawieniu przez przeglądarkę HTML-a. Wówczas, zamiast tekstu, dostajemy ładną hierarchię obiektów – a na obiektach można operować o wiele swobodniej niż na tekście. Nie zgodzę się także z nazywaniem DOM HTML DOM-em – równie dobrze może to być SVG DOM, XML DOM, RSS DOM, SGML DOM itd. Każdy z tych języków może być przekonwertowany do postaci drzewka, zatem w teorii każdy może być oskryptowany w ten sposób (oczywiście w praktyce skryptuje się jedynie HTML i SVG, w rzadkich wypadkach XML). Bardzo płynny i dziwny jest także sam podział, np do zdarzeń HTML zostało zaliczone:

    zmiana zawartości pola do wpisywania danych

    Natomiast kilkanaście linijek niżej czytamy:

    HTML DOM (ang. Document Object Model — model obiektów dokumentu) to standard określający sposoby zmiany zawartości, właściwości i parametrów poszczególnych elementów strony HTML.

    Mam wrażenie, że zostało tutaj pomylone samo zjawisko zdarzeń z systemem obsługi zdarzeń. Co więcej, nie zgodzę się z tłumaczeniem terminu Document Object Model jako modelu obiektów dokumentu. Jest to raczej obiektowy model dokumentu, bo opisuje cały dokument i jego części jako hierarchiczną strukturę, nie natomiast – stronę jako poszczególne obiekty.

  • Dziwi mnie także używanie terminu program do opisywania skryptów JS (a raczej – całych stron internetowych, które są przez nie obsługiwane). Dziwi mnie też używanie tego samego terminu w stosunku do funkcji obsługujących zdarzenia (w tym wypadku, jeśli przystalibyśmy na termin program, bardziej poprawny byłby termin podprogram). Skrypty i funkcje brzmią mniej pretensjonalnie.
  • Później mamy do czynienia z 1. przykładem w tym rozdziale (a 50. w książce), odnośnie zdarzeń związanych z myszą. Mamy nawet ładną tabelkę, w której zebrano zdarzenia HTML DOM związane z myszą. Nie zebrano wszystkich zatem. Brakuje np. zdarzeń związanych z obsługą kółka myszy. Inna rzecz – nazwy zdarzeń nie zawierają on. Polecam spojrzeć do specyfikacji zdarzeń DOM i poszukać zdarzeń myszki. Zapis zdarzeń z on na początku to pozostałość po tzw. DOM0, które od dawien dawna było niestandardowym sposobem wiązania zdarzeń i dopiero ustandaryzowano go w specyfikacji HTML5. DOM0 wywodzi się z całkowicie bzdurnych i przestarzałych atrybutów [on…]. Dlatego nie mogę się zgodzić, że ta tabelka zawiera spis zdarzeń dotyczących myszki – to jest spis zachowanych dla bożka BC starych błędów W3C. Obecnie istnieją o wiele lepsze sposoby przypinania zdarzeń i tego typu antyki powinny w końcu odejść do lamusa – a już na pewno nie powinny być promowane w książce z 2015 roku.

    Pomijam już fakt, że w opisie tych zdarzeń i tak są błędy:

    onmouseout Zdarzenie występuje, gdy użytkownik przesuwa wskaźnik myszy na element lub z jednego z jego dzieci.

    Nie prościej napisać, że użytkownik po prostu zsuwa wskaźnik z elementu lub jednego z jego dzieci?

  • Następnie następuje kod przykładowej strony i choć jest króciutki, łamie wiele z dobrych praktyk. Zacznijmy od początku:

    <!DOCTYPE HTML PUBLIC "
    -//W3C//DTD HTML 4.01 Transitional//EN"
    "http://www.w3.org/TR/html4/loose.dtd">

    Transitional, czyli tryb prawie zgodności ze standardami. Byłoby prawie dobrze, gdybyśmy nie mieli roku 2015.

    There’s absolutely no reason whatsoever for using an HTML4 doctype. Just put the <!DOCTYPE HTML> doctype on your HTML documents and make sure they’re served as text/html and be done with it. Move on with your life.

    Mike[tm] Smith, HTML5 – Check it Before you Wreck it with Mike[tm] Smith

    I taka jest prawda!

    Dalej brakuje znacznika otwierającego html, za to końcowy już jest – ciut konsekwencji.

    <meta http-equiv="CONTENT-LANGUAGE" CONTENT="PL">

    meta[http-equiv] są ekwiwalentem dla nagłówków HTTP, więc to tylko atrapa. Ta jest tym bardziej kaleczna, że… została uznana za całkowicie zbędną i zamiast niej należy używać określania języka przez html[lang].

    <meta http-equiv="content-type" CONTENT="text/html; CHARSET=iso-8859-2">

    UTF-8 powinien być używany de facto wszędzie i nowy walidator W3C zwraca na to uwagę.

    <meta http-equiv="Content-Script-Type" content="text/javascript">

    A ta linijka nie robi nic i nic nie znaczy – można ją z powodzeniem usunąć. W teorii był taki wymóg, ale żadna przeglądarka nigdy tego mechanizmu nie zaimplementowała – i słusznie, bo jest bezsensowny.

    <script>
    document.write("<h1>050</h1>");
    </script>

    document.write powinno być unikane za wszelką cenę, ponieważ blokuje speculative rendering (spekulatywne renderowanie strony) – przeglądarka na każdej tego typu deklaracji musi się zatrzymać, sparsować ją i wykonać, gdyż ta komenda modyfikuje drzewko DOM w miejscu swego wstawienia; w innym wypadku przeglądarka może „zgadywać” DOM, co skutkuje o wiele szybszym wyświetlaniem strony, wyklucza użycie Ajaksu – document.write, wywołany na już załadowanej stronie, nadpisuje ją całą, nie działa w trybie XML (to akurat najmniejszy problem) i nie oferuje żadnej wartości dodanej w stosunku nawet do równie prymitywnego element.innerHTML. A już tworzenie treści strony przy pomocy tej metody to czyste szaleństwo. Treść jest treścią i nie powinna mieć nic wspólnego z JS (prawda, Angular.js?).

    <h1 onclick="this.innerHTML='Dziękuję!'">Kliknij tekst!</h1>

    O tym wspominałem już wcześniej, ale tutaj jeszcze trochę dopowiem. Oprócz już wymienionych powodów, ten zapis miesza warstwy aplikacji i wymusza obniżenie bezpieczeństwa strony, gdyż zaprzecza zasadom Content Security Policy (Polityki Bezpieczeństwa Treści). I nie, zezwolenie na skrypty i style inline nie jest ok – jest głupotą, porównywalną do używania telefonu jako młotka (da się, ale… no właśnie).

  • Kolejny przykład (o numerze 51) cierpi na dokładnie te same problemy, więc nie będę nad nim elaborował.
  • Natomiast przykład 52. jest bardzo ciekawy i jego główna część wygląda tak:

    <div onmouseover="mysz_nad(this)" onmouseout="mysz_na_zewn(this)"
    style="background-color:#EEEEEE;width:200px;height:20px;padding:20px;">
    Przesuń kursor nad prostokąt!</div>

    Co tu mamy? Rollover w stylu starego, dobrego DHTML-a z 2002 roku (serio, dam se rękę uciąć, że podobne przykłady widziałem w… podręczniku do TI właśnie z 2002 roku). Uderza tutaj już sama bzdurność zastosowania atrybutów [on…], co bardzo udziwnia sam proces obsługi zdarzenia.

    function mysz_nad(obj) {
    	obj.innerHTML = "Widzisz, jakie czary!"
    }

    Bardzo rzadko widuję konwencję z podkreślnikiem w JS – raczej się stosuje camelCase. Jeszcze rzadziej widuję nazwy funkcji w języku polskim – angielski jest tutaj niepisanym standardem. A o przekazywaniu do handlera zdarzenia obiektu, na którym zdarzenie zaszło, zapomniałem 10 lat temu. Jeśli ta funkcja byłaby przypięta normalnie, ten obiekt byłby po prostu kontekstem wywołania (byłby dostępny jako this), a my, zamiast bezsensownego przekazywania go jako 1. parametr, zamiast tego dostalibyśmy obiekt samego zdarzenia. I choćby dlatego nie miesza się JS z HTML – z tego nigdy nie wychodzi nic dobrego, tylko dziwactwa tego typu. Jak to można rozwiązać bardziej elegancko? Choćby tak:

    <div
    style="background-color:#EEEEEE;width:200px;height:20px;padding:20px;">
    Przesuń kursor nad prostokąt!</div>
    <script>document.getElementsByTagName('div')[0].addEventListener('mouseover', function(e)
    {
    	this.innerHTML = 'Widzisz, jakie czary!';
    }, false);</script>

    Do tego przerzucić style do CSS, tam, gdzie ich miejsce i dorobić obsługę drugiego zdarzenia i jesteśmy w domu. Elegancko, schludnie, zgodnie ze sztuką. Tutaj trzeba jeszcze zwrócić uwagę, że nie poleca się używania zdarzeń mouseover i mouseout, gdyż de facto zawsze lepsze rezultaty da zastosowanie mouseenter i mouseleavemouseover odpala się bowiem nawet przy przejściu z dziecka na rodzica, co jest po prostu frustrujące (jedynym powodem, dla których te zdarzenia były używane była… opieszałość Chrome, który do niedawna wciąż nie wspierał mouseenter i mouseleave). A w wypadku rollovera JS i tak jest artylerią na muchę, bo wszystko, czego potrzebujemy to :hover i pseudoelementy (bo właściwość CSS content wciąż nie działa na normalnych elementach, chociaż zgodnie ze specyfikacją powinna…).

  • Kolejny, 53., przykład cierpi na inne problemy – jeden związany jest z wykorzystaniem złego zdarzenia, a drugi ze złamaniem konwencji stylistycznej JS, która jest de facto standardem. Zacznijmy od tego drugiego problemu, bo jest o wiele prostszy do zobaczenia i wyjaśnienia.

    function Funkcja()
    {
    var x=document.getElementById("znak");
    x.value=x.value.toUpperCase();
    }

    Chodzi o nazwę tej funkcji – nie powinna być dużą. Zgodnie ze standardowymi konwencjami nazewniczymi, duża litera zarezerwowana jest dla konstruktorów. Kropka.

    Pomijam tutaj jak duża jest niespójność stylistyczna pomiędzy poszczególnymi sposobami – kod JS między przykładem 52. a 53. różni się tyloma szczegółami, że wygląda jakby pisały go dwie różne osoby. To jest niedopuszczalne. Po to istnieją tzw. styleguides, żeby zachować całkowitą spójność w obrębie całego systemu. A przestrzeganie konwencji jest ważne zwłaszcza wówczas, gdy uczymy innych.

    Drugim problemem związanym z tym przykładem jest zastosowanie złego zdarzenia. Owszem, wykrywanie wpisywania danych do pola wykonywało się dawniej przy pomocy zdarzeń takich jak keypress czy keyup, ale te czasy bezpowrotnie minęły. Obecnie od obsługi zdarzeń związanych ze zmianą zawartości pola, oprócz standardowego change, mamy także input. Czemu nowe zdarzenie? Bo reaguje na zmianę zawartości pola, a nie na naciśnięcia klawiszy – jak widać, zakresy użycia tych zdarzeń są różne (można stwierdzić, że niejako input zawiera się w zdarzeniach key…). Co więcej, zdarzenie input jest de facto obsługiwane wszędzie. Zatem lepszy sposób na obsługę tego problemu byłby taki:

    document.getElementById('znak').addEventListener('input', function(e)
    {
    	this.value = this.value.toUpperCase();
    }, false);
  • Kolejny przykład (54.) związany jest z obiektami (ramkami). Nie jest to właściwa nazwa, gdyż obiektami są wszystkie elementy DOM na stronie, w tym ramki. Co więcej, ten przykład operuje na dokumencie, nie na ramce. Poprawne nazewnictwo czasami jest bardzo istotne! Oczywiście mamy także tabelkę z opisem potrzebnych nam zdarzeń, niemniej są w niej rażące błędy.

    onerror Obraz nie został załadowany prawidłowo (dla <object>, <body> i  frameset ).

    A img? A dźwięki? A filmy? A iframe? Zdarzenia tutaj opisane dotyczą wszystkich zasobów. Przy okazji – od dawien dawna nie widziałem object na żywo (hint: standaryzacja embed to dobra rzecz). Pomijam fakt, że body to raczej nie obraz.

    onunload Strona nie została załadowana (ma zastosowanie zarówno dla <body> , jak i <frameset>).

    I znów – co z iframe choćby? frameset wszak nie używa się od lat. No i to zdarzenie oznacza moment, w którym strona jest „odładowywana”, czyli de facto wtedy, gdy użytkownik wyłącza kartę przeglądarki. Jeśli strona nie została załadowana, to, w zależności od powodu, odpala się zdarzenie error lub abort.

    Wygląda na to, że te wszystkie tabelki to niedokładne tłumaczenie ze specyfikacji HTML4.

    Co do samego przykładu – zamiast czekać z odpaleniem JS-a na zdarzenie load (które oczywiście powinno zostać poprawnie przypięte i to nie do body, ale do obiektu window), wystarczy przenieść skrypt na koniec body. Dzięki tej technice de facto od lat nie korzystam ze zdarzenia load dla stron (wyjątkiem jest konieczność odpalenia skryptu dla stron z wczytanymi wszystkimi obrazkami – wówczas trzeba na to zdarzenie poczekać). No i tutaj wypadałoby od razu wspomnieć o zdarzeniu DOMContentLoaded, które jest podstawą dla jQuery’owego $(document).ready.

  • Kolejny przykład dotyczy formularzy, więc standardowo dostajemy tabelkę ze zdarzeniami… w której znów jest błąd.

    onfocus Zdarzenie występuje, gdy element uzyskuje fokus (ma zastosowanie dla <label>, <input>, <select>, <textarea> oraz <button>).

    Zacznijmy od tego, że zdarzenia focus i blur są przeznaczone dla wszystkich elementów focusowalnych, więc np. również dla linków i dla wszystkich tych elementów, które mają atrybut [tabindex] – więc nie są to zdarzenia formularzowe. Co więcej – nie sądzę, żeby label odpalał to zdarzenie, gdyż nie jest elementem focusowalnym.

    Co do podanego przykładu – blur nie jest odpowiednim zdarzeniem do odpalania funkcji na zawartości pola. Do tego służą zdarzenia change i input.

  • A dalej to już w ogóle mega sajgon.

    Zdarzenia HTML DOM związane z właściwościami

    To wyrażenie nie ma najmniejszego sensu! Tym bardziej, że to, co jest hucznie nazywane zdarzeniami HTML DOM, jest tak naprawdę… właściwościami wcześniej już wspominanego przeze mnie obiektu event. Powtórzę raz jeszcze: nazywanie rzeczy poprawnymi nazwami jest ważne – zwłaszcza, jeśli kogoś uczymy!

    Oczywiście dostajemy tabelkę tych własności, w której wcale nie jest lepiej:

    eventPhase Zwraca informację, która faza przepływu zdarzeń jest obecnie oceniana.

    Eh, nienawidzę tworzenia na siłę polskich odpowiedników uznanych ogólnie nazw!!! Jeśli już tworzymy takie dziwactwa, podawajmy też odpowiedniki angielskie. Poza tym – to zdanie nie ma sensu. Jak można oceniać sposób propagacji zdarzenia? Ta własność zwraca typ propagacji zdarzenia (event propagation phase) – niczego nie ocenia!

    Bąbelkowanie to odpowiadanie na zdarzenia w trakcie ich propagacji od obiektu docelowego do obiektów zewnętrznych.

    To chyba najgorsze wytłumaczenie dla bąbelkowania, jakie słyszałem. Nie ma obiektów zewnętrznych – to nie są bańki włożone jedna w drugą. Mówimy o drzewie DOM, zatem to propagacja w górę drzewa. Ale zamiast niepotrzebnie się produkować, odeślę do kogoś, kto umie bardzo dobrze tłumaczyć.

    <p onclick="stoper(event)">

    Jak już pokazałem wyżej, przy normalnie dodanym event handlerze zdarzenie zostałoby dodane z automatu. Składnia dodania tego zdarzenia w JS mogłaby wyglądać następująco:

    document.getElementsByTagName('p')[0].addEventListener('click', stoper, false);

    Tak, wystarczy podać sam uchwyt do funkcji (nazwę, nieotoczoną apostrofami/cudzysłowami).

    Co więcej, podawanie obiektu zdarzenia (zresztą this też to dotyczy) w atrybucie [on…] wygląda dziwnie. Dostajemy bowiem znikąd dwie rzeczy – ki czort?! Jeśli natomiast przeniesiemy całość do JS, kod staje się o wiele przyjemniejszy. No i operujemy na prawdziwym kodzie, a nie evalowanym stringu (kolejny z mega problemów Angulara!).

  • Dla przykładu 57. z kolei zrobiono dziwną rzecz – połączono właściwości zdarzeń MouseEvent i KeyboardEvent. Nie rozumiem tego – to są zupełnie dwa różne interfejsy. No bo chyba wszyscy zdają sobie sprawę, że mysz ma wskaźnik i służy do wskazywania, a klawiatura ma klawisze i służy do pisania. Ba, brakuje dla klawiatury tak podstawowej rzeczy jak własności key (lub keyCode), która przechowuje kod aktualnie wciśniętego klawisza – są za to własności keyIdentifier i keyLocation, które na żywo w kodzie widziałem aż raz i było to demo dla specyfikacji DOM.

    W samym przykładzie natomiast zdarzenie mousedown nazywa się kliknięciem – co nie jest do końca prawdą (i było nawet wyjaśnione w 1. tabelce w tym rozdziale!). Pomijam fakt, że dema dla klawiatury nie ma w ogóle…

  • Przykład 58. nie ma nic wspólnego ze zdarzeniami i w ogóle nie powinien się znajdować w tym rozdziale.

    Obiekt Anchor reprezentuje element <a> języka HTML.

    Zacznijmy od tego, że obiekt Anchor nie istnieje. Po drugie – to nie byłby obiekt, lecz konstruktor DOM-owy, czyli coś zupełnie innego. Tak naprawdę rozchodzi się tutaj o interfejs HTMLAnchorElement (to „klasa”, po której dziedziczą wszystkie linki na stronie). To nie ma nic do czynienia ze zdarzeniami – to po prostu warstwa abstrakcji, pozwalająca dokładnie opisywać konkretny typ elementów na stronie. Być może interfejs ten jest prezentowany z powodu tego, że zawiera dodatkowe metody, dedykowane dla linków? Jeśli tak – to czemu nie prezentuje się jeszcze bardziej wypasionego HTMLAudioElement czy HTMLImageElement?

    Tabelka dla „obiektu Anchor” również zawiera błędy.

    Nie jest obsługiwana w HTML5

    Nie jest dozwolona przez specyfikację HTML5 – a to spora różnica. Przeglądarki te własności linków dalej rozumieją i radzą sobie bez problemu, z powodu bożka BC.

    download Ustawia lub zwraca wartość atrybutu download linku.

    Pomijam już fakt, że to tłumaczenie nic nie tłumaczy (ta tabelka wygląda jak przepisanie co ciekawszych atrybutów ze specyfikacji HTML5). Jest też po prostu błędne. Jest spora różnica między atrybutami elementu, a własnościami obiektu DOM. Owszem, atrybuty są przepisywane na własności, ale własności na atrybuty – niekoniecznie. Od operacji na atrybutach są metody element.getAttribute i element.setAttribute, natomiast odwołania typu element.nazwa działają bezpośrednio na własnościach obiektów DOM. I tą różnicę warto znać i rozumieć.

    name Nie jest obsługiwana w HTML5. Zamiast niej należy używać id. Ustawia lub zwraca wartość atrybutu id linku.

    Oczywiście wszystko, co napisałem powyżej, tyczy się także tego punktu. Niemniej jest tu jeszcze jeden błąd – name ustawia własność name obiektu DOM. Automagicznie nagle w HTML5 nie zaczęło wpływać na element.id – bożek BC czuwa.

    W ogóle jestem zawiedziony tym przykładem – myślę, że fajniejsze byłoby pokazanie dynamicznego parsowania linków z formularza przy pomocy programo utworzonego linku, np. coś takiego.

Powiem tak: jestem przerażony. W przypadku tego przykładowego rozdziału praktycznie każde zdanie zawiera jakiś błąd merytoryczny. To nie napawa optymizmem w stosunku do reszty książki. I, niestety, powiększa moją awersję do polskich wydawnictw informatycznych. W chwili obecnej nie mamy dobrej literatury tego typu…

Napisz komentarz

Uwaga! Uprasza się komentujących, którzy chcą obrazić autora, aby najpierw dokonali niezbędnego researchu jego osoby. Z góry dziękujemy za poświęcony czas.