Das click-Ereignis ist ziemlich einfach und leicht zu verwenden. Sie lauschen auf das Ereignis und führen Code aus, wenn das Ereignis ausgelöst wird. Es funktioniert auf praktisch jedem HTML-Element, eine Kernfunktion der DOM-API.
Wie so oft bei DOM und JavaScript gibt es Nuancen zu beachten. Einige Nuancen des click -Ereignisses sind normalerweise keine große Sorge. Sie sind geringfügig und die meisten Leute würden sie in den meisten Anwendungsfällen wahrscheinlich nie bemerken.
Nehmen Sie zum Beispiel das click-Ereignis, das auf den Großvater interaktiver Elemente, das <button>-Element, reagiert. Mit Button-Klicks sind Nuancen verbunden, und diese Nuancen, wie der Unterschied zwischen einem „Klick“ mit einem Mauszeiger und einem „Klick“ von der Tastatur. So gesehen ist ein Klick nicht immer ein „Klick“, wie er typischerweise definiert wird. Ich bin tatsächlich auf Situationen gestoßen (wenn auch nicht viele), in denen es praktisch ist, zwischen diesen beiden Arten von Klicks zu unterscheiden.
Wie unterscheiden wir zwischen verschiedenen Arten von Klicks? Genau das tauchen wir jetzt ein!
Zuerst die Grundlagen
Das <button>-Element, wie von MDN beschrieben, ist einfach
Das HTML-Element repräsentiert einen klickbaren Button, der zum Absenden von Formularen oder überall in einem Dokument für zugängliche, Standard-Button-Funktionalität verwendet wird. Standardmäßig werden HTML-Buttons in einem Stil präsentiert, der der Plattform ähnelt, auf der der User-Agent läuft, aber Sie können das Aussehen von Buttons mit CSS ändern.
Der Teil, den wir behandeln werden, ist offensichtlich der Teil der Beschreibung „überall in einem Dokument für zugängliche, Standard-Button-Funktionalität“. Wie Sie vielleicht wissen, kann ein Button-Element native Funktionalität innerhalb eines Formulars haben, zum Beispiel kann es in einigen Situationen ein Formular absenden. Wir beschäftigen uns hier eigentlich nur mit der grundlegenden Klickfunktion des Elements. Betrachten Sie also nur einen einfachen Button, der auf der Seite platziert ist und eine bestimmte Funktionalität bietet, wenn jemand damit interagiert.
Beachten Sie, dass ich „interagiert damit“ statt nur „geklickt“ gesagt habe. Aus historischen und Benutzerfreundlichkeitsgründen kann man den Button „klicken“, indem man den Fokus mit der Tabulatortaste darauf legt und dann die Leertaste oder die Enter-Taste auf der Tastatur verwendet. Das ist eine leichte Überschneidung mit Tastaturnavigation und Barrierefreiheit; diese native Funktion existierte lange bevor Barrierefreiheit ein Thema war. Dennoch hilft die Legacy-Funktion aus offensichtlichen Gründen erheblich bei der Barrierefreiheit.
Im obigen Beispiel können Sie auf den Button klicken und seine Textbeschriftung ändert sich. Nach einem Moment wird der ursprüngliche Text zurückgesetzt. Sie können auch irgendwo anders im Pen klicken, mit Tabulator den Fokus auf den Button legen und dann Leertaste oder Enter verwenden, um ihn zu „klicken“. Derselbe Text erscheint und wird zurückgesetzt. Es gibt kein JavaScript, das die Tastaturfunktionalität behandelt; es ist eine native Funktion des Browsers. Im Grunde ist sich der Button in diesem Beispiel nur des Click-Ereignisses bewusst, aber nicht, wie es zustande kam.
Ein interessanter Unterschied, den man berücksichtigen sollte, ist das Verhalten eines Buttons in verschiedenen Browsern, insbesondere die Art und Weise, wie er gestylt wird. Die Buttons in diesen Beispielen sind so eingestellt, dass sie bei ihrem aktiven Zustand die Farben ändern; Sie klicken also darauf und er wird lila. Betrachten Sie dieses Bild, das die Zustände bei der Interaktion mit der Tastatur zeigt.

Der erste ist der statische Zustand, der zweite ist, wenn der Button den Fokus durch Tastatureingabe hat, der dritte ist die Tastaturinteraktion und der vierte ist das Ergebnis der Interaktion. Bei Firefox sehen Sie nur den ersten, zweiten und letzten Zustand; wenn Sie Enter oder Leertaste verwenden, um ihn zu „klicken“, sehen Sie nicht den dritten Zustand. Er bleibt beim zweiten, also „fokussierten“, Zustand während der Interaktion und wechselt dann zum letzten. Der Text ändert sich wie erwartet, aber die Farben nicht. Chrome gibt uns etwas mehr, da Sie die ersten beiden Zustände genauso sehen wie bei Firefox. Wenn Sie die Leertaste verwenden, um den Button zu „klicken“, sehen Sie den dritten Zustand mit der Farbänderung und dann den letzten. Interessanterweise sehen Sie bei Chrome, wenn Sie Enter verwenden, um mit dem Button zu interagieren, nicht den dritten Zustand mit der Farbänderung, ähnlich wie bei Firefox. Falls Sie neugierig sind, Safari verhält sich genauso wie Chrome.
Der Code für den Event-Listener ist ziemlich einfach
const button = document.querySelector('#button');
button.addEventListener('click', () => {
button.innerText = 'Button Clicked!';
window.setTimeout(() => {
button.innerText = '"click" me';
}, 2000);
});
Betrachten wir nun etwas hier mit diesem Code. Was wäre, wenn Sie sich in einer Situation wiederfinden würden, in der Sie wissen möchten, was den „Klick“ verursacht hat? Das Click-Ereignis ist normalerweise an ein Zeigergerät gebunden, typischerweise die Maus, und doch lösen hier die Leertaste oder die Enter-Taste dasselbe Ereignis aus. Andere Formularelemente haben ähnliche Funktionalitäten je nach Kontext, aber alle Elemente, die standardmäßig nicht interaktiv sind, erfordern ein zusätzliches Tastaturereignis, um zu funktionieren. Das Button-Element erfordert diesen zusätzlichen Event-Listener nicht.
Ich werde nicht zu weit auf die Gründe eingehen, warum man wissen möchte, was das Click-Ereignis ausgelöst hat. Ich kann sagen, dass ich gelegentlich auf Situationen gestoßen bin, in denen es hilfreich war, dies zu wissen. Manchmal aus Styling-Gründen, manchmal für Barrierefreiheit und manchmal für spezifische Funktionalität. Oft bieten unterschiedlicher Kontext oder Situationen unterschiedliche Gründe.
Betrachten Sie das Folgende nicht als Den Weg™ , sondern eher als eine Erkundung dieser Nuancen, über die wir sprechen. Wir werden die verschiedenen Möglichkeiten der Interaktion mit einem Button-Element, die generierten Ereignisse und die Nutzung spezifischer Merkmale dieser Ereignisse untersuchen. Hoffentlich können die folgenden Beispiele einige hilfreiche Informationen aus den Ereignissen liefern; oder möglicherweise nach Bedarf auf andere HTML-Elemente verteilt werden.
Welches ist welches?
Eine einfache Möglichkeit, ein Tastatur- vs. Mausklick-Ereignis zu erkennen, ist die Nutzung der keyup- und mouseup-Ereignisse, wobei das Click-Ereignis außer Acht gelassen wird.
Wenn Sie nun die Maus oder die Tastatur verwenden, spiegelt der geänderte Text wider, welches Ereignis welches ist. Die Tastaturversion informiert Sie sogar darüber, ob eine Leertaste oder Enter-Taste verwendet wurde.
Hier ist der neue Code
const button = document.querySelector('#button');
function reset () {
window.setTimeout(() => {
button.innerText = '"click" me';
}, 2000);
}
button.addEventListener('mouseup', (e) => {
if (e.button === 0) {
button.innerText = 'MouseUp Event!';
reset();
}
});
button.addEventListener('keyup', (e) => {
if (e.code === 'Space' || e.code === 'Enter') {
button.innerText = `KeyUp Event: ${e.code}`;
reset();
}
});
Etwas wortreich, zugegeben, aber wir werden uns gleich einem leichten Refactoring widmen. Dieses Beispiel verdeutlicht eine Nuance, die behandelt werden muss. Die mouseup- und keyup-Ereignisse haben ihre eigenen Merkmale, die in dieser Situation berücksichtigt werden müssen.
Beim mouseup-Ereignis könnte fast jede Maustaste dieses Ereignis auslösen. Wir möchten zum Beispiel normalerweise nicht, dass die rechte Maustaste ein „Klick“-Ereignis auf dem Button auslöst. Wir suchen also nach e.button mit dem Wert 0, um die primäre Maustaste zu identifizieren. So funktioniert es wie beim Click-Ereignis, aber wir wissen mit Sicherheit, dass es die Maus war.
Beim keyup-Ereignis geschieht dasselbe, wobei fast jede Taste auf der Tastatur dieses Ereignis auslöst. Wir schauen uns also die code-Eigenschaft des Ereignisses an, um darauf zu warten, dass die Leertaste oder die Enter-Taste gedrückt wird. So funktioniert es jetzt wie beim Click-Ereignis, aber wir wissen, dass die Tastatur verwendet wurde. Wir wissen sogar, welche der beiden Tasten wir auf dem Button erwarten.
Eine andere Herangehensweise, um herauszufinden, welches was ist
Während das vorherige Beispiel funktioniert, scheint es für ein so einfaches Konzept etwas zu viel Code zu sein. Wir wollen eigentlich nur wissen, ob der „Klick“ von einer Maus oder einer Tastatur kam. In den meisten Fällen würden wir uns wahrscheinlich nicht darum kümmern, ob die Quelle des Klicks entweder die Leertaste oder die Enter-Taste war. Aber wenn es uns interessiert, können wir die Eigenschaften des keyup-Ereignisses nutzen, um festzustellen, welches was ist.
Versteckt in den verschiedenen Spezifikationen über das click-Ereignis (was uns zur UI Events-Spezifikation führt) gibt es bestimmte Eigenschaften, die dem Ereignis zugewiesen sind. Einige Browser haben mehr, aber ich möchte mich für den Moment auf die detail-Eigenschaft konzentrieren. Diese Eigenschaft ist direkt mit der Maus-Eingabe verbunden, die das Ereignis selbst ausgelöst hat. Wenn also die Maustaste verwendet wurde, sollte die Eigenschaft den Wert 1 zurückgeben. Sie kann auch potenziell eine höhere Zahl melden, die mehrere Klicks darstellt und oft an den Schwellenwert für Doppelklicks gebunden ist, der vom Betriebssystem des Geräts bestimmt wird. Als Bonus meldet diese Eigenschaft für das Click-Ereignis einen Nullwert, wenn es durch etwas anderes als die Maus-Eingabe verursacht wurde, wie z. B. die Tastatur.
Ich nehme mir einen Moment Zeit für einen Gruß an Jimmy unten in den Kommentaren. Ich hatte ursprünglich eine andere Methode zur Unterscheidung von Tastatur- vs. Mausklicks, aber sie war nicht über alle Browser hinweg konsistent, da Safari Werte leicht unterschiedlich meldete. Jimmy schlug die detail -Eigenschaft vor, da sie konsistenter war; daher habe ich meine Beispiele entsprechend aktualisiert. Danke an Jimmy für den Vorschlag!
Hier ist unser neuer Code
const button = document.querySelector('#button');
button.addEventListener('click', (e) => {
button.innerText = e.detail === 0 ? 'Keyboard Click Event!' : 'Mouse Click Event!';
window.setTimeout(() => {
button.innerText = '"click" me';
}, 2000);
});
Zurück zum click-Ereignis, aber diesmal schauen wir auf den Eigenschaftswert, um zu bestimmen, ob es sich um einen Tastatur- oder Mausklick handelt. Obwohl beachtet werden muss, dass wir hier keine Möglichkeit mehr haben zu bestimmen, welche Taste auf der Tastatur verwendet wurde, ist das in diesem Kontext aber keine große Sorge.
Welches von vielen?
Nun ist es an der Zeit, über Pointer Events zu sprechen. Wie von MDN beschrieben
Viele heutige Web-Inhalte gehen davon aus, dass das Zeigegerät des Benutzers eine Maus sein wird. Da jedoch viele Geräte andere Arten von Zeigegeräten unterstützen, wie Stifte/Stylus und Touchscreens, sind Erweiterungen der bestehenden Zeigegeräte-Ereignismodelle erforderlich. Pointer Events decken diesen Bedarf ab.
Betrachten wir nun den Bedarf, zu wissen, welcher Zeigertyp zum Klicken auf diesen Button verwendet wurde. Sich nur auf das Click-Ereignis zu verlassen, liefert diese Information nicht wirklich. Chrome hat eine interessante Eigenschaft im Click-Ereignis, sourceCapabilities. Diese Eigenschaft hat wiederum eine Eigenschaft namens firesTouchEvents, die ein boolescher Wert ist. Diese Information ist nicht immer verfügbar, da Firefox und Safari sie noch nicht unterstützen. Das Pointer-Ereignis ist jedoch fast überall verfügbar, sogar im IE11 von allen Browsern.
Dieses Ereignis kann interessante Daten über Touch- oder Stiftereignisse liefern. Dinge wie Druck, Kontaktgröße, Neigung und mehr. Für unser Beispiel hier konzentrieren wir uns nur auf pointerType, das uns den Gerätetyp mitteilt, der das Ereignis verursacht hat.
Ein weiterer Punkt im Zusammenhang mit der detail-Eigenschaft im Click-Ereignis, die oben erwähnt wurde. Das Pointer-Ereignis hat ebenfalls eine Detail-Eigenschaft, aber zu diesem Zeitpunkt besagt die Spezifikation, dass der Wert dieser Eigenschaft immer null sein sollte. Das steht offensichtlich im Widerspruch zur vorherigen Idee, dass ein Wert von Null Tastatur und ein Wert über Null Maus-Eingabe bedeutet. Da wir uns nicht auf diese Eigenschaft im Pointer-Ereignis verlassen können, macht es schwierig, sowohl Click- als auch Pointer-Ereignisse in derselben Situation zu berücksichtigen. Fairerweise muss man sagen, dass man das sowieso wahrscheinlich nicht tun würde.
Ein Klick auf den Button teilt Ihnen nun mit, welcher Zeiger verwendet wurde. Der Code dafür ist ziemlich einfach
const button = document.querySelector('#button');
button.addEventListener('pointerup', (e) => {
button.innerText = `Pointer Event: ${e.pointerType}`;
window.setTimeout(() => {
button.innerText = '"click" me';
}, 2000);
});
Wirklich nicht viel anders als die vorherigen Beispiele. Wir lauschen auf das pointerup-Ereignis auf dem Button und geben pointerType des Ereignisses aus. Der Unterschied ist nun, dass kein Event-Listener für ein Click-Ereignis vorhanden ist. Das Tabbing auf den Button und die Verwendung der Leertaste oder Enter-Taste bewirkt also nichts. Das Click-Ereignis wird immer noch ausgelöst, aber wir lauschen nicht darauf. An diesem Punkt haben wir nur Code, der an den Button gebunden ist und nur auf das Pointer-Ereignis reagiert.
Das hinterlässt offensichtlich eine Lücke in der Funktionalität, die Tastaturinteraktion, also müssen wir immer noch ein Click-Ereignis einschließen. Da wir bereits das Pointer-Ereignis für den eher traditionellen Mausklick (und andere Pointer-Ereignisse) verwenden, müssen wir das Click-Ereignis einschränken. Wir müssen nur der Tastatur selbst erlauben, das Click-Ereignis auszulösen.
Der Code dafür ist ähnlich wie im Beispiel „Welches ist welches“ oben. Der Unterschied ist, dass wir pointerup anstelle von mouseup verwenden
const button = document.querySelector('#button');
function reset () {
window.setTimeout(() => {
button.innerText = '"click" me';
}, 2000);
}
button.addEventListener('pointerup', (e) => {
button.innerText = `Pointer Event: ${e.pointerType}`;
reset();
});
button.addEventListener('click', (e) => {
if (e.detail === 0) {
button.innerText = 'Keyboard ||Click Event!';
reset();
}
});
Hier verwenden wir wieder die detail-Eigenschaft, um festzustellen, ob der Klick von der Tastatur verursacht wurde. So würde ein Mausklick vom Pointer-Ereignis behandelt werden. Wenn man wissen möchte, ob die verwendete Taste Leertaste oder Enter war, könnte das oben genannte Keyup-Beispiel verwendet werden. Selbst dann könnte das keyup -Ereignis anstelle des click -Ereignisses verwendet werden, je nachdem, wie man es angehen möchte.
Eine weitere Herangehensweise, um welches von vielen zu bestimmen
Im allgegenwärtigen Bedürfnis, für saubereren Code zu refaktorieren, können wir einen anderen Weg ausprobieren.
Ja, funktioniert wie zuvor. Jetzt ist der Code
const button = document.querySelector('#button');
function btn_handler (e) {
if (e.type === 'click' && e.detail > 0) {
return false;
} else if (e.pointerType) {
button.innerText = `Pointer Event: ${e.pointerType}`;
} else if (e.detail === 0) {
button.innerText = 'Keyboard Click Event!';
} else {
button.innerText = 'Something clicked this?';
}
window.setTimeout(() => {
button.innerText = '"click" me';
}, 2000);
}
button.addEventListener('pointerup', btn_handler);
button.addEventListener('click', btn_handler);
Eine weitere skalierte Version zum Nachdenken: Diesmal haben wir unseren Code auf eine einzige Handler-Methode reduziert, die sowohl von pointerup- als auch von click-Ereignissen aufgerufen wird. Zuerst erkennen wir, ob der Maus-"Klick" das Ereignis verursacht hat, weil die detail -Eigenschaft einen Wert größer als Null hat; wenn ja, möchten wir sie zugunsten des Pointer-Ereignisses ignorieren.
Dann prüft die Methode auf das Pointer-Ereignis und meldet, wenn es gefunden wurde, welchen Zeigertyp es gab. Andernfalls prüft die Methode auf Tastaturinteraktionen, wenn detail null ist, und meldet dies entsprechend. Wenn keines davon der Schuldige ist, meldet sie einfach, dass etwas diesen Code zum Laufen gebracht hat.
Hier haben wir also eine gute Anzahl von Beispielen, wie man Button-Interaktionen behandelt und die Quelle dieser Interaktionen meldet. Dies ist jedoch nur eines der Handvoll Formularelemente, die wir in Projekten gewohnt sind zu verwenden. Wie funktioniert ähnlicher Code mit anderen Elementen?
Checkboxes prüfen
Tatsächlich funktioniert ähnlicher Code bei Checkboxen sehr ähnlich.
Es gibt noch ein paar Nuancen, wie Sie inzwischen vielleicht erwarten. Die normale Verwendung von <input type="checkbox"> ist ein verwandtes Label-Element, das über das for-Attribut mit dem Input verbunden ist. Eine Hauptfunktion dieser Kombination ist, dass das Klicken auf das Label-Element die zugehörige Checkbox aktiviert.
Wenn wir nun Event-Listener für das click-Ereignis für beide Elemente anhängen, erhalten wir Ergebnisse, die offensichtlich sein sollten, auch wenn sie etwas seltsam sind. Zum Beispiel wird beim Klicken auf die Checkbox ein click-Ereignis ausgelöst. Wenn wir auf das Label klicken, werden stattdessen zwei click-Ereignisse ausgelöst. Wenn wir das Ziel dieser Ereignisse in console.log ausgeben, sehen wir bei dem doppelten Ereignis, dass eines für das Label ist (was Sinn macht, da wir darauf geklickt haben), aber es gibt ein zweites Ereignis von der Checkbox. Obwohl ich weiß, dass dies die erwarteten Ergebnisse sein sollten, ist es etwas seltsam, weil wir Ergebnisse von *Benutzer*-Interaktionen erwarten. Doch die Ergebnisse beinhalten Interaktionen, die vom *Browser* verursacht werden.
Der nächste Schritt ist also zu prüfen, was passiert, wenn wir auf pointerup lauschen, wie in einigen der vorherigen Beispiele, in denselben Szenarien. In diesem Fall erhalten wir beim Klicken auf das Label-Element keine zwei Ereignisse. Das ist auch logisch, da wir nicht mehr auf das click-Ereignis lauschen, das von der Checkbox ausgelöst wird, wenn auf das Label geklickt wird.
Es gibt noch ein weiteres Szenario zu bedenken. Denken Sie daran, dass wir die Möglichkeit haben, die Checkbox in das Label-Element einzubetten, was bei benutzerdefinierten Checkboxen aus Styling-Gründen üblich ist.
<label for="newsletter">
<input type="checkbox" />
Subscribe to my newsletter
</label>
In diesem Fall müssen wir wirklich nur auf das Label und nicht auf die Checkbox selbst hören. Das reduziert die Anzahl der beteiligten Event-Listener, und doch erhalten wir dieselben Ergebnisse. Click-Ereignisse werden als einzelnes Ereignis beim Klicken auf das Label ausgelöst und zwei Ereignisse, wenn Sie auf die Checkbox klicken. Die pointerup-Ereignisse verhalten sich wie zuvor, einzelne Ereignisse beim Klicken auf beide Elemente.
Dies sind alles Dinge, die man berücksichtigen muss, wenn man versucht, das Verhalten der vorherigen Beispiele mit dem Button-Element nachzuahmen. Glücklicherweise ist es nicht allzu viel. Hier ist ein Beispiel, das zeigt, welche Art von Interaktion mit einem Checkbox-Formularelement stattgefunden hat
Dieses Beispiel enthält beide Arten von Checkbox-Szenarien, die oben erwähnt wurden; die oberste Zeile ist eine Checkbox/Label-Kombination mit dem for-Attribut, und die untere ist eine Checkbox innerhalb des Labels. Wenn Sie eine davon anklicken, wird darunter eine Nachricht ausgegeben, die angibt, welcher Interaktionstyp stattgefunden hat. Klicken Sie also mit der Maus darauf oder navigieren Sie mit der Tastatur dorthin und interagieren Sie dann mit der Leertaste; genau wie bei den Button-Beispielen sollte es Ihnen anzeigen, welcher Interaktionstyp es verursacht hat.
Um die Sache hinsichtlich der Anzahl der benötigten Event-Listener zu vereinfachen, habe ich die Checkboxen in einen Container-Div verpackt, der tatsächlich auf die Checkbox-Interaktionen reagiert. Sie müssten das nicht unbedingt so machen, aber es war eine bequeme Möglichkeit, dies für meine Bedürfnisse zu tun.
const checkbox_container = document.querySelector('#checkbox_container');
const checkbox_msg = document.querySelector('#checkbox_msg');
function chk_handler (e) {
if (e.target.tagName === 'LABEL' || e.target.tagName === 'INPUT') {
if (e.pointerType) {
checkbox_msg.innerText = `Pointer Event: ${e.pointerType}`;
} else if (e.code === 'Space') {
checkbox_msg.innerText = `Keyboard Event: ${e.code}`;
}
window.setTimeout(() => {
checkbox_msg.innerText = 'waiting...';
}, 2000);
}
}
checkbox_container.addEventListener('pointerup', chk_handler);
checkbox_container.addEventListener('keyup', chk_handler);
Da wir auf diese Ereignisse auf einem Container-Div hören, wollte ich die Ziele auf nur das Label und den Input beschränken. Technisch wäre es in einigen Fällen möglich, auf den Container-Div selbst zu „klicken“; was wir nicht wollen würden. Dann prüfen wir auf ein Pointer-Ereignis und aktualisieren die Nachricht. Danach versuchen wir, den Space -Tastencode zu identifizieren, der vom Keyup-Ereignis stammen könnte. Sie erinnern sich vielleicht, dass die Button-Beispiele oben sowohl die Enter - als auch die Space -Tasten verwendet haben. Es stellt sich heraus, dass Checkboxen oft nicht auf die Enter -Taste in Browsern reagieren. Eine weitere interessante Nuance, die man sich merken sollte.
Radio-Buttons per Radio ansprechen
Glücklicherweise können wir für Radio-Button-Inputs immer noch denselben Code mit ähnlichen HTML-Strukturen verwenden. Das funktioniert meistens gleich, weil Checkboxes und Radio-Buttons im Grunde auf die gleiche Weise erstellt werden – es ist nur so, dass Radio-Buttons tendenziell in Gruppen zusammengefasst sind, während Checkboxes auch in einer Gruppe einzeln sind. Wie Sie im folgenden Beispiel sehen werden, funktioniert es genauso
Auch hier wird derselbe Code an ein ähnliches Container-Div angehängt, um zu vermeiden, dass eine Reihe von Event-Listenern für jedes zugehörige Element erforderlich sind.
Wenn eine Nuance eine Gelegenheit sein kann
Ich fand, dass „Nuance“ eine gute Wortwahl war, denn die Dinge, die wir hier behandelt haben, sind nicht wirklich „Probleme“ mit der typischen negativen Konnotation, die dieses Wort in der Programmierwelt hat. Ich versuche immer, solche Dinge als Lernerfahrungen oder Gelegenheiten zu sehen. Wie kann ich die Dinge, die ich heute weiß, nutzen, um ein bisschen weiterzukommen, oder ist es vielleicht an der Zeit, mich nach außen zu wagen, um neue Dinge zu entdecken, um Probleme zu lösen, mit denen ich konfrontiert bin. Hoffentlich bieten die obigen Beispiele eine etwas andere Sichtweise, je nach den Bedürfnissen des jeweiligen Projekts.
Obwohl sich dieser Artikel aufgrund der Klicknuancen, die sie tendenziell bei Tastaturinteraktionen aufweisen, mehr auf Formularelemente konzentriert, können einige oder alle diese Punkte auf andere Elemente erweitert werden. Es hängt alles vom Kontext der Situation ab. Ich erinnere mich zum Beispiel daran, dass ich in vielen Fällen mehrere Ereignisse für dieselben Elemente in Abhängigkeit vom Kontext handhaben musste; oft aus Gründen der Barrierefreiheit und Tastaturnavigation. Haben Sie ein benutzerdefiniertes <select>-Element erstellt, um ein schöneres Design als das Standardelement zu haben, das auch auf Tastaturnavigation reagiert? Sie werden verstehen, was ich meine, wenn Sie dorthin gelangen.
Denken Sie einfach daran: Ein „Klick“ muss heute nicht mehr das sein, was wir denken, dass ein Klick immer war.
Eine kleine Sache, die mir aufgefallen ist: Bei den Radio-Buttons lösen die Pfeiltasten auf meiner Tastatur ein Click-Ereignis aus. Meiner Meinung nach sollte das nicht passieren. (Chrome Browser)
Ich würde Ihnen zustimmen, aber das ist eine Funktion des Browsers. Nachdem der Fokus auf einen ausgewählten Radio-Button in einer Gruppe gelegt wurde, wählt die Verwendung der Pfeiltasten den nächsten oder vorherigen Radio-Button aus. Ich fände es besser, den Fokus zu setzen, damit man entscheiden kann, ob man ihn auswählen möchte oder nicht. Ich vermute, der Grund dafür ist, dass ein einmal ausgewählter Radio-Button nicht abgewählt werden kann, also kann man genauso gut im Vorbeigehen auswählen. Aber jetzt, wo der Browser Radio-Buttons für Sie auswählt, indem er die Pfeiltasten verwendet, löst er auch das Click-Ereignis aus.
Ich frage mich, ob es möglich ist, zu erkennen, ob das Objekt vor dem Click-Ereignis den Fokus erhalten hat? Vielleicht ist das eine weitere Identifikationsmöglichkeit?
Das wäre schön, aber leider scheint das Focus-Ereignis nicht so viele Informationen zu liefern wie das Click-Ereignis.
Eine weitere Option ist die Verwendung von UIEvent.detail, das für Tastaturereignisse immer
0ist und für Mausereignisse> 0.Mein erster Gedanke war: „Könnte das möglich sein?“ Ich hatte mir die Detail-Eigenschaft schon einmal angesehen (für Doppel- und Dreifachklicks), aber anscheinend habe ich die Spezifikation nicht gut genug gelesen. Die Spezifikation bezieht sich auf die Klickanzahl in der Definition des Click-Ereignisses, was ich als Zählung für das Ereignis selbst interpretierte. Daher dachte ich, dass eine Tastatur- oder Zeigerquelle dasselbe Ergebnis liefern würde. Die Spezifikation definiert, was die aktuelle Klickanzahl bedeutet, in einem anderen Abschnitt, der tatsächlich über dem Abschnitt für das Click-Ereignis liegt, sodass ich ihn völlig übersehen habe.
Die von Ihnen verlinkte MDN-Seite erklärt dies viel besser.
Ich werde nachfragen müssen, ob der Artikel aktualisiert werden soll, um diese Eigenschaft stattdessen zu verwenden, da sie sauberer und näher an meiner ursprünglichen Absicht ist, bevor ich auf mein Safari-Problem gestoßen bin.
Ausgezeichnet. Vielen Dank für Ihren Kommentar, der Artikel kann dadurch besser werden.
Was macht es für Ereignisse, die durch Berührung ausgelöst werden?
Joseph, soweit ich das gesehen habe, sollte die Detail-Eigenschaft bei Touch-Ereignissen, die ein Click-Ereignis auslösen, sehr ähnlich funktionieren. Wenn Sie jedoch die Pointer Events verwenden, wie ich sie in einem Teil des Artikels bespreche, gibt es eine ähnliche Detail-Eigenschaft, aber sie scheint immer auf Null gesetzt zu sein. Daher kann sie in dieser Situation nicht zuverlässig verwendet werden.
Das Tippen auf die Labels der letzten beiden Beispiele im neuesten iOS Safari zeigt diese als Tastaturereignisse statt als Touch-Ereignisse an. Die Checkboxen/Radio-Buttons selbst funktionieren, aber nicht die Labels.
Tatsächlich überdenke ich aufgrund von Jimmys Kommentar oben bestimmte Aspekte der Codebeispiele, um seinen Vorschlag zu nutzen. Das würde auch eine Änderung an den Radio- und Checkbox-Beispielen erfordern.
Eine weitere Nuance, die es wert ist, überprüft zu werden, ist, was passiert, wenn assistierende Technologien ins Spiel kommen. Im Allgemeinen imitieren Screenreader usw. eine Mausinteraktion (um die Kompatibilität mit Inhalten zu verbessern, die historisch gesehen nicht vollständig tastaturzugänglich waren, aber auch, um Versuche zu verschleiern/maskieren, Benutzer als „Screenreader-Nutzer“ zu brandmarken). Für den spezifischen Fall der verschiedenen Bildschirm-/Client-/Offset-Koordinaten taten einige früher einige geniale Dinge (wie die Berechnung der Mitte des Elements und die Übergabe dieser als angebliche X/Y-Koordinaten) – siehe die (heutzutage ziemlich veraltete) https://patrickhlauke.github.io/touch/tests/results/#faked-event-coordinates Tabelle der Ergebnisse, die ich vor Äonen zusammengestellt habe.
Ja, die Screenreader machen die Dinge manchmal etwas anders. Insbesondere da, wie Ihre hilfreiche Liste zeigt, verschiedene Screenreader sich von anderen Screenreadern unterscheiden können. Meine Hoffnung ist, dass, wenn ein Screenreader eine Mausinteraktion imitiert, er sich auch so verhält. In einigen Fällen könnten Sie unterschiedliche Ergebnisse erwarten, je nachdem, wie der Benutzer tatsächlich mit der Seite interagiert, während ein Screenreader aktiv ist. Zum Beispiel könnten sie die integrierten Werkzeuge verwenden, um durch die Seite zu navigieren, und dann Tab verwenden, um durch Formularelemente zu navigieren. Dann könnten sie die integrierten Werkzeuge verwenden, um mit einem Button zu interagieren, oder die Standard-Tastaturtasten. Bei meiner Arbeit hatten wir Situationen, in denen eine Person die Maus benutzte, um mit Elementen auf der Seite zu interagieren, und wollte, dass ein Screenreader den ausgewählten Text vorliest. Das macht die Bestimmung dessen, was die Person tut und was ihre Erwartungen sein könnten, in der Tat sehr interessant.
Ich wollte erwähnen, dass ich einige Artikel und einige Beispiele basierend auf dem Feedback in den Kommentaren aktualisiert habe. Hoffentlich sind die Beispiele browserübergreifend konsistenter. Ich denke, die Vorschläge haben zu besseren Beispielen insgesamt geführt.
Ich schätze und danke Ihnen allen für das Feedback.
Hallo
Vielen Dank für den Artikel! Wirklich interessant. Meine Gedanken gingen sofort zu einem Artikel von Microsoft und Google, in dem sie bessere Eingabesteuerungen angekündigt haben.
Weiß jemand, ob das bereits stattgefunden hat und ob es sich nur um stilistische Änderungen handelte oder auch um Verhaltensänderungen, wie sie bei besserer Touch-Unterstützung angekündigt wurden.
neue Formularsteuerelemente