У нас есть асинхронный поиск, в поле ввода по буквам вводится текст и автоматически обновляются результаты поиска. На первый взгляд — ничего сложного, повесим на input событие keyup, при срабатывании которого будет происходить новый поиск по новой фразе.
document.getElementById('search').addEventListener('keyup', function() {
// Мы не будем описывать тело функции search, она реализует то, что было описано выше
search();
});
Но за то время, пока выполняется запрос, пользователь может успеть набрать следующую букву, тогда результаты предыдущего запроса будут уже неактуальны, а новый запрос не выполнится пока не закончится предыдущий (тут я слукавил, XHR запрос можно и отменить, но это частный случай). Представьте, что пользователь вводит быстро словосочетание «Дешевые билеты в Камбоджу». В таком случае функция search вызовется 25 раз. Это излишне. С другой стороны, если пользователь вводит не так быстро, то хорошо бы показывать ему промежуточные варианты, и еще нежелательно иметь какие-то задержки перед показом результатов.
Для этого и была изначально придумана «Ожидающая функция». Она ждет, пока прекратится ее цикличный вызов, т.е. если пройдет заданное время после ее вызова, и эта функция не будет вызвана повторно, то она выполняется, иначе действие передается следующему вызову.
fnDelay = (function(){
var timer = 0;
return function(callback, ms){
clearTimeout(timer);
timer = setTimeout(callback, ms);
};
})();
И сразу же покажу как ее использовать.
document.getElementById('search').addEventListener('keyup', function() {
fnDelay(function() {
search();
}, 200);
});
Эффективность выполнения этой функции регулируется аргументом ms. Для каждого конкретного случая нужно искать свою золотую середину, чтобы результат был и отзывчивым и не накапливалась очередь невыполненных задач. Теперь если пользователь при вводе сделает паузу хотя бы в 200 мс, то он получит новые результаты. Тем самым мы значительно уменьшаем количество вызовов функции search.
Я не остановился на асинхронном поиске, используя эту же функцию, когда мне нужно что-то сделать при ресайзе страницы, так как изменяя ширину окна всего лишь на 100 пикселей, событие resize может быть вызвано десятки раз.
Добавлю также ссылку на небольшой Фидл с примером.
This entry passed through the Full-Text RSS service — if this is your content and you're reading it on someone else's site, please read the FAQ at http://ift.tt/jcXqJW.
Комментариев нет:
Отправить комментарий