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