Своя команда в правой кнопке мыши на табличной части формы
Содержание
Чтобы добавить команду в контекстное меню табличного поля, откройте форму в Конфигураторе, создайте команду на закладке Команды, перетащите её в узел Контекстное меню нужной таблицы на закладке Элементы и напишите обработчик в модуле формы. Ничего программировать «внутри меню» не нужно: меню собирается из тех элементов, которые вы туда положили.
Частая ошибка новичка: команду создали, а в меню её нет. Причина почти всегда одна — команда существует на форме, но не размещена в контекстном меню таблицы. Или размещена, но у меню включено автозаполнение, и оно ведёт себя не так, как ожидалось. Ниже — по порядку, с кодом и проверками.
Речь об управляемых формах платформы 8.3 (интерфейс «Такси»). В обычных формах устройство меню другое, и здесь они не рассматриваются.
Как устроено контекстное меню таблицы
У каждого табличного поля на управляемой форме есть три связанных объекта. Их стоит различать с самого начала, иначе дальше легко запутаться.
- 🧩 Табличное поле — сам элемент формы, показывающий список или табличную часть.
- 🧰 Командная панель — полоса кнопок над таблицей. Узел
Командная панельесть в дереве элементов под таблицей. - 🖱️ Контекстное меню — меню, которое открывается по правой кнопке мыши на строке. Узел
Контекстное менютоже лежит внутри таблицы.
Команда формы — отдельная сущность. Она имеет имя, заголовок, картинку, сочетание клавиш и действие. Одну и ту же команду можно положить и в командную панель, и в контекстное меню, и в меню «Ещё»: на форме это будут разные кнопки, а действие — одно.
Если у таблицы есть стандартные команды (добавить, копировать, изменить, удалить), они попадают в меню автоматически. Свои команды добавляются к ним.
Полезно понимать и расклад по типам таблиц:
| Таблица | Откуда берутся стандартные команды | Своё меню |
|---|---|---|
| Динамический список | Из свойств списка и объекта | Добавляется вручную |
| Табличная часть документа | Из типа табличной части | Добавляется вручную |
| Таблица значений на форме (реквизит формы) | Набор минимальный | Нужно самим создавать почти всё |
Подготовка: что открыть и что проверить
Перед работой убедитесь, что вы в Конфигураторе, а не в режиме предприятия: меню формы правится только там. Откройте нужный объект (справочник, документ, обработку), в ветке Формы откройте управляемую форму двойным щелчком.
Проверьте три вещи:
- Форма управляемая. У неё в редакторе есть закладки
Элементы,Команды,Реквизиты,Параметры. - Табличное поле уже стоит на форме и привязано к данным (свойство
Путь к данным). - База не открыта чужими пользователями с блокировкой метаданных. На своей копии или тестовой базе работать спокойнее.
Правьте форму в копии базы или хотя бы в расширении, если конфигурация типовая и стоит на поддержке. Прямая правка типовой формы ломает дальнейшие обновления: придётся сравнивать и объединять изменения при каждом релизе.
Создание команды формы
Команда нужна до того, как вы положите что-то в меню.
- Откройте закладку
Командыв редакторе формы. - Нажмите зелёный плюс (
Добавить). - В палитре свойств задайте
Имя, напримерОткрытьКарточкуКонтрагента. Имя — латиницей или кириллицей без пробелов, оно потом используется в коде. - В поле
Заголовокнапишите то, что увидит пользователь: «Открыть карточку контрагента». - В свойстве
Действиенажмите лупу и выберитеСоздать на клиенте. Платформа добавит процедуру в модуль формы и откроет её.
Дополнительно можно задать:
Подсказка— текст при наведении;Картинка— значок рядом с названием;Сочетание клавиш— быстрый вызов без мыши;Использование— условие, при котором команда вообще доступна (связь с функциональной опцией).
Команда пока никуда не добавлена. Если сохранить форму сейчас, пользователь её не увидит.
Размещение команды в контекстном меню
Самый короткий путь — перетаскивание.
- Перейдите на закладку
Элементы. - Разверните дерево табличного поля: под ним будут
Командная панель,Контекстное меню, колонки. - Перетащите команду с закладки
Командына узелКонтекстное меню.
В дереве под узлом появится кнопка. Её свойства (Заголовок, Картинка, Видимость, Доступность) относятся уже к кнопке, а не к самой команде, — это важное различие, к нему вернёмся в разделе про видимость.
Второй путь: правый щелчок по узлу Контекстное меню и пункт добавления. Откроется выбор: кнопка, группа, подменю, разделитель. Для кнопки выберите Команду формы и укажите свою.
Что делает автозаполнение
У узла Контекстное меню есть свойство Автозаполнение. Когда оно включено, платформа сама достраивает меню стандартными командами таблицы. Пока вы не вмешались, в дереве узел выглядит почти пустым, хотя на форме меню полное.
Практика такая:
- хотите добавить своё к стандартному — оставьте автозаполнение включённым и положите свою кнопку, платформа не удалит стандартные;
- хотите собрать меню с нуля, без стандартных пунктов, — выключите автозаполнение и добавьте нужные команды сами.
После выключения автозаполнения пропадут и «Копировать», и «Удалить», и поиск по списку. Верните то, что нужно, вручную: у таблицы есть стандартные команды, их можно перетащить из списка команд формы.
Группы и разделители
Если пунктов больше пяти-шести, меню превращается в простыню. Разделите их:
- 📂
Группа — подменю: пользователь видит один пункт со стрелкой и раскрывает его; - ➖
Разделитель: тонкая линия между логическими блоками (работа с данными, печать, служебные действия); - 🗂️
Группа — обычная: нужна для управления видимостью целого набора кнопок разом.
Обработчик команды в модуле формы
Когда вы выбрали Создать на клиенте, в модуле появилась заготовка:
&НаКлиенте
Процедура ОткрытьКарточкуКонтрагента(Команда)
// ваш код
КонецПроцедуры
Допустим, таблица называется Список, а в строке есть колонка Контрагент. Команда должна открыть карточку контрагента из текущей строки:
&НаКлиенте
Процедура ОткрытьКарточкуКонтрагента(Команда)
ТекущиеДанные = Элементы.Список.ТекущиеДанные;
Если ТекущиеДанные = Неопределено Тогда
Возврат;
КонецЕсли;
Если Не ЗначениеЗаполнено(ТекущиеДанные.Контрагент) Тогда
Возврат;
КонецЕсли;
ПоказатьЗначение(, ТекущиеДанные.Контрагент);
КонецПроцедуры
Что здесь важно:
Элементы.Список.ТекущиеДанныевозвращаетНеопределено, если таблица пуста или курсор стоит на группировке. Без проверки получите ошибку в момент клика.- Для динамического списка в
ТекущиеДанныедоступны только те колонки, которые попали в запрос списка. Нужного поля нет — добавьте его в список. ПоказатьЗначениеоткрывает форму объекта по ссылке, отдельно искать форму не нужно.
Работа с несколькими выделенными строками
Контекстное меню чаще всего вызывают на нескольких отмеченных строках. Тогда ТекущиеДанные не подходит, нужен массив выделенных:
&НаКлиенте
Процедура ОтметитьВыделенные(Команда)
Для Каждого ИдентификаторСтроки Из Элементы.Список.ВыделенныеСтроки Цикл
СтрокаСписка = Элементы.Список.ДанныеСтроки(ИдентификаторСтроки);
Если СтрокаСписка <> Неопределено Тогда
// действие над строкой
КонецЕсли;
КонецЦикла;
КонецПроцедуры
Для обычной таблицы значений и табличной части идентификаторы строк берутся тем же способом, а вот поиск строки идёт через Объект.ТабличнаяЧасть.НайтиПоИдентификатору(ИдентификаторСтроки).
Если действие требует сервера
Запись в базу, запросы, проведение документов выполняются на сервере. Обработчик на клиенте собирает данные и вызывает серверную процедуру:
&НаКлиенте
Процедура ПометитьНаУдаление(Команда)
Ссылки = Новый Массив;
Для Каждого ИдентификаторСтроки Из Элементы.Список.ВыделенныеСтроки Цикл
Ссылки.Добавить(ИдентификаторСтроки);
КонецЦикла;
Если Ссылки.Количество() = 0 Тогда
Возврат;
КонецЕсли;
ПометитьНаУдалениеНаСервере(Ссылки);
Элементы.Список.Обновить();
КонецПроцедуры
&НаСервереБезКонтекста
Процедура ПометитьНаУдалениеНаСервере(Ссылки)
// на сервере работаем со ссылками, а не со строками формы
КонецПроцедуры
В динамическом списке идентификатор строки — это ссылка на элемент, поэтому в серверную процедуру её можно передавать напрямую. Для табличной части это не так: там идентификатор — внутренний номер строки формы.
Видимость и доступность пункта
Здесь чаще всего путаются, потому что свойств два, и работают они по-разному.
| Свойство | Что делает | Где задаётся |
|---|---|---|
Видимость | Пункт скрыт совсем | У кнопки в меню |
Доступность | Пункт виден, но серый | У кнопки и у самой команды |
Использование команды | Команда существует только при условии | У команды |
Если нужно скрыть пункт всегда — снимите флажок Видимость у кнопки в дереве элементов. Если «в зависимости от ситуации», управляйте из кода.
Динамическое управление
Типичный сценарий: пункт «Провести» нужен только для непроведённых документов. Управляем в обработчике события ПриАктивизацииСтроки у таблицы:
&НаКлиенте
Процедура СписокПриАктивизацииСтроки(Элемент)
ТекущиеДанные = Элементы.Список.ТекущиеДанные;
Доступно = ТекущиеДанные <> Неопределено И Не ТекущиеДанные.Проведен;
Команды.ОткрытьКарточкуКонтрагента.Доступность = Доступно;
КонецПроцедуры
Другой вариант — работать с кнопкой напрямую: Элементы.СписокКонтекстноеМенюОткрытьКарточку.Видимость = Ложь;. Имя кнопки состоит из имени таблицы, слова «КонтекстноеМеню» и имени команды (по умолчанию так называет платформа при перетаскивании), но проверьте реальное имя в дереве элементов — оно редактируется.
Команда формы и её кнопки в разных местах — разные объекты. Выключив Доступность у команды, вы погасите все кнопки сразу. Выключив у кнопки — только одну.
Права и функциональные опции
Видимость можно привязать не к коду, а к настройкам:
- у команды в
Использованиеукажите функциональную опцию — пункт появится, только если опция включена; - роли пользователя ограничивают доступ к объектам, а не к пункту меню: если у пользователя нет права на изменение, обработчик на записи упадёт с ошибкой, хотя кнопка видна. Проверяйте права в коде через
ПравоДоступаили скрывайте пункт по итогам проверки.
Если меню ведёт себя не так
Разберём ситуации, которые встречаются на практике.
Контекстное меню таблицы. Проверьте дерево на закладке Элементы: кнопка должна лежать именно под нужной таблицей, а не в командной панели формы.Доступность у кнопки или команды, либо код его выключает. Найдите в модуле формы строки .Доступность = и посмотрите, при каком условии они срабатывают.Действие, или процедура осталась пустой заготовкой. Откройте свойства команды и посмотрите значение поля Действие.ТекущиеДанные нет нужной колонки. Для динамического списка добавьте поле в настройки списка и убедитесь, что оно подключено к запросу.Ещё две ловушки, которые легко пропустить:
- 🔁 Закладка не обновилась. Если после правки форму в режиме предприятия не обновили, меню остаётся прежним. Закройте форму и откройте заново, при необходимости перезапустите сеанс.
- 🧱 Расширение и типовая форма. В расширении можно добавлять команды и элементы в типовую форму, а менять порядок и свойства чужих элементов можно только в пределах возможностей расширения. Если пункт не появляется, проверьте, подключено ли расширение и применён ли к нему
Обновить конфигурацию БД.
Как проверить, что всё работает
Сохраните изменения и запустите 1С:Предприятие в режиме отладки (F5). Откройте форму и пройдите по короткому списку.
Если чего-то не хватает, возвращайтесь в Конфигуратор. Исправлять придётся то же самое: чаще всего проблема в одном из трёх мест — размещение, автозаполнение, обработчик.
Частые вопросы
Можно ли добавить пункт в контекстное меню поля ввода, а не таблицы?
Контекстное меню в дереве элементов, и добавляются команды так же — перетаскиванием.Чем контекстное меню отличается от командной панели таблицы?
Как добавить разделитель между пунктами?
Контекстное меню, добавление, выбор «Разделитель». Затем перетащите его между нужными кнопками.Можно ли сделать меню разным для разных строк?
ПриАктивизацииСтроки: по данным текущей строки включайте или отключайте Доступность и Видимость нужных пунктов.Нужно ли для этого расширение?
Почему после добавления команды форма открывается медленнее?
ПриАктивизацииСтроки, особенно если он ходит на сервер при каждом переходе по строкам.