Итоговая задача: построить прайс-лист с изображениями номенклатур для УТ (т.е. в прайсе предполагается выводить изображения, которые показываются в карточке номенклатуры)
После недолгих поисков выяснилось, что информация которую можно сконвертировать в изображение находится в справочнике НоменклатураПрисоединенныеФайлы, на элементы которого может ссылаться реквизит номенклатуры ФайлКартинки. Сама бинарная информация, которую можно сконвертировать в картинку, может находится либо в регистре сведений ПрисоединенныеФайлы, либо на внешнем по отношению к базе носителе (папка на диске сервера).
Будем дорабатывать стандартный отчет УТ 11.0.9.15 Прайс-лист, для удобства сохраним его в качестве внешнего.
Порядок действий для вывода картинок в печатной форме СКД:
1. К запросу СКД добавляем поле со ссылкой на справочник НоменклатураПрисоединенныеФайлы, соответствущей элементу номенклатуры.
2. При выводе соответствующего элемента макета читаем информацию о картинке и выводим её в соответствующей ячейке:
2.1. Получаем ячейку табличного документа, в которой предполагается вывести кртинку.
2.2. Преобразуем бинарную информацию по ссылке, полученной в п.1. в картинку и выводим её в ячейке, полученной в п.2.1.
2.3. Производим дополнительное оформление ячейки и картинки (меняем размер, цвет линии и тд.)
Итак по вышеописанному плану:
Добавим в запрос СКД новое поле Изображение:
ЦеныНоменклатурыСрезПоследних.Номенклатура.ФайлКартинки КАК Изображение
Видоизменим варианты настроек (добавим группировку по Изображению):
Добавим новый параметр ШиринаКолонкиИзображения, через который будем регулировать размер изображения:
Нам потребуется вмешиваться в процесс формирования отчета, поэтому добавим в конец процедуры модуля объекта ПриКомпоновкеРезультата, следующий код:
СтандартнаяОбработка = Ложь;
ИмяКолонкиИзображения = «Изображение»;
ДокументРезультат.Очистить();
КомпоновщикМакета = Новый КомпоновщикМакетаКомпоновкиДанных;
//Получаем параметр отчета ШиринаКолонкиИзображения, и устанавливаем ширину колонки, в которой предполагаем выводить изображение
ШиринаКолонкиИзображения = ВернутьЗначениеПараметраНастройкиСКД(КомпоновщикНастроек.Настройки.ПараметрыДанных.Элементы, «ШиринаКолонкиИзображения», 20); //В средних символах
ПолеИзображения = СхемаКомпоновкиДанных.НаборыДанных.ПрайсЛист.Поля.Найти(ИмяКолонкиИзображения);
Если Не ПолеИзображения = Неопределено Тогда
ОформлениеМинимальнойШириныКолонки = СхемаКомпоновкиДанных.НаборыДанных.ПрайсЛист.Поля.Найти(ИмяКолонкиИзображения).Оформление.Элементы.Найти(«МинимальнаяШирина»);
ОформлениеМинимальнойШириныКолонки.Использование = Истина;
ОформлениеМинимальнойШириныКолонки.Значение = ШиринаКолонкиИзображения;
КонецЕсли;
//Выводим макет, здесь все почти стандартно.
Макет = КомпоновщикМакета.Выполнить(СхемаКомпоновкиДанных, КомпоновщикНастроек.ПолучитьНастройки(), ДанныеРасшифровки);
ПроцессорКомпоновки = Новый ПроцессорКомпоновкиДанных;
ПроцессорКомпоновки.Инициализировать(Макет, , ДанныеРасшифровки);
ПроцессорВывода = Новый ПроцессорВыводаРезультатаКомпоновкиДанныхВТабличныйДокумент;
ПроцессорВывода.УстановитьДокумент(ДокументРезультат);
ПроцессорВывода.НачатьВывод();
Пока Истина Цикл
ЭлементРезультата = ПроцессорКомпоновки.Следующий();
Если ЭлементРезультата = Неопределено Тогда Прервать;КонецЕсли;
ПроцессорВывода.ВывестиЭлемент(ЭлементРезультата);
Если ЭлементРезультата.ЗначенияПараметров.Количество() = 0 Тогда Продолжить; КонецЕсли;
Для Каждого ЭлементПараметра Из ЭлементРезультата.ЗначенияПараметров Цикл
Если ТипЗнч(ЭлементПараметра.Значение) = Тип(«ИдентификаторРасшифровкиКомпоновкиДанных«) Тогда
Поля = ДанныеРасшифровки.Элементы[ЭлементПараметра.Значение].ПолучитьПоля();
Для Каждого Поле Из Поля Цикл
Если ТипЗнч(Поле.Значение) = Тип(«СправочникСсылка.НоменклатураПрисоединенныеФайлы») Тогда
Если Поле.Значение.Пустая() Тогда Продолжить; КонецЕсли;
//Поиск номера колонки, с нужным именем ИмяКолонкиИзображения, для таки вывода изображения
Для НомерКолонки = 1 По ДокументРезультат.ШиринаТаблицы Цикл
Расшифровка = ДокументРезультат.Область(ДокументРезультат.ВысотаТаблицы, НомерКолонки, ДокументРезультат.ВысотаТаблицы, НомерКолонки).Расшифровка;
Если Расшифровка = Неопределено Тогда Продолжить; КонецЕсли;
Поля = ДанныеРасшифровки.Элементы.Получить(Расшифровка).ПолучитьПоля();
Если Поля.Найти(ИмяКолонкиИзображения) = Неопределено Тогда Продолжить; КонецЕсли;
ОбластьИзображения = ДокументРезультат.Область(ДокументРезультат.ВысотаТаблицы, НомерКолонки);
ВывестиИзображениеЭлементаНоменклатуры(ДокументРезультат, Поле.Значение, ОбластьИзображения, ШиринаКолонкиИзображения);
КонецЦикла;
КонецЕсли;
КонецЦикла;
КонецЕсли;
КонецЦикла;
КонецЦикла;
ПроцессорВывода.ЗакончитьВывод();
Для удобства процедура вывода изображения выделена в отдельную, эта процедура просто получает данные для вывода рисунка, выводит его (используя функцию), настраивает его оформление.
Процедура ВывестиИзображениеЭлементаНоменклатуры(ТД, ЭлементСправочника, Область, ШиринаКолонкиИзображения)
Если ЭлементСправочника.ТипХраненияФайла = Перечисления.ТипыХраненияФайлов.ВИнформационнойБазе Тогда
СтуктураРег = РегистрыСведений.ПрисоединенныеФайлы.Получить(Новый Структура(«ПрисоединенныйФайл», ЭлементСправочника));
ДанныеКартинки = СтуктураРег.ХранимыйФайл.Получить();
Иначе
ДанныеКартинки = ?(ЗначениеЗаполнено(ЭлементСправочника.Том.ПолныйПутьWindows), ЭлементСправочника.Том.ПолныйПутьWindows, ЭлементСправочника.Том.ПолныйПутьLinux)
+ ЭлементСправочника.ПутьКФайлу;
КонецЕсли;
Рисунок = ВывестиИзображениеВОбластиТД(ДанныеКартинки, ТД, Область);
Область.АвтоВысотаСтроки = Ложь;
Область.ВысотаСтроки = ШиринаКолонкиИзображения * 1.31 / 0.3759;// Среднее значение пункта 1 пункт = 0.3759 мм (по Wiki)
Область.Расшифровка = ЭлементСправочника;
Рисунок.ЦветЛинии = Область.ЦветРамки;
КонецПроцедуры
Из предыдущей процедуры вызывается функция, которая непосредственно выводит изображение в заданной области табличного документа
Функция ВывестиИзображениеВОбластиТД(ДанныеКартинки, ТД, Область)
Изображение = ТД.Рисунки.Добавить(ТипРисункаТабличногоДокумента.Картинка);
Изображение.РазмерКартинки = РазмерКартинки.АвтоРазмер;
Индекс = ТД.Рисунки.Индекс(Изображение);
ТД.Рисунки[Индекс].Картинка = Новый Картинка(ДанныеКартинки, Истина);
ТД.Рисунки[Индекс].Расположить(Область);
Возврат ТД.Рисунки[Индекс];
КонецФункции
Кроме того при компоновке используется процедура извлечения параметра из СКД:
Функция ВернутьЗначениеПараметраНастройкиСКД(КоллекцияЭлементовНастройки, ИмяНастройки, ЗначениеПоУмолчанию = Неопределено)
Настройка = КомпоновщикНастроек.Настройки.ПараметрыДанных.Элементы.Найти(ИмяНастройки);
Если Настройка = Неопределено Тогда Возврат ЗначениеПоУмолчанию; КонецЕсли;
НастрокаПоИД = КомпоновщикНастроек.ПользовательскиеНастройки.Элементы.Найти(Настройка.ИдентификаторПользовательскойНастройки);
Если Не ЗначениеЗаполнено(НастрокаПоИД.Значение) Тогда
Если Не ЗначениеПоУмолчанию = Неопределено Тогда
НастрокаПоИД.Значение = ЗначениеПоУмолчанию;
КонецЕсли;
КонецЕсли;
Возврат ?(НастрокаПоИД.Использование, НастрокаПоИД.Значение, ЗначениеПоУмолчанию);
КонецФункции
Готовый отчет доступен к скачиванию.
Сформированный отчет выглядит приблизительно так:
ЗЫ: Существует некоторое незначительное развитие данного отчета: Прайс лист с картинками для УТ11 (добавление логотипа и свободных текстовых полей)
Пришлось немного эту функцию переделать, а то ошибки иногда выдает, а так очень помогло, вывел в прайс на ут 11.1.1.13 картинку.
Функция ВернутьЗначениеПараметраНастройкиСКД(КоллекцияЭлементовНастройки, ИмяНастройки, ЗначениеПоУмолчанию = Неопределено)
Настройка = КомпоновщикНастроек.Настройки.ПараметрыДанных.Элементы.Найти(ИмяНастройки);
Если Настройка = Неопределено Тогда Возврат ЗначениеПоУмолчанию; КонецЕсли;
НастрокаПоИД = КомпоновщикНастроек.ПользовательскиеНастройки.Элементы.Найти(Настройка.ИдентификаторПользовательскойНастройки);
Если НастрокаПоИД = Неопределено Тогда
Возврат ЗначениеПоУмолчанию;
Конецесли;
Если Не ЗначениеЗаполнено(НастрокаПоИД.Значение) Тогда
Если Не ЗначениеПоУмолчанию = Неопределено Тогда
НастрокаПоИД.Значение = ЗначениеПоУмолчанию;
КонецЕсли;
КонецЕсли;
Возврат ?(НастрокаПоИД.Использование, НастрокаПоИД.Значение, ЗначениеПоУмолчанию);
КонецФункции
(1) @lexandr, Странно, у меня вообще ошибок не возникало никогда, причем во всех трех версиях отчета, даже здесьhttp://infostart.ru/public/178422/ , возможно проблема в том, что какое-либо поле исключено из пользовательских настроек.
Отличное решение без доп. макета. На основе публикации сделал похожее для картинок из внешних файлов. Огромное спасибо.
Почему-то у меня не получается изменить высоту строки с изображением. Пробовал и явно, и с помощью изменения в коде
(4) tolyan_ekb,
вот здесь:http://infostart.ru/public/178422/
родной адекватно работающей функции — не нашел.
(4) tolyan_ekb, смотрите пятый комментарий.
(4) tolyan_ekb, еще возможно в Вашем макете стоИт ограничение минимальной высоты строки или автовысота.
(6) спасибо. Но я установил высоту напрямую в условном оформлении, после чего она изменилась. Возможно, программно чего-то не доуказал.
(6) Спасибо!
Не срабатывает инициализация ПроцессорКомпоновки.Инициализировать(Макет, , ДанныеРасшифровки)
Дело в том, что у меня в СКД есть параметры в которых задано выражение, например, Справочники.Валюты.НайтиПоКоду(«156»). Может быть подскажете как получить значение у этих параметров????
(9) varovinm, попробуйте
вообще лучше либо задавать валюту в параметрах (неявно), либо получать её в запросе, например из констант.
Реально ли сделать такой прайс для 1С 8.1, «Управление торговлей для Украины», редакция 2.3 ?
(11) killexx, Реально всё. Если Ваша конфигурация на управляемых формах то за образец можете использовать текущую разработку. Если же на обычных формах — то, например вот этуhttp://infostart.ru/public/151012/ .
Коллеги, а скажите может есть мысли при выведении отчета с картинками уж больно долго выводится. Может у кого нить есть мысли куда копать. (Я попробывал выводить в УПР интерфейсе и в простом, так вот в простом интерфейсе выводится быстрее на порядок). может начать смотреть размеры картинок.
Понравилась реализация, автору плюс! На примере публикации создал отчет. Большое спасибо.
Спасибо автору за публикацию. Очень помогло в собственной разработке.
Попробовал сделать по данной схеме отчёт, выдаёт ошибку
«Поле изображение не может быть использовано в группировке номенклатура, упаковка, характеристика»
Подскажите пожалуйста в чём может быть проблемка?
Делал на УТ 11.1.4.14 , на основе типового отчёта «Прайс»
Если «изображение» как ресурс, то ошибку не выдаёт но и поле «изображение» не выводит вообще
В последних версиях УТ11 этот отчет уже не работает!!!
Ребята из 1С сами задействовали Процедуру ПриКомпоновкеРезультата и если там поставить СтандартнаяОбработка = Ложь. то отчет перестает работать
Да отчет не работает
Метод объекта не обнаружен ПолучитьПараметр
В версии УТ 11 _11.3.2.207 отчет не работает
Метод объекта не обнаружен ПолучитьПараметр
Функция ПоучитьПараметр находится в общем модуле КомпоновкаДанныхКлиентСервер.
прекрасно — работает )
спасибо!
На небольших объемах все это хорошо работает, но когда в отчете тысячи строк и в каждой картинка время ожидание неприемлемо велико. Есть у кого нибудь идеи как оптимизировать этот нюанс? Очень бы хотелось без изменения конфигурации
Хм, делал по аналогии и такая получается штука: в файловой базе 550 строк с картинками выводит за 3-4 минуты, перевожу базу на SQL — спустя полчасатак никаких результатов и не видно… Пока отладку не включал, вставил записи в ЖР: в процедуре «ПриКомпоновкеРезультата» строку «ПроцессорВывода.ЗакончитьВывод();» успешно проходит… Картинки пробовал и в базе размещать, и в каталогах
UPD: спустя 40 минут все-таки вывел
Для текущих версий ЕРП и УТ11 в процедуре ВывестиИзображениеНоменклатуры вместо обращения к РС Присоединенные файлы необходимо прописать следующее (Сначала закомментированный код):
//Если ЭлементСправочника.ТипХраненияФайла = Перечисления.ТипыХраненияФайлов.ВИнформационнойБазе Тогда
// СтуктураРег = РегистрыСведений.ПрисоединенныеФайлы.Получить(Новый Структура(«ПрисоединенныйФайл», ЭлементСправочника));
// ДанныеКартинки = СтуктураРег.ХранимыйФайл.Получить();
//Иначе
// ДанныеКартинки = ?(ЗначениеЗаполнено(ЭлементСправочника.Том.ПолныйПутьWindows), ЭлементСправочника.Том.ПолныйПутьWindows, ЭлементСправочника.Том.ПолныйПутьLinux)
// + ЭлементСправочника.ПутьКФайлу;
//КонецЕсли;
Вместо закомментированного, следующее
ДанныеКартинки = ПолучитьИзВременногоХранилища(РаботаСФайлами.ДанныеФайла(ЭлементСправочника).СсылкаНаДвоичныеДанныеФайла);
P.s. Если кто кинет ссылку на инструкцию как в комментариях красиво код оформлять, буду благодарен. (Чтобы красненькое красненьким было, синенькое сининьким).
(25)
(24) Самое узкое место в выводе отчета с картинками это передача его обратно с сервера на клиента, При передаче платформа сериализует табличный документ и передает таким образом в разы больше информации , чем нужно. А на клиенте съедаются в это время Гигабайты.дискового постранства. У меня при выводе отчета продаж за месяц отчет вообще падал с ошибкой формата потока. Нашел следующий выход:
Если отчет не в типовом решении, то в обработку на сервер не надо передавать табличный документ.
При окончании обработки на сервере созданный табличный документ помещается во временной хранилище. Адрес временного хранилища можно задать или в реквизите формы или передать с клиента. А на клиенте уже из временного хранилища создается табличный документ. Что-то типа следующего:
Показать
Если про типовое решение, то в отчете по себестоимости и выручке продаж сделал так:
1) скопировал и создал из типового отчета свой отчет ОтчетПродажиСИзображением
2) Скопировал общую форму отчета и поместил ее в новый отчет
3) Выбрал форму отчета — новую форму отчета
4) в новой форме отчета добавил реквизит АдресН Тип строка неограниченной длины
5) в форме отчета в процедуре ФоновоеЗаданиеЗагрузитьРезультат закомментировал стандартную передачу результата табличного документа и добавил строку по помещению табличного документа во временное хранилище
6) в процедуре ПослеФормирванияНаКлиенте добавил строку в начале процедуры
Отчет из полутора тысяч строк вводится за 3 минуты. Отчет за месяц, который ранее не выводился вообще, выводится менее 15 минут. Работает в фоне, при условии, что отчет в конфигурации, а не внешний. Все сделанные доработки тоже касаются варианта, что отчет встроенный. Если внешний, то возможно алгоритмы идут по другим веткам и потребуются доработки.
Айайай братюня затащил вообще молодец, все работает, даже без допиливания))) красавчик вообще, лукаснул тебе)))
В 8.3.14 вывод картинок в СКД появится из коробки!
Для системы компоновки данных реализована возможность отображения картинок, расположенных в информационной базе. В отчете могут отображаться картинки, заданные в качестве навигационной ссылки на картинку и собственно картинкой, размещенной в реквизите типа ХранилищеЗначения.
Для объектов ОформлениеКомпоновкиДанных и ОформлениеЯчейкиТаблицыОбластиКомпоновкиДанных реализованы свойства ВыводитьКартинку, РазмерКартинки, ПоложениеТекстаОтносительноКартинки, ГоризонтальноеПоложениеКартинки, ВертикальноеПоложениеКартиинки.
В режиме совместимости с версией 8.3.13 поведение по умолчанию не изменилось.
Источник:https://dl04.1c.ru/content/Platform/8_3_14_1565/1cv8upd_8_3_14_1565.htm#a06301e2-a9ff-11e8-a3f7-0050569f678a
(1) Спасибо, помогло
Добрый день, может кто подскажет ((( Бьюсь с выводом картинок и вроде все норм, кроме того что картинка пустая. Картинки хранятся и в томах и в информационной базе. База УТ 11.3, платформа 8.3.10. Неделю уже всеми способами ковыряюсь, все равно пустые(