
- •2. Что такое события в JavaScript
- •2.1. Как связать событие и JavaScript
- •2.3. Основные события в JavaScript
- •2.4. События, о которых не было сказано
- •3. Return к функциям (функции и события)
- •4. Еще один пример использования функций и событий
- •5. События и его свойства (Event)
- •5.1. Передача объекта Event внутрь обработчика события
- •5.2. Всплывание события cancelBubble
- •5.3. Вызов стандартного обработчика
- •5.4. Практика работы с мышью: перетаскивание элементов
- •6. Функции (нюансы) Итак, события мы рассмотрели полностью, но в функциях существует множество нюансов, поэтому следующая тема будет посвящена именно им.
- •6.1. Знакомство с рекурсией.
- •Пример на рекурсию
- •Р екурсии или итерации?
- •6.2. Функция – это переменная. Несколько видов объявлений функций.
- •6.3. Функция внутри функции
- •6.4. Условная функция
- •7. Самостоятельное задание:
5.3. Вызов стандартного обработчика
Существует ряд элементов в HTML, для которых определены некоторые обработчики событий по умолчанию или стандартные обработчики. Так для элемента <a> (гиперссылка) определен обработчик onСlick выполняющий переход на ресурс, заданный атрибутом href. Если вы желаете, чтобы после вашей обработки некоторого события стандартный обработчик не вызывался, присвойте значение false свойству returnValue объекта event.
<html> <head> <script type="text/javascript"> function clickHandler () { alert ("Пользовательский обработчик!"); } </script> </head> <body> <a class="btn" href="http://www.google.com/" onclick="clickHandler(); event.returnValue = false;">Это гиперссылка</a> </body> </html>
Помните, что то же самое мы могли сделать и при помощи return false. Зачем же нам эта конструкция?
Все дело в том, что return false не работает внутри функции-обработчика, и отменить действия стандартного обработчика внутри функции мы не сможем простым return false.
Давайте рассмотрим следующий пример:
<html> <head> <script type="text/javascript"> function clickHandler (e, elem) { e = e || window.event e.returnValue = confirm('Переход на страницу ' + elem.innerText + '.\nПродолжить?') } </script> </head> <body> <a class="btn" href="http://www.google.com" onclick="clickHandler (event, this);"> http://www.google.com </a> </body> </html>
Разберем пример по порядку. На странице расположена гиперссылка на web-узел Google. При щелчке на гиперссылке будет вызван обработчик события click – clickHandler, в который мы передаем объект Event и указатель на текущий элемент. Внутри обработчика вызывается функция confirm, в зависимости от кнопки, нажатой пользователем в диалоговом окне, будет возвращено значение true или false, которое будет присвоено переменной e.returnValue. Эта переменная отвечает за работу стандартного обработчика. Соответственно, если пользователь нажмет отмену, то по ссылке мы не перейдем. Таким образом, переход по гиперссылке осуществляется только в том случае, если пользователь согласится с переходом.
В принципе то же самое мы можем сделать и при помощи return false, но этот вариант будет предпочтительнее, потому что всю оюработку мы ведем в функции-обработчике.
5.4. Практика работы с мышью: перетаскивание элементов
Как любой уважающий себя web разработчик, вы, наверняка стремитесь сделать свои страницы приятными для пользователей. Это означает, что, наряду с приятным оформлением, ваша страница должна обладать еще и дружественным к пользователю интерфейсом. Последним "писком" в этой области является технология перетаскивания объектов мышью – Drag and Drop.
Предлагаемый для рассмотрения пример демонстрирует минимально функциональную версию реализации технологии перетаскивания объектов мышью. Это учебный пример, на базе которого, я надеюсь, вы сможете создавать собственные, более продвинутые, решения.
Предупреждение:
Этот пример может показаться сложным, но постарайтесь вникнуть в то, как он работает. В дальнейшем мы сможем делать то же самое намного легче, но все равно нам нужно понять, как это можно реализовать стандартными способами.
Для начала зададимся вопросом, какие события мы будем обрабатывать для перетаскиваемого элемента? Во-первых, элемент нужно "схватить" мышью – то есть, нажать на нем левую кнопку мыши. Значит, событие "mousedown" необходимо отрабатывать. Так же дело обстоит и с "отпусканием" элемента. К списку обрабатываемых событий добавляем "mouseup", в тот момент, когда мы его отпускаем. Осталось событие перемещения курсора мыши – "mousemove", при котором мы будем менять позицию перетаскиваемого элемента.
Итак, с событиями мы решили. Теперь разберемся с самими элементами. Дело в том, что задавать координаты элементов (left и top) можно только для абсолютно позиционируемых (в нашем случае) элементов. Значит – в стилевое оформление перетаскиваемых элементов должна входить строка "position: absolute;".
Ниже приводится полный код примера. Обратите внимание на следующую особенность: события mousedown и mouseup обрабатываются для перетаскиваемого элемента, а событие "mousemove" – для элемента <body>. Это связано с тем, что при резком рывке курсора мы рискуем выскочить за пределы перетаскиваемого элемента и "уронить" его. Т.е. нам нужен элемент, который всегда будет следить за движением мыши, т.е. самый большой элемент – body.
<html> <head> <style type="text/css"> #square { width: 50px; height: 50px; position: absolute; left: 10px; top: 10px; border: 1px solid black; background: #DDD; } </style> <script type="text/javascript"> //Переменная отвечает за то, что захвачен элемен или нет //Соответственно хранит захваченный элемент var elementToDrag = null; //"захват" элемента мышью function captureElement (elem) { if (!elementToDrag) { elementToDrag = elem; } } //"отпускание" элемента function releaseElement () { elementToDrag = null; } //"перетаскивание" элемента function dragElement (e) { if (elementToDrag){ e = e || window.event elementToDrag.style.left = e.clientX; elementToDrag.style.top = e.clientY; } } </script> </head> <body onmousemove="dragElement(event)"> <div id="square" onmousedown="captureElement(this)" onmouseup="releaseElement()"> </div> </body> </html>
После выполнения примера, вы столкнетесь (или уже столкнулись) с "маленькой" неприятностью: при "захвате" элемента его верхний левый угол "прыгает" в позицию курсора. В некоторых браузерах после этого отцепиться от элемента не представляется возможным иначе, как перезагрузкой страницы.
Исправим этот недостаток. Для этого будем при "захвате" элемента запоминать смещение курсора относительно верхнего левого угла перетаскиваемого элемента в глобальных переменных. Информация о смещении курсора хранится в свойствах offsetX и offsetY объекта event для IE и некоторых других браузерах, но для FF те же данные хранятся в свойствах layerX и layerY, которые не работают в IE. Соответственно для смещения по оси X мы используем свойство или offsetX или layerX, если они есть следующей записью: offX = e.layerX || e.offsetX, аналогично и для оси Y.
Смотрим пример:
<html> <head> <style type="text/css"> #square { width: 50px; height: 50px; position: absolute; left: 10px; top: 10px; border: 1px solid black; background: #DDD; } </style> <script type="text/javascript"> //Переменная отвечает за то, что захвачен элемен или нет //Соответственно хранит захваченный элемент var elementToDrag = null; //Глобальные переменные для хранения смещения var offX, offY; //"захват" элемента мышью function captureElement (e, elem) { if (!elementToDrag) { elementToDrag = elem; e = e || window.event; offX = e.layerX || e.offsetX; // запоминаем координаты курсора offY = e.layerY || e.offsetY; // в момент щелчка } } //"отпускание" элемента function releaseElement () { elementToDrag = null; } //"перетаскивание" элемента function dragElement (e) { if (elementToDrag){ e = e || window.event; elementToDrag.style.left = e.clientX - offX; elementToDrag.style.top = e.clientY - offY; } } </script> </head> <body onmousemove="dragElement(event)"> <div id="square" onmousedown="captureElement(event, this)" onmouseup="releaseElement()"> </div> </body> </html>
Итак, наш сценарий добросовестно реализует поддержку перетаскивания элементов мышью. Как вы и сами могли убедиться, ничего особенно сложного в этом нет. Надеюсь, пример вам понравился и вам не составит особого труда модифицировать алгоритм его работы для ваших собственных нужд.
Вот такой, мир событий JavaScript. Вам необходимо понять, что без событий и функций JavaScript станет скучным и неинтересным, ведь всякие визуальные эффекты можно делать только при помощи событий и функций.