是否存在jQuery事件可在元素失焦前或下一个元素获焦前触发?
解决方案
最优实现方案(最小改造成本,无兼容问题)
核心思路是给第二个输入框加焦点拦截逻辑,校验完成前拦截它的聚焦触发行为,不需要修改tabindex,也不需要全量拦截键盘/鼠标事件。
具体实现逻辑:
- 用jQuery的
data()方法在元素上挂载状态变量,避免污染全局作用域:isChecking:标记第一个输入框是否正在执行校验逻辑checkPassed:标记第一个输入框的校验是否已经完成且通过
- 给第二个输入框绑定focus事件优先做拦截判断
- 第一个输入框的blur事件里完成校验逻辑后,再手动触发第二个输入框的聚焦
代码示例
// 初始化第一个输入框的状态 $('#input1').data({ isChecking: false, checkPassed: false }) // 第二个输入框的focus事件拦截逻辑 $('#input2').on('focus', function(e) { const $input1 = $('#input1') // 校验未完成时拦截自身modal弹出,把焦点还回第一个输入框 if ($input1.data('isChecking') || !$input1.data('checkPassed')) { e.stopImmediatePropagation() // 阻止自身绑定的其他focus事件(比如弹modal的原有逻辑)执行 $input1.focus() return false } // 校验已通过,正常执行你原有的弹modal代码即可 }) // 第一个输入框的blur校验逻辑 $('#input1').on('blur', function() { const $this = $(this) // 避免重复触发校验 if ($this.data('isChecking') || $this.data('checkPassed')) return $this.data('isChecking', true) // 执行校验ajax请求 $.ajax({ url: '你的校验接口地址', type: 'POST', data: { value: $this.val() }, success: function(res) { $this.data('isChecking', false) // 假设res.exist为true代表值已存在于数据库 if (res.exist) { const userConfirmed = confirm('该值已存在,是否继续?') if (!userConfirmed) { // 用户取消,焦点留在第一个输入框,重置状态等待重新输入 $this.data('checkPassed', false) $this.focus() return } } // 校验通过,更新状态后手动聚焦第二个输入框 $this.data('checkPassed', true) $('#input2').focus() }, error: function() { // 接口异常时的处理,可根据业务需求调整 $this.data('isChecking', false) $this.focus() alert('校验失败,请重试') } }) }) // 可选:如果需要支持第一个输入框值修改后重新校验,添加input事件重置状态 $('#input1').on('input', function() { $(this).data('checkPassed', false) })
注意事项
- 不要使用同步AJAX实现阻塞,会导致整个页面卡死,用户体验极差,上述异步+状态拦截的方案完全可以满足需求
- 如果有其他跳转场景(比如用户直接点击第三个输入框),可根据需求扩展拦截逻辑,或者只限制第二个输入框的聚焦即可
- 代码里的
e.stopImmediatePropagation()可以阻止当前元素后续绑定的focus事件执行,不需要修改你原有第二个输入框的弹modal代码,侵入性极低
内容的提问来源于stack exchange,提问作者Mustafamond77
相关产品推荐
相关产品推荐

