vanilla javascript:拦截输入键并更改键值

Posted

技术标签:

【中文标题】vanilla javascript:拦截输入键并更改键值【英文标题】:vanilla javascript : intercept key on input and change key value 【发布时间】:2018-12-09 09:04:42 【问题描述】:

我想截取在一个输入中键入的键并将它们更改为其他。

例如,我想模拟每次按下一个键时输入一个 1。

我在想这样的事情:

           //this example does not work, it will trigger an endless loop

            Array.from(document.querySelectorAll('.onlyOne')).forEach(input =>
                               input.addEventListener('keydown', (event) =>       
                                event.preventDefault();
                                event.srcElement.dispatchEvent(new KeyboardEvent('keydown',  'key': 49 ));

                            );
                        
                    );

我不能只加 1 event.target.value += 1; 因为当输入中已经有文本并且光标不在文本末尾或者用户已经用鼠标选择了所有文本时,如果在输入末尾添加文本将不会自然地起作用

你能帮帮我吗?

【问题讨论】:

为什么不能在按下任意键时简单地将1 添加到输入值中? this.value += "1" @vsync 当输入中已有文本且光标不在文本末尾或用户用鼠标选择了所有文本时,如果在输入结束 [].forEach.call 会运行 0 次这一事实呢? 您可能应该检查按下了哪个键,因为它现在的编码方式会导致无限循环(如果它有效,请参阅上面的评论) @Kutyel 我更改了这个不寻常的代码以使问题更容易理解 【参考方案1】:

通过从引发相同事件的事件中调度事件,您正在创建一个无限循环,该循环将导致Range Error: Maximum call stack size exceeded.

只需将1 添加到每个按键上的光标所在的位置,而不是事件。

Array.from(document.querySelectorAll('.onlyOne')).forEach(input =>
  input.addEventListener('keydown', (event) => 
    event.preventDefault();
    event.target.insertAtCaret('1');
));


htmlInputElement.prototype.insertAtCaret = function (text) 
  text = text || '';
  if (document.selection) 
    // IE
    this.focus();
    var sel = document.selection.createRange();
    sel.text = text;
   else if (this.selectionStart || this.selectionStart === 0) 
    // Others
    var startPos = this.selectionStart;
    var endPos = this.selectionEnd;
    this.value = this.value.substring(0, startPos) +
      text +
      this.value.substring(endPos, this.value.length);
    this.selectionStart = startPos + text.length;
    this.selectionEnd = startPos + text.length;
   else 
    this.value += text;
  
;
<input class='onlyOne' value="foo">

HTMLInputElement.prototype.insertAtCaret 取自这个答案:https://***.com/a/19961519/3993662

You can change that to a normal function if you don't want to extend the built in's prototype。

【讨论】:

感谢回答,但是当输入中已经有文本并且光标不在文本末尾或用户用鼠标选择了所有文本时,如果键是在输入末尾添加 @VivienPipo 编辑了答案以满足新要求 恭喜恭喜!

以上是关于vanilla javascript:拦截输入键并更改键值的主要内容,如果未能解决你的问题,请参考以下文章

javascript 使用vanilla JavaScript爬上DOM树

javascript 我的vanilla JavaScript插件的入门模板。

javascript 使用Vanilla JavaScript Shopify GraphQL Storefront API

javascript 使用Vanilla JavaScript Shopify GraphQL Storefront API

javascript AJAX与Vanilla JS

javascript JQuery到Vanilla js指南