在JavaScript中监听IME键盘输入事件


Posted in Javascript onMay 29, 2011

输入法应当如何触发键盘事件呢?是每一下击键都触发一次事件,还是选词完毕才触发事件呢?整句输入又该如何触发事件呢?不同的操作系统和不同的浏览器对此有不同的看法。在最糟糕的情况下,用户使用输入法后浏览器就只触发一次 keydown ,之后就没有任何的键盘事件了。这对于 Suggestion 控件的实现来说是个大问题,因为 Suggestion 控件需要监听文本输入框的变化,而事件是最准确也最节省计算资源的做法,如果换成轮询的话性能就可能受到影响。
首先,要监听启用输入法后的击键事件应当使用 keydown 事件,这是信息最丰富的一个事件,因为在启用输入法后别的键盘事件可能不会被触发。其次,大多数操作系统和浏览器都实现了一个事实标准,就是在用户使用输入法输入时, keydown 事件传入的 keyCode 取值为 229 。然而触发 keydown 的频率是不确定的,有些情况下每一下击键都触发事件,有些情况下只有选词完毕才触发事件。这时候,如果我们还是要实时监控文本框的内容变化,就必须使用轮询了。

var timer; 
var imeKey = 229; 
function keydownHandler (e) { 
clearInterval(timer) 
if (e.keyCode == imeKey) { 
timer = setInterval(checkTextValue, 50); 
} else { 
checkTextValue(); 
} 
} 
function checkTextValue() { 
/* handle input text change */ 
}

Opera 是一款有趣的浏览器,别人做的事情它都不做,别人都不做的事情它都喜欢做。例如说,它偏偏不支持 keyCode == 229 这个事实标准,而要使用 keyCode == 197 来表示输入法的使用。因此,你需要在上述代码的基础上做一下改良,如果监测到是 Opera 浏览器,就换一个 keyCode 常量来做比较。
var imeKey = (UA.Opera == 0) ? 229 : 197;
最后,还有一个更不受重视的浏览器叫做 Firefox for Mac 。估计是因为 Mac 版本对于 Mozilla 来说实在是太不重要了,所以很多 Windows 版本都没问题的地方 Mac 版本就会出小问题,例如说对上述事件的支持。 Firefox for Mac 不会出现 keyCode == 229 的情况,而且在输入法启用后只有第一下击键会触发 keydown 事件,因此只能在击键后一直使用轮询。
if (e.keyCode == imeKey || UA.Firefox > 0 && UA.OS == 'Macintosh') {
在添加了这两项改进后,实时监控文本框的变化就没有问题了,即使用户启用了输入法。完整的代码如下:
var timer; 
var imeKey = (UA.Opera == 0) ? 229 : 197; 
function keydownHandler (e) { 
clearInterval(timer) 
if (e.keyCode == imeKey || UA.Firefox > 0 && UA.OS == 'Macintosh') { 
timer = setInterval(checkTextValue, 50); 
} else { 
checkTextValue(); 
} 
} 
function checkTextValue() { 
/* handle input text change */ 
}
Javascript 相关文章推荐
JavaScript 验证码的实例代码(附效果图)
Mar 22 Javascript
基于javascipt-dom编程 table对象的使用
Apr 22 Javascript
JavaScript模拟深蓝vs卡斯帕罗夫的国际象棋对局示例
Apr 22 Javascript
js实现刷新iframe的方法汇总
Apr 27 Javascript
js实现无限级树形导航列表效果代码
Sep 23 Javascript
Javascript实现通过选择周数显示开始日和结束日的实现代码
May 30 Javascript
js实现html table 行,列锁定的简单实例
Oct 13 Javascript
第一次接触神奇的Bootstrap
Oct 14 Javascript
js实现三级联动效果(简单易懂)
Mar 27 Javascript
利用Vue v-model实现一个自定义的表单组件
Apr 27 Javascript
vue项目中mock.js的使用及基本用法
May 22 Javascript
video.js添加自定义组件的方法
Dec 09 Javascript
解读JavaScript代码 var ie = !-[1,] 最短的IE判定代码
May 28 #Javascript
Jquery css函数用法(判断标签是否拥有某属性)
May 28 #Javascript
最新28个很棒的jQuery 教程
May 28 #Javascript
JavaScript使用IEEE 标准进行二进制浮点运算产生莫名错误的解决方法
May 28 #Javascript
真正的JQuery.ajax传递中文参数的解决方法
May 28 #Javascript
jquery 图片上传按比例预览插件集合
May 28 #Javascript
使用jquery实现select添加实现后台权限添加的效果
May 28 #Javascript
You might like
需要发散思维学习PHP
2009/06/29 PHP
php中关于普通表单多文件上传的处理方法
2011/03/25 PHP
php中fsockopen用法实例
2015/01/05 PHP
thinkphp制作404跳转页的简单实现方法
2016/09/22 PHP
php实用代码片段整理
2016/11/12 PHP
让iframe自适应高度(支持XHTML,支持FF)
2007/07/24 Javascript
js切换div css注意的细节
2012/12/10 Javascript
实用的JS正则表达式(手机号码/IP正则/邮编正则/电话等)
2013/01/11 Javascript
手机平板等移动端适配跳转URL的js代码
2014/01/25 Javascript
jQuery实现仿腾讯微博滑出效果报告每日天气的方法
2015/05/11 Javascript
jQuery中借助deferred来请求及判断AJAX加载的实例讲解
2016/05/24 Javascript
jQuery学习心得总结(必看篇)
2016/06/10 Javascript
全面介绍javascript实用技巧及单竖杠
2016/07/18 Javascript
Vue实例简单方法介绍
2017/01/20 Javascript
JavaScript轻松创建级联函数的方法示例
2017/02/10 Javascript
实例分析nodejs模块xml2js解析xml过程中遇到的坑
2017/03/18 NodeJs
详解vue的数据binding绑定原理
2017/04/12 Javascript
windows系统下更新nodejs版本的方案
2017/11/24 NodeJs
详解vue中点击空白处隐藏div的实现(用指令实现)
2018/04/19 Javascript
Vue起步(无cli)的啊教程详解
2019/04/11 Javascript
JavaScript基础之this和箭头函数详析
2019/09/05 Javascript
vue-element-admin 菜单标签失效的解决方式
2019/11/12 Javascript
举例详解Python中threading模块的几个常用方法
2015/06/18 Python
window下eclipse安装python插件教程
2017/04/24 Python
python 读取摄像头数据并保存的实例
2018/08/03 Python
Python字典的基本用法实例分析【创建、增加、获取、修改、删除】
2019/03/05 Python
python程序中的线程操作 concurrent模块使用详解
2019/09/23 Python
CSS3的颜色渐变效果的示例代码
2017/09/29 HTML / CSS
银河香水:Galaxy Perfume
2019/03/25 全球购物
中东最大的在线宠物店:Dubai Pet Food
2020/06/11 全球购物
商铺消防安全责任书
2014/07/29 职场文书
学习十八大标语
2014/10/09 职场文书
领导干部群众路线对照检查材料
2014/11/05 职场文书
2015年民主评议党员工作总结
2015/05/19 职场文书
25张裸眼3D图片,带你重温童年的记忆,感受3D的魅力
2022/02/06 杂记
Win10开机修复磁盘错误怎么跳过?Win10关闭开机磁盘检查的方法
2022/09/23 数码科技