Как разместить inline-блок в Android и iOS

Inline-блок — часть экрана приложения: баннер, промо с текстом и кнопкой, товарные рекомендации. Приложение выделяет место и подключает компонент SDK, а команда в Gravity Field управляет содержимым и условиями показа. Один блок может сочетать изображения, текст, кнопки и товары; SDK также поддерживает Webview и отступы.

1. Настройте кампанию в Gravity Field

  1. Создайте кампанию для мобильного приложения, настройте сценарий и вариацию с форматом Inline-блок. См. начало работы с кампаниями и структуру кампании.
  2. Согласуйте с разработчиком selector — имя места на экране. Значение в кампании и приложении должно совпадать. Например, home-promo — условное имя блока на главном экране, а не готовый selector вашего проекта.
  3. Соберите содержимое и внешний вид: элементы, высоту, отступы и действия по клику. Для рекомендаций добавьте «Продукты», выберите стратегию и количество товаров. Для общего макета Android/iOS используйте Строку: текущий iOS SDK не отображает товарную сетку.
  4. Настройте таргетинг и расписание, опубликуйте вариацию и кампанию. Передайте разработчику selector, ожидаемый контекст экрана и размеры блока.

2. Подготовьте приложение

Установите и один раз инициализируйте Gravity SDK по инструкции для Android или iOS. При GravitySDK.initialize(...) передайте gravityEventCallback для обработки действий. API-ключ и section должны относиться к проекту, где опубликована кампания.

Если блок содержит товары, реализуйте ProductViewBuilder и передайте его в тот же initialize(...) через productViewBuilder. Билдер получает slot, content, campaign и возвращает карточку в дизайне приложения. Для баннера без товаров он не нужен. Примеры: Android, iOS. В Android без билдера используется демонстрационная карточка, в iOS карточки не появятся.

3. Добавьте inline-компонент на экран

Ниже пример для главного экрана: замените home-promo и app://home согласованными значениями. PageContext описывает фактический экран; SKU, категории и другие данные из фида передавайте без изменения регистра. Подробнее: PageContext Android, PageContext iOS.

import ai.gravityfield.gravity_sdk.models.ContextType
import ai.gravityfield.gravity_sdk.models.PageContext
import ai.gravityfield.gravity_sdk.ui.GravityInlineCompose
import org.json.JSONObject

val pageContext = PageContext(
    type = ContextType.HOMEPAGE,
    data = emptyList(),
    location = "app://home",
)

key(pageContext) {
    GravityInlineCompose(
        modifier = Modifier.fillMaxWidth(),
        selector = JSONObject.quote("home-promo"),
        pageContext = pageContext,
        loader = { CircularProgressIndicator() },
    )
}

key — функция Compose; Modifier, fillMaxWidth и индикатор импортируйте из используемых библиотек Compose. Высоту задайте в кампании. Проверьте ограничения родительского контейнера, особенно в прокручиваемом списке.

Для Android 1.0.4 selector передаётся в SDK как JSON-строка; имя в кампании остаётся home-promo. Особенность сериализации.

Для XML используйте GravityInlineView: задайте app:selector, ширину и начальную высоту в layout, затем после инфлейта вызовите inlineView.init(pageContext).

import SwiftUI
import GravitySDK

let pageContext = PageContext(
    type: .homepage,
    data: [],
    location: "app://home"
)

GravityInlineSwiftUIView(
    selector: "home-promo",
    pageContext: pageContext
) {
    ProgressView()
}
.frame(maxWidth: .infinity)
.id(pageContext.location)

Высоту задайте в кампании. Для UIKit добавьте GravityInlineView в иерархию экрана, настройте constraints ширины и положения, затем вызовите:

let inlineView = GravityInlineView(selector: "home-promo")
// Добавьте inlineView в контейнер и настройте constraints.
inlineView.initialize(pageContext: pageContext)

UIKit-компонент обновляет высоту по настройке кампании; не перекрывайте её конфликтующим обязательным constraint.

Компоненты сами запрашивают и отображают контент: отдельный вызов getContentBySelector(...) для этого сценария не нужен. Просмотр экрана передавайте обычным trackView(...) для аналитики, но он не заменяет подключение inline-компонента.

При смене экрана или контекста пересоздавайте компонент: в примерах это обеспечивают key(pageContext) и .id(pageContext.location). Если на iOS меняются данные при прежнем location (например, категория или язык), используйте собственный ID, меняющийся вместе с контекстом. Текущие Compose/SwiftUI-компоненты не гарантируют перезагрузку только от изменения PageContext; на iOS повторный initialize(pageContext:) уже заполненного UIKit-блока также не гарантирует новый запрос. При переиспользовании ячеек учитывайте это, а для Android проверьте кэш inline-блоков.

4. Обработайте действия и аналитику

В gravityEventCallback обработайте FollowUrlEvent и FollowDeeplinkEvent: откройте ссылку или нужный экран средствами приложения. SDK передаёт эти события, но сам такую навигацию не выполняет. Другие callbacks можно использовать для своей аналитики. Справочники: Android, iOS.

По клику можно также открыть модальное окно другим шагом кампании: настройте действие «Перейти на след. шаг»; переход обработает SDK. Компонент должен быть в иерархии текущего экрана, чтобы SDK нашёл Activity/ViewController для показа.

Клик по вашей товарной карточке обработайте внутри ProductViewBuilder: сначала отправьте ProductClickEngagement с переданными билдеру slot, content, campaign, затем откройте товар по данным slot.item через навигацию приложения. Для строки товаров SDK отслеживает видимость карточек, но клик по кастомной карточке отправляет разработчик.

Встроенный inline-компонент отправляет content impression и обрабатывает tracking настроенных действий. Фактическая отправка в GF зависит от tracking-данных кампании; callback сам по себе не подтверждает запись события в отчёт. iOS дополнительно отслеживает visible impression всего блока; у текущих Android inline-компонентов такого трекера нет. Не дублируйте события встроенного UI вручную. Подробнее об engagement: Android, iOS; результаты смотрите в отчётах кампаний.

5. Проверьте запуск

  • На тестовом устройстве открывается нужный экран, selector совпадает с опубликованной кампанией, PageContext проходит таргетинг.
  • Блок виден целиком, высота и отступы корректны при прокрутке и повторном открытии экрана.
  • Баннер/кнопка вызывает ожидаемый callback; ссылка, deeplink и товар открываются правильно. Рекомендации используют вашу карточку, товарный клик отправляется один раз.
  • Без подходящего контента или при ошибке загрузки компоненты убирают содержимое и задают нулевую высоту. Проверьте, что внешние фиксированные размеры и отступы приложения не оставляют пустое место. Пустая выдача — допустимый результат; бесконечный loader не нужен.
  • События и результаты появились в отчёте. При проблеме проверьте публикацию, selector, контекст, размеры и callbacks по Android FAQ или iOS FAQ.