2010-07-30 6 views
9

Ich frage mich, ob man über den folgenden Code ein prägnanter zu machen:Mehrere Selektoren oder mehrere Funktionen - jede Effizienzsteigerung?

$('#americasTrigger').hover(
    function() { 
      $('#americasImg').fadeIn() 
     }, 
    function(){ 
      $('#americasImg').fadeOut() 
    } 
); 

$('#europeTrigger').hover(
    function() { 
     $('#europeImg').fadeIn(); 
    }, 
    function(){ 
     $('#europeImg').fadeOut(); 
    } 
);  

$('#middleEastTrigger').hover(
    function() { 
     $('#middleEastImg').fadeIn(); 
    }, 
    function(){ 
     $('#middleEastImg').fadeOut(); 
    } 
);  

//More etc 

Der Name des Landes bis zum Ende das gleiche für jeden, mit ‚Trigger‘ oder ‚Img‘ hinzugefügt bleibt. Es gibt eine Menge Wiederholungen hier, die darauf hindeuten, dass ich nicht auf diese beste Weise gehe.

Ich hatte Gedanken um:

  • ein Case-Szenario Crearting oder
  • Irgendwie die Wähler immer für eine Auswahl verwendet wird, ist es ein String zu machen, es ist Aufspalten Namen des Landes in Betrieb zu erfassen und Anwendung das zu der verschachtelten FadeIn/Out-Funktion mit 'Img' am Ende.

Ist das möglich oder bin ich zu ausgefallen?

Edit 1: Vielen Dank für alle Antworten, Entschuldigung für die nicht die HTML zu veröffentlichen, habe ich dies nach unten setzen. Kurz gesagt verwende ich Bildkarten über ein bg-Bild (von Erde), da der Schwebeflug zum Ein-/Ausblenden meiner absolut positionierten Schwebeflug-Bilder führt.

<div class="mapTub"> 

    <img src="images/transparentPixel.png" class="mapCover" usemap="#worldMap" width="524px" height="273px"/> 

    <map name="worldMap" id="worldMap"> 
    <area id="americasTrigger" shape="poly" coords="1,2,3" href="#americas" /> 
    <area id="europeTrigger" shape="poly" coords="4,5,6" href="#europe" /> 
    <area id="middleEastTrigger" shape="poly" coords="7,8,9" href="#middleEast" /> 
    </map> 

<img src="images/International_americas_dark.png" class="americas" id="americasImg" /> 
<img src="images/International_europe_dark.png" class="europe" id="europeImg" /> 
<img src="images/International_middleEast_dark.png" class="middleEast" id="middleEastImg" /> 

</div> 

Reigel Antwort scheint, wie die Art und Weise, hier zu gehen, ist es krank Bericht versuchen, zurück, weitere Kommentare willkommen! :)

+1

html Codes bitte ... – Reigel

+0

Ja, ein paar Beispiele dafür, wie HTML aussieht, wären hilfreich. – belugabob

Antwort

2

Me, ohne Kenntnis der html, dieses ...

$('#americasTrigger, #europeTrigger, #middleEastTrigger').hover(
    function() { 
     var id = this.id; 
     $('#'+id.replace('Trigger', 'Img')).fadeIn(); 
     //$('#'+id.slice('0',id.indexOf('Trigger'))+'Img').fadeIn(); 
    }, 
    function(){ 
     var id = this.id; 
     $('#'+id.replace('Trigger', 'Img')).fadeOut(); 
     //$('#'+id.slice('0',id.indexOf('Trigger'))+'Img').fadeOut(); 
    } 
); 

Sie auch .replace() von Anurag im Kommentar wie vorgeschlagen unten verwenden können ...


id ='europeTrigger'; 
alert(id.slice('0',id.indexOf('Trigger'))); // alerts 'europe' 
// '#'+id.slice('0',id.indexOf('Trigger'))+'Img' is '#europeImg' 

demo

+0

Sie könnten das ersetzen mit 'id.replace ('Trigger', 'Img')' – Anurag

+0

@Annurag haha ​​schön! warte, update ... – Reigel

+0

Schön ein Reigel, das hat einen Leckerbissen geklappt, danke! – demolish

2

Da es so aussieht, als ob Sie nur auf unique ids zugreifen, verwenden Sie am besten eine lookup table IMO.

var lookmeup = [ [$('#americasTrigger'), $('#americasImg')], 
        [$('#europeTrigger'), $('#europeImg')], 
        [$('#middleEastTrigger'), $('#middleEastImg')] 
       ]; 

$.each(lookmeup, function(index, element){ 
    element[0].hover(function(){ 
     element[1].fadeIn(); 
    }, function(){ 
     element[1].fadeOut(); 
    }); 
}); 

TROCKEN! alles erledigt!

Eine andere Möglichkeit, es auf eine effizientere Weise zu tun wäre event delegation zu verwenden.

Wenn alle Ihre hover Elemente die gleiche TAG haben, könnte dieser Ansatz nützlich sein:

$(document.body).delegate('div', 'mouseenter', function(e){ 
    $('#' + e.target.id.replace(/Trigger/, 'Img')).fadeIn(); 
}); 

$(document.body).delegate('div', 'mouseleave', function(e){ 
    $('#' + e.target.id.replace(/Trigger/, 'Img')).fadeOut(); 
}); 

Unter der Annahme, dass alle Ihre „hoverable“ Elemente waren DIV s. Sie sollten diesen Elementen immer noch eine classname geben, damit nur die spezifischen Elemente angesprochen werden.

Es ist sehr sinnvoll, die root element für delegate() zu begrenzen.Hier verwende ich document.body, was .live() tun würde. Das Tolle an .delegate() ist, dass, wenn Ihre Hover-Elemente einen Elternknoten teilen, Sie delegate() auf diesem Knoten anwenden können. Auf diese Weise reduzieren Sie die Anzahl der gebundenen Ereignishandler

(2 statt 6).

+0

Hey jAndy, das sieht auch gut aus, ich habe gerade den HTML-Code in der Original-OP veröffentlicht, hast du irgendwelche Gedanken um deine Deligate-Methode gegen Reigals Scheibe/Ersetzungsmethode oben in Bezug auf Leistung? – demolish

0

lol, sieht so aus, kann ungefähr die gleiche Größe oder länger als Ihr Code, aber auf jeden Fall trockener sein.

Dank @Andy für Hinweis auf die Leistungseinbußen mit der vorherigen Version $(..).each.

var regions = ['americas', 'europe', 'middleEast']; 

$.each(regions, function(region) { 
    var trigger = id(region, 'Trigger'); 
    var image = id(region, 'Image'); 

    $(trigger).hover(
     effect(image, 'fadeIn'), 
     effect(image, 'fadeOut'), 
    ); 
}); 

function effect(selector, method) { 
    return function() { 
     $(selector)[method](); 
    }; 
} 

function id(prefix, suffix) { 
    return '#' + prefix + suffix; 
} 

Wenn Sie den HTML-Code ändern kann, würde ich alles Wissen in die Seite selbst, kodieren und nur jQuery Ereignisse einrichten Hover verwenden.

<div class='trigger' data-image='#americasImg'> 
    .. 
</div> 
<div class='trigger' data-image='#europeImg'> 
    .. 
</div> 

Javascript

function imageId(elem) { 
    return $(elem).attr('data-image'); 
} 

// Using the fade function from before 
$('.trigger').hover(
    effect(imageId(this), 'fadeIn'), 
    effect(imageId(this), 'fadeOut') 
); 
+0

Ich würde '$ .each()' verwenden, kein zusätzlicher jQuery-Konstruktor erforderlich. Ist der Unterstrich als erster Parameter ein ganz besonderer Trick oder Tippfehler? :) – jAndy

+0

@jAndy - danke für den Tipp. Ich habe die Leistungseinbußen nie realisiert. (Ich mochte das Aussehen von '$ .each' einfach nicht, aber ich schätze es ist ein notwendiges Übel :).Der Unterstrich war nur ein Signal, um anzuzeigen, dass der Parameter nutzlos ist. – Anurag

0

Oder, um die Dinge viel einfacher, einen Marker-Klasse hinzufügen, die so genannte 'fadingImage' beispielsweise auf jedem der Bilder und dann diesen Code verwenden ...

$('.fadingImage').hover( 
    function() { 
     $(this).fadeIn() 
    }, 
    function(){ 
     $(this).fadeOut() 
    } 
); 

Dies funktioniert, weil alle Bilder, unabhängig von ihrer ID, auf die gleiche Art und Weise behandelt werden, al, die Sie wirklich tun müssen, ist, welche Bilder auf Ihrer Seite identifizieren müssen die Hover-Handler angebracht haben, und thi s ist mit der Marker-Klasse erledigt. Sie können sogar ganz auf die Ids verzichten, wenn sie für nichts anderes verwendet werden.

Update: Nein, dass ich geweckt habe bis (Danke JANDY & Reigel!), Ich werde meinen Beitrag ändern mit der Tatsache zu tun, dass das Element ist, schwebt nicht derjenige ist, der verblasste wird.

Ohne ein Beispiel-Markup zu haben, muss ich einige Annahmen machen, aber das ursprüngliche Poster möchte vielleicht das echte Markup bereitstellen, um die Dinge in einen Zusammenhang zu stellen.

<div> 
    <span class="fadingTrigger">first text to hover over<span> 
    <img class="fadingImage" src="..." alt="first image to be faded"/> 
<div> 
<div> 
    <span class="fadingTrigger">second text to hover over<span> 
    <img class="fadingImage" src="..." alt="second image to be faded"/> 
<div> 

$('.fadingTrigger').hover( 
    function() { 
     $(this).parent().find(".fadingImage").fadeIn() 
    }, 
    function(){ 
     $(this).parent().find(".fadingImage").fadeOut() 
    } 
); 

Abhängig von der Markup-Struktur, wobei das Verfahren die fadingImage zu finden, die mit dem fadingTrigger zugeordnet wird, kann variieren müssen, aber durch eine gut definierte Struktur aufweist, sollte es zuverlässig sein.

Der Grund, warum ich diese Methode gegenüber einem Array von IDs zum Nachschlagen der Elemente bevorzugen würde ist, dass alle Ergänzungen der Markup Änderungen am Javascript erfordern - das wäre besonders problematisch, wenn das Markup dynamisch generiert wird. Das Javascript könnte auch dynamisch generiert werden, um das entsprechende Array von Werten einzuschließen, aber das würde den DRY-Principal verletzen.

+0

+1 mehr vereinfacht =) –

+0

dies funktioniert nicht, da das OP verschiedene Elemente/IDs zum Schweben verwendet. – jAndy

+0

Ja, aber das ist nicht nötig - er gibt sogar zu, dass sein Code sehr repetitiv ist. – belugabob

Verwandte Themen