Автоматическое вычисление поля по другим полям формы

Пишу небольшое приложение на Flask. Необходимо при заполнении формы произвести вычисление третьей ячейки по двум предыдущим на лету, в режиме реального времени. Сейчас реализовал следующий код для одной строчки с использованием id и getElementById:

        <div class="side-fields-calc">
            Процесс, ч:
            <input type="small-text" id="first"  name="{{ name1 }}" value="{{ value1 }}">
            из
            <input type="small-text" id="second" name="{{ name2 }}" value="{{ value2 }}">
            (
            <input type="small-text" id="result" name="{{ name3 }}" value="{{ value1 / value2 * 100  }}">
            %)
        </div>
    {% block scripts %}
    <script>
            var input1 = document.getElementById('first');
            var input2 = document.getElementById('second');
            var result = document.getElementById('result');

            input1.oninput = calculate;
            input2.oninput = calculate;

            function calculate() {
              var value1 = input1.value.split(':');
              var value2 = input2.value.split(':');

              var value1_minutes = (+value1[0]) * 60 + (+value1[1]);
              var value2_minutes = (+value2[0]) * 60 + (+value2[1]);

              result.value = (value1_minutes/value2_minutes*100).toFixed(2);
            }
    </script>
    {% endblock %}

Как мне это масштабировать, если таких полей будет несколько?


Ответы (1 шт):

Автор решения: Denis640Kb

Если брать только масштабирование, то можно так: Добавил несколько комментариев. Напоминаю, что вводить нужно именно время. Не стал менять, чтобы не портить Вам структуру, но рекомендую использовать тип time для полей input. Если что спрашивайте.

    var input1 = document.getElementsByClassName('first'); // получаем элементы по классу
    var input2 = document.getElementsByClassName('second'); // получаем элементы по классу
    [...input1].forEach(function (val1){ // для каждого элемента
        val1.addEventListener('input', function (){ // отслеживаем ввод
            let value1 = this.value.split(':');
            let value2 = this.nextSibling.nextSibling.value.split(':'); // берем через один элемент вперед
            let result = this.nextSibling.nextSibling.nextSibling.nextSibling; // берем элемент на 4 позиции последовательности
            var value1_minutes = (+value1[0]) * 60 + (+value1[1]);
            var value2_minutes = (+value2[0]) * 60 + (+value2[1]);
            result.value = (value1_minutes/value2_minutes*100).toFixed(2);
        })
    });
    [...input2].forEach(function (val1){ // для каждого элемента
        val1.addEventListener('input', function (){ // отслеживаем ввод
            let value1 = this.previousElementSibling.value.split(':');
            let value2 = this.value.split(':');
            let result = this.nextSibling.nextSibling;
            var value1_minutes = (+value1[0]) * 60 + (+value1[1]);
            var value2_minutes = (+value2[0]) * 60 + (+value2[1]);
            result.value = (value1_minutes/value2_minutes*100).toFixed(2);
        })
    })
<div class="side-fields-calc">
    Процесс, ч:
    <input type="small-text" class="first"  name="{{ name1 }}" value="{{ value1 }}">
    из
    <input type="small-text" class="second" name="{{ name2 }}" value="{{ value2 }}">
    (
    <input type="small-text" class="result" name="{{ name3 }}" value="{{ value1 / value2 * 100  }}">
    %)
</div>
<div class="side-fields-calc">
    Процесс, ч:
    <input type="small-text" class="first"  name="{{ name1 }}" value="{{ value1 }}">
    из
    <input type="small-text" class="second" name="{{ name2 }}" value="{{ value2 }}">
    (
    <input type="small-text" class="result" name="{{ name3 }}" value="{{ value1 / value2 * 100  }}">
    %)
</div>
<div class="side-fields-calc">
    Процесс, ч:
    <input type="small-text" class="first" name="{{ name1 }}" value="{{ value1 }}">
    из
    <input type="small-text" class="second" name="{{ name2 }}" value="{{ value2 }}">
    (
    <input type="small-text" class="result" name="{{ name3 }}" value="{{ value1 / value2 * 100  }}">
    %)
</div>

→ Ссылка