javascript - 试图防止无效的按键(不是数字)和多个小数点
问题描述
到目前为止,我使用它来调用函数:
document.getElementById("dzCalculator").addEventListener("keydown", isNumberKey);
function isNumberKey(txt, evt) {
let charCode = (evt.which) ? evt.which : evt.keyCode;
if (charCode == 46) {
evt.preventDefault();
//Check if the text already contains the . character
if (txt.value.indexOf('.') === -1) {
return true;
} else {
return false;
}
} else {
if (charCode > 31 &&
(charCode < 48 || charCode > 57))
return false;
}
return true;
}
但不幸的是我得到了错误: Uncaught TypeError: evt is undefined
我仍然处于学习阶段,所以我还没有看到我所缺少的东西。非常感谢您的帮助。
解决方案
仅将触发它的addEventListener
事件传递给传递的回调,因此在您的情况下txt
是持有事件并且evt
未定义。
您可以使用 提取txt
输入的值evt.target.value
。
document.getElementById("dzCalculator").addEventListener("keydown", isNumberKey);
function isNumberKey(evt) {
let txt = evt.target.value;
//...
至于你的其他逻辑,已经有一些很好的答案:
由于您仍在寻找限制输入的解决方案,因此我将提供此解决方案。您可以在 keyup 之后验证值,而不是控制允许的键。使用input
侦听器,我们可以观察更改和验证,而不会看到无效字符显示,同时还解决了维护预期功能和可访问性而无需指定所有关键响应的总体问题。
此代码段使用input
. event.target.value
触发时,它使用并存储当前光标位置提取当前值。然后它使用destructuring 将字符串重新转换为数组[...value]
。然后使用过滤此数组filter()
,使其仅包含出现在validKeys
字符串中的字符。然后将其还原为字符串,reduce()
在该字符串中包含重复的小数点。如果结果editedValue
与初始值不同value
,evt.target.value
则更新并将光标设置回原来的位置(减一,因为我们删除了一个字符);
document.getElementById("dzCalculator").addEventListener("input", isNumberKey);
function isNumberKey(evt) {
const validKeys = '1234567890.';
const cursorLocation = evt.target.selectionStart;
const value = evt.target.value;
let editedValue = [...value]
.filter(char => validKeys.includes(char))
.reduce((acc, char) => { return acc.includes('.') && char === '.' ? acc : acc + char}, '');
if (editedValue !== value) {
evt.target.value = editedValue;
evt.target.selectionStart = cursorLocation-1;
evt.target.selectionEnd = cursorLocation-1;
}
}
<input id="dzCalculator" value="" />
为了适应负值,您可以调整validKeys
回调reduce()
:
const validKeys = '-1234567890.';
let editedValue = [...value]
.filter(char => validKeys.includes(char))
.reduce((acc, char, i) => {
if (acc.includes('.') && char === '.' || char === '-' && i !== 0) {
return acc
} else {
return acc + char
}
}, '');
推荐阅读
- spring-boot - 在 SpringBoot 2.x(2.1.0) 中自定义过滤过程一次但产生重复数据
- perl - 如何将日期格式化为“2018-10-29 11:49:33”
- mysql - MySql 从表数据返回错误的时间
- java - 无法更改片段 Android 的容器 ID
- mvvm - 按钮在后台返回到我的应用程序,当您恢复时它会再次启动
- mapbox - 添加的标记不可见 - Mapbox 6.7.0
- python - 对于可以离线工作的 python 客户端应用程序,建议使用哪个数据库
- selenium-webdriver - 使用节点js和角度js的硒元素不可交互错误
- dynamics-crm - D365 v9 升级导致问题
- laravel - 在另一个系统上使用数据库安装 Laravel