Despite many article on SO on how to simulate key presses (keydown/keypress) in JS, no one solution seems to be working with the browsers I'm using (Firefox ESR 17.0.7, Chrome 28.0.1500.72, IE 10). The solutions I have tested were taken from here, here, and here.
What I'm trying to do is to simulate ANY keystroke in a textarea / input. While I can append / delete characters directly changing "value", I see no option but input simulation for the keys like "Up", "Down", "Home", and some others.
According to the documentation, it should be simple. For example:
var e = document.createEvent("KeyboardEvent");
if (e.initKeyboardEvent) { // Chrome, IE
e.initKeyboardEvent("keydown", true, true, document.defaultView, "Enter", 0, "", false, "");
} else { // FF
e.initKeyEvent("keydown", true, true, document.defaultView, false, false, false, false, 13, 0);
}
document.getElementById("text").dispatchEvent(e);
indeed fires the "Enter" keydown event, and my handler can catch it. However, it does not affect the textarea in any way - a new line does not appear. Same for other key-codes: characters do not appear, arrows do not change the caret's location, etc.
I have extended the code by Orwellophile and posted it to / , so anyone can play with the code. In my browsers, no button produces any effect on the textarea in any condition.
I would appreciate any help on this issue.
Despite many article on SO on how to simulate key presses (keydown/keypress) in JS, no one solution seems to be working with the browsers I'm using (Firefox ESR 17.0.7, Chrome 28.0.1500.72, IE 10). The solutions I have tested were taken from here, here, and here.
What I'm trying to do is to simulate ANY keystroke in a textarea / input. While I can append / delete characters directly changing "value", I see no option but input simulation for the keys like "Up", "Down", "Home", and some others.
According to the documentation, it should be simple. For example:
var e = document.createEvent("KeyboardEvent");
if (e.initKeyboardEvent) { // Chrome, IE
e.initKeyboardEvent("keydown", true, true, document.defaultView, "Enter", 0, "", false, "");
} else { // FF
e.initKeyEvent("keydown", true, true, document.defaultView, false, false, false, false, 13, 0);
}
document.getElementById("text").dispatchEvent(e);
indeed fires the "Enter" keydown event, and my handler can catch it. However, it does not affect the textarea in any way - a new line does not appear. Same for other key-codes: characters do not appear, arrows do not change the caret's location, etc.
I have extended the code by Orwellophile and posted it to http://jsfiddle/npF3d/4/ , so anyone can play with the code. In my browsers, no button produces any effect on the textarea in any condition.
I would appreciate any help on this issue.
Share Improve this question edited May 23, 2017 at 10:30 CommunityBot 11 silver badge asked Jul 26, 2013 at 12:02 lexassslexasss 3021 gold badge2 silver badges9 bronze badges2 Answers
Reset to default 7I'm pretty certain that this is a "security" thing, as I've run into the same thing when trying to simulate key presses before.
Q: How can I type programatically then?
A: Getting/setting selectionStart, selectionEnd, etc, as well as using these in bination with String methods like slice
to insert characters. (See HTMLTextAreaElement reference)
Q: Why would you still use this kind of event then?
A: All of the event listeners will work as if it was a real key event.
Reduced functionality for arrows/home/end can be achieved thusly DEMO
function homeKey(elm) {
elm.selectionEnd =
elm.selectionStart =
elm.value.lastIndexOf(
'\n',
elm.selectionEnd - 1
) + 1;
}
function endKey(elm) {
var pos = elm.selectionEnd,
i = elm.value.indexOf('\n', pos);
if (i === -1) i = elm.value.length;
elm.selectionStart = elm.selectionEnd = i;
}
function arrowLeft(elm) {
elm.selectionStart = elm.selectionEnd -= 1;
}
function arrowRight(elm) {
elm.selectionStart = elm.selectionEnd += 1;
}
function arrowDown(elm) {
var pos = elm.selectionEnd,
prevLine = elm.value.lastIndexOf('\n', pos),
nextLine = elm.value.indexOf('\n', pos + 1);
if (nextLine === -1) return;
pos = pos - prevLine;
elm.selectionStart = elm.selectionEnd = nextLine + pos;
}
function arrowUp(elm) {
var pos = elm.selectionEnd,
prevLine = elm.value.lastIndexOf('\n', pos),
TwoBLine = elm.value.lastIndexOf('\n', prevLine - 1);
if (prevLine === -1) return;
pos = pos - prevLine;
elm.selectionStart = elm.selectionEnd = TwoBLine + pos;
}
Q: Where does it go wrong?
A: If lines are long enough to be wrapped, it will treat them as if unwrapped.
Sending keys to the browser can be achieved via Selenium: http://docs.seleniumhq/
It provides a driver for each browser that can be programmed. It usually starts with opening a URL then your script will act as a remote control to the browser. Thus allowing you to send actual keys rather than simulating them which is not possible programatically within the browser.
You could for instance achieve this using http://webdriver.io/