Как изменить цвет текущей строки в списке по нажатию кнопки в 1С:УТ 10.3?

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

В обычных формах 1С (платформа 8.2 и 8.3, конфигурация УТ 10.3) задача динамического изменения оформления строк отличается от управляемых форм. Прямое управление цветом в обработчике нажатия кнопки невозможно, так как оформление строк списка определяется декларативно в специальных системных событиях. В данной статье мы разберем, как правильно реализовать «подсветку» строк при нажатии кнопки, рассмотрим два способа хранения состояния и проанализируем технические нюансы работы с коллекцией ОформленияСтрок.

Суть проблемы и механизм отрисовки

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

  1. Изменение состояния: При нажатии кнопки мы фиксируем, что строка должна стать красной (меняем реквизит в базе или значение в переменной формы).
  2. Отрисовка: Мы принудительно обновляем список, чтобы сработало событие ПриПолученииДанных, где система, согласно нашему состоянию, «покрасит» строку.

Способ 1. Использование реквизита объекта (через базу данных)

Этот метод часто выбирают новички. Он заключается в создании дополнительного реквизита в справочнике или документе (например, ЦветФона с типом Булево). Рассмотрим, как реализовать этот подход правильно.

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


Процедура ДействияФормыВыделить(Кнопка)
    // Получаем текущие данные из списка
    ТекущиеДанные = ЭлементыФормы.СправочникСписок.ТекущиеДанные;
    
    Если ТекущиеДанные = Неопределено Тогда
        Возврат;
    КонецЕсли;

    // Получаем объект для изменения реквизита
    ОбъектСсылка = ТекущиеДанные.Ссылка;
    Объект = ОбъектСсылка.ПолучитьОбъект();
    
    // Инвертируем признак подсветки
    Объект.ЦветФона = НЕ Объект.ЦветФона;
    
    Попытка
        Объект.Записать();
        // Принудительно заставляем список перерисоваться
        ЭлементыФормы.СправочникСписок.Обновить();
    Исключение
        Сообщить("Не удалось записать изменения!");
    КонецПопытки;
КонецПроцедуры

Теперь проанализируем, как реализовать саму раскраску. Важно помнить, что процедура ПриПолученииДанных работает сразу с массивом строк, которые видны на экране. Мы должны пройтись циклом по коллекции ОформленияСтрок и проверить значение реквизита ЦветФона для каждой строки через свойство ДанныеСтроки.


Процедура СправочникСписокПриПолученииДанных(Элемент, ОформленияСтрок)
    Для Каждого ОформлениеСтроки Из ОформленияСтрок Цикл
        // Проверяем значение реквизита в данных текущей строки
        Если ОформлениеСтроки.ДанныеСтроки.ЦветФона Тогда
            ОформлениеСтроки.ЦветФона = WebЦвета.Красный;
        Иначе
            // Возвращаем стандартный цвет, если флаг снят
            ОформлениеСтроки.ЦветФона = WebЦвета.Белый;
        КонецЕсли;
    КонецЦикла;
КонецПроцедуры

Способ 2. Оптимизированный (без изменения метаданных)

Создание реквизита в базе данных ради цвета — не всегда оправданное решение, так как это увеличивает размер таблиц и создает лишнюю нагрузку при записи. Рассмотрим альтернативный вариант: хранение списка «подсвеченных» строк в переменной формы.

Выясним, как это работает. В модуле формы объявим переменную СписокВыделенныхСсылок типа Соответствие. При нажатии кнопки мы будем добавлять или удалять ссылку из этого соответствия.


Перем СписокВыделенныхСсылок; // Тип Соответствие

Процедура ПриОткрытии()
    СписокВыделенныхСсылок = Новый Соответствие;
КонецПроцедуры

Процедура ДействияФормыВыделить(Кнопка)
    ТекущаяСсылка = ЭлементыФормы.СправочникСписок.ТекущиеДанные.Ссылка;
    
    // Если ссылка уже есть в списке — удаляем, если нет — добавляем
    Если СписокВыделенныхСсылок.Получить(ТекущаяСсылка) = Неопределено Тогда
        СписокВыделенныхСсылок.Вставить(ТекущаяСсылка, Истина);
    Иначе
        СписокВыделенныхСсылок.Удалить(ТекущаяСсылка);
    КонецЕсли;
    
    // Обновляем визуальное отображение
    ЭлементыФормы.СправочникСписок.Обновить();
КонецПроцедуры

В обработчике ПриПолученииДанных логика проверки немного изменится: вместо обращения к реквизиту объекта мы будем проверять наличие ссылки в нашем соответствии.


Процедура СправочникСписокПриПолученииДанных(Элемент, ОформленияСтрок)
    Для Каждого ОформлениеСтроки Из ОформленияСтрок Цикл
        Если СписокВыделенныхСсылок.Получить(ОформлениеСтроки.ДанныеСтроки.Ссылка) <> Неопределено Тогда
            ОформлениеСтроки.ЦветФона = WebЦвета.ТусклоРозовый;
        КонецЕсли;
    КонецЦикла;
КонецПроцедуры

Важные технические нюансы

Разберем основные моменты, которые влияют на производительность и корректность работы формы:

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

← На главную