Содержание
2 Архитектура 1C: БСП Дополнительные реквизиты и сведения
3 Использование подсистемы 1С: БСП Дополнительные реквизиты
4 Особенности реализации 1С: БСП Дополнительные реквизиты
Введение
Для начала предлагаю разобраться с терминологией 1С: БСП: согласно ИТС дополнительные реквизиты и сведения — это свойства. По моему мнению, подсистема «Свойства» (Управление свойствами) — это очень мощный функционал, который позволяет во многих случаях отказаться от снятия конфигурации с поддержки или внесения ненужных изменений и ошибок в конфигурацию.
Архитектура 1C: БСП Дополнительные реквизиты и сведения
Описание работы с подсистемой «Свойства» на сайте ИТС 1С является исчерпывающим для типовых конфигураций, но в любом случае, для того, чтобы начать работать со свойствами в любой конфигурации с внедрённым 1С: БСП, необходимо установить константу «Использовать дополнительные реквизиты и сведения» в значение «Истина». После этого мы можем открыть справочник «Наборы дополнительных реквизитов и сведений», который содержит список объектов, для них можно создавать дополнительные реквизиты и сведения. При добавлении через стандартные формы 1С: БСП пользователь создаёт новый элемент «Плана видов характеристик», который добавляется в табличную часть элемента.
Дополнительные сведения отличаются от дополнительных реквизитов прежде всего расположением, дополнительные сведения содержатся в отдельном регистре с одноименным названием, а дополнительные реквизиты являются табличной частью объекта, к которому относятся. На рисунке ниже слева направо изображены: элемент справочника «Наборы дополнительных реквизитов и свойств», элемент плана видов характеристик и список регистра сведений «Дополнительные сведения».
Следующий рисунок изображает пример дополнительного реквизита, слева направо: элемент справочника «Наборы дополнительных реквизитов и свойств», элемент плана видов характеристик и элемент справочника, в который был добавлен дополнительный реквизит.
Также стоит учитывать, что большая часть объектов метаданных в справочнике «Наборы дополнительных реквизитов и сведений» является предопределённой:
Однако, заполнение этих данных происходит программно, при внедрении 1С: БСП или обновлении информационной базы — для этого в общих модулях добавляют процедуру ПриПолученииПредопределенныхНаборовСвойств. Уникальный идентификатор задаётся в явном виде, в т.ч. для того, чтобы облегчить процедуры обмена между базами.
// См. УправлениеСвойствамиПереопределяемый.ПриПолученииПредопределенныхНаборовСвойств.
//
// Параметры:
// Наборы - см. УправлениеСвойствамиПереопределяемый.ПриПолученииПредопределенныхНаборовСвойств.Наборы
//
Процедура ПриПолученииПредопределенныхНаборовСвойств(Наборы) Экспорт
Набор = Наборы.Строки.Добавить();
Набор.Имя = "Справочник_ПапкиФайлов";
Набор.Идентификатор = Новый УникальныйИдентификатор("00000000-0000-0000-0000-000000000000");
КонецПроцедуры
С точки зрения интеграции с объектами механизм работы с формами не сильно отличается от аналогичных у других подсистем 1С: БСП: из модуля УправлениеСвойствами вызываются процедуры и функции с названиями, соответствующими названиям событий, для которых они вызываются, например:
&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)
// Обработчик подсистемы "Свойства"
ДополнительныеПараметры = Новый Структура;
ДополнительныеПараметры.Вставить("Объект", Объект);
ДополнительныеПараметры.Вставить("ИмяЭлементаДляРазмещения", "ГруппаДополнительныеРеквизиты");
УправлениеСвойствами.ПриСозданииНаСервере(ЭтаФорма, ДополнительныеПараметры);
КонецПроцедуры
Полный список функций и процедур находится в общем модуле УправлениеСвойствами в блоке, озаглавленном: «Процедуры и функции для стандартной обработки дополнительных реквизитов».
Использование подсистемы 1С: БСП Дополнительные реквизиты
Каждый дополнительный реквизит или свойство содержит поле «Имя», подразумевается, что для программного использования будет использоваться этот реквизит.
Пример использования имени для получения дополнительного реквизита 1С: БСП
ВЫБРАТЬ
ГражданствоФизическихЛиц.ФизическоеЛицо КАК ФизическоеЛицо,
ФизическиеЛицаДополнительныеРеквизиты.Значение КАК Рост,
ГражданствоФизическихЛиц.Страна КАК Страна
ИЗ
Справочник.ФизическиеЛица.ДополнительныеРеквизиты КАК ФизическиеЛицаДополнительныеРеквизиты
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ГражданствоФизическихЛиц КАК ГражданствоФизическихЛиц
ПО ГражданствоФизическихЛиц.ФизическоеЛицо = ФизическиеЛицаДополнительныеРеквизиты.Ссылка
ГДЕ
ГражданствоФизическихЛиц.ФизическоеЛицо = &ФизическоеЛицо
И ФизическиеЛицаДополнительныеРеквизиты.Свойство.Имя = &Имя
Результат:
Пример запроса для получения всех дополнительных свойств
ВЫБРАТЬ
ЦеныНоменклатурыСрезПоследних.Номенклатура КАК Номенклатура,
ЦеныНоменклатурыСрезПоследних.ТипЦен КАК ТипЦен,
ЦеныНоменклатурыСрезПоследних.Цена КАК Цена,
ДополнительныеСведения.Свойство КАК Свойство,
ДополнительныеСведения.Значение КАК Значение,
ДополнительныеСведения.Свойство.Имя КАК ИмяСвойства
ИЗ
РегистрСведений.ЦеныНоменклатуры.СрезПоследних(
&Дата,
Номенклатура = &Номенклатура
И ТипЦен = &ТипЦен) КАК ЦеныНоменклатурыСрезПоследних
ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.ДополнительныеСведения КАК ДополнительныеСведения
ПО ЦеныНоменклатурыСрезПоследних.Номенклатура = ДополнительныеСведения.Объект
ИТОГИ
МАКСИМУМ(Номенклатура),
МАКСИМУМ(Цена)
ПО
ОБЩИЕ,
ТипЦен
Результат:
Примеры получения свойств 1С: БСП без запроса
Рост = ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.найтиПоРеквизиту("Имя", "Рост_12f49d4f164847b79effd75a758186c3");
// Получение дополнительного реквизита
Рост = УправлениеСвойствами.ЗначениеСвойства(ФизическоеЛицо.Ссылка, Рост);
// Получение всех дополнительных реквизитов и сведений объекта
ВсеСвойства = УправлениеСвойствами.ЗначенияСвойств(ФизическоеЛицо.Ссылка);
Особенности реализации 1С: БСП Дополнительные реквизиты
Если с запросами и функциями всё более-менее ясно, неприятным сюрпризом может стать то, что дополнительный реквизит на форме содержит название, отличающееся от этого реквизита, например, такое:
Чтобы найти реквизит на форме, 1С: БСП создаёт новые реквизиты формы Свойства_ОписаниеДополнительныхРеквизитов и Свойства_ОписаниеЗависимыхДополнительныхРеквизитов, с помощью них можно установить однозначное соответствие между элементом и значением объекта:
Второй особенностью реализации можно выделить невозможность создания свойства с му табельным типом, с одной стороны это очевидное ограничение, с другой тип «Список значений» вполне допустим, но только для дополнительного реквизита (у дополнительных сведений невозможность связана с архитектурными ограничениями, так как объект и свойство — это измерения регистра «Дополнительные сведения»). Возможно, отсутствие такого типа связано со сложностями при обмене, а возможно, в скором времени это будет реализовано, предлагаю посмотреть на пример такой реализации ниже.
Как получить дополнительный реквизит в 1С: БСП
1. Добавим дополнительный реквизит
Добавим новый дополнительный реквизит для справочника физические лица «Номера счетов»
2. Получим значение дополнительного реквизита 1С БСП программно
Добавляем программно вторую запись в табличную часть «Дополнительные реквизиты» справочника «Физические лица» с тем же самым свойством:
3. Модифицируем код функций и процедур
Немного модифицируем код функции ЗначенияСвойств в общем модуле УправлениеСвойствамиСлужебный:
А также код процедуры ЗаполнитьДополнительныеРеквизитыВФорме в общем модуле УправлениеСвойствами:
Таким образом мы можем сохранять и восстанавливать значения реквизитов, которые принимают множество значений.
// Создает/пересоздает дополнительные реквизиты и элементы в форме владельца свойств.
//
// Параметры:
// Форма - ФормаКлиентскогоПриложения - уже настроена в процедуре ПриСозданииНаСервере.
//
// Объект - Неопределено - взять объект из реквизита формы "Объект".
// - СправочникОбъектИмяСправочника -
// - ДокументОбъектИмяДокумента -
// - ПланВидовХарактеристикОбъектИмяПланаВидовХарактеристик -
// - БизнесПроцессОбъектИмяБизнесПроцесса -
// - ЗадачаОбъектИмяЗадачи -
// - ПланВидовРасчетаОбъектИмяПланаВидовРасчета -
// - ПланСчетовОбъектИмяПланаСчетов -
// - ДанныеФормыСтруктура -
//
// ПоляНадписей - Булево - если указать Истина, то вместо полей ввода на форме будут созданы поля надписей.
//
// СкрытьУдаленные - Неопределено - не менять текущий режим скрытия удаленных, установленный ранее.
// - Булево - установить/отключить режим скрытия удаленных.
// При вызове процедуры ПередЗаписьюНаСервере в режиме скрытия удаленных, удаленные значения
// очищаются (не переносятся обратно в объект), а режим СкрытьУдаленные устанавливается Ложь.
//
Процедура ЗаполнитьДополнительныеРеквизитыВФорме(Форма, Объект = Неопределено, ПоляНадписей = Ложь, СкрытьУдаленные = Неопределено) Экспорт
Если НЕ Форма.Свойства_ИспользоватьСвойства
ИЛИ НЕ Форма.Свойства_ИспользоватьДопРеквизиты Тогда
Возврат;
КонецЕсли;
Если ТипЗнч(СкрытьУдаленные) = Тип("Булево") Тогда
Форма.Свойства_СкрытьУдаленные = СкрытьУдаленные;
КонецЕсли;
Если Объект = Неопределено Тогда
ОписаниеОбъекта = Форма.Объект;
Иначе
ОписаниеОбъекта = Объект;
КонецЕсли;
Форма.Свойства_НаборыДополнительныхРеквизитовОбъекта = Новый СписокЗначений;
КлючНазначения = Неопределено;
НаборыСвойствОбъекта = УправлениеСвойствамиСлужебный.ПолучитьНаборыСвойствОбъекта(
ОписаниеОбъекта, КлючНазначения);
УправлениеСвойствамиСлужебный.ЗаполнитьНаборыСДополнительнымиРеквизитами(
НаборыСвойствОбъекта,
Форма.Свойства_НаборыДополнительныхРеквизитовОбъекта);
ОбновитьКлючНазначенияФормы(Форма, КлючНазначения);
ОписаниеСвойств = УправлениеСвойствамиСлужебный.ЗначенияСвойств(
ОписаниеОбъекта.ДополнительныеРеквизиты.Выгрузить(),
Форма.Свойства_НаборыДополнительныхРеквизитовОбъекта,
Ложь);
ОписаниеСвойств.Колонки.Добавить("ИмяРеквизитаЗначение");
ОписаниеСвойств.Колонки.Добавить("СтрокаСсылочногоТипа");
ОписаниеСвойств.Колонки.Добавить("ИмяСсылочногоРеквизитаЗначение");
ОписаниеСвойств.Колонки.Добавить("ИмяУникальнаяЧасть");
ОписаниеСвойств.Колонки.Добавить("ДополнительноеЗначение");
ОписаниеСвойств.Колонки.Добавить("Булево");
УдалитьСтарыеРеквизитыИЭлементы(Форма);
// Создание реквизитов.
ДобавляемыеРеквизиты = Новый Массив();
Для каждого ОписаниеСвойства Из ОписаниеСвойств Цикл
ТипЗначенияСвойства = ОписаниеСвойства.ТипЗначения;
СписокТипов = ТипЗначенияСвойства.Типы();
СтроковыйРеквизит = (СписокТипов.Количество() = 1) И (СписокТипов[0] = Тип("Строка"));
// Поддержка строк неограниченной длины.
ИспользоватьНеограниченнуюСтроку = УправлениеСвойствамиСлужебный.ИспользоватьНеограниченнуюСтроку(
ТипЗначенияСвойства, ОписаниеСвойства.МногострочноеПолеВвода);
Если ИспользоватьНеограниченнуюСтроку Тогда
ТипЗначенияСвойства = Новый ОписаниеТипов("Строка");
ИначеЕсли ТипЗначенияСвойства.СодержитТип(Тип("Строка"))
И ТипЗначенияСвойства.КвалификаторыСтроки.Длина = 0 Тогда
// Если нельзя использовать неограниченную строку, а в свойствах реквизита она неограниченная,
// то устанавливаем ограничение в 1024 символа.
ТипЗначенияСвойства = Новый ОписаниеТипов(ОписаниеСвойства.ТипЗначения,
,,, Новый КвалификаторыСтроки(1024));
КонецЕсли;
ОписаниеСвойства.ИмяУникальнаяЧасть =
СтрЗаменить(ВРег(Строка(ОписаниеСвойства.Набор.УникальныйИдентификатор())), "-", "x")
+ "_"
+ СтрЗаменить(ВРег(Строка(ОписаниеСвойства.Свойство.УникальныйИдентификатор())), "-", "x");
// {{ Prosto. [Silantev Oleg Sergeevich] - [26.09.2020 21:51].
Если ОписаниеСвойств.Найти("ДополнительныйРеквизитЗначение_" + ОписаниеСвойства.ИмяУникальнаяЧасть) <> Неопределено Тогда
ОписаниеСвойства.ИмяУникальнаяЧасть = ОписаниеСвойства.ИмяУникальнаяЧасть + "_" + ОписаниеСвойств.Индекс(описаниеСвойства);
КонецЕсли;
// }} {{ Prosto. [Silantev Oleg Sergeevich] - [26.09.2020 21:51].
ОписаниеСвойства.ИмяРеквизитаЗначение =
"ДополнительныйРеквизитЗначение_" + ОписаниеСвойства.ИмяУникальнаяЧасть;
ОписаниеСвойства.СтрокаСсылочногоТипа = Ложь;
Если СтроковыйРеквизит
И Не ИспользоватьНеограниченнуюСтроку
И ОписаниеСвойства.ВыводитьВВидеГиперссылки Тогда
ФорматированнаяСтрока = Новый ОписаниеТипов("ФорматированнаяСтрока");
ОписаниеСвойства.СтрокаСсылочногоТипа = Истина;
ОписаниеСвойства.ИмяСсылочногоРеквизитаЗначение = "СсылочныйДополнительныйРеквизитЗначение_" + ОписаниеСвойства.ИмяУникальнаяЧасть;
Реквизит = Новый РеквизитФормы(ОписаниеСвойства.ИмяСсылочногоРеквизитаЗначение, ФорматированнаяСтрока, , ОписаниеСвойства.Наименование, Истина);
ДобавляемыеРеквизиты.Добавить(Реквизит);
КонецЕсли;
Если ОписаниеСвойства.Удалено Тогда
ТипЗначенияСвойства = Новый ОписаниеТипов("Строка");
КонецЕсли;
Реквизит = Новый РеквизитФормы(ОписаниеСвойства.ИмяРеквизитаЗначение, ТипЗначенияСвойства, , ОписаниеСвойства.Наименование, Истина);
ДобавляемыеРеквизиты.Добавить(Реквизит);
ОписаниеСвойства.ДополнительноеЗначение =
УправлениеСвойствамиСлужебный.ТипЗначенияСодержитЗначенияСвойств(ТипЗначенияСвойства);
ОписаниеСвойства.Булево = ОбщегоНазначения.ОписаниеТипаСостоитИзТипа(ТипЗначенияСвойства, Тип("Булево"));
КонецЦикла;
Форма.ИзменитьРеквизиты(ДобавляемыеРеквизиты);
// Создание элементов формы.
Для Каждого ОписаниеСвойства Из ОписаниеСвойств Цикл
ИмяЭлементаДляРазмещения = Форма.Свойства_ИмяЭлементаДляРазмещения;
Если ТипЗнч(ИмяЭлементаДляРазмещения) <> Тип("СписокЗначений") Тогда
Если ИмяЭлементаДляРазмещения = Неопределено Тогда
ИмяЭлементаДляРазмещения = "";
КонецЕсли;
ЭлементРазмещения = ?(ИмяЭлементаДляРазмещения = "", Неопределено, Форма.Элементы[ИмяЭлементаДляРазмещения]);
Иначе
РазделыДляРазмещения = Форма.Свойства_ИмяЭлементаДляРазмещения;
РазмещениеНабора = РазделыДляРазмещения.НайтиПоЗначению(ОписаниеСвойства.Набор);
Если РазмещениеНабора = Неопределено Тогда
РазмещениеНабора = РазделыДляРазмещения.НайтиПоЗначению("ВсеОстальные");
КонецЕсли;
ЭлементРазмещения = Форма.Элементы[РазмещениеНабора.Представление];
КонецЕсли;
ФормаОписаниеСвойства = Форма.Свойства_ОписаниеДополнительныхРеквизитов.Добавить();
ЗаполнитьЗначенияСвойств(ФормаОписаниеСвойства, ОписаниеСвойства);
// Заполнение таблицы зависимых дополнительных реквизитов.
Если ОписаниеСвойства.ЗависимостиДополнительныхРеквизитов.Количество() > 0
И Не ОписаниеСвойства.Удалено Тогда
ОписаниеЗависимогоРеквизита = Форма.Свойства_ОписаниеЗависимыхДополнительныхРеквизитов.Добавить();
ЗаполнитьЗначенияСвойств(ОписаниеЗависимогоРеквизита, ОписаниеСвойства);
КонецЕсли;
ОтборСтрок = Новый Структура;
ОтборСтрок.Вставить("НаборСвойств", ОписаниеСвойства.Набор);
ЗависимостиДанногоНабора = ОписаниеСвойства.ЗависимостиДополнительныхРеквизитов.НайтиСтроки(ОтборСтрок);
Для Каждого СтрокаТаблицы Из ЗависимостиДанногоНабора Цикл
Если СтрокаТаблицы.ЗависимоеСвойство = "ЗаполнятьОбязательно"
И ОписаниеСвойства.ТипЗначения = Новый ОписаниеТипов("Булево") Тогда
Продолжить;
КонецЕсли;
Если ОписаниеСвойства.Удалено Тогда
Продолжить;
КонецЕсли;
Если ТипЗнч(СтрокаТаблицы.Реквизит) = Тип("Строка") Тогда
ПутьКРеквизиту = "Параметры.ОписаниеОбъекта." + СтрокаТаблицы.Реквизит;
Иначе
ОписаниеДополнительногоРеквизита = ОписаниеСвойств.Найти(СтрокаТаблицы.Реквизит, "Свойство");
Если ОписаниеДополнительногоРеквизита = Неопределено Тогда
Продолжить; // Дополнительный реквизит не существует, условие игнорируется.
КонецЕсли;
ПутьКРеквизиту = "Параметры.Форма." + ОписаниеДополнительногоРеквизита.ИмяРеквизитаЗначение;
КонецЕсли;
УправлениеСвойствамиСлужебный.ПостроитьУсловияЗависимостей(ОписаниеЗависимогоРеквизита, ПутьКРеквизиту, СтрокаТаблицы);
КонецЦикла;
Если ОписаниеСвойства.СтрокаСсылочногоТипа Тогда
Если ЗначениеЗаполнено(ОписаниеСвойства.Значение) Тогда
Значение = ОписаниеСвойства.ТипЗначения.ПривестиЗначение(ОписаниеСвойства.Значение);
СтрокаЗначение = СтроковыеФункции.ФорматированнаяСтрока(Значение);
Иначе
Значение = НСтр("ru = 'не задано'");
СсылкаРедактирования = "НеЗадано";
СтрокаЗначение = Новый ФорматированнаяСтрока(Значение,, ЦветаСтиля.ЦветПустойГиперссылки,, СсылкаРедактирования);
КонецЕсли;
Форма[ОписаниеСвойства.ИмяСсылочногоРеквизитаЗначение] = СтрокаЗначение;
КонецЕсли;
Форма[ОписаниеСвойства.ИмяРеквизитаЗначение] = ОписаниеСвойства.Значение;
Если ОписаниеСвойства.Удалено И Форма.Свойства_СкрытьУдаленные Тогда
Продолжить;
КонецЕсли;
Если НаборыСвойствОбъекта.Количество() > 1 Тогда
ЭлементСписка = Форма.Свойства_ЭлементыГруппДополнительныхРеквизитов.НайтиПоЗначению(
ОписаниеСвойства.Набор);
Если ЭлементСписка <> Неопределено Тогда
Родитель = Форма.Элементы[ЭлементСписка.Представление];
Иначе
ОписаниеНабора = НаборыСвойствОбъекта.Найти(ОписаниеСвойства.Набор, "Набор");
Если ОписаниеНабора = Неопределено Тогда
ОписаниеНабора = НаборыСвойствОбъекта.Добавить();
ОписаниеНабора.Набор = ОписаниеСвойства.Набор;
ОписаниеНабора.Заголовок = НСтр("ru = 'Удаленные реквизиты'")
КонецЕсли;
Если НЕ ЗначениеЗаполнено(ОписаниеНабора.Заголовок) Тогда
ОписаниеНабора.Заголовок = Строка(ОписаниеСвойства.Набор);
КонецЕсли;
ИмяЭлементаНабора = "НаборДополнительныхРеквизитов" + ОписаниеСвойства.ИмяУникальнаяЧасть;
Родитель = Форма.Элементы.Добавить(ИмяЭлементаНабора, Тип("ГруппаФормы"), ЭлементРазмещения);
Форма.Свойства_ЭлементыГруппДополнительныхРеквизитов.Добавить(
ОписаниеСвойства.Набор, Родитель.Имя);
Если ТипЗнч(ЭлементРазмещения) = Тип("ГруппаФормы")
И ЭлементРазмещения.Вид = ВидГруппыФормы.Страницы Тогда
Родитель.Вид = ВидГруппыФормы.Страница;
Иначе
Родитель.Вид = ВидГруппыФормы.ОбычнаяГруппа;
Родитель.Отображение = ОтображениеОбычнойГруппы.Нет;
КонецЕсли;
Родитель.ОтображатьЗаголовок = Ложь;
Родитель.Группировка = ГруппировкаПодчиненныхЭлементовФормы.Вертикальная;
ЗаполненныеСвойстваГруппы = Новый Структура;
Для каждого Колонка Из НаборыСвойствОбъекта.Колонки Цикл
Если ОписаниеНабора[Колонка.Имя] <> Неопределено Тогда
ЗаполненныеСвойстваГруппы.Вставить(Колонка.Имя, ОписаниеНабора[Колонка.Имя]);
КонецЕсли;
КонецЦикла;
ЗаполнитьЗначенияСвойств(Родитель, ЗаполненныеСвойстваГруппы);
КонецЕсли;
Иначе
Родитель = ЭлементРазмещения;
КонецЕсли;
Если ОписаниеСвойства.ВыводитьВВидеГиперссылки Тогда
ИмяГруппыГиперссылки = "Группа_" + ОписаниеСвойства.ИмяУникальнаяЧасть;
ГруппаГиперссылки = Форма.Элементы.Добавить(ИмяГруппыГиперссылки, Тип("ГруппаФормы"), Родитель);
ГруппаГиперссылки.Вид = ВидГруппыФормы.ОбычнаяГруппа;
ГруппаГиперссылки.Отображение = ОтображениеОбычнойГруппы.Нет;
ГруппаГиперссылки.ОтображатьЗаголовок = Ложь;
ГруппаГиперссылки.Группировка = ГруппировкаПодчиненныхЭлементовФормы.ГоризонтальнаяВсегда;
ГруппаГиперссылки.Заголовок = ОписаниеСвойства.Наименование;
Элемент = Форма.Элементы.Добавить(ОписаниеСвойства.ИмяРеквизитаЗначение, Тип("ПолеФормы"), ГруппаГиперссылки); // РасширениеПоляФормыДляПоляНадписи, РасширениеПоляФормыДляПоляВвода
РеквизитДоступен = РеквизитДоступенПоФункциональнымОпциям(ОписаниеСвойства);
Если РеквизитДоступен И Не ПоляНадписей Тогда
ИмяКнопки = "Кнопка_" + ОписаниеСвойства.ИмяУникальнаяЧасть;
Кнопка = Форма.Элементы.Добавить(
ИмяКнопки,
Тип("КнопкаФормы"),
ГруппаГиперссылки);
Кнопка.ТолькоВоВсехДействиях = Истина;
Кнопка.ИмяКоманды = "РедактироватьГиперссылкуРеквизита";
Кнопка.ОтображениеФигуры = ОтображениеФигурыКнопки.ПриАктивности;
КонецЕсли;
Если Не ОписаниеСвойства.СтрокаСсылочногоТипа И ЗначениеЗаполнено(ОписаниеСвойства.Значение) Тогда
Элемент.Гиперссылка = Истина;
КонецЕсли;
Иначе
Элемент = Форма.Элементы.Добавить(ОписаниеСвойства.ИмяРеквизитаЗначение, Тип("ПолеФормы"), Родитель); // РасширениеПоляФормыДляПоляНадписи, РасширениеПоляФормыДляПоляВвода
КонецЕсли;
ФормаОписаниеСвойства.ЭлементФормыДобавлен = Истина;
Если ОписаниеСвойства.Булево И ПустаяСтрока(ОписаниеСвойства.ФорматСвойства) Тогда
Элемент.Вид = ВидПоляФормы.ПолеФлажка;
Элемент.ПоложениеЗаголовка = ПоложениеЗаголовкаЭлементаФормы.Право;
Иначе
Если ПоляНадписей Тогда
Элемент.Вид = ВидПоляФормы.ПолеВвода;
ИначеЕсли ОписаниеСвойства.ВыводитьВВидеГиперссылки
И (ОписаниеСвойства.СтрокаСсылочногоТипа
Или ЗначениеЗаполнено(ОписаниеСвойства.Значение))Тогда
Элемент.Вид = ВидПоляФормы.ПолеНадписи;
Иначе
Элемент.Вид = ВидПоляФормы.ПолеВвода;
Элемент.АвтоОтметкаНезаполненного = ОписаниеСвойства.ЗаполнятьОбязательно И НЕ ОписаниеСвойства.Удалено;
КонецЕсли;
Элемент.РастягиватьПоВертикали = Ложь;
Элемент.ПоложениеЗаголовка = ПоложениеЗаголовкаЭлементаФормы.Лево;
КонецЕсли;
Если ОписаниеСвойства.СтрокаСсылочногоТипа Тогда
Элемент.ПутьКДанным = ОписаниеСвойства.ИмяСсылочногоРеквизитаЗначение;
Элемент.УстановитьДействие("ОбработкаНавигационнойСсылки", "Подключаемый_СвойстваВыполнитьКоманду");
Иначе
Элемент.ПутьКДанным = ОписаниеСвойства.ИмяРеквизитаЗначение;
КонецЕсли;
Элемент.Подсказка = ОписаниеСвойства.Подсказка;
Элемент.УстановитьДействие("ПриИзменении", "Подключаемый_ПриИзмененииДополнительногоРеквизита");
Если Элемент.Вид = ВидПоляФормы.ПолеВвода
И Не ИспользоватьНеограниченнуюСтроку
И ОписаниеСвойства.ТипЗначения.Типы().Найти(Тип("Строка")) <> Неопределено Тогда
Элемент.СвязьПоТипу = Новый СвязьПоТипу("Свойства_ОписаниеДополнительныхРеквизитов.Свойство",
ОписаниеСвойств.Индекс(ОписаниеСвойства));
КонецЕсли;
Если ОписаниеСвойства.МногострочноеПолеВвода > 0 Тогда
Если НЕ ПоляНадписей Тогда
Элемент.МногострочныйРежим = Истина;
КонецЕсли;
Элемент.Высота = ОписаниеСвойства.МногострочноеПолеВвода;
КонецЕсли;
Если НЕ ПустаяСтрока(ОписаниеСвойства.ФорматСвойства)
И Не ОписаниеСвойства.ВыводитьВВидеГиперссылки Тогда
Если ПоляНадписей Тогда
Элемент.Формат = ОписаниеСвойства.ФорматСвойства;
Иначе
ФорматнаяСтрока = "";
Массив = СтрРазделить(ОписаниеСвойства.ФорматСвойства, ";", Ложь);
Для каждого Подстрока Из Массив Цикл
Если СтрНайти(Подстрока, "ДП=") > 0 ИЛИ СтрНайти(Подстрока, "DE=") > 0 Тогда
Продолжить;
КонецЕсли;
Если СтрНайти(Подстрока, "ЧН=") > 0 ИЛИ СтрНайти(Подстрока, "NZ=") > 0 Тогда
Продолжить;
КонецЕсли;
Если СтрНайти(Подстрока, "ДФ=") > 0 ИЛИ СтрНайти(Подстрока, "DF=") > 0 Тогда
Если СтрНайти(Подстрока, "ддд") > 0 ИЛИ СтрНайти(Подстрока, "ddd") > 0 Тогда
Подстрока = СтрЗаменить(Подстрока, "ддд", "дд");
Подстрока = СтрЗаменить(Подстрока, "ddd", "dd");
КонецЕсли;
Если СтрНайти(Подстрока, "дддд") > 0 ИЛИ СтрНайти(Подстрока, "dddd") > 0 Тогда
Подстрока = СтрЗаменить(Подстрока, "дддд", "дд");
Подстрока = СтрЗаменить(Подстрока, "dddd", "dd");
КонецЕсли;
Если СтрНайти(Подстрока, "МММ") > 0 ИЛИ СтрНайти(Подстрока, "MMM") > 0 Тогда
Подстрока = СтрЗаменить(Подстрока, "МММ", "ММ");
Подстрока = СтрЗаменить(Подстрока, "MMM", "MM");
КонецЕсли;
Если СтрНайти(Подстрока, "ММММ") > 0 ИЛИ СтрНайти(Подстрока, "MMMM") > 0 Тогда
Подстрока = СтрЗаменить(Подстрока, "ММММ", "ММ");
Подстрока = СтрЗаменить(Подстрока, "MMMM", "MM");
КонецЕсли;
КонецЕсли;
Если СтрНайти(Подстрока, "ДЛФ=") > 0 ИЛИ СтрНайти(Подстрока, "DLF=") > 0 Тогда
Если СтрНайти(Подстрока, "ДД") > 0 ИЛИ СтрНайти(Подстрока, "DD") > 0 Тогда
Подстрока = СтрЗаменить(Подстрока, "ДД", "Д");
Подстрока = СтрЗаменить(Подстрока, "DD", "D");
КонецЕсли;
КонецЕсли;
ФорматнаяСтрока = ФорматнаяСтрока + ?(ФорматнаяСтрока = "", "", ";") + Подстрока;
КонецЦикла;
Элемент.Формат = ФорматнаяСтрока;
Элемент.ФорматРедактирования = ФорматнаяСтрока;
КонецЕсли;
КонецЕсли;
Если ОписаниеСвойства.Удалено Тогда
Элемент.ЦветТекстаЗаголовка = ЦветаСтиля.ТекстЗапрещеннойЯчейкиЦвет;
Элемент.ШрифтЗаголовка = ШрифтыСтиля.ЗаголовокУдаленногоРеквизитаШрифт;
Если Элемент.Вид = ВидПоляФормы.ПолеВвода Тогда
Элемент.КнопкаОчистки = Истина;
Элемент.КнопкаВыбора = Ложь;
Элемент.КнопкаОткрытия = Ложь;
Элемент.КнопкаВыпадающегоСписка = Ложь;
Элемент.РедактированиеТекста = Ложь;
КонецЕсли;
КонецЕсли;
Если НЕ ПоляНадписей И ОписаниеСвойства.ДополнительноеЗначение И Элемент.Вид = ВидПоляФормы.ПолеВвода Тогда
ПараметрыВыбора = Новый Массив;
ПараметрыВыбора.Добавить(Новый ПараметрВыбора("Отбор.Владелец",
?(ЗначениеЗаполнено(ОписаниеСвойства.ВладелецДополнительныхЗначений),
ОписаниеСвойства.ВладелецДополнительныхЗначений, ОписаниеСвойства.Свойство)));
Элемент.ПараметрыВыбора = Новый ФиксированныйМассив(ПараметрыВыбора);
КонецЕсли;
КонецЦикла;
// Установка видимости, доступности и обязательности заполнения дополнительных реквизитов.
Для Каждого ОписаниеЗависимогоРеквизита Из Форма.Свойства_ОписаниеЗависимыхДополнительныхРеквизитов Цикл
Если ОписаниеЗависимогоРеквизита.ВыводитьВВидеГиперссылки Тогда
ОбрабатываемыйЭлемент = СтрЗаменить(ОписаниеЗависимогоРеквизита.ИмяРеквизитаЗначение, "ДополнительныйРеквизитЗначение_", "Группа_");
Иначе
ОбрабатываемыйЭлемент = ОписаниеЗависимогоРеквизита.ИмяРеквизитаЗначение;
КонецЕсли;
Если ОписаниеЗависимогоРеквизита.УсловиеДоступности <> Неопределено Тогда
Результат = РезультатВычисленияУсловия(Форма, ОписаниеОбъекта, ОписаниеЗависимогоРеквизита.УсловиеДоступности);
Элемент = Форма.Элементы[ОбрабатываемыйЭлемент]; // ПолеФормы
Если Элемент.Доступность <> Результат Тогда
Элемент.Доступность = Результат;
КонецЕсли;
КонецЕсли;
Если ОписаниеЗависимогоРеквизита.УсловиеВидимости <> Неопределено Тогда
Результат = РезультатВычисленияУсловия(Форма, ОписаниеОбъекта, ОписаниеЗависимогоРеквизита.УсловиеВидимости);
Элемент = Форма.Элементы[ОбрабатываемыйЭлемент];
Если Элемент.Видимость <> Результат Тогда
Элемент.Видимость = Результат;
КонецЕсли;
КонецЕсли;
Если ОписаниеЗависимогоРеквизита.УсловиеОбязательностиЗаполнения <> Неопределено Тогда
Если Не ОписаниеЗависимогоРеквизита.ЗаполнятьОбязательно Тогда
Продолжить;
КонецЕсли;
Результат = РезультатВычисленияУсловия(Форма, ОписаниеОбъекта, ОписаниеЗависимогоРеквизита.УсловиеОбязательностиЗаполнения);
Элемент = Форма.Элементы[ОбрабатываемыйЭлемент];
Если Не ОписаниеЗависимогоРеквизита.ВыводитьВВидеГиперссылки
И Элемент.АвтоОтметкаНезаполненного <> Результат Тогда
Элемент.АвтоОтметкаНезаполненного = Результат;
КонецЕсли;
КонецЕсли;
КонецЦикла;
Структура = Новый Структура("ПараметрыСвойств");
ЗаполнитьЗначенияСвойств(Структура, Форма);
Если ТипЗнч(Структура.ПараметрыСвойств) = Тип("Структура")
И Структура.ПараметрыСвойств.Свойство("ВыполненаОтложеннаяИнициализация") Тогда
Форма.ПараметрыСвойств.ВыполненаОтложеннаяИнициализация = Истина;
// Удаление временной декорации, если она была добавлена.
Если Форма.ПараметрыСвойств.Свойство("ДобавленаПустаяДекорация") Тогда
Для Каждого ИмяДекорации Из Форма.ПараметрыСвойств.КоллекцияДекораций Цикл
Форма.Элементы.Удалить(Форма.Элементы[ИмяДекорации]);
КонецЦикла;
Форма.ПараметрыСвойств.Удалить("ДобавленаПустаяДекорация");
КонецЕсли;
КонецЕсли;
КонецПроцедуры
// Возвращает заполненную таблицу значений свойств объекта.
Функция ЗначенияСвойств(ДополнительныеСвойстваОбъекта, Наборы, ЭтоДополнительноеСведение) Экспорт
Если ДополнительныеСвойстваОбъекта.Количество() = 0 Тогда
// Предварительная быстрая проверка использования дополнительных свойств.
СвойстваНеНайдены = ДополнительныеРеквизитыИСведенияНеНайдены(Наборы, ЭтоДополнительноеСведение);
Если СвойстваНеНайдены Тогда
ОписаниеСвойств = Новый ТаблицаЗначений;
ОписаниеСвойств.Колонки.Добавить("Набор");
ОписаниеСвойств.Колонки.Добавить("Свойство");
ОписаниеСвойств.Колонки.Добавить("ВладелецДополнительныхЗначений");
ОписаниеСвойств.Колонки.Добавить("ЗаполнятьОбязательно");
ОписаниеСвойств.Колонки.Добавить("Наименование");
ОписаниеСвойств.Колонки.Добавить("ТипЗначения");
ОписаниеСвойств.Колонки.Добавить("ФорматСвойства");
ОписаниеСвойств.Колонки.Добавить("МногострочноеПолеВвода");
ОписаниеСвойств.Колонки.Добавить("Удалено");
ОписаниеСвойств.Колонки.Добавить("Значение");
Возврат ОписаниеСвойств;
КонецЕсли;
КонецЕсли;
Свойства = ДополнительныеСвойстваОбъекта.ВыгрузитьКолонку("Свойство");
НаборыСвойств = Новый ТаблицаЗначений;
НаборыСвойств.Колонки.Добавить(
"Набор", Новый ОписаниеТипов("СправочникСсылка.НаборыДополнительныхРеквизитовИСведений"));
НаборыСвойств.Колонки.Добавить(
"ПорядокНабора", Новый ОписаниеТипов("Число"));
Для каждого ЭлементСписка Из Наборы Цикл
НоваяСтрока = НаборыСвойств.Добавить();
НоваяСтрока.Набор = ЭлементСписка.Значение;
НоваяСтрока.ПорядокНабора = Наборы.Индекс(ЭлементСписка);
КонецЦикла;
Запрос = Новый Запрос;
Запрос.УстановитьПараметр("Свойства", Свойства);
Запрос.УстановитьПараметр("НаборыСвойств", НаборыСвойств);
Запрос.УстановитьПараметр("ЭтоОсновнойЯзык", ТекущийЯзык() = Метаданные.ОсновнойЯзык);
Запрос.УстановитьПараметр("КодЯзыка", ТекущийЯзык().КодЯзыка);
Запрос.Текст =
"ВЫБРАТЬ
| НаборыСвойств.Набор КАК Набор,
| НаборыСвойств.ПорядокНабора КАК ПорядокНабора
|ПОМЕСТИТЬ НаборыСвойств
|ИЗ
| &НаборыСвойств КАК НаборыСвойств
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| НаборыСвойств.Набор КАК Набор,
| НаборыСвойств.ПорядокНабора КАК ПорядокНабора,
| СвойстваНаборов.Свойство КАК Свойство,
| СвойстваНаборов.ПометкаУдаления КАК ПометкаУдаления,
| СвойстваНаборов.НомерСтроки КАК ПорядокСвойства
|ПОМЕСТИТЬ СвойстваНаборов
|ИЗ
| НаборыСвойств КАК НаборыСвойств
| ВНУТРЕННЕЕ СОЕДИНЕНИЕ Справочник.НаборыДополнительныхРеквизитовИСведений.ДополнительныеРеквизиты КАК СвойстваНаборов
| ПО (СвойстваНаборов.Ссылка = НаборыСвойств.Набор)
| ВНУТРЕННЕЕ СОЕДИНЕНИЕ ПланВидовХарактеристик.ДополнительныеРеквизитыИСведения КАК Свойства
| ПО (СвойстваНаборов.Свойство = Свойства.Ссылка)
|ГДЕ
| НЕ СвойстваНаборов.ПометкаУдаления
| И НЕ Свойства.ПометкаУдаления
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| Свойства.Ссылка КАК Свойство
|ПОМЕСТИТЬ ЗаполненныеСвойства
|ИЗ
| ПланВидовХарактеристик.ДополнительныеРеквизитыИСведения КАК Свойства
|ГДЕ
| Свойства.Ссылка В(&Свойства)
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ
| СвойстваНаборов.Набор КАК Набор,
| СвойстваНаборов.ПорядокНабора КАК ПорядокНабора,
| СвойстваНаборов.Свойство КАК Свойство,
| СвойстваНаборов.ПорядокСвойства КАК ПорядокСвойства,
| СвойстваНаборов.ПометкаУдаления КАК Удалено
|ПОМЕСТИТЬ ВсеСвойства
|ИЗ
| СвойстваНаборов КАК СвойстваНаборов
|
|ОБЪЕДИНИТЬ ВСЕ
|
|ВЫБРАТЬ
| ЗНАЧЕНИЕ(Справочник.НаборыДополнительныхРеквизитовИСведений.ПустаяСсылка),
| 0,
| ЗаполненныеСвойства.Свойство,
| 0,
| ИСТИНА
|ИЗ
| ЗаполненныеСвойства КАК ЗаполненныеСвойства
| ЛЕВОЕ СОЕДИНЕНИЕ СвойстваНаборов КАК СвойстваНаборов
| ПО ЗаполненныеСвойства.Свойство = СвойстваНаборов.Свойство
|ГДЕ
| СвойстваНаборов.Свойство ЕСТЬ NULL
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| ВсеСвойства.Набор КАК Набор,
| ВсеСвойства.Свойство КАК Свойство,
| ДополнительныеРеквизитыИСведения.ВладелецДополнительныхЗначений КАК ВладелецДополнительныхЗначений,
| ДополнительныеРеквизитыИСведения.ЗаполнятьОбязательно КАК ЗаполнятьОбязательно,
| ВЫБОР
| КОГДА &ЭтоОсновнойЯзык
| ТОГДА ДополнительныеРеквизитыИСведения.Заголовок
| ИНАЧЕ ВЫРАЗИТЬ(ЕСТЬNULL(СвойстваПредставления.Заголовок, ДополнительныеРеквизитыИСведения.Заголовок) КАК СТРОКА(150))
| КОНЕЦ КАК Наименование,
| ДополнительныеРеквизитыИСведения.ТипЗначения КАК ТипЗначения,
| ДополнительныеРеквизитыИСведения.ФорматСвойства КАК ФорматСвойства,
| ДополнительныеРеквизитыИСведения.МногострочноеПолеВвода КАК МногострочноеПолеВвода,
| ВсеСвойства.Удалено КАК Удалено,
| ДополнительныеРеквизитыИСведения.Доступен КАК Доступен,
| ДополнительныеРеквизитыИСведения.Виден КАК Виден,
| ВЫБОР
| КОГДА &ЭтоОсновнойЯзык
| ТОГДА ДополнительныеРеквизитыИСведения.Подсказка
| ИНАЧЕ ВЫРАЗИТЬ(ЕСТЬNULL(СвойстваПредставления.Подсказка, ДополнительныеРеквизитыИСведения.Подсказка) КАК СТРОКА(150))
| КОНЕЦ КАК Подсказка,
| ДополнительныеРеквизитыИСведения.ВыводитьВВидеГиперссылки КАК ВыводитьВВидеГиперссылки,
| ДополнительныеРеквизитыИСведения.ЗависимостиДополнительныхРеквизитов.(
| ЗависимоеСвойство КАК ЗависимоеСвойство,
| Реквизит КАК Реквизит,
| Условие КАК Условие,
| Значение КАК Значение,
| НаборСвойств КАК НаборСвойств
| ) КАК ЗависимостиДополнительныхРеквизитов
|ИЗ
| ВсеСвойства КАК ВсеСвойства
| ВНУТРЕННЕЕ СОЕДИНЕНИЕ ПланВидовХарактеристик.ДополнительныеРеквизитыИСведения КАК ДополнительныеРеквизитыИСведения
| ПО ВсеСвойства.Свойство = ДополнительныеРеквизитыИСведения.Ссылка
| ЛЕВОЕ СОЕДИНЕНИЕ ПланВидовХарактеристик.ДополнительныеРеквизитыИСведения.Представления КАК СвойстваПредставления
| ПО (СвойстваПредставления.Ссылка = ДополнительныеРеквизитыИСведения.Ссылка)
| И (СвойстваПредставления.КодЯзыка = &КодЯзыка)
|
|УПОРЯДОЧИТЬ ПО
| Удалено,
| ВсеСвойства.ПорядокНабора,
| ВсеСвойства.ПорядокСвойства";
Если ЭтоДополнительноеСведение Тогда
Запрос.Текст = СтрЗаменить(
Запрос.Текст,
"Справочник.НаборыДополнительныхРеквизитовИСведений.ДополнительныеРеквизиты",
"Справочник.НаборыДополнительныхРеквизитовИСведений.ДополнительныеСведения");
КонецЕсли;
ОписаниеСвойств = Запрос.Выполнить().Выгрузить();
ОписаниеСвойств.Индексы.Добавить("Свойство");
ОписаниеСвойств.Колонки.Добавить("Значение");
// Удаление дублей свойств в нижестоящих наборах свойств.
Если Наборы.Количество() > 1 Тогда
Индекс = ОписаниеСвойств.Количество()-1;
Пока Индекс >= 0 Цикл
Строка = ОписаниеСвойств[Индекс];
НайденнаяСтрока = ОписаниеСвойств.Найти(Строка.Свойство, "Свойство");
Если НайденнаяСтрока <> Неопределено
И НайденнаяСтрока <> Строка Тогда
ОписаниеСвойств.Удалить(Индекс);
КонецЕсли;
Индекс = Индекс-1;
КонецЦикла;
КонецЕсли;
// {{ Prosto. [Silantev Oleg Sergeevich] - [26.09.2020 21:33].
ИспользованныеСвойства = Новый Массив;
// }} {{ Prosto. [Silantev Oleg Sergeevich] - [26.09.2020 21:33].
// Заполнение значений свойств.
Для Каждого Строка Из ДополнительныеСвойстваОбъекта Цикл
ОписаниеСвойства = ОписаниеСвойств.Найти(Строка.Свойство, "Свойство");
Если ОписаниеСвойства <> Неопределено Тогда
// {{ Prosto. [Silantev Oleg Sergeevich] - [26.09.2020 21:34].
Если ИспользованныеСвойства.Найти(ОписаниеСвойства.Свойство) = Неопределено Тогда
ИспользованныеСвойства.Добавить(ОписаниеСвойства.Свойство)
Иначе
НоваяСтрокаОписания = ОписаниеСвойств.Добавить();
ЗаполнитьЗначенияСвойств(НоваяСтрокаОписания, ОписаниеСвойства);
ОписаниеСвойства = НоваяСтрокаОписания;
КонецЕсли;
// }} {{ Prosto. [Silantev Oleg Sergeevich] - [26.09.2020 21:34].
// Поддержка строк неограниченной длины.
Если НЕ ЭтоДополнительноеСведение Тогда
ИспользоватьСтрокуВВидеСсылки = ИспользоватьСтрокуВВидеСсылки(
ОписаниеСвойства.ТипЗначения,
ОписаниеСвойства.ВыводитьВВидеГиперссылки,
ОписаниеСвойства.МногострочноеПолеВвода);
ИспользоватьНеограниченнуюСтроку = ИспользоватьНеограниченнуюСтроку(
ОписаниеСвойства.ТипЗначения,
ОписаниеСвойства.МногострочноеПолеВвода);
НеобходимоПеренестиЗначениеИзСсылки = НеобходимоПеренестиЗначениеИзСсылки(
Строка.ТекстоваяСтрока,
Строка.Значение);
Если (ИспользоватьНеограниченнуюСтроку
Или ИспользоватьСтрокуВВидеСсылки
Или НеобходимоПеренестиЗначениеИзСсылки)
И НЕ ПустаяСтрока(Строка.ТекстоваяСтрока) Тогда
Если Не ИспользоватьСтрокуВВидеСсылки И НеобходимоПеренестиЗначениеИзСсылки Тогда
ЗначениеБезСсылки = ЗначениеБезСсылки(Строка.ТекстоваяСтрока, Строка.Значение);
ОписаниеСвойства.Значение = ЗначениеБезСсылки;
Иначе
ОписаниеСвойства.Значение = Строка.ТекстоваяСтрока;
КонецЕсли;
Иначе
ОписаниеСвойства.Значение = Строка.Значение;
КонецЕсли;
Иначе
ОписаниеСвойства.Значение = Строка.Значение;
КонецЕсли;
КонецЕсли;
КонецЦикла;
Возврат ОписаниеСвойств;
КонецФункции
Работа в примерах была осуществлена с версией БСП: 3.1.2.245.
Источники
Как подключить дополнительные реквизиты к справочнику или документу в БСП 2.3
Создание множественного дополнительного реквизита. Управление торговлей 11