[FIX/REF] barcodes: don't catch keypress if a control key is pressed

This avoids breaking shortcuts on Firefox, which rely on keypress
events instead of keydown / keyup. The tradeoff is that a barcode
cannot be scanned and interpreted if ctrl, alt or cmd is pressed.
Also don't catch function keys.
This commit is contained in:
Arthur Maniet
2015-07-30 07:55:53 +02:00
parent 68ad51b6a9
commit 581aba9fdb
+31 -20
View File
@@ -87,14 +87,15 @@ var BarcodeEvents = core.Class.extend(mixins.PropertiesMixin, {
return $(element).is('input,textarea,[contenteditable="true"]');
},
// This checks that a keypress event is either ESC, TAB or an
// arrow key. This is Firefox specific, in Chrom{e,ium}
// This checks that a keypress event is either ESC, TAB, an arrow
// key or a function key. This is Firefox specific, in Chrom{e,ium}
// keypress events are not fired for these types of keys, only
// keyup/keydown.
is_special_key: function(e) {
if (e.key === "ArrowLeft" || e.key === "ArrowRight" ||
e.key === "ArrowUp" || e.key === "ArrowDown" ||
e.key === "Escape" || e.key === "Tab") {
e.key === "Escape" || e.key === "Tab" ||
/F\d\d?/.test(e.key)) {
return true;
} else {
return false;
@@ -117,24 +118,34 @@ var BarcodeEvents = core.Class.extend(mixins.PropertiesMixin, {
},
handler: function(e){
if (! e.dispatched_by_barcode_reader && ! this.is_special_key(e)) {
// We only stop events targeting elements that are editable. We
// do not stop events targeting other elements because we have
// no way of redispatching 'genuine' key events that trigger
// native event handlers of elements. So this means that our
// fake events will not appear in eg. an <input> element.
if (! this.element_is_editable(e.target) || e.target.getAttribute("barcode_events") === "true") {
this.buffered_key_events.push(e);
e.preventDefault();
e.stopImmediatePropagation();
// Don't catch events we resent
if (e.dispatched_by_barcode_reader)
return;
// Don't catch non-printable keys for which Firefox triggers a keypress
if (this.is_special_key(e))
return;
// Don't catch keypresses which could have a UX purpose (like shortcuts)
if (e.ctrlKey || e.metaKey || e.altKey)
return;
// Don't catch events targeting elements that are editable because we
// have no way of redispatching 'genuine' key events. Resent events
// don't trigger native event handlers of elements. So this means that
// our fake events will not appear in eg. an <input> element.
if (this.element_is_editable(e.target) && e.target.getAttribute("barcode_events") !== "true")
return;
clearTimeout(this.timeout);
if (String.fromCharCode(e.which).match(this.suffix) !== null) {
this.handle_buffered_keys();
} else {
this.timeout = setTimeout(this.handle_buffered_keys.bind(this), this.max_time_between_keys_in_ms);
}
}
// Catch and buffer the event
this.buffered_key_events.push(e);
e.preventDefault();
e.stopImmediatePropagation();
// Handle buffered keys immediately if the the keypress marks the end
// of a barcode or after x milliseconds without a new keypress
clearTimeout(this.timeout);
if (String.fromCharCode(e.which).match(this.suffix)) {
this.handle_buffered_keys();
} else {
this.timeout = setTimeout(this.handle_buffered_keys.bind(this), this.max_time_between_keys_in_ms);
}
},