如何在导致模糊的点击事件后触发Javascript模糊事件?

时间:2010-11-03 06:50:19

标签: javascript jquery events onclick onblur

我遇到过这个问题几次,我对以前用过的解决方案不满意。

我有一个带有模糊事件的输入框,可以验证它的内容,还有一个按钮,可以在点击时填充输入框。问题是单击按钮会触发输入模糊事件,然后点击按钮单击事件,因此按钮插入的内容不会被验证。

请参阅http://jsfiddle.net/jakecr/dL3K3/

我知道这是正确的行为,但我想不出一个彻底解决问题的方法。

6 个答案:

答案 0 :(得分:34)

我们在工作中遇到了类似的问题。我们最终想到了什么 是模糊事件之前,mousedown事件将被触发 允许您在验证之前设置内容甚至取消验证 完全使用旗帜的过程。

检查我用你的例子制作的小提琴 - http://jsfiddle.net/dL3K3/31/

$(function(){
    var flag = true;
    $('input').blur(function(){
        if(!$(this).val() && flag){
            alert("Grrr, It's empty");
        }
    });

    $('button').mousedown(function(){
        flag = false;
    });    
    $('button').mouseup(function(){
        flag = true;
        $('input').val('content').focus();
    });

});

-Edit-

作为@mclin建议,使用mousedown事件和preventDefault将防止模糊行为。 您可以保持原始点击事件不变 -

http://jsfiddle.net/dL3K3/364/

$(function(){
    $('input').blur(function(){
        if(!$(this).val()){
            alert("Grrr, It's empty");
        }
    });

    $('button').mousedown(function(e){
        e.preventDefault();
    });    
    $('button').click(function(){
        $('input').val('content');
    });

});

对于大多数情况,这个解决方案可能会更清洁一点,但是请注意,如果你使用它,你将防止默认和模糊当前关注的任何其他元素,但对于大多数不应该成为问题的用例。

答案 1 :(得分:19)

我有比Yoni Jah更好的解决方案: 在按钮的mousedown事件上调用preventDefault。 onBlur永远不会发生,因此您可以在点击事件中自由地做任何事情。

这样做更好,因为它不会通过鼠标按下而不是鼠标按钮来改变点击行为,这可能是意外的。

答案 2 :(得分:8)

这也可能有所帮助:

设置一个计时器,在触发按钮点击事件之前延迟模糊事件操作。

// Namespace for timer var setTimer = { timer: null }

    $('input,select').blur(function () {
        setTimer.timer = setTimeout(function () {
           functionCall();
        }, 1000);
    });

    $('input,select').focus(function () {
        setTimer.timer = setTimeout(function () {
            functionCall();
        }, 1000);
    });

    $("#btn").click(function () {
        clearTimeout(setTimer.timer);
        functionCall();
    });

答案 3 :(得分:1)

将输入验证逻辑分离为它自己的函数,该函数由blur事件自动调用,然后在修改输入框中的值后由click事件调用。确实你的验证逻辑会被调用两次,但是我没有看到解决方法而没有进行更多的更改。

使用jQuery的示例:

$('input').blur(function() {
    validate(this);
});

$('submit').click(function() {
   //modify the input element
   validate(inputElement);
});

var validate = function(obj) {
   // validate the object
}

答案 4 :(得分:0)

有时在mouseup上获取子对象很有用,但是父对象希望在模糊时隐藏其子对象。我们可以取消隐藏子元素,然后等到我们的mouseup发生,然后在我们准备好时强制模糊

<强> JS

var cancelHide = false;

$('.my-input').blur(function() {
    if (!cancelHide) {
        $('.my-item').hide();
    }
});

$('.my-input').click(function() {
    $('.my-item').show();
});

$('.my-item').mousedown(function() {
    cancelHide = true;
});

$('.my-item').mouseup(function() {
    var text = $(this).text();
    alert(text);
    cancelHide = false;
    $('.my-input').blur();
});

<强> HTML

<input type="text" class="my-input"/>
<div class="my-item">Hello</div>
<div class="my-item">Lovely</div>
<div class="my-item">World</div>

<强> CSS

.my-item {
    display:none;
}

https://jsfiddle.net/tic84/on421rxg/

单击列表项只会在mouseup上发出警告,尽管父母试图在模糊时隐藏它们

答案 5 :(得分:-2)

诀窍不是使用模糊和点击事件,因为它们总是先按模糊顺序执行,然后单击第二步。相反,你应该检查有焦点的元素何时发生了变化,因为只有在点击后才会发生这种情况。

我认为我有一个优雅的解决方案:

var alreadyValidated = 'true';

setInterval(function(){
    if(document.activeElement.id != 'validation-field-id'){
        if(alreadyValidated=='false'){
            alreadyValidated = 'true';
            validate(document.activeElement);       
        }
    }
    else {
        alreadyValidated = 'false';
    }
}, 200);

目前,所有现代浏览器都支持document.activeElement。