Document Object Model
slides: http://codylindley.com/domit
Why is the native DOM rarely written or talked about?
vast source of incompatibility, pain and misery
Nearly every DOM method is broken in some way, in some browser
Clearly it was a mess!
Is it still a mess today?
The mess is not as messy as the mess once was.
Browser Wars
APIs like the Document Object Model
In 2002 the war ended. The aftermath left browser developers with incompatible DOM implementations. So the work of standardizing started.
Standardizing is a complicated & timely venture. The hardships befalling developers and browser venders were many.
A decade later.
Modern browser are more alike than not.
Let us forgive and forget the development pains of the past.
It's time to embrace and know the DOM.
So let's talk modern DOM.
(IE9+, Chrome, Firefox, Opera, Safari)
The DOM is a specification(s) describing how an HTML document can be parsed into a structured tree of JavaScript node objects (with properties and methods) for the purpose of scripting the document and its nodes.
Parsing an HTML document into a tree structure of nodes objects:
Types of nodes:
keys(Node);
values(Node);
We're going to focus on:
Node.DOCUMENT_NODE === 9
Node.ELEMENT_NODE === 1
Node.TEXT_NODE === 3
We're going to focus on:
#document or document
<element></element>
<element>text</element>
We're going to focus on:
$(document)
$('<element></element>');
$(document.createTextNode('foo')).text()
What is the first node in the DOM tree?
Is it <html>
, <!doctype html>
, or document
?
The document node (e.g. #document or document
)
activeElement, doctype, documentElement, head, body, defaultView
The element node
(e.g. <element></element>
)
ownerDocument, tagName
Element node attributes?
(class="foo" data-foo="foo")
attributes
getAttribute(), setAttribute(), hasAttribute(), removeAttribute()
classList, classList.add(), classList.remove(), classList.toggle(), classList.contains()
dataset (no ie9)
style, style.setProperty(), style.getPropertyValue(), style.removeProperty()
The text node
(<tag>text</tag>
)
data, textContent
Let's review.
Find something, do something.
Finding nodes
(i.e. creating or using preselected Nodelists & HTMLCollections)
getElementsByTagName(), getElementsByClassName(),
querySelectorAll(css selector)
Pre-selections:
childNodes, children, document.scripts, document.styles, document.all, document.forms, document.images, document.links
static v.s. live collections/lists
live:
childNodes, children, getElementsByTagName(), getElementsByClassName(), document.scripts, document.styleSheets, document.all, document.images, document.links, document.forms
static:
querySelectorAll()
Iterating DOM nodes
[].forEach.call(document.querySelectorAll('a'),function(elm){});
Finding a specific node
querySelector(), getElementById()
Contextual selecting (i.e. $('a','.context')
)
querySelector(), querySelectorAll(), getElementsByTagName(), getElementsByClassName()
Doing something
Element nodes: innerHTML, outerHTML, textContent, innerText, outerText, insertAdjacentHTML(), insertAdjacentElement(), insertAdjacentText(), insertBefore(), appendChild(), replaceChild(), removeChild()
,prepend(), append(), before(), after(), replace(), remove()
Text nodes: data, appendData(), deleteData(), insertData(), replaceData(), subStringData()
Doing Something, continued
Traversing any node: firstChild, lastChild, nextSibling, previousSibling, parentNode
Traversing element nodes: firstElementChild, lastElementChild, nextElementChild, previousElementChild, parentElement
Dude, jQuery!
Ok, the DOM isn't as bad as it once was. Now what?
Thanks!
window.addEventListener('mousemove',function(){
console.log('window');
},false);
document.addEventListener('mousemove',function(){
console.log('document');
},false);
document.body.addEventListener('mousemove',function(){
console.log('body element');
},false);
The document fragment node
(Node.DOCUMENT_FRAGMENT_NODE === 3
)
var doc = document.createDocumentFragment();
doc.appendChild(document.createElement('div'));
doc.firstChild.innerHTML = '<ul><li>list item</li></ul>';