perché questa chiamata jQuery .animate è così lenta?
-
05-07-2019 - |
Domanda
Ciao a tutti Ho una funzione piuttosto semplice
enableModule : function(moduleName){
var module = $('div#'+moduleName);
console.log('enabling '+moduleName);
console.time('animate');
module.animate({'opacity' : '1.0'}, 300, function(){console.timeEnd('animate');});
module.find('.disabled_sheild').remove();
module.removeClass('disabled');
console.log('end of enable Module');
}
L'animazione stessa, il cambio di opacità, è molto veloce ma c'è un ritardo nel chiamarla. console.time () riporta tempi di 2540 ms e superiori. Sto pensando che potrebbe essere perché il modulo div # viene animato insieme ai suoi figli? ma questo dosaggio ha senso perché ho un'altra funzione "disableModule" che fa la stessa cosa al contrario e funziona a una velocità ragionevole.
Ecco la funzione di disabilitazione del modulo, molto più in corso ma restituisce tempi di circa 242 ms
disableModule : function(moduleName){
$('div#'+moduleName+', div.'+moduleName).each(function(){
var module = $(this);
module.prepend('<div class="disabled_sheild"></div>');
var sheild = module.find('.disabled_sheild');
sheild.css({'position' : 'absolute', 'z-index' : '200'});
sheild.width(module.width());
sheild.height(module.height());
jQuery.each(jQuery.browser, function(i) {
if($.browser.msie){
//module.css("display","none");
//if using ie give sheild a transparent background layout
}else{
console.time('animate');
module.animate({'opacity' : '0.5'}, function(){ console.timeEnd('animate');});
}
});
});
}
Soluzione
Dopo un'ardua risoluzione dei problemi l'ho individuato come un problema con il ciclo di rilevamento del browser nel metodo di disabilitazione:
jQuery.each(jQuery.browser, function(i) {
if($.browser.msie){
//module.css("display","none");
//if using ie give sheild a transparent background layout
}else{
console.time('animate');
module.animate({opacity : 0.5}, 200, function(){console.timeEnd('animate');});
}
});
Commentare questo blocco ha reso tutto più veloce. Mi sono quasi strappato i capelli dopo aver cercato di ottimizzare tutto il resto.
Altri suggerimenti
Hai provato semplicemente a riordinarli?
module.find('.disabled_sheild').remove();
module.removeClass('disabled');
module.animate({'opacity' : '1.0'}, 300, function(){console.timeEnd('animate');});
L'animazione avviene in modo asincrono e i metodi find
e remove
potrebbero consumare risorse (soprattutto perché find
cammina l'albero DOM) che altrimenti potrebbero essere usato per l'animazione.
Inoltre, poiché stai creando dinamicamente lo "schermo disabilitato" nel metodo disable
, è possibile salvarlo
module.data("disabledShield", module.prepend('<div class="disabled_sheild"></div>'));
e usa semplicemente quel riferimento nel tuo metodo enable
per evitare il DOM walk
module.data("disabledShield").remove();
module.removeClass('disabled');
module.animate({'opacity' : '1.0'}, 300, function(){console.timeEnd('animate');});
(Vedi http://docs.jquery.com/Internals/jQuery.data per il documento su $ .data
)