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