Как реализовать добавление и просмотр нескольких изображений для товара в мобильном приложении 1С

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

В процессе разработки мобильных приложений на платформе 1С:Предприятие 8.3 часто возникает задача реализации полноценной галереи для товаров. Стандартный функционал платформы позволяет легко привязать одну картинку, но когда требуется добавить неограниченное количество фото и обеспечить удобную навигацию между ними, разработчику приходится проектировать собственную логику. В этой статье мы подробно разберем, как организовать хранение, загрузку и «листание» нескольких изображений для одной номенклатуры.

Архитектура хранения данных для нескольких изображений

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

Рассмотрим создание справочника ПрисоединенныеФайлы (или использование типового механизма из БСП). Основные требования к справочнику:

  1. Владелец: Реквизит с типом СправочникСсылка.Номенклатура.
  2. ДанныеФайла: Реквизит с типом ХранилищеЗначения, где будет храниться сам бинарный файл картинки.
  3. Порядок: Числовой реквизит для управления последовательностью вывода (чтобы пользователь мог определить, какая картинка будет первой, второй и т.д.).
  4. Индексация: Поле Владелец обязательно должно быть индексировано для быстрого поиска всех файлов конкретного товара.

Получение списка картинок на сервере

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

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


&НаСервере
Процедура ПолучитьСписокКартинокСервер()
    
    // Очищаем текущий массив ссылок на клиенте
    МассивСсылок.Очистить(); 
    
    Запрос = Новый Запрос;
    Запрос.Текст = 
        "ВЫБРАТЬ
        |   ПрисоединенныеФайлы.Ссылка КАК Ссылка
        |ИЗ
        |   Справочник.ПрисоединенныеФайлы КАК ПрисоединенныеФайлы
        |ГДЕ
        |   ПрисоединенныеФайлы.Владелец = &Владелец
        |УПОРЯДОЧИТЬ ПО
        |   ПрисоединенныеФайлы.Порядок";
    
    Запрос.УстановитьПараметр("Владелец", Объект.Ссылка);
    
    Результат = Запрос.Выполнить();
    Выборка = Результат.Выбрать();
    
    Пока Выборка.Следующий() Цикл
        // Формируем навигационную ссылку на реквизит ХранилищеЗначения
        СсылкаНаКартинку = ПолучитьНавигационнуюСсылку(Выборка.Ссылка, "ДанныеФайла");
        МассивСсылок.Добавить(СсылкаНаКартинку);
    КонецЦикла;
    
    Если МассивСсылок.Количество() > 0 Тогда
        ТекущийИндексКартинки = 0;
        ОбновитьИзображениеНаФорме();
    КонецЕсли;

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

Реализация логики перелистывания (кнопки Вперед и Назад)

Проанализируем ситуацию: у нас есть массив строк (навигационных ссылок) и индекс текущего элемента. Теперь нам нужно добавить на форму кнопки управления. Для этого создадим команды Вперед и Назад и привяжем их к кнопкам на форме мобильного приложения.

Выясним, как должна работать логика индексов, чтобы избежать ошибок выхода за границы массива:


&НаКлиенте
Процедура Вперед(Команда)
    Если МассивСсылок.Количество() = 0 Тогда
        Возврат;
    КонецЕсли;

    // Увеличиваем индекс, реализуя цикличность
    Если ТекущийИндексКартинки < МассивСсылок.Количество() - 1 Тогда
        ТекущийИндексКартинки = ТекущийИндексКартинки + 1;
    Иначе
        ТекущийИндексКартинки = 0; // Возврат в начало
    КонецЕсли;

    ОбновитьИзображениеНаФорме();
КонецПроцедуры

&НаКлиенте
Процедура Назад(Команда)
    Если МассивСсылок.Количество() = 0 Тогда
        Возврат;
    КонецЕсли;

    // Уменьшаем индекс
    Если ТекущийИндексКартинки > 0 Тогда
        ТекущийИндексКартинки = ТекущийИндексКартинки - 1;
    Иначе
        ТекущийИндексКартинки = МассивСсылок.Количество() - 1; // Переход в конец
    КонецЕсли;

    ОбновитьИзображениеНаФорме();
КонецПроцедуры

&НаКлиенте
Процедура ОбновитьИзображениеНаФорме()
    // Реквизит формы "Фото" (тип Строка) связан с элементом управления "Поле картинки"
    Фото = МассивСсылок[ТекущийИндексКартинки].Значение;
КонецПроцедуры

Добавление новых фото через камеру мобильного устройства

Для мобильного приложения критически важно уметь добавлять фото «на лету». Рассмотрим, как программно вызвать камеру и сохранить результат в наш справочник. Для этого воспользуемся объектом СредстваМультимедиа.


&НаКлиенте
Процедура СделатьСнимок(Команда)
    #Если МобильноеПриложениеКлиент Тогда
        ДанныеФото = СредстваМультимедиа.СделатьФотоснимок();
        Если ДанныеФото <> Неопределено Тогда
            СохранитьФотоНаСервере(ДанныеФото.ПолучитьДвоичныеДанные());
        КонецЕсли;
    #КонецЕсли
КонецПроцедуры

&НаСервере
Процедура СохранитьФотоНаСервере(ДвоичныеДанные)
    НовыйФайл = Справочники.ПрисоединенныеФайлы.СоздатьЭлемент();
    НовыйФайл.Владелец = Объект.Ссылка;
    НовыйФайл.ДанныеФайла = Новый ХранилищеЗначения(ДвоичныеДанные);
    НовыйФайл.Наименование = "Фото от " + ТекущаяДата();
    НовыйФайл.Записать();
    
    // После записи обновляем массив ссылок
    ПолучитьСписокКартинокСервер();
КонецПроцедуры

Оптимизация: использование ленты миниатюр

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

Посмотрим на алгоритм реализации такой ленты:

  1. Создаем на форме таблицу (тип СписокЗначений), у которой включен режим отображения Список.
  2. В свойствах таблицы устанавливаем горизонтальную ориентацию (если позволяет экран) или используем компактный вертикальный список.
  3. В колонке таблицы отображаем саму картинку. В платформе 1С для этого у элемента формы «Поле» нужно установить вид Поле картинки.
  4. При событии ПриАктивизацииСтроки этой таблицы мы просто обновляем основное большое изображение, передавая в него адрес из текущей строки миниатюр.

Важный момент для мобильных платформ: Память мобильных устройств ограничена. Если вы загружаете в ленту миниатюр полноразмерные фотографии (по нескольку мегабайт каждая), приложение может начать тормозить или аварийно завершаться. Рекомендуем при сохранении фото на сервере генерировать «превью» — уменьшенную копию изображения, и хранить её в отдельном реквизите справочника. В ленте миниатюр отображайте именно «легкие» копии.

Использование Поля HTML-документа для современного UI

Проанализируем еще одну интересную идею. Вместо стандартных кнопок и полей картинок можно использовать Поле HTML-документа. Это позволит реализовать полноценный слайдер с поддержкой жестов (свайпов).

Для этого потребуется:

Такой подход сделает мобильное приложение более «нативным» и приятным для пользователя, так как листание пальцем — это стандартное поведение в современных мобильных интерфейсах. Однако этот метод требует знаний HTML/JS и более сложен в отладке.

Таким образом, мы рассмотрели несколько способов работы с изображениями. Самый простой и надежный для реализации в 1С — это использование динамического массива ссылок и кнопок навигации, что позволяет пользователю комфортно работать с любым количеством фотографий товара.

← На главную