1. Code
  2. JavaScript
  3. jQuery

14 hilfreiche jQuery-Tricks, Hinweise und bewährte Vorgehensweisen

Wenn es etwas Schlechtes an jQuery gibt, dann ist das Einstiegsniveau so erstaunlich niedrig, dass es eher diejenigen anzieht, die kein JavaScript-Wissen haben. Das ist zum einen fantastisch. Auf der anderen Seite führt dies jedoch auch zu einem verpatzten, ehrlich gesagt widerwärtig schlechten Code (von dem ich einige selbst geschrieben habe!).
Scroll to top

German (Deutsch) translation by Władysław Łucyszyn (you can also view the original English article)

Wenn es etwas Schlechtes an jQuery gibt, dann ist das Einstiegsniveau so erstaunlich niedrig, dass es eher diejenigen anzieht, die kein JavaScript-Wissen haben.  Das ist zum einen fantastisch. Auf der anderen Seite führt dies jedoch auch zu einem verpatzten, ehrlich gesagt widerwärtig schlechten Code (von dem ich einige selbst geschrieben habe!).

Aber das ist OK; erschreckend schlechter Code, der sogar Ihre Großmutter zum Keuchen bringen würde, ist ein Durchgang. Der Schlüssel ist, über den Hügel zu klettern, und das werden wir im heutigen Tutorial besprechen.


1. Methoden Gibt das jQuery-Objekt zurück

Beachten Sie, dass die meisten Methoden das jQuery-Objekt zurückgeben. Dies ist äußerst hilfreich und ermöglicht die so häufig verwendete Verkettungsfunktion.

1
2
$someDiv
3
  .attr('class', 'someClass')
4
  .hide()
5
  .html('new stuff');

Da wir wissen, dass das jQuery-Objekt immer zurückgegeben wird, können wir damit manchmal überflüssigen Code entfernen. Betrachten Sie zum Beispiel den folgenden Code:

1
2
var someDiv = $('#someDiv');
3
someDiv.hide();

Der Grund, warum wir die Position des someDiv-Elements "zwischenspeichern", besteht darin, die Anzahl der Male zu begrenzen, die das DOM für dieses Element durchlaufen muss, auf einmal.

Der obige Code ist vollkommen in Ordnung. Sie können die beiden Linien jedoch genauso leicht zu einer einzigen kombinieren, während Sie dasselbe Ergebnis erzielen.

1
2
var someDiv = $('#someDiv').hide();

Auf diese Weise verbergen wir immer noch das someDiv-Element, aber die Methode gibt auch das jQuery-Objekt zurück, auf das über die someDiv-Variable verwiesen wird.


2. Die Suchauswahl

Solange Ihre Selektoren nicht lächerlich schlecht sind, optimiert jQuery sie optimal, und Sie müssen sich normalerweise nicht allzu viele Sorgen machen. Trotzdem gibt es einige Verbesserungen, die die Leistung Ihres Skripts ein wenig verbessern können.

Eine solche Lösung ist, wenn möglich, die find() -Methode zu verwenden. Der Schlüssel ist weg von jQuery zu zwingen, seine Sizzle-Engine zu verwenden, wenn dies nicht notwendig ist.  Sicher wird es Zeiten geben, in denen dies nicht möglich ist - und das ist in Ordnung; Wenn Sie jedoch keinen zusätzlichen Aufwand benötigen, suchen Sie nicht danach.

1
2
// Fine in modern browsers, though Sizzle does begin "running"

3
$('#someDiv p.someClass').hide();
4
5
// Better for all browsers, and Sizzle never inits.

6
$('#someDiv').find('p.someClass').hide();

Die neuesten modernen Browser unterstützen QuerySelectorAll, sodass Sie CSS-ähnliche Selektoren übergeben können, ohne dass dazu jQuery erforderlich ist. jQuery selbst prüft auch diese Funktion.

Ältere Browser, nämlich IE6 / IE7, bieten jedoch verständlicherweise keinen Support. Dies bedeutet, dass diese komplizierteren Selektoren die komplette Sizzle-Engine von jQuery auslösen, die zwar brillant ist, aber auch etwas mehr Aufwand verursacht.

Sizzle ist eine brillante Masse Code, die ich niemals verstehen kann. In einem Satz muss der Selektor jedoch zuerst in ein "Array" umgewandelt werden, das aus jeder Komponente des Selektors besteht.

1
2
// Rough idea of how it works

3
 ['#someDiv, 'p'];

Dann beginnt es von rechts nach links, jedes Element mit regulären Ausdrücken zu entschlüsseln. Das bedeutet auch, dass der ganz rechte Teil Ihres Selektors so genau wie möglich sein sollte - zum Beispiel eine ID oder ein Tag-Name.

Fazit, wenn möglich:

  • Halten Sie Ihre Selektoren einfach
  • Verwenden Sie die find() -Methode. Auf diese Weise können wir die systemeigenen Funktionen des Browsers verwenden, anstatt Sizzle zu verwenden.
  • Optimieren Sie bei Verwendung von Sizzle den Bereich ganz rechts Ihres Selektors so weit wie möglich.

Kontext stattdessen?

Sie können Ihren Selektoren auch einen Kontext hinzufügen, z.

1
2
$('.someElements', '#someContainer').hide();

Dieser Code weist jQuery an, eine Auflistung aller Elemente mit einer Klasse von someElements - die Kinder von someContainer sind - in jQuery zu umschließen. Die Verwendung eines Kontexts ist eine hilfreiche Methode, um die DOM-Durchquerung zu begrenzen. JQuery verwendet jedoch im Hintergrund stattdessen die find-Methode.

1
2
$('#someContainer')
3
  .find('.someElements')
4
  .hide();

Beweis

1
2
// HANDLE: $(expr, context)

3
// (which is just equivalent to: $(context).find(expr)

4
} else {
5
   return jQuery( context ).find( selector );
6
}

3. Missbrauche $(this) nicht

Ohne Kenntnis der verschiedenen DOM-Eigenschaften und -Funktionen kann das jQuery-Objekt leicht unnötig missbraucht werden. Zum Beispiel:

1
2
$('#someAnchor').click(function() {
3
  // Bleh

4
	alert( $(this).attr('id') );
5
});

Wenn das jQuery-Objekt nur auf das ID-Attribut des Ankertags zugreifen muss, ist dies verschwenderisch. Besser bei "rohem" JavaScript bleiben.

1
2
$('#someAnchor').click(function() {
3
	alert( this.id );
4
});

Bitte beachten Sie, dass es drei Attribute gibt, auf die immer über jQuery zugegriffen werden sollte: "src", "href" und "style". Diese Attribute erfordern die Verwendung von getAttribute in älteren IE-Versionen.

Beweis

1
2
// jQuery Source

3
var rspecialurl = /href|src|style/;
4
// ... 

5
var special = rspecialurl.test( name );
6
// ...

7
var attr = !jQuery.support.hrefNormalized && notxml && special ?
8
	// Some attributes require a special call on IE

9
	elem.getAttribute( name, 2 ) :
10
	elem.getAttribute( name );

Mehrere jQuery-Objekte

Noch schlimmer ist das wiederholte Abfragen des DOM und das Erstellen mehrerer jQuery-Objekte.

1
2
	$('#elem').hide();
3
	$('#elem').html('bla');
4
	$('#elem').otherStuff();

Hoffentlich wissen Sie bereits, wie ineffizient dieser Code ist. Wenn nicht, ist das okay. wir lernen alle. Die Antwort besteht darin, entweder eine Verkettung zu implementieren oder den Ort von #elem zu #elem.

1
2
	// This works better

3
	$('#elem')
4
	  .hide()
5
	  .html('bla')
6
	  .otherStuff();
7
8
	// Or this, if you prefer for some reason.

9
	var elem = $('#elem');
10
	elem.hide();
11
	elem.html('bla');
12
	elem.otherStuff();

4. jQuery's Shorthand Ready-Methode

Mit jQuery ist es lächerlich einfach zu hören, wann das Dokument zur Bearbeitung bereit ist.

1
2
$(document).ready(function() {
3
	// let's get up in heeya

4
});

Es ist jedoch sehr wahrscheinlich, dass Sie auf eine andere, verwirrendere Funktion zum Einwickeln gestoßen sind.

1
2
$(function() {
3
	// let's get up in heeya

4
});

Obwohl letzteres etwas weniger lesbar ist, sind die beiden obigen Ausschnitte identisch. Glaub mir nicht Überprüfen Sie einfach die jQuery-Quelle.

1
2
// HANDLE: $(function)

3
// Shortcut for document ready

4
if ( jQuery.isFunction( selector ) ) {
5
	return rootjQuery.ready( selector );
6
}

rootjQuery ist einfach ein Verweis auf das Root-jQuery (document). Wenn Sie einen Selektor an die jQuery-Funktion übergeben, wird festgelegt, welchen Selektortyp Sie übergeben haben: Zeichenfolge, Tag, ID, Funktion usw.  Wenn eine Funktion übergeben wurde, ruft jQuery die ready() -Methode auf und übergibt Ihre anonyme Funktion als Selektor.


5. Bewahren Sie Ihren Code auf

Bei der Entwicklung von Code für die Verteilung ist es immer wichtig, mögliche Namenskollisionen auszugleichen. Was würde passieren, wenn ein nach Ihrem importiertes Skript auch eine $ -Funktion hätte? 

Schlechte Dinge!Die Antwort besteht darin, entweder noConflict() von jQuery aufzurufen oder Ihren Code in einer selbstaufrufenden anonymen Funktion zu speichern und dann jQuery an sie zu übergeben.

Methode 1: NoConflict

1
2
var j = jQuery.noConflict();
3
// Now, instead of $, we use j. 

4
j('#someDiv').hide();
5
6
// The line below will reference some other library's $ function.

7
$('someDiv').style.display = 'none';

Seien Sie vorsichtig mit dieser Methode und verwenden Sie sie nicht, wenn Sie Ihren Code verteilen. Das würde den Benutzer Ihres Skripts wirklich verwirren! :)

Methode 2: Übergeben von jQuery

1
2
(function($) {
3
	// Within this function, $ will always refer to jQuery

4
})(jQuery);

Die letzte Parens unten ruft die Funktion automatisch auf - function(){}(). Beim Aufruf der Funktion übergeben wir jedoch auch jQuery, das dann durch $ dargestellt wird.

Methode 3: Übergeben von $ über die Ready-Methode

1
2
jQuery(document).ready(function($) {
3
 // $ refers to jQuery

4
});
5
6
// $ is either undefined, or refers to some other library's function.

6. Sei klug

Denken Sie daran - jQuery ist nur JavaScript. Gehen Sie nicht davon aus, dass es die Fähigkeit hat, Ihre fehlerhafte Codierung zu kompensieren. :)

Dies bedeutet, dass, genauso wie Dinge wie JavaScript for Anweisungen optimiert werden müssen, dasselbe für each Methode von jQuery gilt. Und warum sollten wir nicht? Es ist nur eine Hilfsmethode, die hinter den Kulissen eine for-Anweisung erzeugt.

1
2
// jQuery's each method source

3
	each: function( object, callback, args ) {
4
		var name, i = 0,
5
			length = object.length,
6
			isObj = length === undefined || jQuery.isFunction(object);
7
8
		if ( args ) {
9
			if ( isObj ) {
10
				for ( name in object ) {
11
					if ( callback.apply( object[ name ], args ) === false ) {
12
						break;
13
					}
14
				}
15
			} else {
16
				for ( ; i < length; ) {
17
					if ( callback.apply( object[ i++ ], args ) === false ) {
18
						break;
19
					}
20
				}
21
			}
22
23
		// A special, fast, case for the most common use of each

24
		} else {
25
			if ( isObj ) {
26
				for ( name in object ) {
27
					if ( callback.call( object[ name ], name, object[ name ] ) === false ) {
28
						break;
29
					}
30
				}
31
			} else {
32
				for ( var value = object[0];
33
					i < length && callback.call( value, i, value ) !== false; value = object[++i] ) {}
34
			}
35
		}
36
37
		return object;
38
	}

Schrecklich

1
2
someDivs.each(function() {
3
	$('#anotherDiv')[0].innerHTML += $(this).text();
4
});
  1. Sucht für jede Iteration nach anotherDiv
  2. Ruft die innerHTML-Eigenschaft zweimal ab
  3. Erstellt ein neues jQuery-Objekt, um auf den Text des Elements zuzugreifen.

Besser

1
2
var someDivs = $('#container').find('.someDivs'),
3
      contents = [];
4
5
someDivs.each(function() {
6
	contents.push( this.innerHTML );
7
});
8
$('#anotherDiv').html( contents.join('') );

Auf diese Weise müssen Sie in der each Methode (for) nur einen neuen Schlüssel zu einem Array hinzufügen ... anstatt das DOM abzufragen, die innerHTML-Eigenschaft des Elements zweimal zu verwenden usw.

Dieser Tipp ist generell eher JavaScript-basiert als jQuery-spezifisch. Es ist wichtig zu wissen, dass jQuery schlechte Codierung nicht kompensiert.

Dokumentfragmente

Wenn wir gerade dabei sind, können Dokumentfragmente auch für diese Art von Situationen verwendet werden.

1
2
var someUls = $('#container').find('.someUls'),
3
	frag = document.createDocumentFragment(),
4
	li;
5
	
6
someUls.each(function() {
7
	li = document.createElement('li');
8
	li.appendChild( document.createTextNode(this.innerHTML) );
9
	frag.appendChild(li);
10
});
11
12
$('#anotherUl')[0].appendChild( frag );

Der Schlüssel hier ist, dass es mehrere Möglichkeiten gibt, einfache Aufgaben wie diese auszuführen, und jede hat ihre eigenen Leistungsvorteile von Browser zu Browser.  Je mehr Sie sich an jQuery halten und JavaScript lernen, desto öfter beziehen Sie sich auf die nativen Eigenschaften und Methoden von JavaScript. Und wenn ja, das ist fantastisch!

jQuery bietet eine erstaunliche Abstraktionsebene, die Sie nutzen sollten. Dies bedeutet jedoch nicht, dass Sie dazu gezwungen werden, seine Methoden zu verwenden.  In dem obigen Fragmentbeispiel verwenden wir beispielsweise each Methode von jQuery. Wenn Sie es vorziehen, stattdessen eine for oder while-Anweisung zu verwenden, ist das auch in Ordnung!

Bedenken Sie dabei, dass das jQuery-Team diese Bibliothek stark optimiert hat. Die Debatten über jQuerys each() und die native for-Anweisung sind dumm und trivial.  Wenn Sie jQuery in Ihrem Projekt verwenden, sparen Sie Zeit und verwenden Sie ihre Hilfsmethoden. Dafür sind sie da! :)


7. AJAX-Methoden

Wenn Sie gerade erst anfangen, sich mit jQuery zu beschäftigen, können die verschiedenen AJAX-Methoden, die es uns zur Verfügung stellt, etwas abschreckend wirken. obwohl sie nicht brauchen In der Tat handelt es sich bei den meisten nur um Hilfsmethoden, die direkt zu $.ajax führen.

  • get
  • getJSON
  • post
  • ajax

Sehen wir uns als Beispiel getJSON an, mit dem wir JSON abrufen können.

1
2
$.getJSON('path/to/json', function(results) {
3
	// callback

4
	// results contains the returned data object

5
});

Hinter den Kulissen ruft diese Methode zunächst $.get auf.

1
2
getJSON: function( url, data, callback ) {
3
	return jQuery.get(url, data, callback, "json");
4
}

$.get kompiliert dann die übergebenen Daten und ruft erneut die $.ajax-Methode "master" (Art) auf.

1
2
get: function( url, data, callback, type ) {
3
	// shift arguments if data argument was omited

4
	if ( jQuery.isFunction( data ) ) {
5
		type = type || callback;
6
		callback = data;
7
		data = null;
8
	}
9
10
	return jQuery.ajax({
11
		type: "GET",
12
		url: url,
13
		data: data,
14
		success: callback,
15
		dataType: type
16
	});
17
}

Schließlich leistet $.ajax eine enorme Menge an Arbeit, damit wir erfolgreich asynchrone Anfragen über alle Browser hinweg ausführen können!

Dies bedeutet, dass Sie die $.ajax-Methode für alle Ihre AJAX-Anforderungen genauso direkt und ausschließlich verwenden können.  Die anderen Methoden sind einfach Hilfsmethoden, die dies ohnehin tun. Wenn Sie möchten, schneiden Sie den mittleren Mann aus. Es ist in keiner Weise ein wichtiges Thema.

Total gut

1
2
$.getJSON('path/to/json', function(results) {
3
	// callback

4
	// results contains the returned data object

5
});

Mikroskopisch effizienter

1
2
$.ajax({
3
	type: 'GET',
4
	url : 'path/to/json',
5
	data : yourData,
6
	dataType : 'json',
7
	success : function( results ) {
8
		console.log('success');
9
	})
10
});

8. Zugriff auf native Eigenschaften und Methoden

Sie haben also ein bisschen JavaScript gelernt und gelernt, dass Sie beispielsweise auf Ankertags direkt auf Attributwerte zugreifen können:

1
2
var anchor = document.getElementById('someAnchor');
3
 //anchor.id

4
// anchor.href

5
// anchor.title

6
// .etc

Das einzige Problem ist, dass dies nicht funktioniert, wenn Sie mit jQuery auf die DOM-Elemente verweisen, oder? Na natürlich nicht.

Funktioniert nicht

1
2
	// Fails

3
	var id = $('#someAnchor').id;

Wenn Sie also auf das Attribut href (oder auf eine andere native Eigenschaft oder Methode) zugreifen müssen, haben Sie einige Optionen.

1
2
// OPTION 1 - Use jQuery

3
var id = $('#someAnchor').attr('id');
4
5
// OPTION 2 - Access the DOM element

6
var id = $('#someAnchor')[0].id;
7
8
// OPTION 3 - Use jQuery's get method

9
var id = $('#someAnchor').get(0).id;
10
11
// OPTION 3b - Don't pass an index to get

12
anchorsArray = $('.someAnchors').get();
13
var thirdId = anchorsArray[2].id;

Die get-Methode ist besonders hilfreich, da sie Ihre jQuery-Sammlung in ein Array übersetzen kann.


9. AJAX-Anforderungen mit PHP erkennen

Natürlich können wir uns bei der großen Mehrheit unserer Projekte nicht nur bei der Validierung oder bei AJAX-Anfragen auf JavaScript verlassen. Was passiert, wenn JavaScript deaktiviert ist?  Aus diesem Grund ist es eine übliche Technik, zu ermitteln, ob eine AJAX-Anforderung mit der serverseitigen Sprache der Wahl erfolgt ist.

jQuery macht dies lächerlich einfach, indem ein Header innerhalb der $.ajax-Methode festgelegt wird.

1
2
// Set header so the called script knows that it's an XMLHttpRequest

3
// Only send the header if it's not a remote XHR

4
if ( !remote ) {
5
	xhr.setRequestHeader("X-Requested-With", "XMLHttpRequest");
6
}

Mit diesem Headerset können wir nun PHP (oder eine andere Sprache) verwenden, um nach diesem Header zu suchen und entsprechend vorzugehen. Dazu prüfen wir den Wert von $_SERVER['HTTP_X_REQUESTED_WITH']

Verpackung

1
2
function isXhr() {
3
  return $_SERVER['HTTP_X_REQUESTED_WITH'] === 'XMLHttpRequest';
4
}

10. jQuery und $

Haben Sie sich jemals gefragt, warum / wie Sie jQuery und $ austauschbar verwenden können? Um Ihre Antwort zu finden, zeigen Sie die jQuery-Quelle an und scrollen Sie ganz nach unten. Dort sehen Sie:

1
2
window.jQuery = window.$ = jQuery;

Das gesamte jQuery-Skript ist natürlich in eine selbstausführende Funktion eingeschlossen, sodass das Skript die Anzahl der globalen Variablen so weit wie möglich begrenzen kann. Dies bedeutet jedoch auch, dass das jQuery-Objekt außerhalb der anonymen Wrapping-Funktion nicht verfügbar ist.

Um dies zu beheben, wird jQuery für das globale window objekt verfügbar gemacht. Dabei wird auch ein Alias - $ - erstellt.


11. Bedingtes Laden von jQuery

HTML5 Boilerplate bietet einen praktischen One-Liner, der eine lokale Kopie von jQuery lädt, wenn aus irgendeinem Grund Ihr CDN ausfällt.

1
2
<!-- Grab Google CDN jQuery. fall back to local if necessary -->
3
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js"></script>

4
<script>!window.jQuery && document.write('<script src="js/jquery-1.4.2.min.js"><\/script>')</script>

Um den Code oben zu "formulieren": Wenn window.jQuery nicht definiert ist, muss beim Herunterladen des Skripts vom CDN ein Problem aufgetreten sein. Fahren Sie in diesem Fall auf der rechten Seite des Operators && fort und fügen Sie ein Skript ein, das auf eine lokale Version von jQuery verweist.


12. jQuery Filters

1
2
<script>
3
	$('p:first').data('info', 'value'); // populates $'s data object to have something to work with
4
	
5
	$.extend(
6
		jQuery.expr[":"], {
7
			block: function(elem) {
8
				return $(elem).css("display") === "block";
9
			},
10
			
11
			hasData : function(elem) {				
12
				return !$.isEmptyObject( $(elem).data() );
13
			}
14
		}
15
	);
16
	
17
	$("p:hasData").text("has data"); // grabs paras that have data attached
18
	$("p:block").text("are block level"); // grabs only paragraphs that have a display of "block"
19
</script>

Hinweis: jQuery.expr [':'] ist einfach ein Alias für jQuery.expr.filters.


13. Eine einzelne Hover-Funktion

Ab jQuery 1.4 können wir jetzt nur eine einzige Funktion an die hover-Methode übergeben. Vorher waren sowohl die In- als auch die Out-Methode erforderlich.

Vor

1
2
$('#someElement').hover(function() {
3
  // mouseover

4
}, function() {
5
 // mouseout

6
});

Jetzt

1
2
$('#someElement').hover(function() {
3
  // the toggle() method can be used here, if applicable

4
});

Beachten Sie, dass dies kein alter und neuer Deal ist. Häufig müssen Sie noch zwei Funktionen zum hover weitergeben, und das ist absolut akzeptabel.  Wenn Sie jedoch nur ein Element (oder ähnliches) umschalten müssen, können Sie durch Übergeben einer einzelnen anonymen Funktion eine Handvoll Zeichen speichern.


14. Übergeben eines Attributobjekts

Ab jQuery 1.4 können wir nun ein Objekt als zweiten Parameter der jQuery-Funktion übergeben. Dies ist hilfreich, wenn neue Elemente in das DOM eingefügt werden müssen. Zum Beispiel:

Vor

1
2
$('<a />')
3
  .attr({
4
    id : 'someId',
5
    className : 'someClass',
6
    href : 'somePath.html'
7
  });

Nach dem

1
2
$('</a>', {
3
    id : 'someId',
4
    className : 'someClass',
5
    href : 'somePath.html'
6
});

Dies spart nicht nur ein paar Zeichen, sondern sorgt auch für saubereren Code. Zusätzlich zu den Elementattributen können wir auch jQuery-spezifische Attribute und Ereignisse wie click oder text übergeben.


Danke fürs Lesen!