Ich verwende jQuery, um benutzerdefinierte Optionsfelder zu erstellen, und ich habe ein Problem. Wenn Sie auf die Beschriftung klicken, die dem Radio zugeordnet ist, werden die Klickereignisse zweimal ausgelöst. Wenn ich nur auf das Radio selbst klicke, funktioniert dies einwandfrei (eigentlich ist es nicht das Radio, auf das ich klicke, sondern das Div, das die gesamte Eingabe und Beschriftung umschließt). Hier ist der Code:
Der HTML:
<div id="box">
<asp:RadioButtonList ID="RadioButtonList1" runat="server">
<asp:ListItem>RADIO1</asp:ListItem>
<asp:ListItem>RADIO2</asp:ListItem>
<asp:ListItem>RADIO3</asp:ListItem>
</asp:RadioButtonList>
</div>
jQuery:
<script type="text/javascript">
$(function () {
$('#box').find('input:radio').each(function (i) {
var input = $(this);
// get the associated label using the input's id
var label = $('label[for=' + input.attr('id') + ']');
// wrap the input + label in a div
$('<div class="custom-radio"></div>').insertBefore(input).append(label, input);
var wrapperDiv = input.parent();
// find all inputs in this set using the shared name attribute
var allInputs = $('input[name=' + input.attr('name') + ']');
// necessary for browsers that don't support the :hover pseudo class on labels
label.hover(
function () {
$(this).addClass('hover');
}, function () {
$(this).removeClass('hover checkedHover');
});
//bind custom event, trigger it, bind click,focus,blur events
wrapperDiv.bind('updateState', function () {
if ($(this)[0].children[1].checked) {
allInputs.each(function () {
var curDiv = $('div > label[for=' + $(this).attr('id') + ']').parent();
curDiv.removeClass('custom-radio-checked');
curDiv.addClass('custom-radio');
});
$(this).toggleClass('custom-radio custom-radio-checked');
}
else {
$(this).removeClass('custom-radio-checked checkedHover checkedFocus');
}
})
.trigger('updateState')
.click(function () { console.log('click'); })
.focus(function () {
label.addClass('focus');
}).blur(function () {
label.removeClass('focus checkedFocus');
});
});
});
</script>
Gibt es eine Lösung für dieses Verhalten?
jQuery('input').prop('checked', true);
return false;
ist äquivalent zu `evt.stopPropagation (); evt.preventDefault (); ( in jQuery )Ich habe versucht, die obige Lösung hinzuzufügen, indem ich Folgendes hinzufügte:
hat aber nicht funktioniert. Fügen Sie jedoch Folgendes hinzu:
Problem gelöst! :) :)
quelle
evt.stopPropagation(); evt.preventDefault();
nicht; 'tBinden Sie das Klickereignis an die Eingabe und nicht an die Beschriftung. Wenn auf das Etikett geklickt wird, tritt das Ereignis weiterhin auf, da, wie Dustin erwähnt hat, ein Klick auf das Etikett einen Klick auf die Eingabe auslöst. Dadurch kann das Etikett seine normale Funktionalität beibehalten.
Anstatt
quelle
change
sogar an das Optionsfeld binden, da der Text eines Etiketts anklickbar ist - sie klicken nicht immer auf das Optionsfeld selbst.label > input
Setup verwenden, ist dies DIE Antwort, keine Antwort. Das Hinzufügenevt.stopPropagation()
oder Hinzufügenevt.preventDefault()
zu Ihrem Code ist zwar effektiv, aber ein Hack, der vermieden werden sollte, wenn die richtige Lösung viel sauberer und effizienter ist.Wenn Sie versuchen, einen äußeren Container als Klickelement zu verwenden, können Sie die Ereignisse auch auf natürliche Weise sprudeln lassen und in Ihrem Klick-Handler auf das erwartete Element testen. Dieses Szenario ist nützlich, wenn Sie versuchen, eine eindeutige Klickzone für ein Formular zu erstellen.
quelle
if (e.target == e.currentTarget) {}
Um dies auf einfache Weise zu beheben, entfernen Sie das Attribut "for" auf dem Etikett. Ein Klick auf die Beschriftung löst auch einen Klick auf das zugehörige Element aus. (In Ihrem Fall wird Ihr Klickereignis zweimal ausgelöst.)
Viel Glück
quelle
Normalerweise benutze ich diese Synthax
anstatt
quelle
Die beste Antwort ist in Kommentaren versteckt:
Diese Geige zeigt , dass alle anderen Lösungen -
stopPropagation
,stopImmediatePropagation
,preventDefault
,return false
- entweder nichts ändern oder die Checkbox / Radio Funktionalität zerstören). Es zeigt auch, dass dies ein Vanille-JavaScript-Problem ist, kein jQuery-Problem.BEARBEITEN: Eine andere funktionierende Lösung, die ich gerade in einem anderen Thread gefunden habe, besteht darin, das
onclick
an die Eingabe und nicht an das Etikett zu binden . Geige aktualisiert .quelle
Ich habe versucht, durch Hinzufügen von Lösung.
hat aber nicht funktioniert.
Beim Hinzufügen
Problem gelöst! :) :)
quelle
Das Problem mit e.preventDefault (); verhindert, dass das Klicken auf das Etikett das Optionsfeld aktiviert.
Eine bessere Lösung wäre, einfach eine Schnellprüfung "wird geprüft" wie folgt hinzuzufügen:
quelle
Mein Problem ist ein bisschen anders, da das
evt.stopPropagation();evt.preventDefault();
bei mir nicht funktioniert, füge ichreturn false;
am Ende einfach hinzu , dann funktioniert es.quelle
In meinem Fall war das Problem, dass ich das Klickereignis in einer Funktion hatte und die Funktion zweimal ausgeführt wurde . Jede Ausführung der Funktion erzeugt ein neues Klickereignis. - Gesichtspalme -
Nach dem Verschieben des Klickereignisses außerhalb der Funktion funktionierte alles wie erwartet! :) :)
quelle
Versuchen Sie, Ihr Eingabe-Tag außerhalb des Trigger-Elements zu platzieren, da das Label-Tag den Klick emuliert, sodass Sie immer mehr als einen Aufruf haben.
quelle
Ich hatte das gleiche Problem, weil ich mein Radio wie folgt mit dem an radio_div angehängten Handler in das Label verschachtelt hatte. Durch Entfernen des verschachtelten Labels wurde das Problem behoben.
quelle
Das Etikett löst das zu prüfende Radio / Kontrollkästchen aus.
Es verhindert insbesondere das Label, dieses Verhalten auszulösen.
quelle
Der Klick auf die Beschriftung mit dem Attribut for = "some-id" löst einen neuen Klick aus, jedoch nur, wenn das Ziel vorhanden ist und eine Eingabe ist. Ich konnte es mit e.preventDefault () oder ähnlichen Dingen nicht perfekt lösen, also habe ich es so gemacht:
Zum Beispiel, wenn Sie diese Struktur haben und ein Ereignis beim Klicken auf .some-class möchten
Was funktionierte war:
quelle