Событие keydown в js странно себя ведет, почему?

209
22 мая 2018, 16:40
input.addEventListener('keydown', fninput);

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

Почему так происходит с событием keydown и какое есть решение?

Код:

// создаю ссылки и задаю параметры 
const input = document.querySelector('input[name=inputData]'); 
const outputData = document.querySelector('#noticeForUser'); 
const getInputClass = input.getAttribute('class'); 
input.setAttribute('placeholder', 'Введите значение'); 
// объявляю функцию 
const fninput = (handler) => { 
  let output = Math.ceil(input.value / 0.97); 
  if (input.value >= 1) { 
    return outputData.innerHTML = output + ' руб.', input.removeAttribute('class'), input.setAttribute('class', getInputClass), outputData.removeAttribute('class'); 
  } else if (isNaN(input.value)) { 
    return outputData.innerHTML = 'Введите цифры', input.setAttribute('class', 'bgred'), outputData.setAttribute('class', 'bgred'); 
  } else if (input.value === '') { 
    return outputData.innerHTML = 'Введите значение', input.removeAttribute('class'), input.setAttribute('class', getInputClass), outputData.removeAttribute('class'); 
  } else if (input.value <= 0) { 
    return outputData.innerHTML = 'Введите значение больше нуля', input.setAttribute('class', 'bgred'), outputData.setAttribute('class', 'bgred'); 
  } else { 
    return outputData.innerHTML = '', input.removeAttribute('class'), input.setAttribute('class', getInputClass), outputData.removeAttribute('class'); 
  } 
} 
input.addEventListener('click', () => outputData.innerHTML = 'Введите значение'); 
input.addEventListener('keydown', fninput);
.row { 
  background: #f8f9fa; 
  margin-top: 20px; 
} 
 
.col { 
  border: solid 1px #6c757d; 
  padding: 10px; 
}
<!DOCTYPE html> 
<html lang="ru"> 
 
<head> 
  <meta charset="UTF-8"> 
  <meta name="viewport" content="width=device-width, initial-scale=1.0"> 
  <meta http-equiv="X-UA-Compatible" content="ie=edge"> 
  <link href="https://fonts.googleapis.com/css?family=Roboto:300,400,700&amp;subset=cyrillic-ext" rel="stylesheet"> 
  <link rel="stylesheet" href="../css/style.css"> 
  <link rel="stylesheet" href="../css/bootstrap-grid.min.css"> 
  <link rel="stylesheet" href="../css/bootstrap-reboot.min.css"> 
  <title>Store</title> 
</head> 
 
<body> 
  <div class="container-fluid"> 
 
    <header class="header"> 
      <div class="logo bg"> 
        <div class="row"> 
          <div class="col">ГЛАВНАЯ</div> 
        </div> 
      </div> 
 
      <nav class="header-nav bg"> 
        <div class="row"> 
          <div class="col">МЕНЮ</div> 
        </div> 
      </nav> 
    </header> 
 
    <section id="main" class="main bg"> 
      <div class="row"> 
        <div class="col align-self-center"> 
          <a id="link" href="/html/main.html">ссылка</a> 
        </div> 
        <div class="col align-self-center">2</div> 
        <div class="col align-self-center">3</div> 
      </div> 
      <div class="row"> 
        <div class="col"> 
          <form name="myform"> 
            <span id="noticeForUser"></span> 
            <br> 
            <input class="brblack" type="text" name="inputData" autocomplete="off"> 
            <br> 
            <br> 
            <input type="submit" name="submit" value="Отправить"> 
          </form> 
        </div> 
      </div> 
    </section> 
 
 
 
 
 
 
 
 
 
 
 
 
 
    <footer class="footer bg"> 
      <div class="row"> 
        <div class="col"> 
          FOOTER 
        </div> 
      </div> 
    </footer> 
 
    <script src="/js/jquery-3.3.1.min.js"></script> 
    <script src="/js/bootstrap.min.js"></script> 
    <script src="/js/app.js"></script> 
 
  </div> 
</body> 
 
</html>

https://jsfiddle.net/abnf6uac/

Answer 1

Проблема в том, что значение в поле ввода обновляется после события keydown.

Из-за этого проверка input.value - не дает результата, так как в value еще не добавлен нажатый символ.

Если в проверке нуждается не конкретный введенный символ, а полная строка можно воспользоваться, как советует @Other, событием input.

Answer 2

А у меня все работает:

const log = document.getElementById('log'); 
const fninput = (e) => { 
  log.innerHTML = "<br>" + e.code + log.innerHTML; 
} 
 
const input = document.getElementById("xmm"); 
input.addEventListener('keydown', fninput);
<input id="xmm" type="text" /> 
 
<p id="log"></p>

READ ALSO
Возможно ли изменить анимацию открытию bootstrap burger менью?

Возможно ли изменить анимацию открытию bootstrap burger менью?

Как можно изменить стандартную анимацию открытия бургер менью в Bootstrap

252
Выбор двух дат при условии не disabled

Выбор двух дат при условии не disabled

air datepicker Не получается сделать условие, при котором нельзя будет выбирать range, когда между датами есть disabledКто знает, не стесняйтесь подсказывать...

174
Jquery to native js

Jquery to native js

есть JQ код:

223
Почему в данном случае не получается привязать контекст?

Почему в данном случае не получается привязать контекст?

К сожалению, не могу продемонстрировать код в работе, так как здесь осуществляется работа с сервером с помощью ajaxУпрощенный пример

224