При разработке управляемых форм в 1С часто возникает задача: отобразить итоговую сумму по табличной части в отдельном поле над ней — для этого есть обработка вывода итогов веса и объема в заказ. Многие начинающие разработчики сталкиваются с трудностями при выборе события, в котором нужно производить расчет. Давайте разберем, как правильно реализовать этот функционал, учитывая особенности архитектуры 1С:Предприятия.
Самый правильный и «чистый» способ решения задачи в современных управляемых формах — это использование встроенных механизмов платформы — есть готовый конструктор заполнения и контроля данных без программирования. Вы можете выполнять добавление реквизитов и элементов формы без кодирования, чтобы поле суммы обновлялось автоматически.
ПутьКДанным.Платформа 1С умеет автоматически вычислять итоги по колонкам табличной части, если правильно настроен элемент формы. Для быстрой правки свойств в рантайме подойдет редактор форм в режиме предприятия, что избавляет от необходимости вызывать функцию Итог() при каждом чихе пользователя.
Если вам необходимо, чтобы значение рассчитывалось и записывалось в реквизит документа при каждом изменении состава строк (поможет расширение для автоматизации заполнения реквизитов документа) (например, при смене количества или цены), используйте метод Итог(). Важно понимать: код должен срабатывать при изменении данных в табличной части, а не самого поля суммы.
Разберем пример кода, который нужно поместить в обработчик события ПриИзменении для колонок табличной части (например, для Количество, Цена):
&НаКлиенте
Процедура ТоварыКоличествоПриИзменении(Элемент)
// Рассчитываем сумму текущей строки
ТекущиеДанные = Элементы.Товары.ТекущиеДанные;
ТекущиеДанные.Сумма = ТекущиеДанные.Количество * ТекущиеДанные.Цена;
// Пересчитываем итоговую сумму документа
Объект.СуммаДокумента = Объект.Товары.Итог("Сумма");
КонецПроцедуры
Почему это работает: Мы используем встроенный метод Итог(), который суммирует значения указанной колонки по всем строкам табличной части Товары. Вызов этого кода в обработчике изменения строки гарантирует, что итоговая сумма на форме всегда будет актуальной.
Этот способ необходим, если вам нужно, чтобы итоговая сумма гарантированно сохранялась в базу данных, даже если документ создается программно или через групповую обработку, минуя форму документа. Расчеты, критичные для логики работы документа, лучше переносить из модуля формы в модуль объекта.
Рассмотрим, как это реализовать:
Процедура ПередЗаписью(Отказ, РежимЗаписи, РежимПроведения)
// Метод Итог доступен и в модуле объекта
СуммаДокумента = Товары.Итог("Сумма");
КонецПроцедуры
Использование события ПередЗаписью — это профессиональный подход, так как он обеспечивает целостность данных в информационной базе независимо от того, как именно происходит запись документа.
Итог() работает быстро, но если табличная часть содержит тысячи строк, стоит задуматься об оптимизации процесса пересчета.СуммаДокумента на форме — это лишь элемент управления. Пользователь не должен менять его вручную, поэтому оно должно быть либо предназначено только для чтения (свойство ТолькоПросмотр), либо обновляться автоматически через код, описанный выше.Изучая 1С, всегда стремитесь понять, почему код не срабатывает. В данном случае ошибка заключалась в том, что автор пытался повесить логику пересчета на событие изменения самой суммы, хотя инициатором изменений всегда выступает содержимое табличной части. Анализируйте состав событий формы, и ваши программы станут надежнее! В этом поможет набор инструментов разработчика с консолью кода и запросов.