При разработке интерфейсов на обычных формах в платформе 1С:Предприятие 8 часто возникает необходимость вывести на экран вычисляемую (виртуальную) колонку табличного поля — например, сумму с учетом наценки, скидки или коэффициента, задаваемого в шапке документа. Вместе с отображением значений в самих строках требуется выводить и общий итог по всей колонке в подвале таблицы.
Штатный механизм автоматического подсчета итогов работает только тогда, когда у колонки заполнено свойство Данные и колонка напрямую связана с числовым реквизитом табличной части. Для вычисляемых полей подсчет итогов необходимо реализовывать программно. Разберем, как правильно организовать этот расчет и каких типичных ошибок следует избегать.
Проанализируем частую ошибку начинающих разработчиков: попытку рассчитать общую сумму и установить значение подвала непосредственно внутри события ПриВыводеСтроки или ПриПолученииДанных.
Делать это категорически нельзя по следующим причинам:
Выясним правильную архитектуру решения. Расчет итогового значения должен производиться только в те моменты, когда меняются исходные данные, влияющие на результат. Для этого мы выносим расчет итога в отдельную процедуру модуля формы и записываем вычисленное значение в свойство ТекстПодвала нужной колонки табличного поля.
Рассмотрим по шагам настройку элементов формы и реализацию программного кода.
Перед написанием кода проверим настройки в палитре свойств элементов формы:
ЭлементыФормы.СоставУслуг) свойство Подвал должно быть установлено в значение Истина.СуммаНовая) убедимся, что свойство Данные оставлено пустым, а для свойства ГоризонтальноеПоложениеВПодвале выбрано значение Право (для корректного выравнивания чисел).Создадим универсальную процедуру, которая будет обходить строки табличной части документа, рассчитывать итоговую сумму с учетом введенного процента и форматировать вывод в подвале.
Посмотрим на пример реализации с обходом строк табличной части:
Процедура ПересчитатьИтогВиртуальнойКолонки()
ИтогСумма = 0;
Процент = ЭлементыФормы.ПроцентУслуги.Значение;
Коэффициент = 1 + Процент / 100;
// Обходим коллекцию строк объекта, а не элементы формы
Для Каждого Стр Из ЭтотОбъект.СоставУслуги Цикл
// Если в строках используется округление, учитываем его и при суммировании
ТекущаяНоваяСумма = Окр(Стр.Сумма * Коэффициент, 2);
ИтогСумма = ИтогСумма + ТекущаяНоваяСумма;
КонецЦикла;
// Форматируем число и передаем в свойство ТекстПодвала
ЭлементыФормы.СоставУслуг.Колонки.СуммаНовая.ТекстПодвала = Формат(ИтогСумма, "ЧДЦ=2; ЧГ=3,0");
КонецПроцедуры
Важный нюанс оптимизации: Если значение в строке не требует построчного округления копеек, можно существенно ускорить расчет, воспользовавшись встроенным методом коллекции Итог(), без использования цикла:
Процедура ПересчитатьИтогВиртуальнойКолонкиБыстро()
БазовыйИтог = ЭтотОбъект.СоставУслуги.Итог("Сумма");
Процент = ЭлементыФормы.ПроцентУслуги.Значение;
ИтогСумма = БазовыйИтог * (1 + Процент / 100);
ЭлементыФормы.СоставУслуг.Колонки.СуммаНовая.ТекстПодвала = Формат(ИтогСумма, "ЧДЦ=2; ЧГ=3,0");
КонецПроцедуры
Чтобы итоговая сумма в подвале всегда оставалась актуальной, вызовем созданную процедуру во всех точках, где могут измениться исходные параметры:
ПриОткрытии для первичного расчета итога при просмотре сохраненного документа.ПриИзменении поля ввода процента.ПриОкончанииРедактирования, ПослеУдаления, а также в процедурах подбора или пакетного заполнения строк.Разберем пример вызова в обработчике изменения процента в шапке документа:
Процедура ПроцентУслугиПриИзменении(Элемент)
// Пересчитываем подвал
ПересчитатьИтогВиртуальнойКолонки();
// Обновляем отображение строк таблицы на экране
ЭлементыФормы.СоставУслуг.ОбновитьСтроки();
КонецПроцедуры
Такой подход гарантирует высокую скорость работы интерфейса, корректность математических расчетов независимо от прокрутки таблицы и своевременное обновление итогов при любых действиях пользователя.