2011-03-10 9 views
6

El siguiente código funciona bien en IE y Firefox, pero Chrome lo odia (se ejecuta pero es muy lento). Estoy seguro de que podría hacerse más amigable para el navegador, pero ¿cómo? itemPlaceholder es cientos de divs flotados 100x100 (por ejemplo, marcadores de posición de imagen). Estoy usando jquery 1.4.4 y Chrome v10.0.648.127.jQuery desplazamiento evento - detección de elemento desplazado a la vista - bajo rendimiento en Chrome

$(function() { 

    ReplaceVisible(); 
    $(this).scroll(function() { 
     ReplaceVisible(); 
    }); 
}); 

function ReplaceVisible() { 
    $('.itemPlaceholder').each(function (index) { 
     if (HasBeenScrolledTo(this)) { 
      $itemPlaceholder = $(this); 

      $itemPlaceholder.replaceWith('<img src="bicycle.jpg" />'); 
     } 
     else { 
      return false; 
     } 
    }); 
} 

function HasBeenScrolledTo(elem) { 
    var docViewTop = $(window).scrollTop(); 
    var docViewBottom = docViewTop + $(window).height(); 
    var elemTop = $(elem).offset().top; 

    return elemTop < docViewBottom; 
} 

Editar: reemplazado append con replaceWith otra manera conseguimos un montón de imágenes adjuntas al mismo elemento.

Respuesta

5

Esto se ejecuta lentamente en cromo porque Chrome activa el evento onscroll continuamente a medida que se desplaza la página (IE y Firefox solo disparan cuando se detiene el desplazamiento).

Puede mejorar el rendimiento de Chrome en este caso al poner en fila las invocaciones de ReplaceVisible y solo permitiendo que se dispare una vez en un período de tiempo determinado. Un ejemplo de invocaciones de cola está disponible aquí (https://github.com/tilleryj/rio/blob/master/public/javascripts/lib/delayed_task.js)

+2

y recto de la boca del caballo: http://ejohn.org/blog/learning-from-twitter/ –

+0

Hmm, cromo hace producir más eventos de desplazamiento, pero no es más órdenes de magnatude. El problema parece deberse a la edición del DOM (append). Quita esa línea, y el desplazamiento es suave. – Sprintstar

0

Tuve un problema similar cuando tuve que detectar el cambio de tamaño de los eventos, que como era de esperar dispararon un montón de ellos y bloquearon el navegador. No lo he probado, así que informe si funciona. :)

$(function() { 
    replaceVisible(); 
    $(this).scroll(replaceVisible); 
}); 

var replaceVisible = (function(){ 
    var last_scroll = null; // Last time we scrolled 
    var paused = false; // We've paused scrolling 
    var delay = 1000; // Delay in between acting on the scroll (ms). 
    return function(){ 
     if(paused) return; 
     if(new Date() - last_scroll < delay){ 
      setTimeout(function(){ paused = false; replaceVisible(); }, delay) 
      paused = true; 
     } 
     $('.itemPlaceholder').filter(HasBeenScrolledTo) 
      .replaceWith('<img src="bicycle.jpg" />'); 
     last_scroll = new Date(); 
    } 
})(); 

function HasBeenScrolledTo(index) { 
    var docViewTop = $(window).scrollTop(); 
    var docViewBottom = docViewTop + $(window).height(); 
    var elemTop = $(this).offset().top; 
    return elemTop < docViewBottom; 
} 
+0

Gracias por su código, aprendí mucho de él, y estoy seguro de que redujo la carga en los navegadores. Sin embargo, Chrome todavía no le gusta la edición DOM ... :( – Sprintstar

+0

Puede intentar cargar todo pero con el oculto y luego llamar a show() cuando quiere que esté visible? Deberá publicar una página de prueba si quieres ayuda más precisa ya que no estoy seguro de por qué Chrome tendría problemas con el código en este momento. –

Cuestiones relacionadas