Как показать загрузку спиннера в jQuery?
В прототипе я могу показать "загрузку..."изображение с этим кодом:
var myAjax = new Ajax.Request( url, {method: 'get', parameters: pars,
onLoading: showLoad, onComplete: showResponse} );
function showLoad () {
...
}
В jQuery я могу загрузить серверную страницу в элемент следующим образом:
$('#message').load('index.php?pg=ajaxFlashcard');
Но как мне присоединить загрузочный спиннер к этой команде, как я сделал в прототипе?
24 ответов:
Есть несколько способов. Мой предпочтительный способ-прикрепить функцию к событиям ajaxStart/Stop на самом элементе.
$('#loadingDiv') .hide() // Hide it initially .ajaxStart(function() { $(this).show(); }) .ajaxStop(function() { $(this).hide(); }) ;Функции ajaxStart / Stop будут срабатывать всякий раз, когда вы выполняете какие-либо вызовы Ajax.
Update : начиная с jQuery 1.8, в документации указано, что
.ajaxStart/Stopследует присоединять только кdocument. Это преобразует приведенный выше фрагмент в:var $loading = $('#loadingDiv').hide(); $(document) .ajaxStart(function () { $loading.show(); }) .ajaxStop(function () { $loading.hide(); });
Для jQuery я использую
jQuery.ajaxSetup({ beforeSend: function() { $('#loader').show(); }, complete: function(){ $('#loader').hide(); }, success: function() {} });
Вы можете просто использовать функцию jQuery
.ajaxи использовать ее опциюbeforeSendи определить некоторую функцию, в которой вы можете показать что-то вроде загрузчика div, а при выборе варианта успеха вы можете скрыть этот загрузчик div.jQuery.ajax({ type: "POST", url: 'YOU_URL_TO_WHICH_DATA_SEND', data:'YOUR_DATA_TO_SEND', beforeSend: function() { $("#loaderDiv").show(); }, success: function(data) { $("#loaderDiv").hide(); } });Вы можете иметь любое вращающееся изображение Gif. Вот сайт, который является отличным генератором загрузчиков AJAX в соответствии с вашей цветовой схемой: http://ajaxload.info/
Вы можете вставить анимированное изображение в DOM прямо перед вызовом AJAX и выполнить встроенную функцию для его удаления...
$("#myDiv").html('<img src="images/spinner.gif" alt="Wait" />'); $('#message').load('index.php?pg=ajaxFlashcard', null, function() { $("#myDiv").html(''); });Это обеспечит запуск анимации в том же кадре при последующих запросах (если это имеет значение). Обратите внимание, что в старых версиях IE могут возникнуть трудности с анимацией.
Удачи!
$('#message').load('index.php?pg=ajaxFlashcard', null, showResponse); showLoad(); function showResponse() { hideLoad(); ... }
Если вы используете
$.ajax(), Вы можете использовать что-то вроде этого:$.ajax({ url: "destination url", success: sdialog, error: edialog, // shows the loader element before sending. beforeSend: function () { $("#imgSpinner1").show(); }, // hides the loader after completion of request, whether successfull or failor. complete: function () { $("#imgSpinner1").hide(); }, type: 'POST', dataType: 'json' });
Используйте загрузочный плагин: http://plugins.jquery.com/project/loading
$.loading.onAjax({img:'loading.gif'});
Вариант: у меня есть значок с id= "logo" в левом верхнем углу главной страницы; когда ajax работает, сверху накладывается spinner gif (с прозрачностью).
jQuery.ajaxSetup({ beforeSend: function() { $('#logo').css('background', 'url(images/ajax-loader.gif) no-repeat') }, complete: function(){ $('#logo').css('background', 'none') }, success: function() {} });
Я закончил двумя изменениями в исходном ответе .
- начиная с jQuery 1.8, ajaxStart и ajaxStop должны быть присоединены только к
document. Это затрудняет фильтрацию только некоторых запросов ajax. Су...- переключение наajaxSend иajaxComplete позволяет просмотреть текущий запрос ajax перед показом спиннера.
Вот код после этих изменений:
$(document) .hide() // hide it initially .ajaxSend(function(event, jqxhr, settings) { if (settings.url !== "ajax/request.php") return; $(".spinner").show(); }) .ajaxComplete(function(event, jqxhr, settings) { if (settings.url !== "ajax/request.php") return; $(".spinner").hide(); })
Я также хочу внести свой вклад в этот ответ. Я искал что-то подобное в jQuery, и это то, что я в конечном итоге использовал.
Я получил свой загрузочный спиннер от http://ajaxload.info/. мое решение основано на этом простом ответе в http://christierney.com/2011/03/23/global-ajax-loading-spinners/.
В основном ваша разметка HTML и CSS будет выглядеть следующим образом:
<style> #ajaxSpinnerImage { display: none; } </style> <div id="ajaxSpinnerContainer"> <img src="~/Content/ajax-loader.gif" id="ajaxSpinnerImage" title="working..." /> </div>И тогда ваш код для jQuery будет выглядеть примерно так это:
<script> $(document).ready(function () { $(document) .ajaxStart(function () { $("#ajaxSpinnerImage").show(); }) .ajaxStop(function () { $("#ajaxSpinnerImage").hide(); }); var owmAPI = "http://api.openweathermap.org/data/2.5/weather?q=London,uk&APPID=YourAppID"; $.getJSON(owmAPI) .done(function (data) { alert(data.coord.lon); }) .fail(function () { alert('error'); }); }); </script>Это так просто:)
Вы можете просто назначить изображение загрузчика тому же тегу, на который вы позже загрузите содержимое, используя вызов Ajax:
$("#message").html('<span>Loading...</span>'); $('#message').load('index.php?pg=ajaxFlashcard');Вы также можете заменить тег span тегом image.
Помимо установки глобальных значений по умолчанию для событий ajax, вы можете задать поведение для определенных элементов. Может быть, достаточно просто сменить класс?
$('#myForm').ajaxSend( function() { $(this).addClass('loading'); }); $('#myForm').ajaxComplete( function(){ $(this).removeClass('loading'); });Пример CSS, чтобы скрыть #myForm с помощью spinner:
.loading { display: block; background: url(spinner.gif) no-repeat center middle; width: 124px; height: 124px; margin: 0 auto; } /* Hide all the children of the 'loading' element */ .loading * { display: none; }
$('#loading-image').html('<img src="/images/ajax-loader.gif"> Sending...'); $.ajax({ url: uri, cache: false, success: function(){ $('#loading-image').html(''); }, error: function(jqXHR, textStatus, errorThrown) { var text = "Error has occured when submitting the job: "+jqXHR.status+ " Contact IT dept"; $('#loading-image').html('<span style="color:red">'+text +' </span>'); } });
Я использовал следующее В диалоге пользовательского интерфейса jQuery. (Может быть, это работает с другими обратными вызовами ajax?)
$('<div><img src="/i/loading.gif" id="loading" /></div>').load('/ajax.html').dialog({ height: 300, width: 600, title: 'Wait for it...' });Содержит анимированный загрузчик до тех пор, пока его содержимое не будет заменено по завершении вызова ajax.
JavaScript
$.listen('click', '#captcha', function() { $('#captcha-block').html('<div id="loading" style="width: 70px; height: 40px; display: inline-block;" />'); $.get("/captcha/new", null, function(data) { $('#captcha-block').html(data); }); return false; });CSS
#loading { background: url(/image/loading.gif) no-repeat center; }
Обратите внимание, что вы должны использовать асинхронные вызовы для работы блесен (по крайней мере, это то, что заставило mine не показывать до тех пор, пока вызов ajax не исчез, а затем быстро исчез, когда вызов закончился и удалил блесну).
$.ajax({ url: requestUrl, data: data, dataType: 'JSON', processData: false, type: requestMethod, async: true, <<<<<<------ set async to true accepts: 'application/json', contentType: 'application/json', success: function (restResponse) { // something here }, error: function (restResponse) { // something here } });
Это очень простой и умный плагин для этой конкретной цели: https://github.com/hekigan/is-loading
Я делаю это:
var preloaderdiv = '<div class="thumbs_preloader">Loading...</div>'; $('#detail_thumbnails').html(preloaderdiv); $.ajax({ async:true, url:'./Ajaxification/getRandomUser?top='+ $(sender).css('top') +'&lef='+ $(sender).css('left'), success:function(data){ $('#detail_thumbnails').html(data); } });
Я думаю, что вы правы. Этот метод слишком глобален...
Однако-это хорошее значение по умолчанию для тех случаев, когда ваш вызов AJAX не влияет на саму страницу. (например, сохранение фона). ( вы всегда можете отключить его для определенного вызова ajax, передав "global": false-смотрите документацию по адресу jquery
Когда вызов AJAX предназначен для обновления части страницы, мне нравится, чтобы мои "загрузочные" изображения были специфичны для обновленного раздела. Я хотел бы посмотреть, какая часть обновлена.
Представьте, как было бы здорово, если бы вы могли просто написать что-то вроде:
$("#component_to_refresh").ajax( { ... } );И это будет показывать "загрузку" в этом разделе. Ниже я написал функцию, которая также обрабатывает" загрузку " дисплея, но она специфична для области, которую вы обновляете в ajax.
Во-первых, позвольте мне показать вам, как его использовать
<!-- assume you have this HTML and you would like to refresh it / load the content with ajax --> <span id="email" name="name" class="ajax-loading"> </span> <!-- then you have the following javascript --> $(document).ready(function(){ $("#email").ajax({'url':"/my/url", load:true, global:false}); })И это функция-базовый старт, который вы можете улучшить по своему желанию. он очень гибкий.
jQuery.fn.ajax = function(options) { var $this = $(this); debugger; function invokeFunc(func, arguments) { if ( typeof(func) == "function") { func( arguments ) ; } } function _think( obj, think ) { if ( think ) { obj.html('<div class="loading" style="background: url(/public/images/loading_1.gif) no-repeat; display:inline-block; width:70px; height:30px; padding-left:25px;"> Loading ... </div>'); } else { obj.find(".loading").hide(); } } function makeMeThink( think ) { if ( $this.is(".ajax-loading") ) { _think($this,think); } else { _think($this, think); } } options = $.extend({}, options); // make options not null - ridiculous, but still. // read more about ajax events var newoptions = $.extend({ beforeSend: function() { invokeFunc(options.beforeSend, null); makeMeThink(true); }, complete: function() { invokeFunc(options.complete); makeMeThink(false); }, success:function(result) { invokeFunc(options.success); if ( options.load ) { $this.html(result); } } }, options); $.ajax(newoptions); };
Если вы не хотите писать свой собственный код, есть также много плагинов, которые делают именно это:
Если вы планируете использовать загрузчик каждый раз, когда вы делаете запрос на сервер, вы можете использовать следующий шаблон.
jTarget.ajaxloader(); // (re)start the loader $.post('/libs/jajaxloader/demo/service/service.php', function (content) { jTarget.append(content); // or do something with the content }) .always(function () { jTarget.ajaxloader("stop"); });Этот код, в частности, использует плагин jajaxloader (который я только что создал)
Вы всегда можете использовать Block UI jQuery plugin, который делает все за вас, и даже блокирует страницу любого ввода во время загрузки ajax. В случае, если плагин, кажется, не работает, вы можете прочитать о правильном способе его использования в этом ответе. Проверьте это.
Мой ajax-код выглядит так, по сути, я только что прокомментировал async: false line и spinner появляется.
$.ajax({ url: "@Url.Action("MyJsonAction", "Home")", type: "POST", dataType: "json", data: {parameter:variable}, //async: false, error: function () { }, success: function (data) { if (Object.keys(data).length > 0) { //use data } $('#ajaxspinner').hide(); } });Я показываю спиннер в функции перед кодом ajax:
$("#MyDropDownID").change(function () { $('#ajaxspinner').show();Для Html я использовал класс Font awesome:
<i id="ajaxspinner" class="fas fa-spinner fa-spin fa-3x fa-fw" style="display:none"></i>Надеюсь, что это помогает кто-то.
Comments