Как программно создать колонку с типом Дата без времени в 1С

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

При динамическом создании колонок в табличных частях и табличных полях разработчики часто сталкиваются с ситуацией, когда дата отображается вместе со временем (например, 01.01.2024 0:00:00 вместо желаемого 01.01.2024). Разберем, как устроена работа с датами на платформе 1С, почему популярный подход с преобразованием в строку ошибочен и как правильно настроить программное создание колонки.

Особенности типа данных Дата в 1С

Проанализируем внутреннее устройство платформы: в 1С физически не существует отдельного типа «только дата». Любое значение типа Дата всегда содержит и календарную часть, и время в диапазоне от 0001-01-01 00:00:00 до 3999-12-31 23:59:59.

Когда мы указываем квалификатор ЧастиДаты.Дата, платформа не удаляет время из структуры хранения, а принудительно устанавливает временную составляющую в 00:00:00 при интерактивном вводе и валидации, а также определяет поведение элемента управления по умолчанию.

Почему нельзя сохранять дату в виде строки

Иногда разработчики пытаются решить задачу простым форматированием значения при записи в строку таблицы:

НовСтрока.ПериодРегистрации = Формат(Док.ПериодРегистрации, "ДФ=dd.MM.yyyy");

Выясним, почему такой подход считается грубой ошибкой и приводит к скрытым багам:

  1. Некорректная сортировка: Строковые значения сортируются посимвольно слева направо. В результате дата 01.12.2023 при сортировке окажется раньше, чем 02.01.2022, что полностью ломает хронологию при клике пользователя по заголовку колонки.
  2. Потеря возможности вычислений: К строке нельзя применить стандартные функции НачалоМесяца(), КонецДня(), сложение периодов или разность дат без предварительного ручного парсинга.
  3. Проблемы при передаче данных: При дальнейшей передаче таблицы в запросы, СКД или алгоритмы проведения строковая колонка не сможет участвовать в интервальных сравнениях.

Способ 1. Указание квалификатора даты при создании колонки

Посмотрим на классическое решение для табличного поля в обычном приложении. Чтобы колонка имела строгий тип Дата и скрывала время, передадим в конструктор ОписаниеТипов объект КвалификаторыДаты со значением ЧастиДаты.Дата:


Квалификатор = Новый КвалификаторыДаты(ЧастиДаты.Дата);
ТипКолонки = Новый ОписаниеТипов("Дата", , , Квалификатор);

ТабличноеПоле.Колонки.Добавить("ПериодРегистрации", ТипКолонки, "Период регистрации", 10);

Или в компактном виде одной строкой:


ТабличноеПоле.Колонки.Добавить("ПериодРегистрации", Новый ОписаниеТипов("Дата", , , Новый КвалификаторыДаты(ЧастиДаты.Дата)), "Период регистрации", 10);

Способ 2. Настройка формата отображения колонки

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


Колонка = ТабличноеПоле.Колонки.Найти("ПериодРегистрации");
Если Колонка <> Неопределено Тогда
    Колонка.Формат = "ДФ=dd.MM.yyyy";
    Колонка.ФорматРедактирования = "ДФ=dd.MM.yyyy";
КонецЕсли;

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

Способ 3. Программное создание колонки на управляемых формах

Разберем по шагам, как решается аналогичная задача в управляемом интерфейсе, где создание реквизитов и элементов интерфейса разделено на два этапа:

  1. Создание реквизита на сервере: описываем типизированный реквизит формы и применяем изменения через ИзменитьРеквизиты().
  2. Создание элемента формы: добавляем поле ввода в таблицу формы и задаем маску формата.

Посмотрим на пример серверного кода:


&НаСервере
Процедура ДобавитьКолонкуДатыНаСервере()

    // Шаг 1. Добавление реквизита в структуру данных формы
    МассивРеквизитов = Новый Массив;
    Квалификатор = Новый КвалификаторыДаты(ЧастиДаты.Дата);
    ТипДатаБезВремени = Новый ОписаниеТипов("Дата", , , Квалификатор);
    
    РеквизитКолонки = Новый РеквизитФормы(
        "ПериодРегистрации", 
        ТипДатаБезВремени, 
        "ИмяТаблицыФормы", 
        "Период регистрации"
    );
    МассивРеквизитов.Добавить(РеквизитКолонки);
    ИзменитьРеквизиты(МассивРеквизитов);
    
    // Шаг 2. Создание элемента интерфейса
    ТаблицаЭлемент = Элементы.ИмяТаблицыФормы;
    НовоеПоле = Элементы.Добавить("ИмяТаблицыФормыПериодРегистрации", Тип("ПолеФормы"), ТаблицаЭлемент);
    НовоеПоле.Вид = ВидПоляФормы.ПолеВвода;
    НовоеПоле.ПутьКДанным = "ИмяТаблицыФормы.ПериодРегистрации";
    НовоеПоле.Формат = "ДФ=dd.MM.yyyy";
    НовоеПоле.ФорматРедактирования = "ДФ=dd.MM.yyyy";

КонецПроцедуры

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

← На главную