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