Почему форма 1С не устанавливает признак модифицированности автоматически при программных изменениях?

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

При работе с формами в 1С:Предприятии, свойство Модифицированность является ключевым индикатором для пользователя о том, что данные, отображаемые в форме, были изменены и требуют сохранения. Когда этот признак взведен, в заголовке формы мы видим характерный символ "*", сигнализирующий о необходимости записи изменений.

Платформа 1С автоматически устанавливает признак модифицированности формы в определенных случаях. Рассмотрим подробнее эти сценарии:

  1. При интерактивном изменении данных через элементы управления формы, которые связаны с реквизитами основного объекта.
  2. При вызове команд формы, у которых установлен флаг "Изменяет сохраняемые данные".

Однако, нередко возникают ситуации, когда мы вносим изменения в данные формы программно, но автоматического взведения флага Модифицированность не происходит. Стоит отметить, что помимо программных доработок существуют и другие способы изменения интерфейса, такие как добавление реквизитов и элементов формы без кодирования через расширения или даже интерактивное изменение с помощью специальных инструментов, например, редактора форм в режиме предприятия — поможет набор инструментов для разработки и отладки форм. В данной статье мы сосредоточимся именно на программном аспекте. Выясним причину такого поведения и разберем, как с этим работать.

Почему автоматическое взведение Модифицированности может не работать при программных изменениях?

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

  1. Прямое программное изменение данных: Если мы изменяем данные объекта или табличной части программно, без непосредственного интерактивного взаимодействия с элементами формы или без использования команд, явно помеченных как "Изменяет сохраняемые данные", то система может "не знать" об этих изменениях. Она не всегда отслеживает каждое программное изменение, чтобы автоматически взводить флаг модифицированности.
  2. Различие между объектом формы и объектом базы данных: Важно понимать, что объект, загруженный в форму, и сам объект в базе данных — это разные сущности. Изменение данных объекта, находящегося в оперативной памяти формы, не всегда напрямую инициирует изменение флага Модифицированность формы. Особенно это актуально, если изменения происходят на сервере и не имеют прямого "отражения" в клиентской части формы. Мы можем наблюдать, что изменение объекта не равносильно изменению данных формы в контексте механизма модифицированности.
  3. Отсутствие связи с основным реквизитом формы: Если мы программно изменяем реквизиты формы или элементы табличной части, которые не являются основным реквизитом формы или не связаны с ним напрямую через стандартные механизмы, автоматическое взведение флага может не произойти.
  4. Путаница с методом Объект.Модифицированность(): Не следует путать свойство формы Модифицированность с методом объекта Объект.Модифицированность(). Метод объекта, доступный на сервере, может возвращать Истина даже при отсутствии интерактивных изменений, например, из-за версионности данных перед записью. Этот метод имеет свою область применения, но он не управляет признаком модифицированности самой формы.

Таким образом, когда мы сталкиваемся с тем, что "встроенный механизм не работает" при программных изменениях, это не является ошибкой, а скорее особенностью архитектуры. Нам приходится самостоятельно заботиться об установке флага модифицированности формы, чтобы обеспечить корректное поведение интерфейса для пользователя.

Как вручную установить признак модифицированности формы?

В большинстве случаев, когда автоматическое взведение флага Модифицированность не происходит, единственным надежным решением является его ручная установка. Разберем по шагам, как это сделать, и в каких сценариях это необходимо.

  1. Основное решение: Для ручной установки признака модифицированности формы, нам нужно присвоить свойству Модифицированность значение Истина. Это делается с помощью следующего кода: ЭтаФорма.Модифицированность = Истина;

    Данный код должен быть вызван после того, как мы программно изменили данные формы или объекта, находящегося на форме — есть готовое автоматизация заполнения реквизитов объектов в 1С.

  2. При программном изменении табличных частей или реквизитов: Если мы программно добавляем, удаляем или изменяем строки в табличной части, или изменяем другие реквизиты формы, которые не приводят к автоматическому взведению флага, нам следует явно установить Модифицированность = Истина;.

    Посмотрим на пример изменения табличной части документа:

    
    &НаСервере
    Процедура ЗаполнитьТоварыНаСервере()
        // Предположим, что Объект - это основной реквизит формы типа ДокументОбъект
        Объект.Товары.Очистить();
        НоваяСтрока = Объект.Товары.Добавить();
        НоваяСтрока.Номенклатура = Справочники.Номенклатура.НайтиПоНаименованию("ПримерНоменклатуры");
        НоваяСтрока.Количество = 10;
        НоваяСтрока.Цена = 100;
        НоваяСтрока.Сумма = НоваяСтрока.Количество * НоваяСтрока.Цена;
    
        // После программного изменения табличной части
        // устанавливаем признак модифицированности формы
        ЭтаФорма.Модифицированность = Истина;
    КонецПроцедуры
    

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

  3. При выполнении команд, которые изменяют данные, но не имеют флага "Изменяет сохраняемые данные": Если у нас есть команда формы, которая вызывает серверную процедуру для изменения данных объекта, но у самой команды в конфигураторе не установлен флаг "Изменяет сохраняемые данные", то флаг модифицированности формы не будет установлен автоматически. В этом случае, после выполнения логики изменения данных, нам также необходимо вручную установить ЭтаФорма.Модифицированность = Истина;.

Многие типовые конфигурации 1С активно используют ручную установку Модифицированность = Истина;, что подтверждает этот подход как стандартную практику при программном изменении данных.

Когда сбрасывать признак модифицированности?

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

Для сброса флага модифицированности, мы устанавливаем его в Ложь:

ЭтаФорма.Модифицированность = Ложь;

Обычно это делается в обработчиках событий, которые срабатывают после записи объекта, например, в ПриЗаписиНаСервере() или после вызова команды "Записать". Платформа также автоматически сбрасывает этот признак после успешной записи объекта, однако для реализации более сложной логики иногда требуется самодельный обработчик ПослеЗаписи, который будет выполнен гарантированно после завершения транзакции.

Дополнительные рекомендации и нюансы

Проанализируем некоторые важные аспекты, связанные с признаком модифицированности формы:

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

← На главную