В процессе разработки интерфейсов на управляемых формах 1С часто возникает задача визуального выделения данных. Например, необходимо подсветить статус номенклатуры, наличие спецификации или отклонение по стоимости. Одной из самых частых трудностей, с которой сталкиваются разработчики, является попытка связать цвет текста с переменной, существующей только в коде модуля, а не в данных формы. В этой статье мы подробно разберем, как правильно реализовать динамическую раскраску ячеек, проанализируем типичные ошибки и выясним, как сделать код эффективным.
Рассмотрим ситуацию, когда в коде на сервере вычисляется некое значение (например, переменная Цвет), и в зависимости от него нужно покрасить текст в колонке «Спецификация». Основная ошибка заключается в попытке передать эту переменную напрямую в УсловноеОформление. Механизм условного оформления работает на стороне платформы и «видит» только те данные, которые содержатся в реквизитах формы или объекта. Локальные переменные модуля или результаты функций общего модуля для него недоступны.
Проанализируем ситуацию: когда вы создаете ЭлементОтбораКомпоновкиДанных, вы указываете ЛевоеЗначение как Новый ПолеКомпоновкиДанных("ПутьКДанным"). Этот путь должен указывать на колонку, которая физически присутствует в вашей таблице. Если данных в таблице нет, условие никогда не выполнится.
Чтобы раскраска заработала, нам необходимо «приземлить» вычисляемый цвет в данные каждой строки табличной части. Разберем по шагам, что для этого нужно сделать:
Запасы) необходимо добавить новый реквизит. Назовем его СостояниеЦвета (тип Число).СостояниеЦвета соответствующий код (1 для черного, 2 для красного, 3 для зеленого).Посмотрим на пример кода для заполнения данных в табличной части:
Для Каждого СтрокаЗапасов Из Объект.Запасы Цикл
// Вызываем ваш общий модуль или выполняем расчет на месте
РезультатРасчета = МойОбщийМодуль.ОпределитьСтатус(СтрокаЗапасов.Спецификация);
Если РезультатРасчета = "ВНаличии" Тогда
СтрокаЗапасов.СостояниеЦвета = 1; // Зеленый
ИначеЕсли РезультатРасчета = "Отсутствует" Тогда
СтрокаЗапасов.СостояниеЦвета = 2; // Красный
КонецЕсли;
КонецЦикла;
Теперь, когда у нас есть данные в каждой строке, мы можем настроить правила оформления. Важно помнить: если вы добавляете элементы оформления программно, их нужно добавлять один раз (например, в процедуре ПриСозданииНаСервере) либо очищать коллекцию перед повторным добавлением, чтобы не раздувать УсловноеОформление.Элементы.
Выясним, как правильно сконфигурировать элемент оформления для одного цвета:
// 1. Очищаем старые правила, если это необходимо
УсловноеОформление.Элементы.Очистить();
// 2. Создаем правило для КРАСНОГО цвета (СостояниеЦвета = 2)
ЭлементУО = УсловноеОформление.Элементы.Добавить();
// Указываем, ЧТО мы хотим оформить (ЦветТекста)
ЭлементУО.Оформление.УстановитьЗначениеПараметра("ЦветТекста", WebЦвета.Красный);
// Указываем, КАКОЕ поле на форме будет раскрашено
ОформляемоеПоле = ЭлементУО.Поля.Элементы.Добавить();
ОформляемоеПоле.Поле = Новый ПолеКомпоновкиДанных("ЗапасыСпецификация"); // Имя элемента на форме
// Настраиваем отбор: когда СостояниеЦвета равно 2
ЭлементОтбора = ЭлементУО.Отбор.Элементы.Добавить(Тип("ЭлементОтбораКомпоновкиДанных"));
ЭлементОтбора.ЛевоеЗначение = Новый ПолеКомпоновкиДанных("Объект.Запасы.СостояниеЦвета");
ЭлементОтбора.ВидСравнения = ВидСравненияКомпоновкиДанных.Равно;
ЭлементОтбора.ПравоеЗначение = 2;
Как отмечалось в обсуждении, для каждого цвета необходимо создать отдельный элемент условного оформления. Если у вас 3 возможных цвета, у вас будет 3 элемента в коллекции УсловноеОформление.Элементы. Рассмотрим подробнее структуру добавления нескольких правил:
// Массив настроек для удобства
ЦветаСтатусов = Новый Структура;
ЦветаСтатусов.Вставить("Зеленый", 1);
ЦветаСтатусов.Вставить("Красный", 2);
ЦветаСтатусов.Вставить("Оранжевый", 3);
Для Каждого Вариант Из ЦветаСтатусов Цикл
ЭлементУО = УсловноеОформление.Элементы.Добавить();
// Установка цвета в зависимости от ключа структуры
Если Вариант.Ключ = "Зеленый" Тогда
Цвет = WebЦвета.Зеленый;
ИначеЕсли Вариант.Ключ = "Красный" Тогда
Цвет = WebЦвета.Красный;
Иначе
Цвет = WebЦвета.Оранжевый;
КонецЕсли;
ЭлементУО.Оформление.УстановитьЗначениеПараметра("ЦветТекста", Цвет);
// Поле, которое красим
ПолеОформления = ЭлементУО.Поля.Элементы.Добавить();
ПолеОформления.Поле = Новый ПолеКомпоновкиДанных("ЗапасыСпецификация");
// Условие по скрытому реквизиту
Отбор = ЭлементУО.Отбор.Элементы.Добавить(Тип("ЭлементОтбораКомпоновкиДанных"));
Отбор.ЛевоеЗначение = Новый ПолеКомпоновкиДанных("Объект.Запасы.СостояниеЦвета");
Отбор.ВидСравнения = ВидСравненияКомпоновкиДанных.Равно;
Отбор.ПравоеЗначение = Вариант.Значение;
КонецЦикла;
Проанализируем несколько критических моментов, которые помогут избежать ошибок в будущем:
ПолеКомпоновкиДанных для отбора (ЛевоеЗначение) всегда пишется путь к данным через точку (Объект.ИмяТЧ.ИмяРеквизита). В ОформляемоеПоле.Поле пишется имя элемента (колонки), как оно названо в дереве элементов формы.WebЦвета.Красный лучше использовать системные цвета, например ЦветаСтиля.ОсобыйТекст. Это гарантирует, что ваш текст останется читаемым, если пользователь переключится на темную тему оформления.УсловноеОформление.Элементы.Резюме: Чтобы раскраска работала корректно, всегда передавайте признак для оформления в данные (реквизиты строки), настраивайте правила один раз при создании формы и следите за соответствием имен полей и путей к данным.