1

Тема: JS счетчик символов в тексте с пробелами

Пример: поле с контролем СМС

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

Посмотрим, как их использовать, на примере.

Сделаем поле для СМС, рядом с которым должно показываться число символов, обновляющееся при каждом изменении поля.

Как такое реализовать?

Событие input идеально решит задачу во всех браузерах, кроме IE9-. Собственно, если IE9- нам не нужен, то на этом можно и остановиться.

IE9-

В IE8- событие input не поддерживается, но, как мы видели ранее, есть onpropertychange, которое может заменить его.

Что же касается IE9 – там поддерживаются и input и onpropertychange, но они оба не работают при удалении символов. Поэтому мы будем отслеживать удаление при помощи keyup на Delete и BackSpace . А вот удаление командой «вырезать» из меню – сможет отловить лишь oncut.

Получается вот такая комбинация:

 <input type="text" id="sms"> символов: <span id="result"></span>
<script>
  function showCount() {
    result.innerHTML = sms.value.length;
  }

  sms.onkeyup = sms.oninput = showCount;
  sms.onpropertychange = function() {
    if (event.propertyName == "value") showCount();
  }
  sms.oncut = function() {
    setTimeout(showCount, 0); // на момент oncut значение еще старое
  };
</script>

Здесь мы добавили вызов showCount на все события, которые могут приводить к изменению значения. Да, иногда изменение будет обрабатываться несколько раз, но зато с гарантией. А лишние вызовы легко убрать, например, при помощи throttle-декоратора, описанного в задаче Тормозилка.

2

Re: JS счетчик символов в тексте с пробелами

Есть и совсем другой простой, но действенный вариант: через setInterval регулярно проверять значение и, если оно слишком длинное, обрезать его.

Чтобы сэкономить ресурсы браузера, мы можем начинать отслеживание по onfocus, а прекращать – по onblur, вот так:

<input type="text" id="sms"> символов: <span id="result"></span>

<script>
  var timerId;

  sms.onfocus = function() {

    var lastValue = sms.value;
    timerId = setInterval(function() {
      if (sms.value != lastValue) {
        showCount();
        lastValue = sms.value;
      }
    }, 20);
  };

  sms.onblur = function() {
    clearInterval(timerId);
  };

  function showCount() {
    result.innerHTML = sms.value.length;
  }
</script>

Обратим внимание – весь этот «танец с бубном» нужен только для поддержки IE8-, в которых не поддерживается oninput и IE9, где oninput не работает при удалении.