Событие ввода не работает, если значение изменяется с помощью jQuery val () или JavaScript

Если я изменю значение поля ввода программно,input а такжеchange события не стреляют. Например, у меня есть этот сценарий:

var $input = $('#myinput');

$input.on('input', function() {
  // Do this when value changes
  alert($input.val());
});

$('#change').click(function() {
  // Change the value
  $input.val($input.val() + 'x');
});
<input id="myinput" type="text" />
<button id="change">Change value</button>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

Эта проблема: Событие запускается, когда я набираю текстовое поле, но не когда я нажимаю кнопку. Есть ли способ достичь этого с помощью какого-либо события или иным образом без необходимости делать это вручную?

Что я не хочу делать: Я мог бы пройти весь мой код, чтобы добавитьtrigger или вызов функции везде вручную, но это не то, что я ищу.

Зачем: Основная причина, по которой я хотел бы сделать это автоматически, заключается в том, что у меня много полей ввода и много разных мест, где я изменяю эти входы программно. Это сэкономило бы мне много времени, если бы был способ провести мероприятиеавтоматически когда любой вход изменяется в любом месте моего кода.

 Arminius19 июн. 2016 г., 00:29
Как насчет ... функции? Если все, что вам нужно, это не повторять себя, все остальное излишне.
 codefreaK16 июн. 2016 г., 22:52
LOL Я понятия не имею, почему этот вопрос получает так много отрицательных голосов
 Jaqen H'ghar13 июн. 2016 г., 18:41
@Duncan привет, я действительно не знаю, почему ваш вопрос получает отрицательные голоса. Я полагаю, это может быть связано с тем, что этот вопрос освещался много раз, но я считаю, что ваш случай особенный, поскольку вы не можете использовать стандартное решение. Итог, ваш вопрос в порядке и не возражайте против понижений слишком много. В любом случае мне действительно интересно узнать причину, по которой вы не хотите вызыватьinput или жеchange События. Это потому, что это не только автоматически, или у вас есть дополнительные проблемы с этим решением? Спасибо
 codefreaK16 июн. 2016 г., 23:42
Я проголосовал за него, поскольку нашел вопрос интересным, и удивился этому, и тогда только я узнал о пользовательских событиях сейчас, но этот вопрос заставил меня задуматься, есть ли другой вариант, кроме пользовательских событий.
 Vitaly07 июн. 2016 г., 20:39
такие событияinput не существует, попробуйтеkeyup keydown События
 codefreaK16 июн. 2016 г., 22:54
Дункан +1 от LOL, и я хочу знать, почему вы не хотите использовать пользовательские события или вызвать событие изменения в строке в следующий раз, когда значение будет изменено
 Duncan Luk13 июн. 2016 г., 19:16
@ JaqenH'ghar Спасибо за ваш комментарий. Основная причина, по которой я хотел бы проверить это автоматически, состоит в том, что у меня много полей ввода и много разных мест, где я изменяю эти входы программно. Я мог бы пройти весь мой код, чтобы добавитьtrigger везде, но это сэкономило бы мне много времени, если бы был способ не делать это. Кроме того, меня просто интересуют решения, которые могут придумать люди.
 Duncan Luk16 июн. 2016 г., 23:14
@SachinDivakar Как я уже говорил в этом вопросе, в моем коде есть много мест, где я изменяю поля ввода, поэтому необходимость вручную запускать события - это просто дополнительная работа. Я просто надеюсь, что есть способы, позволяющие некоторому коду выполнить эту дополнительную работу за меня. В конце концов, для этого и нужны обработчики событий, верно? О отрицательных голосах; Я просто ищу ответ, который также может помочь другим, и все эти отрицательные голоса не помогают привлечь внимание, и они значительно уменьшают шансы на хорошие ответы. Этот вопрос имел -6 в какой-то момент, так что спасибо всем за голосование!
 zer00ne07 июн. 2016 г., 21:23
Если вы используетеchange вместоinput,change не будет стрелять до#myInput не в фокусе. Если вы хотите, чтобы событие срабатывало при нажатии кнопки, это расфокусировало бы (или размыло)#myInput иchange событие будет срабатывать в контексте#myInput.

Ответы на вопрос(5)

$input.val($input.val() + 'x')
$input.trigger('change');

Событие изменения срабатывает только при размытии ввода.

Есть несколько способов, как этого добиться. Здесь вы можете использовать HTML-код leveluponinput() Событие, которое происходит немедленно, когда элемент изменяется и вызывает функцию.

<input id="myinput" type="text" oninput="sample_func()" />
<button id="change">Change value</button>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

.

var input = $("#myinput");

function sample_func(){
  alert(input.val());
}

$('#change').click(function() {
  input.val(input.val() + 'x');
});

Или это JQuery,input вещь (только что связанная с приведенным выше примером).

<input id="myinput" type="text" />
<button id="change">Change value</button>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

.

var input = $("#myinput");

input.on("input", function() {
  alert(input.val());
});

$('#change').click(function() {
  input.val(input.val() + 'x');
});

Вы также можете использовать JavaScriptsetInterval() который постоянно работает с заданным интервалом времени. Это только необязательно и лучше, если вы делаете программу, связанную со временем.

<input id="myinput" type="text" />
<button id="change">Change value</button>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

.

var input = $("#myinput");

setInterval(function() { ObserveInputValue(input.val()); }, 100);

$('#change').click(function() {
  input.val(input.val() + 'x');
});
 tgkprog19 июн. 2016 г., 00:37
arnt большинство полуколоний необязательно? хотя хорошая идея использовать их в каждом утверждении
 rhavendc13 июн. 2016 г., 08:51
И, эй, @Duncan Я только что обнаружил, что в вашем коде чего-то не хватает (возможно, причина, по которой ваш код не работает). В$('#change').click(function() { ..... });ты забыл; сразу после$input.val($input.val() + 'x')

Похоже, что нет другого пути, кроме использования.trigger().

Давайте попробуем то же самое, используя.change() событие:

var $input = $("#myinput");

$input.on('change paste keyup', function() {
  alert($(this).val());
});

$('#change').click(function() {
  $input.val($input.val() + 'x').trigger("change");
});
<input id="myinput" type="text" />
<button id="change">Change value</button>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

Или вам нужно запустить его вручную:

$('#change').click(function() {
  $input.val($input.val() + 'x').trigger("input");
});

отрывок

var $input = $("#myinput");

$input.on('input', function() {
  alert($(this).val());
});

$('#change').click(function() {
  $input.val($input.val() + 'x').trigger("input");
});
<input id="myinput" type="text" />
<button id="change">Change value</button>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

 Praveen Kumar Purushothaman07 июн. 2016 г., 20:39
@ gh9 Понятно .. Дай мне обновить мой ответ.
 Bekim Bacaj12 июн. 2016 г., 03:19
@ gh9 jQuery - сторонний фреймворк.
 gh907 июн. 2016 г., 20:40
круто мне тоже любопытно как это сделать в чистом виде
 gh907 июн. 2016 г., 20:39
Я не думаю, что OP хочет программно инициировать изменение входа. Я думаю, что он хочет поставить наблюдателя на него, поэтому, если кто-нибудь изменит ввод из любого места, будет активировано предупреждение OP
 gh908 июн. 2016 г., 14:22
То, что использует только JQUERY и / или ванильный JavaScript. Не другой сторонний фреймворк с двухсторонней привязкой данных
 Praveen Kumar Purushothaman08 июн. 2016 г., 00:31
@ gh9 Чистый JQuery?
Решение Вопроса

Простое решение:

Спусковой крючокinput после звонкаval():

$input.trigger("input");

var $input = $("#myinput");

$input.on('input', function() {
  alert($(this).val());
});

$('#change').click(function() {
  // Change the value and trigger input
  $input.val($input.val() + 'x').trigger("input");
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

<input id="myinput" type="text" />
<button id="change">Change value</button>

Конкретное решение:

Как уже упоминалось, вы не хотите, чтобы вызватьinput вручную. Это решение запускает событие автоматически, переопределяяval().

Просто добавьте это в свой код:

(function ($) {
    var originalVal = $.fn.val;
    $.fn.val = function (value) {
        var res = originalVal.apply(this, arguments);

        if (this.is('input:text') && arguments.length >= 1) {
            // this is input type=text setter
            this.trigger("input");
        }

        return res;
    };
})(jQuery);

УвидетьJSFiddle Demo

PS

уведомлениеthis.is('input:text') в состоянии. Если вы хотите вызвать событие для других типов, добавьте их в условие.

 Praveen Kumar Purushothaman18 июн. 2016 г., 14:59
@ JaqenH'ghar Как насчет настройкиinput.value = 'something'? Будет ли это работать для этого?
 Jaqen H'ghar18 июн. 2016 г., 21:18
ОП вопросы и ответ оба относятся к JQueryval(), Если вы хотите установить значение безval() как с помощьюinput.value = 'something' лучший и самый простой способ для вас, вероятно, состоит в том, чтобы вызвать событие вручную (что-то, чего OP не хотел, но может быть лучше для вас)
 Arminius19 июн. 2016 г., 00:26
Я бы посоветовал не перекрывать такую ​​вездесущую функцию, какval, Некоторые плагины jQuery, которые вы хотите добавить позже, могут положиться на негоне запуск события ввода и начать действовать странно, если вы делаете. Например, если плагин выполняет дезинфекцию пользовательского ввода и записывает измененное значение, используяval Вы застряли в бесконечном цикле.
 Duncan Luk13 июн. 2016 г., 19:41
Лучшее решение, которое я видел. Я никогда не думал о переопределении, очень приятно!

Слушатели jQuery работают только с реальными событиями браузера, и они не генерируются при программном изменении чего-либо.

Вы можете создать собственное миниатюрное расширение jQuery для прокси, чтобы вы всегда вызывали событие, но делали это только в одном модульном месте, например так:

$.fn.changeTextField = function (value) {
  return $(this).val(value).trigger("change");
}

Затем просто вызывайте новую функцию всякий раз, когда вы хотите обновить текстовое поле, вместо использования функции val в jQuery:

$("#myInput").changeTextField("foo");

Вот версия, работающая с прокси-функцией:

    <!DOCTYPE html>
    <html>
        <head>
            <title>Test stuff</title>
            <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.2.2/jquery.min.js"></script>
        </head>
        <body>

  <input id="myInput" type="text" />
        <button id="myButton">Change value</button>

        <script type="text/javascript">
            $.fn.changeTextField = function (value) {
             return $(this).val(value).trigger("change");
            }

            $( document ).ready(function() {
                var $input = $("#myInput");

                $input.on("change", function() {
                    alert($input.val());
                });

                $('#myButton').click(function() {
                    $("#myInput").changeTextField("foo");
                });
            });
        </script>
        </body>
    </html>

Для справки, этот вопрос действительно уже был дан ответ здесь:Почему событие изменения jquery не срабатывает, когда я устанавливаю значение выбора с помощью val ()?

и здесь:JQuery обнаруживает событие Programatic change

Ваш ответ на вопрос