Estoy comenzando un proyecto con jQuery.
¿Qué trampas / errores / conceptos erróneos / abusos / usos incorrectos tuvo en su proyecto jQuery?
Estoy comenzando un proyecto con jQuery.
¿Qué trampas / errores / conceptos erróneos / abusos / usos incorrectos tuvo en su proyecto jQuery?
Respuestas:
No estar al tanto del golpe de rendimiento y usar en exceso los selectores en lugar de asignarlos a variables locales. Por ejemplo:-
$('#button').click(function() {
$('#label').method();
$('#label').method2();
$('#label').css('background-color', 'red');
});
Más bien que:-
$('#button').click(function() {
var $label = $('#label');
$label.method();
$label.method2();
$label.css('background-color', 'red');
});
O incluso mejor con el encadenamiento : -
$('#button').click(function() {
$("#label").method().method2().css("background-color", "red");
});
Encontré este el momento esclarecedor cuando me di cuenta de cómo funcionan las pilas de llamadas.
Editar: sugerencias incorporadas en los comentarios.
var $label = $('#label');
Comprende cómo usar el contexto. Normalmente, un selector jQuery buscará todo el documento:
// This will search whole doc for elements with class myClass
$('.myClass');
Pero puede acelerar las cosas buscando dentro de un contexto:
var ct = $('#myContainer');
// This will search for elements with class myClass within the myContainer child elements
$('.myClass', ct);
[0]
. $('.myClass', ct);
o si sabe que ct es una instancia de jQuery, puede usar findct.find(".myClass")
No use selectores de clase básica, como este:
$('.button').click(function() { /* do something */ });
Esto terminará mirando cada elemento para ver si tiene una clase de "botón".
En cambio, puede ayudarlo, como:
$('span.button').click(function() { /* do something */ });
$('#userform .button').click(function() { /* do something */ });
Esto lo aprendí el año pasado del blog de Rebecca Murphy
Actualización : esta respuesta se dio hace más de 2 años y no es correcta para la versión actual de jQuery. Uno de los comentarios incluye una prueba para probar esto. También hay una versión actualizada de la prueba que incluye la versión de jQuery en el momento de esta respuesta.
$('.b')
podría usarse document.getElementsByClassName('b')
si el navegador lo admite, pero al hacerlo $('a.b')
, obtendrá todos los elementos coincidentes con la clase b
y luego confirmará que son anclas en una operación de dos etapas. Esto último me parece más trabajo. Para una analogía de la vida real, intente esto: encuentre todos los calcetines en mi habitación. Ahora, tira las que no estén en mi tocador.
Intente dividir las funciones anónimas para poder reutilizarlas.
//Avoid
$('#div').click( function(){
//do something
});
//Do do
function divClickFn (){
//do something
}
$('#div').click( divClickFn );
(anonymous)
. Lea más sobre este consejo aquí: stackoverflow.com/questions/182630/jquery-tips-and-tricks/…
He visto cientos de líneas de código dentro de la declaración doc ready. Feo, ilegible e imposible de mantener.
Durante el uso $.ajax
función para las solicitudes de Ajax al servidor, debe evitar usar el complete
evento para procesar los datos de respuesta. Se disparará si la solicitud fue exitosa o no.
En lugar de complete
usar success
.
Ver Ajax Events en los documentos.
Suponga que desea animar un párrafo que desaparece al hacer clic en él. También quería eliminar el elemento del DOM después. Puede pensar que simplemente puede encadenar los métodos:
$("p").click(function(e) {
$(this).fadeOut("slow").remove();
});
En este ejemplo, se llamará a .remove () antes de que se complete .fadeOut (), destruyendo su efecto de desvanecimiento gradual y simplemente haciendo que el elemento desaparezca instantáneamente. En cambio, cuando desee disparar un comando solo al finalizar el anterior, use la devolución de llamada:
$("p").click(function(e){
$(this).fadeOut("slow", function(){
$(this).remove();
});
});
El segundo parámetro de .fadeOut () es una función anónima que se ejecutará una vez que la animación .fadeOut () se haya completado. Esto produce un desvanecimiento gradual y una posterior eliminación del elemento.
Si vincula () el mismo evento varias veces, se activará varias veces. Usualmente siempre voy unbind('click').bind('click')
solo para estar seguro
No abuses de los complementos.
La mayoría de las veces solo necesitará la biblioteca y tal vez la interfaz de usuario. Si lo mantiene simple, su código será mantenible a largo plazo. No todos los complementos son compatibles y se mantienen, en realidad la mayoría no. Si puede imitar la funcionalidad utilizando elementos centrales, lo recomiendo encarecidamente.
Los complementos son fáciles de insertar en su código, le ahorran algo de tiempo, pero cuando necesite algo extra, es una mala idea modificarlos, ya que pierde las posibles actualizaciones. El tiempo que ahorra al principio se perderá más tarde al cambiar los complementos obsoletos.
Elija los complementos que usa sabiamente. Además de la biblioteca y la interfaz de usuario, uso constantemente $ .cookie , $ .form , $ .validate y thickbox . Por lo demás, principalmente desarrollo mis propios complementos.
Peligro: usar bucles en lugar de selectores.
Si te encuentras buscando el método jQuery '.each' para iterar sobre elementos DOM, pregúntate si puedes usar un selector para obtener los elementos.
Más información sobre los selectores jQuery:
http://docs.jquery.com/Selectors
Peligro: NO usar una herramienta como Firebug
Firebug fue hecho prácticamente para este tipo de depuración. Si vas a estar jugando en el DOM con Javascript, necesitas una buena herramienta como Firebug para darte visibilidad.
Más información sobre Firebug: http://getfirebug.com/
Otras grandes ideas están en este episodio del podcast polimórfico: (jQuery Secrets with Dave Ward) http://polymorphicpodcast.com/shows/jquery/
Malentendido de usar este identificador en el contexto correcto. Por ejemplo:
$( "#first_element").click( function( event)
{
$(this).method( ); //referring to first_element
$(".listOfElements").each( function()
{
$(this).someMethod( ); // here 'this' is not referring first_element anymore.
})
});
Y aquí una de las muestras de cómo puedes resolverlo:
$( "#first_element").click( function( event)
{
$(this).method( ); //referring to first_element
var $that = this;
$(".listOfElements").each( function()
{
$that.someMethod( ); // here 'that' is referring to first_element still.
})
});
Evite buscar en todo el DOM varias veces. Esto es algo que realmente puede retrasar su secuencia de comandos.
Malo:
$(".aclass").this();
$(".aclass").that();
...
Bueno:
$(".aclass").this().that();
Malo:
$("#form .text").this();
$("#form .int").that();
$("#form .choice").method();
Bueno:
$("#form")
.find(".text").this().end()
.find(".int").that().end()
.find(".choice").method();
Siempre almacene $ (this) en una variable significativa, especialmente en un .each ()
Me gusta esto
$(selector).each(function () {
var eachOf_X_loop = $(this);
})
$self
o $this
si es demasiado vago para pensar en un buen nombre de variable.
Evite la creación múltiple de los mismos objetos jQuery
//Avoid
function someFunc(){
$(this).fadeIn();
$(this).fadeIn();
}
//Cache the obj
function someFunc(){
var $this = $(this).fadeIn();
$this.fadeIn();
}
$this = $(this);
en una línea separada. Si puede (sin ensuciar), olvídese $this
y $(this).fadeIn().fadeIn();
Haciendo demasiadas manipulaciones DOM. Si bien los métodos .html (), .append (), .prepend (), etc. son excelentes, debido a la forma en que los navegadores procesan y vuelven a procesar las páginas, usarlos con demasiada frecuencia provocará retrasos. A menudo es mejor crear el html como una cadena e incluirlo en el DOM una vez, en lugar de cambiarlo varias veces.
En vez de:
var $parent = $('#parent');
var iterations = 10;
for (var i = 0; i < iterations; i++){
var $div = $('<div class="foo-' + i + '" />');
$parent.append($div);
}
Prueba esto:
var $parent = $('#parent');
var iterations = 10;
var html = '';
for (var i = 0; i < iterations; i++){
html += '<div class="foo-' + i + '"></div>';
}
$parent.append(html);
O incluso esto ($ wrapper es un elemento recién creado que aún no se ha inyectado al DOM. Agregar nodos a este contenedor wrap div no causa ralentizaciones, y al final agregamos $ wrapper a $ parent, usando solo una manipulación DOM ):
var $parent = $('#parent');
var $wrapper = $('<div class="wrapper" />');
var iterations = 10;
for (var i = 0; i < iterations; i++){
var $div = $('<div class="foo-' + i + '" />');
$wrapper.append($div);
}
$parent.append($wrapper);
Usar ClientID para obtener la identificación "real" del control en proyectos ASP.NET.
jQuery('#<%=myLabel.ClientID%>');
Además, si está utilizando jQuery dentro de SharePoint, debe llamar a jQuery.noConflict ().
Pasar ID en lugar de objetos jQuery a funciones:
myFunc = function(id) { // wrong!
var selector = $("#" + id);
selector.doStuff();
}
myFunc("someId");
Pasar un conjunto envuelto es mucho más flexible:
myFunc = function(elements) {
elements.doStuff();
}
myFunc($("#someId")); // or myFunc($(".someClass")); etc.
Uso excesivo de encadenamiento.
Mira esto:
this.buttonNext[n ? 'bind' : 'unbind'](this.options.buttonNextEvent, this.funcNext)[n ? 'removeClass' : 'addClass'](this.className('jcarousel-next-disabled')).attr('disabled', n ? false : true);
Utilice cadenas de estilo acumulador
Usando el operador +, se crea una nueva cadena en la memoria y se le asigna el valor concatenado. Solo después de esto, el resultado se asigna a una variable. Para evitar la variable intermedia para el resultado de concatenación, puede asignar directamente el resultado usando el operador + =. Lento:
a += 'x' + 'y';
Más rápido:
a += 'x';
a += 'y';
Las operaciones primitivas pueden ser más rápidas que las llamadas a funciones
Considere el uso de operaciones primitivas alternativas sobre llamadas de función en bucles y funciones críticas de rendimiento. Lento:
var min = Math.min(a, b);
arr.push(val);
Más rápido:
var min = a < b ? a : b;
arr[arr.length] = val;
Lea más en JavaScript Mejores prácticas de rendimiento
Si desea que los usuarios vean entidades html en su navegador, use 'html' en lugar de 'texto' para inyectar una cadena Unicode, como:
$('p').html("Your Unicode string")
Mis dos centavos)
Por lo general, trabajar con jquery significa que no tiene que preocuparse por los elementos DOM reales todo el tiempo. Puede escribir algo como esto, $('div.mine').addClass('someClass').bind('click', function(){alert('lalala')})
y este código se ejecutará sin arrojar ningún error.
En algunos casos esto es útil, en algunos casos, para nada, pero es un hecho que jquery tiende a ser, bueno, compatible con los partidos vacíos. Todavía,replaceWith
arrojará un error si uno intenta usarlo con un elemento que no pertenece al documento. Lo encuentro bastante contra-intuitivo.
Otro error es, en mi opinión, el orden de los nodos devueltos por el método prevAll () - $('<div><span class="A"/><span class="B"/><span class="C"/><span class="D"/></div>').find('span:last-child').prevAll()
. No es un gran problema, en realidad, pero debemos tener en cuenta este hecho.
Si planea Ajax en muchos datos, como por ejemplo, 1500 filas de una tabla con 20 columnas, entonces ni siquiera piense en usar jQuery para insertar esos datos en su HTML. Use JavaScript simple. jQuery será demasiado lento en máquinas más lentas.
Además, la mitad del tiempo, jQuery hará cosas que harán que sea más lento, como tratar de analizar las etiquetas de script en el HTML entrante y tratar las peculiaridades del navegador. Si desea una velocidad de inserción rápida, utilice JavaScript simple.
.innerHTML
lo hará. Pero si está creando algo como Gmail donde el usuario mantiene la pestaña abierta durante horas, solo tendrá que morder la bala y lidiar con la lentitud adicional. Para los curiosos, esto es exactamente lo que hace jQuery .html()
: james.padolsey.com/jquery/#v=1.4&fn=jQuery.fn.html
Usar jQuery en un pequeño proyecto que se puede completar con solo un par de líneas de JavaScript ordinario.
couple of lines of ordinary JavaScript
Claro que no hay problema. ¿Pero cuándo es solo eso? Las personas que dicen "¿por qué no usar vanilla javascript?" IE aún no me ha mordido lo suficiente ... y sin mencionar la cantidad de código sin formato y repetitivo que tiene que escribir para hacer cosas simples en JS.
No entiendo el evento vinculante. JavaScript y jQuery funcionan de manera diferente.
Por demanda popular, un ejemplo:
En jQuery:
$("#someLink").click(function(){//do something});
Sin jQuery:
<a id="someLink" href="page.html" onClick="SomeClickFunction(this)">Link</a>
<script type="text/javascript">
SomeClickFunction(item){
//do something
}
</script>
Básicamente, los ganchos necesarios para JavaScript ya no son necesarios. Es decir, uso el marcado en línea (onClick, etc.) porque simplemente puede usar los ID y las clases que un desarrollador normalmente aprovecharía para fines de CSS.