现象:鼠标拖拽滑块离开对话框释放鼠标时一直处于验证中,没有触发验证。

分析:V3版本问题,V2无该问题。初步定位是因为V3滑块离开滑块弹框范围时释放鼠标,没有触发mouseup事件,导致插件没有回调验证函数;
解决思路:尝试拖拽在滑块框外面时,手动触发校验,分析getInstance方法返回实列没有对外提供方法触发校验;
思考:手动触发滑块按钮事件,看是不能触发插件的校验回调,通过JS获取滑块dom节点,研究mousedown,mosemove,mouseup, click事件,发现调用滑块的click事件可用触发插件校验回调函数(返回账号密码等信息),效果满足。
结合react工程代码整理如下:
javascript
// 获取验证码实例
const getInstance = useCallback(
(instance: ICaptchaInstance) => {
// 验证码弹窗Dom
const sliderElement = document.getElementById('aliyunCaptcha-sliding-slider');
// 滑块按钮Dom
const modalElement = document.getElementById('vnnox-care-captcha-modal');
// 先清理上一次注册的事件,避免重复绑定
if (dragCleanupRef.current) {
dragCleanupRef.current();
dragCleanupRef.current = null;
}
if (sliderElement && modalElement) {
const handleMouseDown = () => {
isDraggingRef.current = true;
};
const handleMouseMove = () => {
// 仅用于标记拖拽过程,不在此处触发点击
if (!isDraggingRef.current) return;
};
const handleMouseUp = (event: MouseEvent) => {
if (!isDraggingRef.current) return;
isDraggingRef.current = false;
const rect = modalElement.getBoundingClientRect();
const { clientX, clientY } = event;
const isInside =
clientX >= rect.left &&
clientX <= rect.right &&
clientY >= rect.top &&
clientY <= rect.bottom;
// 当拖拽结束(mouseup)时,如果鼠标位置已滑出父元素区域,则触发一次点击
if (!isInside) {
// 添加到setTimeout中调用click,解决因调用click验证码弹框消失问题
setTimeout(()=>{
sliderElement.click();
});
}
};
sliderElement.addEventListener('mousedown', handleMouseDown);
window.addEventListener('mousemove', handleMouseMove);
window.addEventListener('mouseup', handleMouseUp);
dragCleanupRef.current = () => {
sliderElement.removeEventListener('mousedown', handleMouseDown);
window.removeEventListener('mousemove', handleMouseMove);
window.removeEventListener('mouseup', handleMouseUp);
};
}
.
.
.
},
[getErrorMessage, handleErrorWithDebounce]
);