登录
前端开发时,很多场景需要监听input输入,当值发生变化,需要进行调用接口、对值进行校验、实时过滤内容等操作。
但当我们使用拼音输入法输入汉语时,可能会遇到一些问题,每次输入拼音的一个字母,都会触发input方法,但得到的内容是正在进行组合的拼音,此时得到的是无效的值,比如如下代码:
<input id="inputDom" />
<script>
const inputDom = document.querySelector('#inputDom')
inputDom.addEventListener('input', (e) => {
console.log('input触发', e.target.value)
})
</script>
我们用英文输入hello
,然后切换为中文输入法,再输入你好
两个字,得到的打印如下:
input触发 h
input触发 he
input触发 hel
input触发 hell
input触发 hello
input触发 hellon
input触发 helloni
input触发 helloni'h
input触发 helloni'ha
input触发 helloni'hao
input触发 hello你好
就很不对!
这时就需要使用input框的另两个事件,compositionstart
和 compositionend
。
当开始输入拼音时,会触发compositionstart
事件,拼音输入完成,会触发compositionend
,见如下代码:
<input id="inputDom" />
<script>
const inputDom = document.querySelector('#inputDom')
let isCompositioning = false
inputDom.addEventListener('input', (e) => {
console.log(`input触发${isCompositioning ? '(组合中)' : ''}`, e.target.value)
})
inputDom.addEventListener('compositionstart', (e) => {
console.log('开始组合')
// 标记正在组合中
isCompositioning = true
})
inputDom.addEventListener('compositionend', (e) => {
// 标记组合结束
isCompositioning = false
console.log('组合结束', e.target.value)
})
</script>
同样再输入hello你好
,得到的打印:
input触发 h
input触发 he
input触发 hel
input触发 hell
input触发 hello
开始组合
input触发(组合中) hellon
input触发(组合中) helloni
input触发(组合中) helloni'h
input触发(组合中) helloni'ha
input触发(组合中) helloni'hao
input触发(组合中) hello你好
组合结束 hello你好
所以,我们可以通过input
、compositionstart
和 compositionend
三个时间配合,得到我们想要的输入监听结果。
<input id="inputDom" />
<script>
const inputDom = document.querySelector('#inputDom')
let isCompositioning = false
inputDom.addEventListener('input', (e) => {
if (isCompositioning) return
inputChange(e.target.value)
})
inputDom.addEventListener('compositionstart', (e) => {
// 标记正在组合中
isCompositioning = true
})
inputDom.addEventListener('compositionend', (e) => {
// 标记组合结束
isCompositioning = false
// 触发一次修改事件
inputChange(e.target.value)
})
function inputChange(value) {
console.log(value)
}
</script>