val ()을 사용하여 select의 값을 설정할 때 jquery change 이벤트가 트리거되지 않는 이유는 무엇입니까?


377

change()의해 설정 될 때 이벤트 핸들러 의 로직 이 실행되지 val()않지만 사용자가 마우스로 값을 선택할 때 실행됩니다. 왜 이런거야?

<select id="single">
    <option>Single</option>
    <option>Single2</option>
</select>

<script>
    $(function() {
        $(":input#single").change(function() {
           /* Logic here does not execute when val() is used */
        });
    });

    $("#single").val("Single2");
</script>

답변:


589

때문에 change이벤트는 사용자가 대신 자바 스크립트 코드를 통해 시작 실제 브라우저 이벤트가 필요합니다.

대신이 작업을 수행하십시오.

$("#single").val("Single2").trigger('change');

또는

$("#single").val("Single2").change();

1
안녕하세요,이 업데이트 드롭 다운을 수행하십시오. 그러나 onChange () 재귀 적으로 호출됩니다.
Pankaj

3
나는이 대답을 파다. 작동하지만 jQuery를 사용하는 더 좋은 방법은 없습니까? 변경 처리기가 설정된 값 (sarcasm)을 변경할 때마다 반드시이 작업을 수행해야합니다. 데이터 바인딩을 사용하는 프레임 워크가이를 더 잘 해결할 수 있습니까?
Jess

@ user113716 당신은 어떤 값도 몰라도 그것을 촉발하는 방법을 알고 있습니까?
BKSpurgeon

4
나는 이것이 정답이라고 동의하지만 이것은 내가하려는 일을 절대적으로 짜증나게합니다.
더스틴 포 아상

$ ( "# single"). trigger ({type : "change", val : "Single2"})를
시도하십시오

44

다음과 같이 변경 이벤트를 수동으로 트리거 할 수 있다고 생각합니다 trigger().

$("#single").val("Single2").trigger('change');

왜 자동으로 실행되지 않더라도 모르겠습니다.


이 작업도 할 수 없습니다. $ ( "# single"). val ( "Single2"). change (); 동적으로 드롭 다운을 만들고 값을 변경하고 있습니다 (잘 작동합니다).하지만 변경을 트리거하려고하면 작동하지 않습니다.
Maneesh Kumar

4
"비트"는 뒤늦게되었지만 무한 루프로 이어지기 때문에 자동으로 실행되지 않습니다. 생각$('#foo').change(function() { $( this ).val( 'whatever' ); });
JJJ

@Juhana 나는 무한한 루프가 "변경"바인딩을 트리거하는 신비한 val ()보다 훨씬 쉽게 알아 차리고 진단하고 수정하는 것이 좋다고 생각한다.
iono

.change () 호출은 .trigger ( 'change') 호출의 약어입니다.
Triynko

9

val () 다음에이 코드를 추가하면 작동하는 것 같습니다.

$(":input#single").trigger('change');

6
예,하지만를 사용하여 별도의 DOM 선택을 수행 할 필요는 없습니다 $(":input#single"). 실제로 당신은 정말로해서는 안됩니다. 뒤에 체인을 연결하십시오 .val(). 당신은 사용할 수 있습니다 .trigger('change')또는 .change(). 그들은 똑같습니다.
user113716

8

API에서 읽을 수있는 한. 이벤트는 사용자가 옵션을 클릭 할 때만 발생합니다.

http://api.jquery.com/change/

선택 상자, 확인란 및 라디오 버튼의 경우 사용자가 마우스로 선택하면 이벤트가 즉시 시작되지만 다른 요소 유형의 경우 요소가 포커스를 잃을 때까지 이벤트가 지연됩니다.


다른 요소 유형에 대한 대안은 무엇입니까? input요소가 포커스를 잃을 때가 아니라 'change'이벤트가 요소에 대해 즉시 발생하기를 원합니다 . 당신은 알고 있습니까?
Dan Nissenbaum

1
"즉시"라는 말은 "입력에서 키를 누를 때마다"onchangeup이 아니라 onkeyup, onkeypress 및 onkeydown 이벤트를 찾고 있다는 의미입니다.
user2867288

6

사용자 정의 함수를 쉽게 추가하고 값을 변경하면 변경이 트리거되기를 원할 때 언제든지 호출 할 수 있습니다.

$.fn.valAndTrigger = function (element) {
    return $(this).val(element).trigger('change');
}

$("#sample").valAndTirgger("NewValue");

또는 val 함수를 재정 의하여 val이 호출 될 때 항상 변경 사항을 호출 할 수 있습니다

(function ($) {
    var originalVal = $.fn.val;
    $.fn.val = function (value) {
        this.trigger("change");
        return originalVal.call(this, value);
    };
})(jQuery);

http://jsfiddle.net/r60bfkub/의 샘플


브라우저가 재귀가 너무 많다고 불평합니다.
Bhargav Nanekalva

change컨트롤을 통해 -event를 수신 change하고 동일한 컨트롤을 통해 (직접 또는 간접적으로) -event를 다시 트리거하는 콜백을 실행합니다 . 수동으로 트리거하는 이벤트 (예 :)에 다른 이름을 사용 explicit.change하여 change-event를 다시 트리거하지 않고 루프를 방지하며 여전히 이벤트에 반응 할 수 있도록하는 것이 좋습니다.
Kamafeather

3

기본 변경 이벤트와 혼합하고 싶지 않은 경우 사용자 정의 이벤트를 제공 할 수 있습니다

$('input.test').on('value_changed', function(e){
    console.log('value changed to '+$(this).val());
});

값 설정시 이벤트를 트리거하려면 다음을 수행하십시오.

$('input.test').val('I am a new value').trigger('value_changed');

3

Wordpress와 함께 CMB2를 사용하는 동안 동일한 문제가 발생하여 파일 업로드 메타 박스의 변경 이벤트에 연결하고 싶었습니다.

따라서 변경을 호출하는 코드 (이 경우 CMB2 스크립트)를 수정할 수없는 경우 아래 코드를 사용하십시오. 값이 설정된 후에 트리거가 호출되고, 그렇지 않으면 변경 eventHandler가 작동하지만 값은 설정되는 값이 아닌 이전 값이됩니다.

내가 사용하는 코드는 다음과 같습니다.

(function ($) {
    var originalVal = $.fn.val;
    $.fn.val = function (value) {
        if (arguments.length >= 1) {
            // setter invoked, do processing
            return originalVal.call(this, value).trigger('change');
        }
        //getter invoked do processing
        return originalVal.call(this);
    };
})(jQuery);

이것은 좋지만 하나의 특정 입력으로 제한하는 방법을 보여줄 수 있습니까?
jwebb

@jwebb 무슨 뜻인지 잘 모르겠습니까? jQuery val () 함수를 재정의하고 있습니다. 변경 이벤트 핸들러를 특정 입력에 바인딩합니다.
user2075039

@ user2075039, jQuery val () 함수를 사용하여 페이지에 여러 입력이 있고 사용자 정의 변경 이벤트 핸들러를 그중 하나에 만 바인딩하지 않으려면 어떻게해야합니까?
jwebb

@jwebb 특정 선택기 this.selector의 재정의 $.fn.val기능 내부 를 확인할 수 있습니다 (선택기에 사용되는 항목에 따라 다름). 이것은 내가 특정 분야에 대해서만이 작업을 수행 할 때 찾은 최선의 방법입니다. 문제는 선택기에서 무엇을 사용하는지 알아야한다는 것입니다.
sMyles

1
$(":input#single").trigger('change');

이것은 내 스크립트에서 효과가있었습니다. 3 개의 콤보가 있고 chainSelect 이벤트와 바인딩합니다 .URL로 3 개의 값을 전달해야하며 기본적으로 모두 드롭 다운을 선택하십시오. 나는 이것을 사용했다

$('#machineMake').val('<?php echo $_GET['headMake']; ?>').trigger('change');

그리고 첫 번째 행사는 효과가있었습니다.


10
나는 당신이 현실 세계에서 이것을하지 않기를 바랍니다. 말할 필요도없이 $ _GET [ 'whatever']는 신뢰할 수 없습니다.
Denis V

1

선택 옵션을 양식에 추가하고 변경 이벤트를 트리거하려는 경우 setTimeout이 필요하다는 것을 알았습니다. 그렇지 않으면 jQuery가 새로 추가 된 선택 상자를 선택하지 않습니다.

window.setTimeout(function() { jQuery('.languagedisplay').change();}, 1);
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.