문제

jQuery 이벤트를 일시적으로 억제하는 우아한 방법이 있습니까? 나는 다음과 같은 코드를 사용합니다.

$(element).unbind(event, function1).unbind(event, function2);
// code for which the event is suppressed
$(element).bind(event, function1).bind(event, function2);

그러나 나는 그것이 약간 서투르고 많은 사건에 대해서는 확장 할 수 없다는 것을 알았습니다. 이벤트를 일시적으로 억제하고 싶은 이유는 무엇입니까? Ajax 액세스 중에 Blockui 플러그인을 사용하여 UI를 차단합니다. 이것은 다음과 같습니다. $ (). ajaxstart ($. blockui) .ajaxstop ($. Unblockui) Blockui가 제안한대로.

그러나 하나의 Ajax 액세스는 특별하므로 다른 메시지가 필요합니다. AJAXSTART 및 AJAXSTOP 이벤트는 메시지 코드를 방해합니다 (아무것도 표시되지 않음).

function message(text, callback) {
  if (text == undefined) {
     $.unblockUI();
     return;
  }

  // $().unbind('ajaxStop', $.unblockUI).unbind('ajaxStart', $.blockUI);
  $("#message_text").html(text);
  $.blockUI({message: $("#message")});
  $("#message_ok").click(function() { 
    // $().bind('ajaxStop', $.unblockUI).bind('ajaxStart', $.blockUI);
    $.unblockUI();
    if (callback != undefined) callback();
  });
}

Unbind ()와 bind () 라인을 무너 뜨리는 경우에만 작동합니다.

도움이 되었습니까?

해결책

나는이 질문이 오래되었다는 것을 알고 있지만, 같은 질문에 대한 답을 찾는 동안 그것을 발견했고, 이벤트 핸들러의 간단한 응용 프로그램에서 잘 작동하는 다른 해결책을 찾았습니다.

$(element).click(function(e) {
  e.preventDefault();

  // Check for fired class
  if ($(this).hasClass('fired') == false) {
     // Add fired class to all instances of element
     $(element).addClass('fired');

     // Do the rest of the function...

     // Remove fired class to 'reactivate' events
     $(element).removeClass('fired');   
  }
}

이벤트의 코드가 발사되는 동안 '요소에 클래스를 추가하면 다른 클릭 이벤트의 결과로 추가 코드가 실행되는 것을 방지 할 수 있습니다. 따라서 실제로 다른 클릭 이벤트를 방해하지는 않지만 결과 코드가 실행되는 것을 방지합니다. 단순하고 조잡한 것은 묶여 있고 바인딩되지 않은 설교의 사용을 무시하지만 효과가 있습니다.

다른 팁

이 스크립트를 마치고 유용하기를 바랍니다.

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta content="text/html; charset=utf-8" http-equiv="Content-Type" />
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3.2/jquery.min.js"></script> 
<script type="text/javascript">
$(function(){

    //ini plugin

    jQuery.event.freezeEvents = function(elem) {

        if (typeof(jQuery._funcFreeze)=="undefined")
            jQuery._funcFreeze = [];

        if (typeof(jQuery._funcNull)=="undefined")
            jQuery._funcNull = function(){ };

        // don't do events on text and comment nodes
        if ( elem.nodeType == 3 || elem.nodeType == 8 )
            return;

        var events = jQuery.data(elem, "events"), ret, index;

        if ( events ) {

            for ( var type in events )
            {
                if ( events[type] ) {

                    var namespaces = type.split(".");
                    type = namespaces.shift();
                    var namespace = RegExp("(^|\\.)" + namespaces.slice().sort().join(".*\\.") + "(\\.|$)");

                    for ( var handle in events[type] )
                        if ( namespace.test(events[type][handle].type) ){
                            if (events[type][handle] != jQuery._funcNull){
                                jQuery._funcFreeze["events_freeze_" + handle] = events[type][handle];
                                events[type][handle] = jQuery._funcNull;
                            }
                        }
                }

            }
        }
    }

    jQuery.event.unFreezeEvents = function(elem) {

        // don't do events on text and comment nodes
        if ( elem.nodeType == 3 || elem.nodeType == 8 )
            return;

        var events = jQuery.data(elem, "events"), ret, index;

        if ( events ) {

            for ( var type in events )
            {
                if ( events[type] ) {

                    var namespaces = type.split(".");
                    type = namespaces.shift();

                    for ( var handle in events[type] )
                        if (events[type][handle]==jQuery._funcNull)
                            events[type][handle] = jQuery._funcFreeze["events_freeze_" + handle];

                }
            }
        }
    }

    jQuery.fn.freezeEvents = function() {

        return this.each(function(){
            jQuery.event.freezeEvents(this);
        });

    };

    jQuery.fn.unFreezeEvents = function() {

        return this.each(function(){
            jQuery.event.unFreezeEvents(this);
        });

    };

    //end plugin

    jQuery("#test1").ajaxStart(function test1(){
        jQuery("#result").append('test1 ajaxStop<br>');
    });

    jQuery("#test1").ajaxStop(function test2(){
        jQuery("#result").append('test1 click<br>');
    });

    jQuery("#test1").bind("click", function test3(){
        jQuery("#result").append('test1 click<br>');
    });

    jQuery("#test2").bind("click", function test5(){
        jQuery("#result").append('test2 click<br>');
    });

    jQuery("#freez").click(function(){
        jQuery("#test1").freezeEvents();
        jQuery("#test2").freezeEvents();
    });

    jQuery("#unfreez").click(function(){
        jQuery("#test1").unFreezeEvents();
        jQuery("#test2").unFreezeEvents();
    });

});
</script>
</head>
<body>
<button id="freez">freez</button>
<button id="unfreez">un freez</button>
<br />
<div id="test1">test1 click mousemove</div>
<div id="test2">test2 click mousemove</div>
<br />
<div id="result"></div>
</body>
</html>

나는이 문제에 대한 Andres의 접근 방식을 정말로 좋아했지만, 그가 코드를 생각해 낸 이후 jQuery 이벤트 모델이 변경되었으므로 최근 버전의 jQuery에서 그의 코드는 작동하지 않습니다. 여기에 현대화됩니다. 1.8.2에서 테스트 (가볍게) :

$.event.freezeEvents = function(elem) {

        if (typeof($._funcFreeze)=="undefined") {
            $._funcFreeze = [];
        }

        if (typeof($._funcNull)=="undefined") {
            $._funcNull = function() {};
        }                

        // don't do events on text and comment nodes
        if ( elem.nodeType == 3 || elem.nodeType == 8 ) {
            return;
        }

        var events = $._data(elem, "events");

        if (events) {
            $.each(events, function(type, definition) {
                $.each(definition, function(index, event) {
                    if (event.handler != $._funcNull){
                        $._funcFreeze["events_freeze_" + event.guid] = event.handler;
                        event.handler = $._funcNull;
                    }
                })
            })
        }
    }

    $.event.unFreezeEvents = function(elem) {

        // don't do events on text and comment nodes
        if ( elem.nodeType == 3 || elem.nodeType == 8 )
                return;

        var events = $._data(elem, "events");

        if (events) {
            $.each(events, function(type, definition) {
                $.each(definition, function(index, event) {
                    if (event.handler == $._funcNull){
                        event.handler = $._funcFreeze["events_freeze_" + event.guid];
                    }
                })
            })
        }
    }

    $.fn.freezeEvents = function() {
        return this.each(function(){
            $.event.freezeEvents(this);
        });
    };

    $.fn.unFreezeEvents = function() {
        return this.each(function(){
            $.event.unFreezeEvents(this);
        });
    };

나는 두 가지 이벤트가있는 요소를 넘어서서 이것을 테스트하지 않았지만 그것은 나에게 잘 작동합니다. 이것이 누군가를 돕기를 바랍니다.

이를 수행하는 가장 간단한 방법은 바운드 메소드의 시작 부분에 검사를 추가하여 메소드가 실행되어야하는지 확인하는 것입니다. 그렇지 않다면 단순히 메소드에서 돌아 오십시오.

var doThing = true;

$("#foo").bind("click", function(e) {
    if(!doThing){return;}
    //do thing
}

function bar(){
    //temp unbind click
    doThing = false;

    //do stuff...

    //rebind click
    doThing = true;
}

전체 이벤트 개체를 단순히 저장하고 복원 할 수 있습니다.

var events=$._data(elem, 'events'); // save events
$._data(elem, 'events', {}); // cancel all events
// any code here will not fire events
$._data(elem, 'events', events); // restore events

이것은 나를 위해 효과가 있었지만 부작용이 알려지지 않았을 수도 있습니다 ...

그렇다면 페이지를 차단하고 여러 Ajax 요청을 발사 한 다음 페이지를 차단 해제하는 아이디어입니까?

이 경우 (그리고 질문을 올바르게 이해했다) 블록 카운터를 사용할 수 있습니까?

예 : var blockcounter = 0;

function block(){
if(blockcounter==0)
 {$.blockUI({message: "Hai", showOverlay:true});}
blockcounter++;
}

function unblock(){
blockcounter--;
if(blockcounter==0)
{$.unblockUI();}
}

그런 다음 코드에서

function dostuff(){
block();
... do whatever ajax you need
... call unblock() in the success event of your ajax call
}

function dostuff2(){
block();
... do some more ajax - this might take a bit longer to complete though
... call unblock() in the success event
}

dostuff();
dostuff2();

차단은 한 번만 발생해야하며 중간에 모든 것을 자유롭게 할 수 있습니다.

이 메소드는 차단과 차단 해제 사이에 여러 이벤트가 발생하는 웹 사이트와 다양한 AJAX 이벤트가 다양한 시간 내에 완료 될 수있는 웹 사이트에서 성공적으로 사용합니다. 네임 스페이스로 전체를 감싸면 글로벌 VARS와 함께 장소를 쓰지 않도록 할 수도 있습니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top