Общее количество слов во всех текстовых полях

#jquery #word #counter

#jquery #word #счетчик

Вопрос:

Я пытаюсь подсчитать количество слов, которые пользователь вводит в каждой текстовой области, сложить их и показать пользователю по мере ввода. У меня пока это есть:

 $("[class^='count[']").bind('keyup click blur focus change paste', function() {

    sum = 0;

        $("[class^='count[']").each(function() {

            var Words = jQuery.trim($(this).val()).split(' ').length;

            sum  = Number(Words);

            if($(this).val() === '') { sum = 0; }

            $('#maxwords').children('span').text(sum);



        });



});
  

и вот мой HTML:

 <ul id="forms">

            <li><textarea name="PresentationAbstract1"  id="PresentationAbstract1"style="width:700px"></textarea></li>

            <li><textarea name="PresentationAbstract2"  id="PresentationAbstract2"style="width:700px"></textarea></li>

            <li><textarea name="PresentationAbstract3"  id="PresentationAbstract3"style="width:700px"></textarea></li>


            <li id="maxwords">Total words (<span>0</span>)</li>
        </ul>
  

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

Вот URL-адрес необходимого проекта: http://www.meetingproceedings.com/harvester2/wordcount.html . Любые идеи будут оценены.

Ответ №1:

Есть несколько вещей, которые вы можете улучшить с помощью кода, но больше всего бросалось в глаза то, что $('#maxwords').children('span').text(sum); было внутри вашей .each() итерации. Это заставит ваш код записывать количество слов каждый раз, когда подсчитывалось количество слов в текстовой области. И затем есть if($(this).val() === '') { sum = 0; } строка, которая сбрасывает количество слов, если внутри текстовой области ничего не было (вот почему количество слов «выводится» только на интервал при записи в третьей текстовой области).

Попробуйте вместо этого этот код:

 $(function() {

    var countWords = function () {
        var sum = 0;
        $("textarea").each(function() {

            var words = $(this).val().split(' ');
            $.each(words, function(i, v) {
                if ($.trim(v) !== '') {sum  ;}
            });

        });

        $('#maxwords span').text(sum);
    };

    // this binds our counting function to the textareas
    $("textarea").bind('keyup click blur focus change paste', countWords);

    // let's run this on document ready
    countWords();

});
  

Это O(n^2) алгоритм (или, скорее, O(nm) ?), но он корректно проверяет наличие повторяющихся пробелов. Возможно, вам было бы лучше попытаться сопоставить с регулярным выражением, чтобы немного снизить сложность.

Это работает над моим jsFiddle здесь.

Редактировать

Обновлено решение, чтобы также запускать функцию подсчета при готовности документа. В качестве альтернативы, вы также можете добавить ready обработчик к textarea привязке (т.Е. $("textarea").bind('ready keyup click blur focus change paste', countWords) ) вместо вызова самой функции, и это также должно привести к появлению обработчика document ready, но я просто предпочитаю записать это так, чтобы было понятно.

Комментарии:

1. Большое спасибо, Ричард. Работает отлично! Есть идеи о том, как отобразить общее количество слов в готовом документе, если какая-либо из текстовых областей была предварительно заполнена базой данных?!

2. Чтобы запустить это $(document).ready() , вы можете инкапсулировать всю логику подсчета отображения в функцию и просто вызвать ее вместо этого. Позвольте мне изменить свой ответ для вас.

Ответ №2:

Почему у вас есть эта строка? Попробуйте удалить его.

 if($(this).val() === '') { sum = 0; }
  

Это заставляет вас сбрасывать сумму до нуля, если вы сталкиваетесь с пустым полем, что вы всегда будете делать, пока все поля после заполненного поля не будут содержать содержимое.

Ответ №3:

 $("#form textarea").live('KeyUp', function(){
var sum = 0;
$("#form textarea").each(function(){
   sum = $(this).val().split(' ').length;

});
//put sum in your span
});
  

если вы хотите, чтобы это было в режиме реального времени, вам нужно поработать над событием keyup.