Слушатели событий, зарегистрированные для фазы захвата, не запускаются до пузырения - почему?

Я пытаюсь понять, что определяет порядок срабатывания обработчиков событий при нажатии вложенного <div> - то, что я вижу, похоже, противоречит документированному поведению, поэтому я ищу небольшую помощь для понимания он.

У меня есть 2 вложенных divs, и у меня есть 2 обработчика событий, прикрепленных к каждому, один для фазы захвата и один для фазы барботирования:

<html>
    <head>
        <script>
            function setup(){
                var outer = document.getElementById('outer');
                outer.addEventListener('click', function(){console.log('outer false');}, false);
                outer.addEventListener('click', function(){console.log('outer true');}, true);

                var inner = document.getElementById('inner');
                inner.addEventListener('click', function(){console.log('inner false');}, false);
                inner.addEventListener('click', function(){console.log('inner true');}, true);
            }           
        </script>
        <style>
            div {
                border: 1px solid;
                padding: 1em;
            }
        </style>
    </head>
    <body onload="setup()">
        <div id="outer">
            <div id="inner">
                CLICK
            </div>
        </div>
    </body>
</html>

В соответствии с тем, что я прочитал, вывод должен быть:

outer true
inner true
inner false
outer false

но то, что я на самом деле вижу (в Chrome и Firefox):

outer true
inner false
inner true
outer false

Может ли кто-нибудь объяснить несоответствие?

Ответы

Ответ 1

Спецификация потока событий W3C (т.е. реализация Chrome и Firefox) заключается в том, что все события сначала захватываются до тех пор, пока они не достигнут целевого элемента, после чего они снова начнут пузыриться. Однако, когда поток событий достигает самой цели события, событие больше не захватывает или не пузырится - оно на самой цели. Поскольку барботирование/захват не применимо, обработчики событий срабатывают в том порядке, в котором они зарегистрированы. Попробуйте поменять порядок обработчиков событий вашего внутреннего элемента, вы обнаружите, что он также изменяет порядок вывода консоли.

Пример jsFiddle: http://jsfiddle.net/RTfwd/1/

Более поздние версии спецификации DOM Event делают эту точку более ясной (http://dev.w3.org/2006/webapi/DOM-Level-3-Events/html/DOM3-Events.html):

фаза барботированияПроцесс, с помощью которого событие может обрабатываться одним из целевых предков после обработки целевым объектом. Подробнее см. Описание фазы пузырька в контексте потока событий.

фаза захвата. Процесс, с помощью которого событие может обрабатываться одним из целевых предков, прежде чем обрабатывать цель события. Видеть описание фазы захвата в контексте потока событий для более подробная информация.