При разработке интерфейсов на управляемых формах 1С часто возникает задача: связать несколько таблиц так, чтобы при выборе строки в первой или второй таблице в третьей зависимой таблице сразу отображались детальные данные. Однако стандартное событие таблицы ПриАктивизацииСтроки срабатывает только тогда, когда внутри самой таблицы меняется активная строка. Если в таблице всего одна строка или пользователь переключает фокус между таблицами, щелкая по уже выбранной строке, платформа 1С не инициирует событие, так как значение свойства ТекущаяСтрока формально не изменилось.
В платформе 1С:Предприятие 8.3 у элементов управляемой формы отсутствуют штатные события получения и потери фокуса ввода, а у формы нет отдельного события при смене активного элемента. Разберем несколько способов обойти данное ограничение и гарантированно отслеживать выбор пользователем нужной таблицы.
Проанализируем механику работы события ПриАктивизацииСтроки. Событие генерируется в момент, когда строка переходит из неактивного состояния в активное. Если при активации строки в первой таблице программно сбросить фокус и выделение во второй таблице, то при последующем клике пользователя по второй таблице платформа зафиксирует новую активацию строки и вызовет нужный обработчик.
Для реализации этого подхода выполним следующие шаги:
ПриАктивизацииСтроки.Посмотрим на пример клиентского кода:
&НаКлиенте
Процедура ТЗ1ПриАктивизацииСтроки(Элемент)
// Сбрасываем выделение во второй таблице
Элементы.ТЗ2.ВыделенныеСтроки.Очистить();
Элементы.ТЗ2.ТекущаяСтрока = Неопределено;
// Обновляем зависимые данные
ОбработатьВыборСтроки(Элемент);
КонецПроцедуры
&НаКлиенте
Процедура ТЗ2ПриАктивизацииСтроки(Элемент)
// Сбрасываем выделение в первой таблице
Элементы.ТЗ1.ВыделенныеСтроки.Очистить();
Элементы.ТЗ1.ТекущаяСтрока = Неопределено;
// Обновляем зависимые данные
ОбработатьВыборСтроки(Элемент);
КонецПроцедуры
&НаКлиенте
Процедура ОбработатьВыборСтроки(Элемент)
Если Элемент.ТекущиеДанные = Неопределено Тогда
Возврат;
КонецЕсли;
// Заполняем третью таблицу по выбранному объекту
ТекущийДокумент = Элемент.ТекущиеДанные.Док;
ЗаполнитьДанныеТЗ3(ТекущийДокумент);
КонецПроцедуры
Этот вариант является наиболее простым, не создает лишней нагрузки на клиентское приложение и работает полностью на штатных механизмах платформы.
Если требуется непрерывно контролировать, в каком именно элементе формы находится пользователь, можно использовать фоновый опрос формы на клиенте с помощью метода ПодключитьОбработчикОжидания.
Разберем логику работы обработчика ожидания:
ЭтаФорма.ТекущийЭлемент с сохраненным ранее значением. Если фокус перешел на другую таблицу или ее колонку, обновим данные и сохраним новое состояние.Рассмотрим пример реализации:
&НаКлиенте
Перем ПредыдущийЭлемент;
&НаКлиенте
Процедура ПриОткрытии(Отказ)
ПодключитьОбработчикОжидания("ПроверитьСменуФокуса", 0.2);
КонецПроцедуры
&НаКлиенте
Процедура ПроверитьСменуФокуса()
Текущий = ЭтаФорма.ТекущийЭлемент;
Если Текущий = Неопределено Или Текущий = ПредыдущийЭлемент Тогда
Возврат;
КонецЕсли;
Если Текущий = Элементы.ТЗ1 Или Текущий.Родитель = Элементы.ТЗ1 Тогда
ПредыдущийЭлемент = Текущий;
ОбработатьВыборСтроки(Элементы.ТЗ1);
ИначеЕсли Текущий = Элементы.ТЗ2 Или Текущий.Родитель = Элементы.ТЗ2 Тогда
ПредыдущийЭлемент = Текущий;
ОбработатьВыборСтроки(Элементы.ТЗ2);
КонецЕсли;
КонецПроцедуры
Важно: постоянный опрос через обработчик ожидания создает небольшую дополнительную нагрузку на клиентский сеанс, поэтому данный способ рекомендуется применять только тогда, когда сброс выделения через обработчики строк по каким-то причинам не подходит.
Еще один надежный способ зафиксировать действие пользователя — перевести взаимодействие из пассивного выделения строки в явное нажатие.
Для этого в таблицах на форме настраивают ключевую колонку (например, представление документа):
Вид в значение ПолеНадписи или ПолеВвода.Гиперссылка (устанавливаем в значение Истина).Нажатие для данного поля.Событие Нажатие гарантированно срабатывает при каждом клике пользователя по ячейке, даже если строка уже была активна до этого.
В специфических сценариях (например, когда требуется точный перехват фокуса для управления раскладкой клавиатуры или оборудования) применяют внешние компоненты, скомпилированные по технологии Native API. Компонента через системные хуки отслеживает фокус оконных элементов и отправляет в 1С внешнее событие с помощью метода ВнешнееСобытие формы.
Однако для типовых прикладных задач управляемых форм использование внешних компонент избыточно и усложняет кроссплатформенную поддержку (работа в веб-клиенте или под управлением Linux).
Для корректного отслеживания переключения между несколькими таблицами значений оптимальным решением является программная очистка выделения ВыделенныеСтроки.Очистить() в соседних таблицах при срабатывании ПриАктивизацииСтроки. Это восстанавливает чувствительность события и позволяет точно синхронизировать отображение зависимых данных в интерфейсе.