14 KiB
Задание к занятию "Двоичные данные"
Результат выполнения первых двух задач вышлите одним файлом (.dt)
Задача 1 Создать в справочнике Номенклатура возможность загрузки и хранения картинки.
Описание задачи
Добавить возможность загрузки и хранения картинки в справочнике Номенклатура.
Требования к результату
Выгрузка информационной базы (.dt) с конфигурацией из предыдущих заданий, в которой реализована возможность загружать и просматривать из формы элемента номенклатуры.
Можно выбрать каталог и картинку для загрузки.
Процесс выполнения
-
Добавим реквизит "ФайлКартинки" с типом Хранилище значения в справочнике Номенклатура.
-
Добавим реквизит "ПутьКартинки" на форму элемента, укажем тип "Строка". В нем будет адрес картинки во временном хранилище. Разместим реквизит на форме с видом "Поле картинки". Установим для элемента формы флажок "Гиперссылка".
-
Добавим на событие Нажатие процедуру "ПутьКартинкиНажатие".
-
Внутри процедуры вызовем асинхронную процедуру для выбора файла с картинкой. Дополнительная процедура нужна т.к. обработчик элемента формы не может быть асинхронной процедурой.
&НаКлиенте
Процедура ПутьКартинкиНажатие(Элемент, СтандартнаяОбработка)
СтандартнаяОбработка = Ложь;
ПрочитатьКартинкуНоменклатуры();
КонецПроцедуры
Добавим выбор файла с логичными для этого фильтрами отбора формата файла, проверим, что пользователь выбрал файл и сохраним адрес временного хранилища.
&НаКлиенте
Асинх Процедура ПрочитатьКартинкуНоменклатуры()
ПараметрыПомещенияФайла = Новый ПараметрыДиалогаПомещенияФайлов;
ПараметрыПомещенияФайла.Фильтр = "Картинка (*.jpg)|*.jpg";
ОписаниеФайла = Ждать ПоместитьФайлНаСерверАсинх(,,, ПараметрыПомещенияФайла, УникальныйИдентификатор);
Если ОписаниеФайла = Неопределено Тогда
Возврат;
КонецЕсли;
Если ОписаниеФайла.ПомещениеФайлаОтменено Тогда
Возврат;
КонецЕсли;
ПутьКартинки = ОписаниеФайла.Адрес;
КонецПроцедуры
-
Перед записью на сервере запишем в хранилище значений картинку.
-
При чтении на сервере получим картинку из хранилища значений.
Пример получения через временное хранилище и записи в реквизит объекта через Хранилище значений.
&НаСервере
Процедура ПередЗаписьюНаСервере(Отказ, ТекущийОбъект, ПараметрыЗаписи)
ДвоичныеДанные = ПолучитьИзВременногоХранилища(ПутьКартинки);
ТекущийОбъект.ФайлКартинки = Новый ХранилищеЗначения(ДвоичныеДанные);
КонецПроцедуры
&НаСервере
Процедура ПриЧтенииНаСервере(ТекущийОбъект)
ДвоичныеДанные = ТекущийОбъект.ФайлКартинки.Получить();
ПутьКартинки = ПоместитьВоВременноеХранилище(ДвоичныеДанные, УникальныйИдентификатор);
КонецПроцедуры
Задача 2 Сохранение картинки номенклатуры с установленной шириной
Описание задачи
Добавить возможность сохранения в файл картинки номенклатуры с шириной 100 писелей
Требования к результату
Выгрузка информационной базы (.dt) с конфигурацией из предыдущих заданий, в которой реализована возможность загружать и просматривать из формы элемента номенклатуры.
Ранее выбранную картинку номенклатуры можно сохранить в файл, при этом ширина сохраненной картинки будет 100 пикселей.
Процесс выполнения
-
Добавим на форму элемента справочника Номенклатура команду СохранитьКартинку, создадим связанную с командой кнопку на коммандной панели формы.
-
Реализуем обработчик команды, в котором вызовем серверный метод для подготовки картинки и предложим пользователю сохранить картинку.
&НаКлиенте
Асинх Процедура СохранитьКартинку(Команда)
АдресРезультата = ПодготовитьКартинку();
// Если для номенклатуры не загружена картика, то не будем открывать окно сохранения файла
Если Не ЗначениеЗаполнено(АдресРезультата) Тогда
Возврат;
КонецЕсли;
ПараметрыПолученияФайла = Новый ПараметрыДиалогаПолученияФайлов;
ПолучитьФайлССервераАсинх(АдресРезультата, Объект.Наименование + ".jpg", ПараметрыПолученияФайла);
КонецПроцедуры
- Реализуем на сервере функцию для подготовки картинки.
&НаСервере
Функция ПодготовитьКартинку()
ДвоичныеДанныеИзображения = ПолучитьИзВременногоХранилища(ПутьКартинки);
Если ДвоичныеДанныеИзображения = Неопределено Тогда
Сообщение = Новый СообщениеПользователю;
Сообщение.Текст = "Картинка номенклатуры не загружена";
Сообщение.Сообщить();
Возврат Неопределено;
КонецЕсли;
Картинка = Новый Картинка(ДвоичныеДанныеИзображения);
ОбрабатываемаяКартинка = Новый ОбрабатываемаяКартинка(Картинка);
ОбрабатываемаяКартинка.УстановитьРазмер(100, Неопределено);
Картинка = ОбрабатываемаяКартинка.ПолучитьКартинку();
ДвоичныеДанныеИзображения = Картинка.ПолучитьДвоичныеДанные();
Возврат ПоместитьВоВременноеХранилище(ДвоичныеДанныеИзображения, УникальныйИдентификатор);
КонецФункции
Задача 3 (со звездочкой) Разбить файл на части и склеить после этого.
Описание задачи
Изучить системные глобальные методы "РазделитьФайл" и "ОбъединитьФайлы". Реализовать аналогичную пару методов самостоятельно во внешней обработке (при реализации не использовать "РазделитьФайл" и "ОбъединитьФайлы", необходимо реализовать их аналоги, пользуясь работой с файлами и потоками). Внешняя обработка должна содержать 2 закладки:
- Разделить файл
- Объединить файлы
На первой закладке расположено поле "Имя файла", в которой пользователь с помощью стандартного диалога выберет произвольный файл на диске. Так же на закладке расположено числовое поле "Размер части" и текстовое поле "Путь", в котором пользователь с помощью стандартного диалога выбора каталога выберет путь, в котором нужно разместить полученные части файла.
На второй закладке должен быть размещен элемент управления ТаблицаФормы, в котором пользователь сможет указать в нужном ему порядке перечень имен файлов. Так же на закладке должен быть размещен элемент "Результат", в котором пользователь с помощью стандартного диалога сохранения укажет место, в которое нужно сохранить результат склейки.
Порядок выполнения
Разбиение файлов
- Создать внешнюю обработку с реквизитами: "ИмяФайла", "РазмерЧасти", "Путь", "Результат" и табличной частью "ИменаЧастей" с единственным реквизитом "ИмяЧасти"
- В обработке создать форму и разместить в ней 2 страницы "Разделить файл" и "Объединить файлы". На странице "Разделить файл" разместить реквизиты "Имя файла" и "Размер части".
- В элементе управления "ИмяФайла" и "Путь" включить отображение кнопки выбора "КнопкаВыбора = Да";
- Реализовать алгоритм выбора файла с помощью стандартного диалога в поле "ИмяФайла" в обработчике "НачалоВыбора".
- Повторить для элемента управления "Путь", но использовать диалог в режиме выбора каталога
- Создать команду "РазделитьФайл" и разместить ее на форме на закладке "Разделить файл"
- Написать алгоритм разбиения файла на части. Каждая часть сохраняется в отдельный файл.
Подсказка по алгоритму разбиения
- Выяснить размер исходного файла и записать в переменную "ОсталосьПрочитать". См. объект "Файл" и "ФайловыйПоток"
- В цикле открыть новый файловый поток для записи. Имя части сгенерировать как
"Часть_"+"Счетчик
- Записать в файловый поток части методом
ИсходныйПоток.КопироватьВ(ПотокЧасти, РазмерЧасти)
- Перед записью проконтролировать, что
РазмерЧасти
меньше переменнойОсталосьПрочитать
. Если РазмерЧасти больше - скопировать только оставшееся число байт - Уменьшить переменную "ОсталосьПрочитать" на "РазмерЧасти"
Объединение файлов
- На закладке "Объединение файлов" разместить табличную часть "ИменаЧастей" и поле реквизита "Результат".
- В поле реквизита "Результат" включить отображение кнопки выбора и написать алгоритм выбора пути файла
- Создать команду "Объединить файлы" и разместить ее на форме
- Написать обработчик команды таким образом, чтобы он создал файл с именем, указанным в поле "Результат" и перенес в него содержимое всех файлов, перечисленных в таблице "ИменаЧастей"
Подсказка по алгоритму объединения
- Открыть для записи поток в файл из поля "Результат"
- В цикле по таблице
ИменаЧастей
открывать потоки для чтения текущей строки таблицы и копировать их в поток-результат методомПотокИсточник.КопироватьВ
- Количество байт контролировать в данном случае не надо.