2016-04-05 11 views
0

So habe ich eine ul von Kontrollkästchen und ich möchte Benutzern erlauben, irgendwo auf die li Elemente klicken, um das entsprechende Kontrollkästchen zu aktivieren/deaktivieren, dann übernehmen Sie die Änderungen auf der Seite über Javascript . Beachten Sie, dass alle Kontrollkästchen aktiviert sind. Dies ist das Layout, abgesehen von ein paar weiteren li Elementen.Eigenschaft von DOM-Element unterscheidet sich je nach Selektor - jQuery

<ul class="dropdown-menu"> 
    <li class="cat-header"> 
     <strong>Category</strong> 
    </li> 
    <li> 
     <a class="filter-link"> Red 
      <input checked="true" class="cat-check" data-filter="red" data-type="color" type="Checkbox"> 
     </a> 
    </li> 

Ich versuche dann Javascript, um die Seite auf der checked Eigenschaft der Kontrollkästchen Basis zu verändern, zu verwenden. Allerdings erhalte ich unterschiedliche Werte, je nachdem, wie ich die Elemente auswähle. Meine Funktion sieht so aus

setFilter = function(checkbox) { 
    console.log(checkbox); 
    if ($(checkbox).attr('data-type') === "color") { 
    if (!$(checkbox).prop('checked')) { 
     $(checkbox).prop('checked', false); 
     colorFilter = colorFilter.replace($(checkbox).attr('data-filter') + " ", ""); 
    } else { 
     $(checkbox).prop('checked', true); 
     colorFilter = colorFilter + $(checkbox).attr('data-filter') + " "; 
    } 
    } else if ($(checkbox).attr('data-type') === "shape") { 
    if (!$(checkbox).prop('checked')) { 
     $(checkbox).prop('checked', false); 
     shapeFilter = shapeFilter + $(checkbox).attr('data-filter') + " "; 
    } else { 
     $(checkbox).prop('checked', true); 
     shapeFilter = shapeFilter.replace($(checkbox).attr('data-filter') + " ", ""); 
    } 
    } 
}; 

Ein paar Notizen. Erstens ist die Farbe einschließlich (d. H. Zeige es, wenn sie diese Farbe hat), während die Form exklusiv ist (d. H., Zeige sie nicht, wenn sie diese Form hat), daher die etwas andere Logik. Zweitens .prop() Funktion war es, die entgegengesetzte Werte zurückzukehren, was ich erwartet hatte damit die if (!$(checkbox).prop('checked'))

Wenn ich es so nennen, druckt es sich als wahr heraus

$('.filter-link').click(function(e) { 
    setFilter($(this).children("input")[0]); 
    }); 

aber wenn ich es so nennen, es ausdruckt falsch

$('.cat-check').click(function(e) { 
    setFilter($(this)[0]); 
    }); 

ich habe versucht, die Wirkung in JSFiddle (https://jsfiddle.net/eg9c4vkv/6/) konnte aber nicht duplizieren den Effekt zu reproduzieren. Ich dachte auch, dass es mit console.log (How can I change the default behavior of console.log? (*Error console in safari, no add-on*)) verwandt sein könnte, aber theoretisch sollte sich die Funktion genauso verhalten, solange die Eingabe die gleiche ist. Hat jemand irgendwelche Ideen?

+0

Es ist schwer zu sagen, ohne mehr von 'setFilter' Funktion zu sehen. Greifen Sie auf die Eigenschaften genauso zu wie auf Ihre jsFiddle? – Kevin

+0

Ich habe im Hauptteil der 'setFilter' Methode hinzugefügt – cfatt10

Antwort

1

Ich sehe ein paar kleinere Probleme, aber nichts ist offensichtlich.

Zuerst wäre die Art und Weise, in der Sie auf das Attribut data zugreifen. Zweitens, wie binden Sie Handler (sind Sie sicher, dass jedes Mal, wenn Sie auf das Kontrollkästchen klicken, ein Ereignis weder für .cat-check AND .filter-link ausgelöst wird, was zu unerwartetem Verhalten führen könnte) es hilft.

Indem Sie das Präfix data- in das Attribut einfügen, geben Sie jQuery vor, den Wert automatisch zu speichern, wenn es fertig ist.
Refer to jQuery data docs for more info

<a href="" data-filter="hello">Hello</a>

würde

$('a').data('filter', 'hello'); 

Um auf die Daten zugreifen können, müssen Sie nur den Schlüssel verwenden, die in diesem Fall wäre filter oder type gleichwertig sein. Es ist erwähnenswert, dass Sie Zugriff auf das Attribut direkt wie Sie sind, aber verwenden Sie das eine oder das andere (vorzugsweise .data).

z.B. mit Markup ..

<a href="" data-filter="hello">Hello</a> 

$('a').on('click', function(e) { 
    var $this = $(this); 
    $this.data('filter', 'I changed'); 
    //what will the value be? It's going to be 'Hello', because we're accessing the attribute in the DOM 
    alert($this.attr('data-filter')); 

    //what will the value be? It's going to be 'I changed', because we're accessing the data cache 
    alert($this.data('filter')); 
}); 

Geben Sie diesem einen Versuch, ich denke, ich verstehe, was Sie zu tun versuchen (die folgenden Code-Schnipsel sollte für Sie arbeiten)

var colorFilter = 'red green yellow '; 
 

 
$('.dropdown-menu') 
 
    .on('click', 'li', function(e) { 
 
    \t //check the source of the event, if the checkbox was already clicked then let it continue 
 
    if (e.target.type != "checkbox") { 
 
     $(this).find(".cat-check").click(); 
 
    } 
 
    }) 
 
    .on('click', '.cat-check', function() { 
 
    console.log(this); 
 
    var $checkbox = $(this), 
 
     type = $checkbox.data('type'), 
 
     filter = $checkbox.data('filter'), 
 
     isChecked = $checkbox.prop('checked'); 
 
    console.log(isChecked); 
 
    if (type === "color") { 
 
     if (isChecked) { 
 
     if (colorFilter.indexOf(filter) < 0) { 
 
      colorFilter = colorFilter + filter + " "; 
 
     } 
 
     } else { 
 
     colorFilter = colorFilter.replace(filter + " ", ""); 
 
     } 
 
     $('#filter').text(colorFilter); 
 
    } else if (type === "shape") { 
 
     if (isChecked) { 
 
     if (colorFilter.indexOf(filter) < 0) { 
 
      shapeFilter = shapeFilter + filter + " "; 
 
     } 
 
     } else { 
 
     shapeFilter = shapeFilter.replace(filter + " ", ""); 
 
     } 
 
     console.log(shapeFilter); 
 
    } 
 
    });
li { 
 
    cursor: pointer; 
 
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> 
 

 
<div id='filter'> 
 
    red green yellow 
 
</div> 
 
<ul class="dropdown-menu"> 
 
    <li class="cat-header"> 
 
    <strong>Category</strong> 
 
    </li> 
 
    <li> 
 
    <a class="filter-link"> Red 
 
      <input checked="true" class="cat-check" data-filter="red" data-type="color" type="Checkbox"> 
 
     </a> 
 
    </li> 
 
    <li> 
 
    <a class="filter-link"> Green 
 
      <input checked="true" class="cat-check" data-filter="green" data-type="color" type="Checkbox"> 
 
     </a> 
 
    </li> 
 
    <li> 
 
    <a class="filter-link"> Yellow 
 
      <input checked="true" class="cat-check" data-filter="yellow" data-type="color" type="Checkbox"> 
 
     </a> 
 
    </li> 
 
</ul>

+0

Es stellte sich heraus, dass, wenn die Checkbox geklickt wurde, anstatt der' a', die 'checked' Eigenschaft wurde geschaltet, bevor die Funktion aufgerufen wurde, so dass die entgegengesetzte Eingabe. Ihre Lösung vermeidet dieses Problem, indem sie '$ (this) .find (". Cat-check "). Click();' Wenn das Ziel kein Kontrollkästchen ist, das ist viel eleganter als die von mir entwickelte Lösung auf eigene Faust. – cfatt10

0

Es stellte sich heraus Wenn das Kontrollkästchen anstelle der a geklickt wurde, würde die Eigenschaft checked umgeschaltet werden, bevor die Methode aufgerufen wurde, wodurch die verschiedenen Werte zur Laufzeit angegeben wurden. Die einfache Problemumgehung besteht darin, ein Klickereignis im Kontrollkästchen auszulösen, wenn auf a geklickt wird.

Dank @Kevin für Hilfe und eine elegantere Lösung als ich ursprünglich entwickelt.

Verwandte Themen