К статье
Практический материал

Разработка и Конфигурация · 11 мин

Как обратиться к реквизиту формы в 1С

Как обратиться к реквизиту формы в 1С: обращение через ЭтаФорма, Объект, реквизиты объекта и формы, примеры кода, типичные ошибки и отличия клиент-серверных контекстов.

Обращение к реквизиту формы — одна из базовых задач при доработке управляемых форм в 1С:Предприятие 8.3. Разработчику нужно считать или изменить значение реквизита, созданного в конфигураторе на закладке «Реквизиты» формы, либо получить данные самого объекта (документа, справочника), который форма редактирует. Способ обращения зависит от того, где находится реквизит: в данных объекта или среди реквизитов самой формы.

Ключевая путаница у начинающих разработчиков возникает из-за того, что в управляемой форме существуют два разных хранилища данных. Основной реквизит формы типа «ДанныеФормыСтруктура» (обычно называется «Объект») содержит данные редактируемого объекта базы, а дополнительные реквизиты формы — служебные значения, которые в базу не записываются. К каждому из них обращаются по-разному.

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

Различие между реквизитом формы, реквизитом объекта и элементом формы

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

Реквизит формы — это дополнительное данное, созданное разработчиком в редакторе формы (панель «Реквизиты» рядом с деревом элементов). Оно живёт только в памяти, пока форма открыта, и в базу не записывается. Типичные примеры: признак «ПоказыватьАрхив», промежуточная сумма, выбранное значение отбора.

Элемент формы — это визуальный объект: поле ввода, кнопка, таблица, надпись. Элемент лишь отображает реквизит через свойство «ПутьКДанным». Обращение к элементу нужно, когда требуется изменить видимость, доступность, заголовок или оформление, а не само значение.

Обращение к реквизиту формы по имени

Внутри модуля формы к реквизиту формы обращаются напрямую по имени, потому что реквизиты формы являются свойствами объекта УправляемаяФорма. Оба варианта ниже работают одинаково:

// Чтение значения реквизита формы "ТекущийСклад"

ВыбранныйСклад = ТекущийСклад;

// То же самое через ЭтаФорма

ВыбранныйСклад = ЭтаФорма.ТекущийСклад;

// Запись значения

ТекущийСклад = Справочники.Склады.НайтиПоНаименованию("Основной");

Явное обращение через ЭтаФорма делает код читаемее и снижает риск конфликта имён с локальными переменными процедуры. Если в процедуре объявлена переменная с тем же именем, что и реквизит формы, обращение без ЭтаФорма вернёт локальную переменную — это частая причина трудноуловимых ошибок.

Из внешнего кода (модуль объекта, общий модуль, другая форма) реквизит формы недоступен напрямую. Форма — это клиентский объект, и обращаться к её реквизитам с сервера или из другого объекта можно только через открытый программный интерфейс: экспортные процедуры и функции модуля формы, либо через оповещения.

Обращение к реквизитам объекта через «Объект»

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

&НаКлиенте

Процедура ПриИзмененииКоличества(Элемент)

// Реквизит документа "Количество"

Объект.Сумма = Объект.Количество * Объект.Цена;

КонецПроцедуры

Обращение к табличной части объекта выполняется так же — через Объект и имя табличной части:

// Перебор строк табличной части "Товары"

Для Каждого Строка Из Объект.Товары Цикл

Строка.Сумма = Строка.Количество * Строка.Цена;

КонецЦикла;

Важно понимать: на форме «Объект» — это не объект базы данных, а объект типа ДанныеФормыСтруктура. У него нет методов записи (Записать(), Провести() вызвать нельзя напрямую). Для записи используется метод формы Записать(), который преобразует данные формы в объект и сохраняет его.

Обращение к элементам формы через «Элементы»

Если задача — не прочитать значение, а управлять отображением, обращение идёт через коллекцию Элементы. По имени элемента (не реквизита!) доступны его свойства:

// Скрыть поле ввода

Элементы.Комментарий.Видимость = Ложь;

// Сделать поле только для чтения

Элементы.СуммаДокумента.ТолькоПросмотр = Истина;

// Изменить заголовок кнопки

Элементы.КнопкаСохранить.Заголовок = "Сохранить и закрыть";

Имена элементов и имена реквизитов могут совпадать, но это разные сущности. Если элемента с указанным именем нет, обращение вернёт Неопределено, а попытка установить свойство вызовет ошибку. Поэтому при динамическом формировании имён полезна проверка:

Элемент = Элементы.Найти("Поле_" + ИмяРеквизита);

Если Элемент <> Неопределено Тогда

Элемент.Видимость = Ложь;

КонецЕсли;

Типичные ошибки
01
Обращение к элементу формы по имени реквизита — имена могут не совпадать, и код падает с ошибкой «Поле объекта не обнаружено»
02
Попытка вызвать Объект.Записать() на форме — у ДанныеФормыСтруктура нет такого метода, нужно использовать метод формы Записать()
03
Обращение к реквизиту формы из модуля объекта или общего модуля — реквизиты формы доступны только в модуле самой формы
04
Использование локальной переменной с именем реквизита — обращение без ЭтаФорма возвращает переменную, а не реквизит

Работа в клиентских и серверных процедурах

Директивы компиляции &НаКлиенте и &НаСервере влияют на то, какие данные доступны. В клиентской процедуре доступны реквизиты формы простых типов и данные объекта (в виде ДанныеФормыСтруктура). Можно свободно читать и менять Объект.Реквизит и реквизиты формы — изменения отобразятся на форме автоматически.

В серверной процедуре контекст формы передаётся на сервер, и там доступен тот же синтаксис. Но если нужно получить «настоящий» объект базы данных (например, чтобы вызвать его методы или обратиться к непереданным на форму данным), используется преобразование:

&НаСервере

Процедура ЗаполнитьПоДаннымОбъекта()

ДокументОбъект = РеквизитФормыВЗначение("Объект");

// Теперь доступны методы объекта

ДокументОбъект.Заполнить(ДокументОбъект.ДокументОснование);

ЗначениеВРеквизитФормы(ДокументОбъект, "Объект");

КонецПроцедуры

Методы РеквизитФормыВЗначение и ЗначениеВРеквизитФормы — это «мост» между данными формы и объектом базы. После обратного преобразования форма автоматически отобразит обновлённые данные. Учтите: эти операции затратны по производительности, особенно для объектов с большими табличными частями, поэтому не стоит вызывать их в цикле.

bsl
&НаСервере
Функция ПолучитьСсылкуТекущегоОбъекта()
    Возврат РеквизитФормыВЗначение("Объект").Ссылка;
КонецФункции

Обращение к реквизитам извне и программное создание реквизитов

Иногда реквизит нужно добавить на форму программно — например, когда состав полей зависит от настроек. Для этого служит метод формы ИзменитьРеквизиты, доступный только в серверном контексте:

&НаСервере

Процедура ДобавитьРеквизитПрограммно()

Добавляемые = Новый Массив;

Добавляемые.Добавить(Новый РеквизитФормы("СлужебныйПризнак",

Новый ОписаниеТипов("Булево"), "", "Служебный признак"));

ИзменитьРеквизиты(Добавляемые);

// Теперь можно обращаться: ЭтаФорма.СлужебныйПризнак

КонецПроцедуры

После добавления реквизита обращение к нему ничем не отличается от обычного. Если нужно отобразить его на форме, дополнительно создаётся элемент через Элементы.Добавить с привязкой через ПутьКДанным.

Для обращения к данным формы из другой формы корректный способ — передать значение через параметры при открытии (Параметры формы) или через механизм Оповестить / ОбработкаОповещения. Прямое обращение вида Форма.Реквизит технически возможно, если получен объект формы, но делает решение хрупким: форма может быть закрыта, и обращение вызовет ошибку.

Маршрут решения

Как выбрать способ обращения

Нужно значение служебного поля, созданного в редакторе формыОбращайтесь напрямую: ЭтаФорма.ИмяРеквизита
Нужно поле документа или справочника, хранящееся в базеИспользуйте Объект.ИмяРеквизита
Нужно скрыть, заблокировать или переименовать поле на формеРаботайте через Элементы.ИмяЭлемента
Нужны методы объекта или данные вне формыВ серверной процедуре используйте РеквизитФормыВЗначение("Объект")
Реквизит появляется динамически по настройкамСоздайте его методом ИзменитьРеквизиты в серверной процедуре

Проверка результата и ограничения

После написания кода проверьте его в трёх режимах: при открытии существующего объекта, при создании нового и при работе в тонком клиенте (если решение используется не только в веб-клиенте). Ошибки обращения к реквизитам чаще всего проявляются как «Поле объекта не обнаружено (ИмяРеквизита)» — это значит, что обращение идёт не к тому объекту или реквизит ещё не создан.

Полезная практика — проверять наличие реквизита формы перед обращением, если код универсальный. Прямого метода «ЕстьРеквизит» у формы нет, но можно получить список через ПолучитьРеквизиты() и проверить наличие по имени в цикле, либо обернуть обращение в попытку-исключение.

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

Контрольные точки

Как проверить результат

Обращение к реквизиту формы
Норма

Значение читается и изменяется, форма обновляет отображение

Тревожный признак

Ошибка «Поле объекта не обнаружено» — проверьте имя и контекст

Изменение реквизита объекта
Норма

После изменения Объект.Реквизит поле на форме показывает новое значение

Тревожный признак

Значение изменилось в переменной, но не на форме — изменена локальная копия

Серверная процедура
Норма

РеквизитФормыВЗначение возвращает объект, изменения видны после ЗначениеВРеквизитФормы

Тревожный признак

Данные объекта изменены, но форма показывает старые — пропущен обратный вызов ЗначениеВРеквизитФормы

Итог

Что важно запомнить

Реквизит формы читается напрямую по имени (ЭтаФорма.Имя), реквизит объекта — через Объект.Имя, элемент управления — через Элементы.Имя. Для работы с объектом базы на сервере используется РеквизитФормыВЗначение. Явное обращение через ЭтаФорма защищает от конфликтов имён с локальными переменными.

Часто задаваемые вопросы

Чем отличается ЭтаФорма.Реквизит от Объект.Реквизит?

Первый вариант обращается к реквизиту самой формы — служебному данному, которое не хранится в базе. Второй обращается к реквизиту редактируемого объекта (документа, справочника) через основной реквизит формы, и его значение сохраняется в базу при записи.

Почему возникает ошибка «Поле объекта не обнаружено»?

Чаще всего обращение идёт по неверному имени, к неправильному объекту (например, к Объект вместо ЭтаФорма) или к элементу формы, который ещё не создан. Проверьте точное имя в редакторе формы и контекст выполнения процедуры.

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

Напрямую — не рекомендуется. Передайте значение через параметры при открытии формы, через структуру в ОписаниеОповещения или механизм Оповестить/ОбработкаОповещения. Если форма получена как объект, технически доступ возможен, но зависит от её открытости.

Можно ли обратиться к реквизиту формы из модуля объекта?

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

Как программно узнать, существует ли реквизит на форме?

Используйте метод ПолучитьРеквизиты() — он возвращает массив реквизитов формы, в котором можно найти нужный по свойству Имя. Альтернатива — обернуть обращение в конструкцию Попытка...Исключение.

Работает ли обращение к реквизитам формы в расширении конфигурации?

Да, в заимствованном модуле формы расширения синтаксис полностью совпадает: ЭтаФорма.ИмяРеквизита, Объект.ИмяРеквизита, Элементы.ИмяЭлемента. Дополнительно в расширении можно создавать собственные реквизиты формы и обращаться к ним так же.