Je veux simuler des événements de keydown sur un élément textarea donné dans une page html. Depuis que j'utilise Chrome, j'ai appelé initKeyboardEvent
sur ma variable et j'ai passé le keyCode que je veux taper dans la zone de texte. Voici ce que j'ai essayé:
var keyEvent = document.createEvent('KeyboardEvent');
keyEvent.initKeyboardEvent('keydown', true, false, null, 0, false, 0, false, 77, 0);
inputNode.dispatchEvent(keyEvent);
Dans ce code, je tape la lettre m
mais la zone de texte ne reçoit que le keyCode 13
qui est la touche Enter
. J'ai donc essayé un code de remplacement que j'ai vu en ligne qui définit la valeur sur keyCodeVal, mais sans succès
var keyEvent = document.createEvent('KeyboardEvent');
Object.defineProperty(keyEvent, 'keyCode', {
get : function() {
return this.keyCodeVal;
}
});
keyEvent.initKeyboardEvent('keydown', true, false, null, 0, false, 0, false, 77, 0);
keyEvent.keyCodeVal = 77;
inputNode.dispatchEvent(keyEvent);
Quelqu'un at-il une idée de la façon de définir la valeur keyCode?
Donc très très proche ...
Vous aviez juste besoin de remplacer la propriété 'which'. Voici un exemple de code:
Podium = {};
Podium.keydown = function(k) {
var oEvent = document.createEvent('KeyboardEvent');
// Chromium Hack
Object.defineProperty(oEvent, 'keyCode', {
get : function() {
return this.keyCodeVal;
}
});
Object.defineProperty(oEvent, 'which', {
get : function() {
return this.keyCodeVal;
}
});
if (oEvent.initKeyboardEvent) {
oEvent.initKeyboardEvent("keydown", true, true, document.defaultView, false, false, false, false, k, k);
} else {
oEvent.initKeyEvent("keydown", true, true, document.defaultView, false, false, false, false, k, 0);
}
oEvent.keyCodeVal = k;
if (oEvent.keyCode !== k) {
alert("keyCode mismatch " + oEvent.keyCode + "(" + oEvent.which + ")");
}
document.dispatchEvent(oEvent);
}
Exemple d'utilisation:
Podium.keydown(65);
Remarque: ce code n'est pas conçu pour fonctionner dans IE, Safari ou d'autres navigateurs. Eh bien, peut-être avec Firefox. YMMV.
La solution d'Orwellophile fonctionne.
Ici, j'ai écrit fonction initKeyboardEvent multi-navigateur (Gist):
Exemple:
var a = window.crossBrowser_initKeyboardEvent("keypress", {"key": 1, "char": "!", shiftKey: true})
alert(a.type + " | " + a.key + " | " + a.char + " | " + a.shiftKey)
Et voici mon polyfill DOM Keyboard Event Level avec le constructeur KeyboardEvent multi-navigateur.
Exemple:
var a = new KeyboardEvent("keypress", {"key": 1, "char": "!", shiftKey: true})
alert(a.type + " | " + a.key + " | " + a.char + " | " + a.shiftKey)
Remarque importante 1: charCode, keyCode et quelles propriétés sont obsolètes. Donc, ni mon constructeur crossBrowser_initKeyboardEvent no KeyboardEvent ne sont absolument garantis des valeurs correctes de ces propriétés dans certains navigateurs. Vous pouvez utiliser les propriétés "key" et "char" à la place ou modifier my Gist pour forcer l'utilisation d'initEvent dans les navigateurs avec charCode en lecture seule, keyCode et quelles propriétés.
Remarque importante 2: l'événement keypress est obsolète et pour l'instant non pris en charge dans mon Polyfill Keyboard Event Level . Cela signifie que les propriétés de clé et de caractère dans l'événement keypress peuvent avoir des valeurs aléatoires. Je travaille pour résoudre ce problème de compatibilité descendante.
Pour que le script de @ Orwellophile fonctionne sur Google Chrome 26.0.1410.65 (sur Mac OS X 10.7.5, si cela importe), j'ai dû changer une ligne: son script semble avoir les paramètres de initKeyboardEvent
dans un ordre différent de documentation MDN pour initKeyboardEvent .
La ligne modifiée ressemble à ceci:
oEvent.initKeyboardEvent("keydown", true, true, document.defaultView, k, k, "", "", false, "");
Eh bien, les solutions ci-dessus ont fonctionné, également grâce à @dland pour la pointe des paramètres. Voici quelque chose que j'ai trouvé utile, si vous ne parvenez pas à déclencher les événements au bon endroit.
Le script de @ Orwellophile déclenche l'événement sur le document. Il est possible que l'écouteur d'événements ne soit pas toujours enregistré sur document
. J'ai changé la dernière ligne en suivant et maintenant cela fonctionne à peu près à chaque fois.
document.activeElement.dispatchEvent(oEvent);
Le document.activeElement
déclenche toujours l'événement sur l'élément sur lequel l'utilisateur se concentre actuellement.
Toutes les solutions ci-dessus fonctionnent, mais j'ai trouvé un cas où elles ne fonctionneront pas.
Si Dart est utilisé, le code Dart qui utilise KeyboardEvents ne fonctionnera pas sur un événement général.
Vous obtiendrez quelque chose comme get $ keyCode n'est pas défini.
après m'être cogné la tête pendant des heures à ce sujet, j'ai trouvé l'astuce suivante:
function __triggerKeyboardEvent(el, keyCode)
{
var eventObj = document.createEventObject ?
document.createEventObject() : document.createEvent("Events");
var tempKeyboardObj = document.createEvent("KeyboardEvents");
if(eventObj.initEvent){
eventObj.initEvent("keydown", true, true);
}
eventObj.___Dart_dispatch_record_ZxYxX_0_ = tempKeyboardObj.___Dart_dispatch_record_ZxYxX_0_
eventObj.keyCode = keyCode;
eventObj.which = keyCode;
el.dispatchEvent ? el.dispatchEvent(eventObj) : el.fireEvent("onkeydown", eventObj);
}
Tromper l'intercepteur Dart pour que notre événement soit en fait un événement KeyboardEvent, a fait l'affaire.
Laissez-le ici, pour le pauvre gars qui essaie de tester l'application Dart sur un navigateur basé sur un kit Web.