Pro jQuery

Pro jQuery

Адам Фриман

Перечисление методов обработки событий для форм

Как я уже упоминал в главе 9, есть набор методов jQuery, которые обрабатывают события, связанные с формой и ее элементами. Сейчас я хочу перечислить эти методы, потому что мы работаем именно с формами. В таблице 13-2 представлены эти методы и события, которым они соответствуют.

Совет

Не забывайте, что jQuery определяет набор расширенных селекторов, которые подходят элементам формы. Для информации смотрите главу 5.

Таблица 13-2: Методы jQuery для обработки событий форм
Метод Событие Описание
blur(function) blur Вызывается, когда элемент теряет фокус
change(function) change Вызывается, когда меняется значение элемента
focus(function) focus Вызывается, когда элемент получает фокус
select(function) select Вызывается, когда пользователь выбирает текст внутри элемента
submit(function) submit Вызывается, когда пользователь хочет отправить форму

Работа с фокусом формы

Элементы blur и focus позволяют реагировать на изменения фокуса. Общепринятое использование этих методов заключается в том, чтобы помочь пользователю выделить элемент с фокусом (и, следовательно, элемент, который получит введенные данные с клавиатуры). В листинге 13-3 представлен пример.

Листинг 13-3: Управление фокусом элемента
<script type="text/javascript">
	$(document).ready(function () {
		var data = [
			{ name: "Astor", product: "astor", stocklevel: "10", price: "2.99" },
			{ name: "Daffodil", product: "daffodil", stocklevel: "12", price: "1.99" },
			{ name: "Rose", product: "rose", stocklevel: "2", price: "4.99" },
			{ name: "Peony", product: "peony", stocklevel: "0", price: "1.50" },
			{ name: "Primula", product: "primula", stocklevel: "1", price: "3.12" },
			{ name: "Snowdrop", product: "snowdrop", stocklevel: "15", price: "0.99" },
		];

		var templResult = $('#flowerTmpl').tmpl(data);
		templResult.slice(0, 3).appendTo('#row1');
		templResult.slice(3).appendTo("#row2");

		$('input').focus(handleFormFocus).blur(handleFormFocus);

		function handleFormFocus(e) {
			var borderVal = e.type == "focus" ? "medium solid green" : "";
			$(this).css("border", borderVal);
		}
	});
</script>

В этом примере я выбираю все элементы input и регистрирую функцию handleFormFocus в качестве обработчика для обоих событий focus и blur. Функция рисует зеленую рамку, если элемент получает фокус, и убирает ее, если элемент его теряет. Результат можно увидеть на рисунке 13-3.

Рисунок 13-3: Выделение элемента с фокусом

Обратите внимание, что я использовал селектор input. Другими словами, я выбрал элементы по тегу. jQuery предоставляет расширенный селектор :input (я описал расширенные селекторы в главе 5). Этот расширенный селектор в некоторых браузерах соответствует более широкому спектру элементов, в частности, он будет соответствовать кнопке, которая может отправлять форму. Это обозначает, что если вы будете использовать расширенный селектор, то ваша рамка будет применяться как к действующим элементам input, так и к элементу button. На рисунке 13-4 можно увидеть результат, если элемент button находится в фокусе.

Рисунок 13-4: Разница между селекторами input и :input

Какой селектор вы используете, это дело вашего личного предпочтения, просто обращайте внимание на эту разницу.

Работа с изменением значений

Событие change запускается, когда пользователь меняет значение элемента формы. Это действительно полезное событие, если вы предоставляете суммарную информацию, основываясь на значениях в форме. В листинге 13-4 показано, как можно использовать это событие, чтобы отследить общее число выбранных единиц продукции цветочного магазина. Это тот же самый подход, который я применял, когда делал рефакторинг примера в конце главе 11 этой книги.

Листинг 13-4: Отклик на событие change
<script type="text/javascript">
	$(document).ready(function () {
		var data = [
			{ name: "Astor", product: "astor", stocklevel: "10", price: "2.99" },
			{ name: "Daffodil", product: "daffodil", stocklevel: "12", price: "1.99" },
			{ name: "Rose", product: "rose", stocklevel: "2", price: "4.99" },
			{ name: "Peony", product: "peony", stocklevel: "0", price: "1.50" },
			{ name: "Primula", product: "primula", stocklevel: "1", price: "3.12" },
			{ name: "Snowdrop", product: "snowdrop", stocklevel: "15", price: "0.99" },
		];

		var templResult = $('#flowerTmpl').tmpl(data);
		templResult.slice(0, 3).appendTo('#row1');
		templResult.slice(3).appendTo("#row2");

		$('input').focus(handleFormFocus).blur(handleFormFocus);

		function handleFormFocus(e) {
			var borderVal = e.type == "focus" ? "medium solid green" : "";
			$(this).css("border", borderVal);
		}

		var total = $('#buttonDiv')
			.prepend("<div>Total Items: <span id=total>0</span></div>")
			.css({ clear: "both", padding: "5px" });
		$('<div id=bbox />').appendTo("body").append(total).css("clear: left");

		$('input').change(function (e) {
			var total = 0;
			$('input').each(function (index, elem) {
				total += Number($(elem).val());
			});
			$('#total').text(total);
		});
	});
</script>

В этом примере я реагирую на событие change, подсчитывая значения всех элементов input и выводя результат в элемент span, который я ранее добавил в документ.

Совет

Обратите внимание, что я использую метод val, чтобы получить значения элементов input.

Работа с отправкой формы

Многие продвинутые технические приемы, которые вы можете совершать с формами, доступны тогда, когда вы предотвращаете выполнение действий по умолчанию для браузера. В листинге 13-5 показан простой пример.

Листинг 13-5: Перехват отправки формы
<script type="text/javascript">
	$(document).ready(function () {
		var data = [
			{ name: "Astor", product: "astor", stocklevel: "10", price: "2.99" },
			{ name: "Daffodil", product: "daffodil", stocklevel: "12", price: "1.99" },
			{ name: "Rose", product: "rose", stocklevel: "2", price: "4.99" },
			{ name: "Peony", product: "peony", stocklevel: "0", price: "1.50" },
			{ name: "Primula", product: "primula", stocklevel: "1", price: "3.12" },
			{ name: "Snowdrop", product: "snowdrop", stocklevel: "15", price: "0.99" },
		];

		var templResult = $('#flowerTmpl').tmpl(data);
		templResult.slice(0, 3).appendTo('#row1');
		templResult.slice(3).appendTo("#row2");

		$('form').submit(function (e) {
			if ($('input').val() == 0) {
				e.preventDefault();
			}
		});
	});
</script>

В этом скрипте я регистрирую встроенную функцию для события submit. Это событие сработает, если пользователь нажмет на кнопку Place Order. Если значение первого элемента input равно 0, я вызываю метод preventDefault, чтобы прервать действие по умолчанию для формы, то есть отправку данных на сервер. Для любых других значений форма отправляется.

Совет

В качестве альтернативы, чтобы получить такой же результат, можно вернуть функцией false.

Есть способы, которыми можно сделать так, чтобы форма отправлялась программно. Можно использовать jQuery метод submit без аргументов и можно использовать метод submit, который определяется для элементов form в спецификации HTML5. В листинге 13-6 показано использование обоих этих способов.

Листинг 13-6: Отправка формы напрямую
<script type="text/javascript">
	$(document).ready(function () {
		var data = [
			{ name: "Astor", product: "astor", stocklevel: "10", price: "2.99" },
			{ name: "Daffodil", product: "daffodil", stocklevel: "12", price: "1.99" },
			{ name: "Rose", product: "rose", stocklevel: "2", price: "4.99" },
			{ name: "Peony", product: "peony", stocklevel: "0", price: "1.50" },
			{ name: "Primula", product: "primula", stocklevel: "1", price: "3.12" },
			{ name: "Snowdrop", product: "snowdrop", stocklevel: "15", price: "0.99" },
		];

		var templResult = $('#flowerTmpl').tmpl(data);
		templResult.slice(0, 3).appendTo('#row1');
		templResult.slice(3).appendTo("#row2");

		$('form').submit(function (e) {
			if ($('input').val() == 0) {
				e.preventDefault();
			}
		});

		$('<button>DOM API</button>').appendTo('#buttonDiv').click(function (e) {
			document.getElementsByTagName("form")[0].submit();
			e.preventDefault();
		});

		$('<button>jQuery Method</button>').appendTo('#buttonDiv').click(function (e) {
			$('form').submit();
			e.preventDefault();
		});
	});
</script>

Я добавил в документ два элемента button. Одна кнопка, которая использует jQuery метод submit, заканчивается вызовом функции обработки событий, и если значение первого элемента input равно нулю, форма не будет отправлена. Однако, элемент button, который использует DOM API и вызывает метод submit, определенный элементом form, обходит ваш обработчик событий, а форма все всегда будет отправлена.

Совет

Конечно же, я рекомендую придерживаться методов jQuery, но если вы предпочитаете использовать DOM метод, вы, как минимум, поймете, какой результат вы получите.

или RSS канал: Что новенького на smarly.net