Как в СКД жестко ограничить выбор периода рамками одного месяца?

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

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

Ограничение средствами схемы компоновки данных без изменения формы

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

  1. Перейдем на вкладку Параметры в схеме компоновки данных.
  2. Создадим пользовательский параметр, назовем его, например, ПериодОтчета с типом Дата.
  3. В колонке Параметры редактирования для этого параметра укажем формат редактирования: ДФ=MM.yyyy или ДФ='MMMM yyyy'. Это задаст отображение месяца и года.
  4. Для системных параметров запроса (например, НачалоПериода и КонецПериода) снимем флажок доступности пользователю (колонка Ограничение доступности).
  5. В поле Выражение для параметра НачалоПериода пропишем формулу: НачалоПериода(&ПериодОтчета, "Месяц").
  6. В поле Выражение для параметра КонецПериода пропишем формулу: КонецПериода(&ПериодОтчета, "Месяц").

Если в отчете используется стандартный параметр с типом СтандартныйПериод, можно не убирать его, а принудительно пересчитывать дату окончания от даты начала, как предлагалось участниками обсуждения. Для этого в выражении параметра КонецПериода достаточно указать выражение: КонецПериода(&Период.ДатаНачала, "Месяц"). Однако при таком подходе пользователь все равно увидит стандартный диалог выбора интервала, что может вызвать путаницу в интерфейсе.

Использование таблицы доступных значений в СКД

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

Если заполнить список доступных значений конкретными датами (например, первыми числами каждого месяца года с соответствующим представлением вида «Январь 2026», «Февраль 2026»), платформа переключит элемент управления в режим выбора из фиксированного списка. Пользователь физически не сможет открыть стандартный календарь или диалог ввода периода и будет выбирать только предопределенные месяцы.

Программный контроль в событии ПриКомпоновкеРезультата

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


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

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

Реализация через собственную управляемую форму отчета

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

Способ 1. Поле ввода с режимом выбора из списка

Создадим на форме реквизит ПериодМесяц с типом Дата и вынесем его на форму. Настроим свойства элемента формы:

  1. Установим свойство РежимВыбораИзСписка в значение Истина.
  2. Включим свойство КнопкаВыпадающегоСписка.
  3. Отключим свойство КнопкаВыбора, чтобы исключить открытие стандартного календаря.

Заполним выпадающий список при открытии формы в серверной процедуре:


&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)
    
    ЭлементПериод = Элементы.ПериодМесяц;
    ЭлементПериод.СписокВыбора.Очистить();
    
    ТекущаяДатаОтчета = НачалоГода(ТекущаяДатаСеанса());
    Для НомерМесяца = 1 По 12 Цикл
        ДатаМесяца = ДобавитьМесяц(ТекущаяДатаОтчета, НомерМесяца - 1);
        Представление = Формат(ДатаМесяца, "ДФ='MMMM yyyy'");
        ЭлементПериод.СписокВыбора.Добавить(ДатаМесяца, Представление);
    КонецЦикла;
    
    // Устанавливаем текущий месяц по умолчанию
    ПериодМесяц = НачалоПериода(ТекущаяДатаСеанса(), "Месяц");
    
КонецПроцедуры

При нажатии кнопки формирования отчета передадим значение реквизита в параметры СКД:


&НаСервере
Процедура УстановитьПараметрыСКД()
    
    ПараметрНачало = Отчет.КомпоновщикНастроек.Настройки.ПараметрыДанных.Элементы.Найти("НачалоПериода");
    Если ПараметрНачало <> Неопределено Тогда
        ПараметрНачало.Значение = НачалоПериода(ПериодМесяц, "Месяц");
        ПараметрНачало.Использование = Истина;
    КонецЕсли;
    
    ПараметрКонец = Отчет.КомпоновщикНастроек.Настройки.ПараметрыДанных.Элементы.Найти("КонецПериода");
    Если ПараметрКонец <> Неопределено Тогда
        ПараметрКонец.Значение = КонецПериода(ПериодМесяц, "Месяц");
        ПараметрКонец.Использование = Истина;
    КонецЕсли;
    
КонецПроцедуры

Способ 2. Раздельный выбор года и месяца

Посмотрим на альтернативный вариант компоновки интерфейса. Создадим два отдельных реквизита формы: ВыбранныйГод (тип Число, длина 4) и ВыбранныйМесяц (тип Число, длина 2).

  1. Для поля года включаем кнопки регулирования (с шагом 1).
  2. Для поля месяца устанавливаем РежимВыбораИзСписка = Истина и заполняем список числами от 1 до 12 с текстовыми представлениями от «Январь» до «Декабрь».

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


&НаСервере
Процедура ЗаполнитьГраницыПериода(Год, НомерМесяца)
    
    ДатаНачала = Дата(Год, НомерМесяца, 1);
    ДатаОкончания = КонецМесяца(ДатаНачала);
    
    // Передаем полученные значения в компоновщик настроек отчета
    КомпоновщикНастроек.Настройки.ПараметрыДанных.УстановитьЗначениеПараметра("НачалоПериода", ДатаНачала);
    КомпоновщикНастроек.Настройки.ПараметрыДанных.УстановитьЗначениеПараметра("КонецПериода", ДатаОкончания);
    
КонецПроцедуры

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

← На главную