Как в отчете 1С 7.7 изменить цвет ячейки в зависимости от условия?

Программист 1С v7.7
← На главную

При формировании отчетов в 1С 7.7 часто возникает задача выделить определенные данные цветом — например, подсветить красным отрицательные значения или зеленым — выполненные показатели. Однако попытка изменить цвет ячейки программно может привести к неожиданным результатам, таким как появление пустых строк и сдвиг всего отчета. Рассмотрим, почему так происходит и как правильно реализовать условное форматирование.

Проблема, с которой часто сталкиваются разработчики, заключается в неверном порядке действий. Попытка обратиться к ячейке по ее координатам из макета до того, как эта ячейка была фактически выведена в итоговую таблицу, приводит к ошибке. Давайте разберем эту ситуацию по шагам и найдем правильное решение.

Анализ проблемы: почему появляются пустые строки?

Исходный код автора выглядел примерно так: в цикле перебора данных сначала предпринималась попытка изменить цвет ячейки, а затем выводилась секция.


// Неправильный код
Цикл
    // ...
    // Попытка изменить цвет ячейки ДО ее вывода
    ВыбОбласть = Таб.Область("R9C16");
    ВыбОбласть.ЦветТекста(100,100,100);
    // ...
    // Вывод секции
    Таб.ВывестиСекцию("Строка");
КонецЦикла;

Причина странного поведения с добавлением пустых строк кроется в механизме работы объекта "Таблица". Когда мы обращаемся к области таблицы через метод Таб.Область("R9C16") или Таб.Область(9, 16), мы работаем с уже сформированным отчетом. Если на момент обращения в отчете еще нет строки с номером 9, платформа 1С автоматически расширяет таблицу до указанной строки, создавая недостающие пустые строки.

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

Ключевой вывод: Координаты ячейки в макете (например, "R9C16") и ее координаты в итоговом, выведенном отчете — это разные вещи. В итоговом отчете номер строки зависит от того, сколько строк (заголовок, шапка, предыдущие данные) уже было выведено.

Решение 1: Правильный порядок действий

Чтобы избежать проблемы, необходимо строго следовать правилу: сначала выводим данные в отчет, и только потом изменяем их форматирование.

Разберем алгоритм по шагам:

  1. Внутри цикла, после подготовки всех данных для вывода, сначала выполняем метод Таб.ВывестиСекцию("Секция"). Этот метод добавляет новую строку в конец формируемого отчета.
  2. Сразу после вывода секции нам нужно узнать номер строки, которую мы только что добавили. Для этого идеально подходит метод Таб.ВысотаТаблицы(). Он вернет общее количество строк в отчете, что и будет номером последней выведенной строки.
  3. Теперь, зная точный номер строки и номер нужной колонки, мы можем безопасно получить объект ячейки через метод Таб.Область().
  4. Получив объект ячейки, применяем к нему методы форматирования, такие как ЦветТекста(R, G, B) или ЦветФона(R, G, B).

Посмотрим, как будет выглядеть исправленный код:


Таб = СоздатьОбъект("Таблица");
Таб.ИсходнаяТаблица("Сформировать");
Таб.ВывестиСекцию("Заголовок");
// ...

// Начало цикла по данным
Цикл
    // ... здесь мы подготавливаем переменные для вывода в секцию ...

    // 1. СНАЧАЛА выводим секцию в итоговую таблицу
    Таб.ВывестиСекцию("Строка");

    // 2. Проверяем условие, по которому нужно изменить цвет
    Если УсловиеДляОкрашивания = 1 Тогда
        
        // 3. Получаем номер только что выведенной строки
        НомерТекущейСтроки = Таб.ВысотаТаблицы();
        
        // Допустим, нам нужно покрасить ячейку в 16-й колонке
        НомерНужнойКолонки = 16;

        // 4. Получаем объект ячейки по ее реальным координатам в отчете
        ВыбОбласть = Таб.Область(НомерТекущейСтроки, НомерНужнойКолонки, НомерТекущейСтроки, НомерНужнойКолонки);
        
        // 5. Применяем форматирование
        // Устанавливаем красный цвет текста (R=255, G=0, B=0)
        ВыбОбласть.ЦветТекста(255, 0, 0); 
        // Устанавливаем светло-желтый цвет фона (R=255, G=255, B=150)
        ВыбОбласть.ЦветФона(255, 255, 150);
        
    КонецЕсли;

КонецЦикла;

Таб.ТолькоПросмотр(1);
Таб.Показать("Мой отчет", "");

Важный момент: Метод Область() может принимать как строковые координаты ("R5C16"), так и числовые (5, 16). Использование числовых координат с динамическим расчетом номера строки через Таб.ВысотаТаблицы() является наиболее надежным способом.

Решение 2: Альтернативный и более производительный способ

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

Идея заключается в том, чтобы заранее подготовить в макете отчета несколько вариантов одной и той же секции с разным оформлением.

Рассмотрим этот способ:

  1. Откройте макет вашего отчета в конфигураторе.
  2. Создайте копию вашей основной секции для вывода данных. Например, если у вас есть секция "Строка", создайте ее копию и назовите ее "СтрокаВыделенная".
  3. В новой секции ("СтрокаВыделенная") сразу в макете задайте нужное форматирование для ячеек: измените цвет шрифта, фона, сделайте текст жирным и т.д.
  4. В программном коде, внутри цикла, вам остается только проверить условие и в зависимости от него вывести ту или иную секцию.

Пример кода для этого подхода:


// ... (начало формирования отчета)

// Начало цикла по данным
Цикл
    // ... подготовка переменных для вывода ...

    // В зависимости от условия выводим заранее отформатированную секцию
    Если УсловиеДляОкрашивания = 1 Тогда
        Таб.ВывестиСекцию("СтрокаВыделенная");
    Иначе
        Таб.ВывестиСекцию("Строка");
    КонецЕсли;

КонецЦикла;

// ... (показ отчета)

Преимущества этого метода:

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

← На главную