Как программно получить значения из формы записи регистра и обновить ячейку отчета без переформирования?

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

В процессе разработки отчетов на системе компоновки данных (СКД) часто возникает задача интерактивного взаимодействия с пользователем. Типичный сценарий: пользователь кликает по ячейке отчета, открывается форма записи регистра сведений для ввода комментария или статуса, и после сохранения данных внесенные изменения должны мгновенно отобразиться в отчете. При этом крайне важно избежать полного переформирования отчета, которое может занимать длительное время на больших объемах данных. Разберем детально, как реализовать этот механизм в управляемом приложении 1С.

Механизм взаимодействия через глобальные оповещения

Рассмотрим самый распространенный способ — использование метода Оповестить. Этот метод позволяет передать данные из одной формы во все другие открытые формы в рамках текущего сеанса. Это особенно удобно, когда форма записи регистра не знает напрямую о том, кто её вызвал, но нам нужно передать сигнал об обновлении.

Проанализируем шаги реализации:

  1. В форме записи регистра сведений (которую мы открываем программно) необходимо переопределить событие ПослеЗаписи. Именно здесь мы будем отправлять сигнал.
  2. Внутри этого события мы вызываем метод Оповестить, передавая имя события и структуру с данными записи.

Пример кода в модуле формы записи регистра:


&НаКлиенте
Процедура ПослеЗаписи(ПараметрыЗаписи)
    СтруктураДанных = Новый Структура;
    СтруктураДанных.Вставить("Комментарий", Объект.Комментарий);
    СтруктураДанных.Вставить("ОбъектСвязки", Объект.ОбъектСвязки); // Ключевое поле для поиска строки в отчете
    
    Оповестить("ОбновлениеКомментарияВОтчете", СтруктураДанных, ЭтаФорма);
КонецПроцедуры

Теперь перейдем к форме отчета. Чтобы «поймать» это сообщение, в модуле формы отчета должен быть определен обработчик события ОбработкаОповещения. Рассмотрим, как это выглядит:


&НаКлиенте
Процедура ОбработкаОповещения(ИмяСобытия, Параметр, Источник)
    Если ИмяСобытия = "ОбновлениеКомментарияВОтчете" Тогда
        // Здесь мы вызываем процедуру обновления конкретной ячейки
        ОбновитьТекстЯчейкиВТабличномДокументе(Параметр);
    КонецЕсли;
КонецПроцедуры

Использование ОписанияОповещения для точечного возврата данных

Более современный и архитектурно «чистый» подход заключается в использовании объекта ОписаниеОповещения. Этот метод позволяет четко определить процедуру, которая должна выполниться именно после закрытия конкретной формы. Рассмотрим подробнее, как это реализовать при программном открытии формы записи.

Для начала, в форме отчета, когда мы инициируем открытие формы записи, мы создаем объект ОписаниеОповещения. Выясним, как правильно передать параметры:


&НаКлиенте
Процедура ОткрытьФормуЗаписи(ВыбраннаяОбласть)
    // Сохраняем адрес текущей области, чтобы знать, куда вернуть значение
    АдресЯчейки = ВыбраннаяОбласть.Имя;
    
    ПараметрыОповещения = Новый ОписаниеОповещения("ЗавершитьРедактированиеКомментария", ЭтаФорма, АдресЯчейки);
    
    ПараметрыФормы = Новый Структура;
    // Настраиваем отбор, чтобы открылась существующая запись или заполнились поля новой
    ПараметрыФормы.Вставить("Ключ", ПолучитьКлючЗаписи(ВыбраннаяОбласть)); 
    
    ОткрытьФорму("РегистрСведений.Комментарии.Форма.ФормаЗаписи", ПараметрыФормы, ЭтаФорма, , , , ПараметрыОповещения);
КонецПроцедуры

Проанализируем ситуацию в процедуре завершения. Когда форма записи закроется, управление передастся в указанный нами метод ЗавершитьРедактированиеКомментария. Важно помнить: чтобы данные вернулись в этот обработчик, в форме записи при закрытии нужно вызвать Закрыть(Результат), где Результат — это наши данные.

Прямое обновление Табличного документа без переформирования

Самый ответственный момент — визуальное обновление данных. Чтобы пользователь сразу увидел свой комментарий, мы должны программно изменить текст в ТабличныйДокумент (реквизит формы, где отображается результат СКД). Для этого нам нужно знать адрес ячейки или найти её по контексту.

Посмотрим на пример процедуры обновления, которая работает с объектом Результат (стандартное имя элемента формы для отчета):


&НаКлиенте
Процедура ОбновитьТекстЯчейкиВТабличномДокументе(Данные)
    // Допустим, мы сохранили адрес в контексте или ищем по текущей области
    ТекущаяОбласть = Элементы.Результат.ТекущаяОбласть;
    
    Если ТекущаяОбласть <> Неопределено Тогда
        // Устанавливаем текст напрямую в ячейку табличного документа
        Элементы.Результат.Документ.Область(ТекущаяОбласть.Имя).Текст = Данные.Комментарий;
        
        // Дополнительно можно изменить цвет фона ячейки, чтобы выделить изменения
        Элементы.Результат.Документ.Область(ТекущаяОбласть.Имя).ЦветФона = ЦветаСтиля.ЦветФонаФайла;
    КонецЕсли;
КонецПроцедуры

Важный нюанс: Такое обновление является чисто визуальным. Если пользователь нажмет кнопку «Сформировать», отчет будет перестроен заново из данных базы. Поэтому крайне важно, чтобы форма записи регистра действительно записывала данные в БД, а в схеме компоновки данных было предусмотрено ЛЕВОЕ СОЕДИНЕНИЕ с этим регистром сведений. Тогда при следующем формировании данные подтянутся автоматически.

Реализация через ОбработкуВыбора

Если форма отчета указана владельцем открываемой формы записи (третий параметр в ОткрытьФорму), можно использовать стандартный механизм ОбработкаВыбора. Рассмотрим по шагам:

  1. В форме записи после успешного выполнения операции Записать вызываем: ОповеститьОВыборе(Объект.Комментарий).
  2. В форме отчета создаем обработчик события ОбработкаВыбора у элемента формы Результат или у самой формы.
  3. Внутри обработчика проверяем тип пришедшего значения и записываем его в текущую ячейку.

Этот метод считается более простым в реализации, так как не требует явного описания оповещений, однако он менее гибкий, если из одной формы может производиться выбор разных типов данных.

Советы по оптимизации работы пользователя

Чтобы сделать интерфейс еще более дружелюбным, рекомендуем обратить внимание на следующие моменты:

Выяснив все технические детали, мы видим, что наиболее надежным и современным способом является связка ОписаниеОповещения и прямого манипулирования областью ТабличногоДокумента. Это обеспечивает высокую скорость отклика интерфейса и корректную работу с данными в базе.

← На главную