Статьи

Автор: lusever
Опубликована: 10 апреля 2008, lusever.livejournal.com/18870.html

Нативные события в браузерах

Примечание от sunnybear: в данной заметке lusever рассматривает наиболее компактные способы назначения обработчиков событий для элементов DOM-дерева. Рекомендуется читать вместе со статьями «отложенная» загрузка и ускоряем обработку событий.

Только практические javascript решения, без всякой теории о всплытии и захвате.

Рекомендую использовать выражения, идущие в конце логического блока.

Ловим

В html

  • В начале выполнится функция, потом переход по ссылке
    <a href="#" onclick="func()">я ссылка</a>
  • Переход не выполнится (см. preventDefault)
    <a href="#" onclick="func(); return false">я ссылка</a>
  • Переход зависит от того, вернет ли func false
    <a href="#" onclick="return func()">я ссылка</a>
  • Передаем доступные параметры (порядок не важен):
    this — нода
    event — тут значение имеет то, что мы передаем:
    • function(event) — получим кросс-браузерный вариант
    • function(e) — передаст объект Event только для не IE браузеров
    <a href="#" onclick="func(this, event)">я ссылка</a>

В javascript

  • <a href="#" id="link">я ссылка</a>
  • var node = document.getElementById('link')
  • Назначаем напрямую
    node.onclick = function(){
    
        this == node // true
        }
  • Если нужно несколько событий, или просто «осторожничаем». Это распространенная запись
    if (node.addEventListener)
        node.addEventListener('click', function(e){}, false)
    
    else
        node.attachEvent('onclick', function(){})
  • То же самое, но меньше символов
    if (node.attachEvent)
        node.attachEvent('onclick', function(){})
    
    else
        node.addEventListener('click', function(e){}, false)
  • Способ с переменной
    var addEvent = node.attachEvent || node.addEventListener
    addEvent(/*@cc_on 'on'+@*/'click', function(){}, false)
  • В одну строку с использованием условной компиляции
    node[/*@cc_on !@*/0 ? 'attachEvent' : 'addEventListener'](/*@cc_on 'on'+@*/'click', function(){}, false)

Работаем с событиями

  • node[/*@cc_on !@*/0 ? 'attachEvent' : 'addEventListener'](/*@cc_on 'on'+@*/'click', function(e){
    
        var target = e.target || e.srcElement
    
        // или
        if (!e.target)
    
            e.target = e.srcElement
    
        // или если нам надо всего разочек
        (e.target || e.srcElement).tagName
    
    
        this == node // true везде кроме IE, в котором  this == window
    
    
        /* Отменяем всплытие */
        if (e.stopPropagation)
            e.stopPropagation()
    
        else
            e.cancelBubble
    
        // или просто: используем вариант, который для совместимости работает во всех браузерах. 
        // В FF2 причем быстрее stopPropagation, в остальных не смотрел
        e.cancelBubble = true
    
    
        /* Убираем действие по умолчанию (в данном случае клик) */
        if (e.preventDefault)
            e.preventDefault()
    
        else
            e.returnValue = false
    
        // при attachEvent (как здесь) работает только в IE; 
        // при назначении напрямую (node.onclick)  везде
    
        return false
    
    }, false)

Дополнительный материал:

Спасибо за помощь shabunc shabunc и crazyprotein crazyprotein.

Все комментарии