В статьях jQuery UI API и Фабрика элементов интерфейса jQuery UI я кратко рассказал о внутреннем устройстве надстройки jQuery UI. На примере кнопки я покажу, как можно писать очень полезные виджеты.
Задача: Написать виджет, имитирующий нажатие и блокирование кнопки. Он так же должен оповещать подписчиков о событиях, происходящих с этой кнопкой.
Объявляем наш виджет.
$.widget("trv.button", {
Так как я его изначально писал для проекта под кодовым названием «TRAVEL», то и пространство имен у меня будет особое, а не стандартное «ui». Если вы будете использовать свое пространство имен (а я настоятельно рекомендую вам это, чтобы избежать путаницы), то не забудьте переименовать классы CSS.
Далее объявляем инициализирующий метод нашего будущего виджета.
_init: function() {
var me = this;
me.element
.bind('mousedown.' + me.name, function() {
me._down();
return false;
})
.bind('mouseup.' + me.name, function () {
me._up();
return false;
})
.bind('click.' + me.name, function(event) {
if (!me._getData('disabled')) {
me._trigger('press', event);
}
return false;
});
},
В этом методе подписываемся на события, связанные с нажатием левой кнопки мыши — «mousedown», «mouseup» и «click». Я не буду создавать дополнительные элементов для оформления кнопки, так-как предполагаю, что вся необходимая верстка присутствует на странице.
destroy: function() {
var me = this;
me.element
.unbind('mousedown.' + me.name)
.unbind('mouseup.' + me.name)
.unbind('click.' + me.name);
},
Лично я в своей практике не применял метод удаления виджета, но тем не мене создал его, как предписывает руководство.
Следующие методы носят исключительно вспомогательный характер и не доступны извне.
_down: function () {
var me = this;
if (!me._getData('disabled')) {
me.element
.addClass(me.widgetBaseClass + '-pressed')
.one('mouseout.' + me.name, function () {
me._up();
me.element.one('mouseover.' + me.name, function () {
me._down();
});
});
$(document).one('mouseup.' + me.name, function () {
me._up();
});
}
},
Имитируем нажатие кнопки, добавляя CSS класс, и отслеживаем момент, когда указатель мышки покинет область кнопки, чтобы вернуть кнопку в исходное состояние.
Стоит заметить, что событие «mouseup» ловится на документе потому, что когда указатель мышки покинет элемент, то он уже не сможет ловить это событие.
_up: function () {
var me = this;
me.element
.unbind('mouseout.' + me.name)
.unbind('mouseover.' + me.name)
.removeClass(this.widgetBaseClass + '-pressed');
}
Убираем дополнительный CSS класс с элемента, чтобы вернуть кнопку в исходное состояние, и отписываемся от событий «mouseout» и «mouseover».
});
Верстка кнопки может варьироваться вне зависимости от кода. Например, я использую такую:
<span class="trv-button">
<span class="first-child">
<em>Press me!</em>
</span>
</span>
Кнопка полностью состоит из строчных элементов и теоретически может быть размещена внутри текста.
Когда на нее нажимают, то к основному элементу добавляется класс «trv-button-press». Этот класс автоматически создается из названия виджета и суффикса «-press».
Отслеживать нажатие кнопки можно через функцию обратного вызова «press» или соответствующее событие «buttonpress». Выбирайте, что вам больше нравится.