DOM — робота з тегами HTML в JavaScript
ADO в Delphi AJAX Android C++ CakePHP CMS COM CSS Delphi Flash Flex HTML Internet Java JavaScript MySQL PHP RIA SCORM Silverlight SQL UML XML Бази даних Веб-розробка Генетичні алгоритми ГІС Гітара Дизайн Економіка Інтелектуальні СДН Колір Масаж Математика Медицина Музика Нечітка логіка ООП Патерни Подання знань Розкрутка сайту, SEO САПР Сесії в PHP Системне програмування Системний аналіз Тестологія Тестування ПЗ Фреймворки Штучний інтелект
|
DOM — робота з тегами HTML в JavaScript
Чтобы менять документ при помощи javascript, нужно знать DOM, а желательно и CSS. DOM (Document Object Model) - иерархическая модель документа. Вложенным HTML-таги соответствуют вложенные узлы дерева.
|
Выделить код <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> <html> <head> <title>Документ</title> </head> <body> <div id="dataKeeper">Data</div> <ul> <li style="background-color:red">Осторожно</li> <li class="info">Информация</li> </ul> <div id="footer">Made in Russia ©</div> </body> </html> |
Верхний таг - html
, у него дети head
и body
, и так далее. Получается дерево тагов:
Текст тоже образует DOM-узел. На рисунке такие узлы отмечены как #text
.
Это дерево представляет собой нормализованный DOM, в котором не создаются узлы из пустого текста. Такого подхода придерживается браузер Internet Explorer.
Firefox - другого мнения, он создает DOM-элемент из каждого текстового фрагмента.
Поэтому в Firefox дерево этого документа выглядит так:
На рисунке для краткости текстовые узлы обозначены просто решеткой. У body
вместо 3 появилось 7 детей.
Opera тоже имеет чем похвастаться. Она может добавить лишний пустой элемент "просто от себя".
Чтобы это увидеть - откройте документ по этой ссылке. Он выдает число дочерних узлов document.body
, включая текстовые.
У меня получается 3 для IE, 7 для Firefox и 8 (!?) для Opera.
На практике эта несовместимость не создает больших проблем, но нужно о ней помнить, особенно при обращении к свойству firstChild
и при переборе детей в цикле.
У каждого элемента в DOM-модели есть тип. Его номер хранится в атрибуте elem.nodeType
Всего в DOM различают 12 типов элемента.
Обычно используется только один: Node.ELEMENT_NODE
, номер которого равен 1. Элементам этого типа соответствуют HTML-таги.
Иногда полезен еще тип Node.TEXT_NODE
, который равен 3. Это текстовые элементы.
Остальные типы не используются.
Например, вот так выглядит документ из примера выше, если каждый видимый элемент обвести рамкой с цифрой nodeType
в правом верхнем углу.
Любой доступ и изменения DOM происходит через объект document
.
Самый верхний таг. В случае корректной HTML-страницы, это будет <html>
.
Таг <body>
, если есть в документе (обязан быть).
childNodes
. Например:
Выделить код for(var i=0; i<document.body.childNodes.length; i++) { if (document.body.childNodes[i].tagName == 'UL') { break; } } |
firstChild
и lastChild
показывают на первый и последний дочерние элементы и равны null
, если детей нет.parentNode
указывает на родителя. Например, для <body>
таким элементом является <html>
:
alert(document.body.parentNode == document.documentElement) // true |
previousSibling
и nextSibling
указывают на левого и правого братьев узла.
В общем. если взять отдельно <body>
с детьми из нормализованного DOM - такая картинка получается ОТ <body>
:
И такая - для ссылок наверх и между узлами:
childNodes
firstChild
, lastChild
.parentNode
previousSibling
, nextSibling
Этих свойств вполне хватает для удобного обращения к соседям.
У DOM-элементов есть масса свойств. Обычно используется максимум треть из них. Некоторые из них можно читать и устанавливать, другие - только читать.
Есть еще и третий вариант, встречающийся в IE - когда устанавливать свойство можно только во время создания элемента.
Рассмотрим здесь еще некоторые (не все) свойства элементов, полезные при работе с DOM.
tagName
Атрибут есть у элементов-тагов и содержит имя тага в верхнем регистре, только для чтения.
Например,
alert(document.body.tagName) // => BODY |
style
Это свойство управляет стилем. Оно аналогично установке стиля в CSS.
Например, можно установить element.style.width
:
Исходный код этой кнопки:
Выделить код
<input
type="button"
style="width: 300px"
onclick="this.style.width = parseInt(this.style.width)-10+'px'"
value="Укоротить на 10px"
/> |
onclick
обращается в этом примере к свойству this.style.width
, т.к значением this
в обработчике события является текущий элемент (т.е сама кнопка). Подробнее об этом - во введении в события.
Есть общее правило замены - если CSS-атрибут имеет дефисы, то для установки style
нужно заменить их на верхний регистр букв.
Например, для установки свойства z-index
в 1000, нужно поставить:
element.style.zIndex = 1000 |
innerHTML
Когда-то это свойство поддерживалось только в IE. Теперь его поддерживают все современные браузеры.
Оно содержит весь HTML-код внутри узла, и его можно менять.
Свойство innerHTML применяется, в основном, для динамического изменения содержания страницы, например:
document.getElementById('footer').innerHTML = '<h1>Bye!</h1> <p>See ya</p>' |
Пожалуй, innerHTML - одно из наиболее часто используемых свойств DOM-элемента.
className
Это свойство задает класс элемента. Оно полностью аналогично html-атрибуту "class".
elem.className = 'newclass' |
onclick
, onkeypress,
onfocus
..... И другие свойства, начинающиеся на "on...", хранят функции-обработчики соответствующих событий. Например, можно присвоить обработчик события onclick
.
Подробнее об этих свойствах и обработчиках событий - см. введение в события.
DOM-элемент может иметь любое количество атрибутов. Для работы с ними служат следующие методы:
setAttribute(name, value)
getAttribute(name)
hasAttribute(name)
removeAttribute(name)
Имя атрибута является регистронезависимым. Поэтому будет работать, например. такой код:
document.body.setAttribute('test',123) document.body.getAttribute('TEST') // 123 |
Между атрибутами и свойствами есть одно существенное сходство. Установка некоторых атрибутов автоматически влияет на свойство, и наоборот.
Но есть и куча существенных различий.
document.body.setAttribute('abc', 1) document.body.setAttribute('ABC', 5) alert(document.body.getAttribute('abc')) // => о, уже 5 |
Но это два разных свойства.
document.body.abc = 1 document.body.ABC = 5 alert(document.body.abc) // => все еще 1 |
<body>
атрибут tagName
, но соответствующее свойство - только для чтения, поэтому оно не изменится:
document.body.setAttribute('tagName',1) document.body.getAttribute('tagName') // 1 document.body.tagName // "BODY" |
Вообще говоря, браузер не гарантирует синхронизацию атрибута и свойства.
onclick
, не является функцией и не будет работать:
elem.setAttribute('onclick', 'alert(something)') // в IE не работает |
Firefox корректно преобразовывает строку в функцию, поэтому там этот фрагмент работать будет. Но, вообще говоря, никакой браузер не обязан этого делать.
document.body.setAttribute('v',{a:5}) alert(document.body.getAttribute('v')) // "[object Object]" в Firefox alert(document.body.getAttribute('v').a) // 5 в IE |
В первой строке атрибуту присвоено значение-объект. Firefox тут же автоматически преобразовал его в строку. А IE, в нарушение стандартов, оставил атрибут объектом.
className
class
соответствует свойство className
. Так получилось из-за того, что class
является зарезервированным словом javascript.
В IE также является исключением ключевое атрибут for
, для него используется свойство forHtml
.
Cвойство элемента и атрибут - это разные вещи. Не используйте одно вместо другого.
Copyright © 2008—2022 Портал Знань.
При використанні матеріалів посилання, для інтернет-ресурсів — гіперпосилання, на Znannya.org обов'язкове.
Зв'язок
|
НТУУ "КПІ" Інженерія програмного забезпечення КПІ Лабораторія СЕТ |
|