Шаблон проездного билета

Для проездных билетов поддерживается отрисовка шаблонов. Если шаблон не задан, используется шаблон по умолчанию.

Определение шаблона

Шаблон карты определяется на уровне класса и используется для показа любого объекта, связанного с этим классом. Шаблон определяет, какие поля будут показываться в разных разделах карты.

Шаблон разделен на следующие разделы:

Android

Обзор разделов и позиций макета шаблона карты

Веб

Обзор разделов и позиций макета шаблона карты

Заголовок подсказки

Android

Элементы макета и позиции полей в заголовке карточки Название карточки по умолчанию
  1. class.logo
  2. class.localizedIssuerName
    или class.issuerName
  3. object.ticketLeg.originName
  4. object.ticketLeg.destinationName
  5. object.ticketLeg.originStationCode
  6. object.ticketLeg.destinationStationCode
  7. object.tripType
  8. object.hexBackgroundColor
    или class.hexBackgroundColor

Заголовок карточки с широким логотипом
  1. class.wideLogo
  2. object.ticketLeg.originName
  3. object.ticketLeg.destinationName
  4. object.ticketLeg.originStationCode
  5. object.ticketLeg.destinationStationCode
  6. object.tripType
  7. object.hexBackgroundColor
    или class.hexBackgroundColor

Веб

Элементы макета и позиции полей в заголовке карточки Название карточки по умолчанию
  1. class.logo
  2. class.localizedIssuerName
    или class.issuerName
  3. object.ticketLeg.originName
  4. object.ticketLeg.destinationName
  5. object.ticketLeg.originStationCode
  6. object.ticketLeg.destinationStationCode
  7. object.tripType
  8. object.hexBackgroundColor
    или class.hexBackgroundColor

Заголовок карточки с широким логотипом
  1. class.wideLogo
  2. object.ticketLeg.originName
  3. object.ticketLeg.destinationName
  4. object.ticketLeg.originStationCode
  5. object.ticketLeg.destinationStationCode
  6. object.tripType
  7. object.hexBackgroundColor
    или class.hexBackgroundColor

В заголовке карточки показывается логотип, название транспортного оператора и сводка поездки. Все три элемента обязательны. Ссылки на поля, используемые для их заполнения, и их положение изменить нельзя.

Однако логика отрисовки допускает некоторую гибкость для верхнего ряда. Верхняя строка билета, в которой приводится сводная информация о поездке, управляется следующими полями в TransitObject для поездки с одним этапом:

  • object.tripType
  • object.ticketLeg.originName
  • object.ticketLeg.destinationName
  • object.ticketLeg.originStationCode
  • object.ticketLeg.destinationStationCode

Внешний вид карты зависит от того, какие поля заполнены. Это можно сделать следующими способами:

  • "Только название источника". Будет показываться только название источника. Это особенно полезно для билетов, которые действуют в определенной зоне, а не на конкретном маршруте.
  • Пункт отправления и пункт назначения. Пункт отправления находится слева, а пункт назначения – справа. Символ между ними зависит от типа поездки. Пункт отправления и пункт назначения указываются одним из следующих способов:
    • Названия и коды станций. Коды станций показываются над названиями более мелким шрифтом.
    • "Только имена". Будут показываться только имена.
    • "Только коды станций". Будут показываться коды станций.

Объекты TransitObject с несколькими сегментами работают похожим образом. В этом случае не используйте object.ticketLeg. Вместо этого используйте список object.ticketLegs[]. Необходимо указать и пункты отправления, и пункты назначения. Названия или коды станций (или и то, и другое) должны быть указаны одинаково для каждого участка. В качестве пункта отправления будет показан пункт отправления первого элемента массива, а в качестве пункта назначения – пункт назначения последнего элемента массива.

Цвет фона карты не является обязательным полем и может быть определен как на уровне класса, так и на уровне объекта. Поле объекта имеет более высокий приоритет и может использоваться для переопределения поля класса.

Если поле широкого логотипа заполнено, на устройствах Android заголовок шаблона по умолчанию с логотипом и названием поставщика заменяется широким логотипом.

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

Шаблон карточки

Android

Элементы макета строки шаблона карточки и позиции полей

Веб

Элементы макета строки шаблона карточки и позиции полей

Раздел шаблона карточки используется для показа дополнительных строк. Эти строки могут содержать текстовые поля структурированных данных или поля текстовых модулей.

Вы можете указать количество строк, определяющих количество объектов в списке class.classTemplateInfo.cardTemplateOverride.cardRowTemplateInfos[]. В списке должен быть хотя бы один элемент, но мы рекомендуем использовать не более двух. Каждый элемент должен относиться к одному из следующих типов:

  • oneItem, который принимает один элемент:
    • item
  • twoItems, который принимает два элемента:
    • startItem
    • endItem
  • threeItems, который принимает три элемента:
    • startItem
    • middleItem
    • endItem

Каждый элемент может быть определен как один селектор поля (.firstValue), два селектора поля (.firstValue и .secondValue) или предопределенный элемент (.predefinedItem). Отображаются как значения выбранного поля, так и соответствующие им ярлыки. Если вы зададите два селектора полей, значения выбранных полей будут разделены косой чертой. То же самое относится к ярлыкам выбранных полей. Стандартные элементы используются для более сложного рендеринга.

В приведенном ниже примере кода показано, как переопределить разделы строк карточки в шаблоне, чтобы указать две строки. Каждая строка содержит три элемента, каждый из которых ссылается на шесть дополнительных полей textModuleData на уровне класса и их заголовки в качестве ярлыков:

Python

 {
   ... //Rest of class
   "textModulesData": [
        {
            "header": "Label 1",
            "body": "Some info 1",
            "id": "myfield1"
        },
        {
            "header": "Label 2",
            "body": "Some info 2",
            "id": "myfield2"
        },
        {
            "header": "Label 3",
            "body": "Some info 3",
            "id": "myfield3"
        },
        {
            "header": "Label 4",
            "body": "Some info 4",
            "id": "myfield4"
        },
        {
            "header": "Label 5",
            "body": "Some info 5",
            "id": "myfield5"
        },
        {
            "header": "Label 6",
            "body": "Some info 6",
            "id": "myfield6"
        }
    ],
   "classTemplateInfo": {
        "cardTemplateOverride": {
            "cardRowTemplateInfos": [{
                "threeItems": {
                    "startItem": {
                        "firstValue": {
                            "fields": [{
                                "fieldPath": "class.textModulesData['myfield1']"
                            }]
                        }
                    },
                    "middleItem": {
                        "firstValue": {
                            "fields": [{
                                "fieldPath": "class.textModulesData['myfield2']"
                            }]
                        }
                    },
                    "endItem": {
                        "firstValue": {
                            "fields": [{
                                "fieldPath": "class.textModulesData['myfield3']"
                            }]
                        }
                    },
                }
            },{
                "threeItems": {
                    "startItem": {
                        "firstValue": {
                            "fields": [{
                                "fieldPath": "class.textModulesData['myfield4']"
                            }]
                        }
                    },
                    "middleItem": {
                        "firstValue": {
                            "fields": [{
                                "fieldPath": "class.textModulesData['myfield5']"
                            }]
                        }
                    },
                    "endItem": {
                        "firstValue": {
                            "fields": [{
                                "fieldPath": "class.textModulesData['myfield6']"
                            }]
                        }
                    },
                }
            }]
        }
    }
}
    

Java

// Rest of class
  .setTextModulesData((new ArrayList<TextModuleData>() {
    {
      add((new TextModuleData()).setHeader("Label 1")
        .setBody("Some info 1")
        .setId("myfield1"));
      add((new TextModuleData()).setHeader("Label 2")
        .setBody("Some info 1")
        .setId("myfield2"));
      add((new TextModuleData()).setHeader("Label 3")
        .setBody("Some info 3")
        .setId("myfield3"));
      add((new TextModuleData()).setHeader("Label 4")
        .setBody("Some info 4")
        .setId("myfield4"));
      add((new TextModuleData()).setHeader("Label 5")
        .setBody("Some info 5")
        .setId("myfield5"));
      add((new TextModuleData()).setHeader("Label 6")
        .setBody("Some info 5")
        .setId("myfield6"));
    }
  }))
  .setClassTemplateInfo((new ClassTemplateInfo())
    .setCardTemplateOverride((new CardTemplateOverride())
      .setCardRowTemplateInfos(new ArrayList<CardRowTemplateInfo>() {
        {
          add((new CardRowTemplateInfo()).setThreeItems((new CardRowThreeItems())
            .setStartItem((new TemplateItem()).setFirstValue((new FieldSelector()).setFields(new ArrayList<FieldReference>(){
              {
                add((new FieldReference()).setFieldPath("class.textModulesData['myfield1']"));
              }
            })))
            .setMiddleItem((new TemplateItem()).setFirstValue((new FieldSelector()).setFields(new ArrayList<FieldReference>(){
              {
                add((new FieldReference()).setFieldPath("class.textModulesData['myfield2']"));
              }
            })))
            .setEndItem((new TemplateItem()).setFirstValue((new FieldSelector()).setFields(new ArrayList<FieldReference>(){
              {
                add((new FieldReference()).setFieldPath("class.textModulesData['myfield3']"));
              }
            })))
          ));
          add((new CardRowTemplateInfo()).setThreeItems((new CardRowThreeItems())
            .setStartItem((new TemplateItem()).setFirstValue((new FieldSelector()).setFields(new ArrayList<FieldReference>(){
              {
                add((new FieldReference()).setFieldPath("class.textModulesData['myfield4']"));
              }
            })))
            .setMiddleItem((new TemplateItem()).setFirstValue((new FieldSelector()).setFields(new ArrayList<FieldReference>(){
              {
                add((new FieldReference()).setFieldPath("class.textModulesData['myfield5']"));
              }
            })))
            .setEndItem((new TemplateItem()).setFirstValue((new FieldSelector()).setFields(new ArrayList<FieldReference>(){
              {
                add((new FieldReference()).setFieldPath("class.textModulesData['myfield6']"));
              }
            })))
          ));
          }
  })))
    

PHP

// Rest of class
    $textModulesData1 = new Google_Service_Walletobjects_TextModuleData();
    $textModulesData1->setBody("Some info 1");
    $textModulesData1->setHeader("Label 1");
    $textModulesData1->setId("myfield1");

    $textModulesData2 = new Google_Service_Walletobjects_TextModuleData();
    $textModulesData2->setBody("Some info 2");
    $textModulesData2->setHeader("Label 2");
    $textModulesData2->setId("myfield2");

    $textModulesData3 = new Google_Service_Walletobjects_TextModuleData();
    $textModulesData3->setBody("Some info 3");
    $textModulesData3->setHeader("Label 3");
    $textModulesData3->setId("myfield3");

    $textModulesData4 = new Google_Service_Walletobjects_TextModuleData();
    $textModulesData4->setBody("Some info 4");
    $textModulesData4->setHeader("Label 4");
    $textModulesData4->setId("myfield4");

    $textModulesData5 = new Google_Service_Walletobjects_TextModuleData();
    $textModulesData5->setBody("Some info 5");
    $textModulesData5->setHeader("Label 5");
    $textModulesData5->setId("myfield5");

    $textModulesData6 = new Google_Service_Walletobjects_TextModuleData();
    $textModulesData6->setBody("Some info 6");
    $textModulesData6->setHeader("Label 6");
    $textModulesData6->setId("myfield6");

    $textModulesDatas = array($textModulesData1, $textModulesData2, $textModulesData3,
                  $textModulesData4, $textModulesData5, $textModulesData6);

    $startItemField = new Google_Service_Walletobjects_FieldReference();
    $startItemField->setFieldPath("class.textModulesData['myfield1']");

    $startItemFirstValue = new Google_Service_Walletobjects_FieldSelector();
    $startItemFirstValue->setFields(array($startItemField));

    $startItem = new Google_Service_Walletobjects_TemplateItem();
    $startItem->setFirstValue($startItemFirstValue);

    $middleItemField = new Google_Service_Walletobjects_FieldReference();
    $middleItemField->setFieldPath("class.textModulesData['myfield2']");

    $middleItemFirstValue = new Google_Service_Walletobjects_FieldSelector();
    $middleItemFirstValue->setFields(array($middleItemField));

    $middleItem = new Google_Service_Walletobjects_TemplateItem();
    $middleItem->setFirstValue($middleItemFirstValue);

    $endItemField = new Google_Service_Walletobjects_FieldReference();
    $endItemField->setFieldPath("class.textModulesData['myfield3']");

    $endItemFirstValue = new Google_Service_Walletobjects_FieldSelector();
    $endItemFirstValue->setFields(array($endItemField));

    $endItem = new Google_Service_Walletobjects_TemplateItem();
    $endItem->setFirstValue($endItemFirstValue);

    $cardRowTemplate = new Google_Service_Walletobjects_CardRowThreeItems();
    $cardRowTemplate->setStartItem($startItem);
    $cardRowTemplate->setMiddleItem($middleItem);
    $cardRowTemplate->setEndItem($endItem);

    $cardRowTemplateInfo1 = new Google_Service_Walletobjects_CardRowTemplateInfo();
    $cardRowTemplateInfo1->setThreeItems($cardRowTemplate);

    $startItemField2 = new Google_Service_Walletobjects_FieldReference();
    $startItemField2->setFieldPath("class.textModulesData['myfield4']");

    $startItemFirstValue2 = new Google_Service_Walletobjects_FieldSelector();
    $startItemFirstValue2->setFields(array($startItemField2));

    $startItem2 = new Google_Service_Walletobjects_TemplateItem();
    $startItem2->setFirstValue($startItemFirstValue2);

    $middleItemField2 = new Google_Service_Walletobjects_FieldReference();
    $middleItemField2->setFieldPath("class.textModulesData['myfield5']");

    $middleItemFirstValue2 = new Google_Service_Walletobjects_FieldSelector();
    $middleItemFirstValue2->setFields(array($middleItemField2));

    $middleItem2 = new Google_Service_Walletobjects_TemplateItem();
    $middleItem2->setFirstValue($middleItemFirstValue2);

    $endItemField2 = new Google_Service_Walletobjects_FieldReference();
    $endItemField2->setFieldPath("class.textModulesData['myfield6']");

    $endItemFirstValue2 = new Google_Service_Walletobjects_FieldSelector();
    $endItemFirstValue2->setFields(array($endItemField2));

    $endItem2 = new Google_Service_Walletobjects_TemplateItem();
    $endItem2->setFirstValue($endItemFirstValue2);

    $cardRowTemplate2 = new Google_Service_Walletobjects_CardRowThreeItems();
    $cardRowTemplate2->setStartItem($startItem2);
    $cardRowTemplate2->setMiddleItem($middleItem2);
    $cardRowTemplate2->setEndItem($endItem2);

    $cardRowTemplateInfo2 = new Google_Service_Walletobjects_CardRowTemplateInfo();
    $cardRowTemplateInfo2->setThreeItems($cardRowTemplate2);

    $cardTemplateOverride = new Google_Service_Walletobjects_CardTemplateOverride();
    $cardTemplateOverride->setCardRowTemplateInfos(array($cardRowTemplateInfo1,
                  $cardRowTemplateInfo2));

    $classTemplateInfo = new Google_Service_Walletobjects_ClassTemplateInfo();
    $classTemplateInfo->setCardTemplateOverride($cardTemplateOverride);

    $payload->setTextModulesData($textModulesDatas);
    $payload->setClassTemplateInfo($classTemplateInfo);
    

Код создает карту со следующим форматом раздела шаблона кода:

Пример переопределения ярлыка.

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

Если вы не переопределите шаблон карточки, будут использоваться количество строк, количество элементов и ссылки на поля по умолчанию. Подробнее о шаблоне по умолчанию…

Если вы зададите главное изображение, оно может появиться после первой строки, если в списке cardRowTemplateInfos несколько строк, или над строкой, если она только одна.

Штрихкод карты

Android

Элементы макета штрихкода карты и их расположение
  1. class.classTemplateInfo
      .cardBarcodeSectionDetails
      .firstTopDetail
  2. class.classTemplateInfo
      .cardBarcodeSectionDetails
      .secondTopDetail
  3. object.barcode.type и object.barcode.value
    или object.ticketNumber
  4. object.barcode.alternateText
  5. class.classTemplateInfo
      .cardBarcodeSectionDetails
      .firstBottomDetail

Веб

Элементы макета штрихкода карты и их расположение
  1. class.classTemplateInfo
      .cardBarcodeSectionDetails
      .firstTopDetail
  2. class.classTemplateInfo
      .cardBarcodeSectionDetails
      .secondTopDetail
  3. object.barcode.type и object.barcode.value
    или object.ticketNumber
  4. object.barcode.alternateText
  5. class.classTemplateInfo
      .cardBarcodeSectionDetails
      .firstBottomDetail

Раздел штрихкода карты используется для показа дополнительного текста или изображений до и после штрихкода. В этом разделе нет обязательных полей.

Для определения двух полей рядом друг с другом перед штрихкодом и одного поля после него можно использовать три селектора полей. Они показываются без ярлыка и могут быть текстовыми полями структурированных данных, полями текстового модуля или полями модуля изображения. Если вы используете изображения, они должны соответствовать правилам фирменного оформления.

Штрихкод определяется типом и значением. Список поддерживаемых типов штрихкодов приведен в справочнике. Кроме того, под штрихкодом может быть показан текст. Это может упростить сканирование штрихкодов.

В примере кода ниже показано, как переопределить раздел штрихкода в карте, чтобы над штрихкодом показывалось изображение.

Python

#... rest of class
    "imageModulesData": [
        {
            "mainImage": {
                "sourceUri": {
                    "uri":  "http://farm4.staticflickr.com/3738/12440799783_3dc3c20606_b.jpg",
                    "description": "Coffee"
                }
            },
            "id": "myimage"
        }
    ],
    "classTemplateInfo": {
        "cardBarcodeSectionDetails": {
            "firstTopDetail": {
                "fieldSelector": {
                    "fields": [
                        {
                        "fieldPath": "class.imageModulesData['myimage'].mainImage"
                        }
                    ]
                }
            }
        }
    }
}
    

Java

//... rest of class
  .setImageModulesData((new ArrayList<ImageModuleData>() {
    {
      add((new ImageModuleData())
        .setId("myimage")
        .setMainImage((new Image()).setSourceUri((new ImageUri()).setDescription("Coffee beans")
          .setUri("http://farm4.staticflickr.com/3738/12440799783_3dc3c20606_b.jpg"))));
        }
      }))
      .setClassTemplateInfo((new ClassTemplateInfo())
        .setCardBarcodeSectionDetails((new CardBarcodeSectionDetails())
          .setFirstTopDetail((new BarcodeSectionDetail())
            .setFieldSelector((new FieldSelector())
              .setFields((new ArrayList<FieldReference>(){
                {
                  add((new FieldReference()).setFieldPath("class.imageModulesData['myimage'].mainImage"));
                }
            })))))
      }
    

PHP

//... rest of class
    $imageUri = new Google_Service_Walletobjects_ImageUri();
    $imageUri->setUri("https://farm8.staticflickr.com/7340/11177041185_a61a7f2139_o.jpg");
    $imageUri->setDescription("Baconrista flights image");
    $image = new Google_Service_Walletobjects_Image();
    $image->setSourceUri($imageUri);
    $imageModulesData = new Google_Service_Walletobjects_ImageModuleData();
    $imageModulesData->setMainImage($image);
            $imageModulesData->setId("myimage");

    $cardBarcodeFieldReference = new Google_Service_Walletobjects_FieldReference();
    $cardBarcodeFieldReference->setFieldPath("class.imageModulesData['myimage'].mainImage");

    $cardBarcodeFieldSelector = new Google_Service_Walletobjects_FieldSelector();
    $cardBarcodeFieldSelector->setFields(array($cardBarcodeFieldReference));

    $cardBarcodeDetail = new Google_Service_Walletobjects_BarcodeSectionDetail();
    $cardBarcodeDetail->setFieldSelector($cardBarcodeFieldSelector);

    $cardBarcodeSectionDetails = new Google_Service_Walletobjects_CardBarcodeSectionDetails();
    $cardBarcodeSectionDetails->setFirstTopDetail($cardBarcodeDetail);

    $classTemplateInfo = new Google_Service_Walletobjects_ClassTemplateInfo();
    $classTemplateInfo->setCardBarcodeSectionDetails($cardBarcodeSectionDetails);

    $payload->setClassTemplateInfo($classTemplateInfo);
            $payload->setImageModuleData($imageModulesData);
    

Код создает карту со следующим форматом раздела штрихкода:

Пример переопределения штрихкода карты.

Если вы не переопределите раздел штрихкода, будут использоваться поля штрихкода по умолчанию. Подробнее о шаблоне по умолчанию…

Нижний раздел

Android

Нижние разделы и элементы шаблона сведений
  • Маршрут с несколькими пересадками
  • class.classTemplateInfo.detailsTemplateOverride
      .detailsItemInfos[0].item
  • class.classTemplateInfo.detailsTemplateOverride
      .detailsItemInfos[1].item
  • class.classTemplateInfo.detailsTemplateOverride
      .detailsItemInfos[2].item
  • …

Веб

Нижние разделы и элементы шаблона сведений
  • Маршрут с несколькими пересадками
  • class.classTemplateInfo.detailsTemplateOverride
      .detailsItemInfos[0].item
  • class.classTemplateInfo.detailsTemplateOverride
      .detailsItemInfos[1].item
  • class.classTemplateInfo.detailsTemplateOverride
      .detailsItemInfos[2].item
  • …

В нижней части находится список элементов class.classTemplateInfo.detailsTemplateOverride.detailsItemInfos[]. Объекты могут содержать любые поля структурированных данных, текстовых модулей, модулей ссылок, модулей изображений или сообщений.

Каждый элемент можно определить как один селектор поля (.firstValue), два селектора поля (.firstValue и .secondValue) или предопределенный элемент (.predefinedItem). Отображаются как значения выбранного поля, так и соответствующие им ярлыки. Если вы зададите два селектора полей, значения выбранных полей будут разделены косой чертой. То же самое относится к ярлыкам выбранных полей. Стандартные элементы используются для более сложной отрисовки. Поля модуля изображений отображаются на всю ширину без ярлыка.

В примере кода ниже показано, как переопределить нижний раздел карты, чтобы в нем показывалось одно поле linksModuleData с ярлыком.

Python

//... rest of class
   "linksModuleData": {
        "uris": [
            {
                "uri": "http://maps.google.com/",
                "description": "Nearby Locations",
                "id":"mylink"
            }
        ]
    },
   "classTemplateInfo": {
        "detailsTemplateOverride": {
            "detailsItemInfos": [
                {
                    "item":{
                        "firstValue": {
                            "fields": [{
                                "fieldPath": "class.linksModuleData.uris['mylink']"
                            }]
                        }
                    }
                }
            ]
        }
     }
//... rest of class
    

Java

 //... rest of class
  .setLinksModuleData((new ArrayList<LinksModuleData>() {
    {
      add((new LinksModuleData()).setDescription("Nearby Locations")
        .setUri("http://maps.google.com/")
        .setId("mylink"));
      }))
      .setClassTemplateInfo((new ClassTemplateInfo())
        .setDetailsTemplateOverride((new DetailsTemplateOverride())
          .setDetailsItemInfos(new ArrayList<DetailsItemInfo>(){
            {
              add((new DetailsItemInfo())
                .setItem((new TemplateItem()).setFirstValue((new FieldSelector()).setFields(new ArrayList<FieldReference>(){
                  {
                    add((new FieldReference()).setFieldPath("class.linksModuleData.uris['mylink']"));
                  }
                }))));
              }
            }))
//... rest of class
    

PHP

    //... rest of class building
    $locationUri = new Google_Service_Walletobjects_Uri();
    $locationUri->setUri("http://maps.google.com/");
    $locationUri->setDescription("Nearby Locations");
    $locationUri->setId("mylink");

    $linksModuleData = new Google_Service_Walletobjects_LinksModuleData();
    $linksModuleData->setUris(array($locationUri));

    $detailItemFieldReference = new Google_Service_Walletobjects_FieldReference();
    $detailItemFieldReference->setFieldPath("class.linksModuleData.uris['mylink']");
    $detailItemFieldSelector = new Google_Service_Walletobjects_FieldSelector();
    $detailItemFieldSelector->setFields(array($detailItemFieldReference));

    $detailItem = new Google_Service_Walletobjects_TemplateItem();
    $detailItem->setFirstValue($detailItemFieldSelector);

    $detailsItemInfo = new Google_Service_Walletobjects_DetailsItemInfo();
    $detailsItemInfo->setItem($detailItem);

    $cardDetailsTemplateOverride = new Google_Service_Walletobjects_DetailsTemplateOverride();
    $cardDetailsTemplateOverride->setDetailsItemInfos(array($detailsItemInfo));

    $classTemplateInfo = new Google_Service_Walletobjects_ClassTemplateInfo();
    $classTemplateInfo->setDetailsTemplateOverride($cardDetailsTemplateOverride);

    $payload->setClassTemplateInfo($classTemplateInfo);
    $payload->setLinksModuleData($linksModuleData);
    //... rest of class
    

Код создает карту со следующим форматом нижнего раздела:

Пример переопределения нижнего раздела.

Если элемент пустой, он не показывается. Подробную информацию вы найдете в справочнике по полям.

Если вы не переопределите нижний раздел, будет показан список полей по умолчанию в стандартном порядке. Подробнее о шаблоне по умолчанию…

Если поездка состоит из нескольких этапов, в верхней части раздела показывается простой маршрут, который нельзя переместить. Если поездка состоит из одного этапа, можно показать простой маршрут, задав свойство class.enableSingleLegItinerary.

Маршрут с несколькими отрезками
  1. class.tranistType
  2. object.ticketLegs[i].originName
    или object.ticketLegs[i].originStationCode
  3. object.ticketLegs[i].departureDateTime (только время)
  4. object.ticketLegs[i].transitOperatorName
  5. COACH или class.customCoachLabel
  6. object.ticketLegs[i].ticketSeat.coach
    или object.ticketLegs[i].ticketSeats[*].coach
  7. SEAT или class.customSeatLabel
  8. object.ticketLegs[i].ticketSeat.seat
    , object.ticketLegs[i].ticketSeat.seatAssignment
    , object.ticketLegs[i].ticketSeats[*].seat
    , object.ticketLegs[i].ticketSeats[*].seatAssignment
    или NO SPECIFIC SEAT
  9. object.hexBackgroundColor
    или class.hexBackgroundColor
  10. object.ticketLegs[i].destinationName
    или object.ticketLegs[i].destinationStationCode
  11. object.ticketLegs[i].arrivalDateTime (только время)
  12. TRANSFER TO: PLATFORM
    или TRANSFER TO: class.customPlatformLabel
    или TRANSFER (если платформа не определена)
  13. object.ticketLegs[i+1].platform

Шаблон списка

Как получить список элементов шаблона
  1. class.classTemplateInfo.listTemplateOverride
      .firstRowOption.fieldOption.fields[]
  2. object.ticketLeg.departureDateTime (сгруппировано)
    или class.classTemplateInfo.listTemplateOverride
      .secondRowOption.fields[]
  3. class.logo
  4. object.hexBackgroundColor
    или class.hexBackgroundColor
  5. <# passes> (сгруппировано)

Раздел шаблона списка используется для выбора поля, которое будет отображаться в представлении "Карты" приложения "Google Кошелек". Карта представлена в списке с логотипом, цветом фона и тремя строками.

В приведенном ниже примере кода показано, как переопределить шаблон списка карты, чтобы в первой строке шаблона списка показывалось поле даты окончания срока действия одного объекта карты.

Python

#... rest of class definition
   "classTemplateInfo": {
        "listTemplateOverride":{
            "firstRowOption": {
                "fieldOption":{
                    "fields": [{
                        "fieldPath": "object.validTimeInterval.end"
                    }]
                }
            }
        }
   }
}
    

Java

//... rest of class
  .setClassTemplateInfo((new ClassTemplateInfo())
    .setListTemplateOverride((new ListTemplateOverride())
      .setFirstRowOption((new FirstRowOption())
        .setFieldOption((new FieldSelector()).setFields(new ArrayList<FieldReference>(){
          {
            add((new FieldReference()).setFieldPath("object.validTimeInterval.end"));
          }
        }))))
//... rest of class
    

PHP

    //... rest of class
    $fieldReference = new Google_Service_Walletobjects_FieldReference();
    $fieldReference->setFieldPath("object.validTimeInterval.end");

    $fieldOption = new Google_Service_Walletobjects_FieldSelector();
    $fieldOption->setFields(array($fieldReference));

    $firstRowOption = new Google_Service_Walletobjects_FirstRowOption();
    $firstRowOption->setFieldOption($fieldOption);

    $listTemplateOverride = new Google_Service_Walletobjects_ListTemplateOverride();
    $listTemplateOverride->setFirstRowOption($firstRowOption);

    $classTemplateInfo = new Google_Service_Walletobjects_ClassTemplateInfo();
    $classTemplateInfo->setListTemplateOverride($listTemplateOverride);

    $payload->setClassTemplateInfo($classTemplateInfo);
    //... rest of class
    

Код создает карту со следующим представлением шаблона списка:

Пример переопределения списка.

В первой строке можно указать селектор поля или сводку по пути. Сводка может быть представлена в одном из следующих форматов:

  • originAndDestinationCodes
  • originAndDestinationNames
  • originName

Вторую и третью строки можно задать только с помощью селектора полей. Поля отображаются без ярлыка. Для сгруппированных билетов во второй строке всегда указывается дата отправления, а в третьей – количество билетов в группе.

Ярлыки

У всех полей структурированных данных есть ярлык, предоставленный Google. Google отвечает за перевод каждого из этих ярлыков на все поддерживаемые языки.

Некоторые из этих ярлыков можно настроить с помощью одного из полей class.custom<name_of_the_field>Label. Если вы измените ярлык, то вам нужно будет самостоятельно перевести его на все языки, которые вы хотите поддерживать.

Ссылки на поля

Ссылки на поля используются в разных частях шаблона в формате class.classTemplateInfo.*.fields[]. Ссылка на поле содержит список путей к полям структурированных данных, текстовых модулей, модулей ссылок, модулей изображений или сообщений.

Не все типы путей разрешены в каждой ссылке на поле. Например, некоторые ссылки на поля разрешают только пути к полям структурированных данных на основе текста или полям текстовых модулей. Текстовые структурированные поля – это поля структурированных данных типа string, localized string, date или money.

Этот список можно использовать для реализации резервной логики. Это означает, что если первый путь в списке ведет к пустому полю, то оценивается следующий путь. Резервная логика в основном предназначена для текстовых полей структурированных данных или полей текстовых модулей. Не смешивайте разные типы полей в одном списке. Используйте резервную логику с осторожностью и только в определенных ситуациях, когда вы ожидаете согласованного шаблона полей, которые существуют в одних объектах, но не в других. В большинстве случаев проще создать отдельные классы для разных вариантов использования.

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

Чтобы сослаться на поле, содержащееся в списке, можно использовать индекс поля в списке или, в большинстве случаев, идентификатор ссылки. У элементов списка, на которые можно ссылаться по идентификатору, есть поле .id. Рекомендуем использовать идентификатор ссылки, а не индекс поля в списке, если он доступен.

Ниже приведен пример того, как ссылаться на поля, содержащиеся в списке.

  • object.imageModulesData[0].id = my-first-id
  • object.imageModulesData[1].id = my-second-id
  • class.detailsTemplateOverride.detailsItemInfos[0].item.firstValue.fields[0].fieldPath = object.imageModulesData[‘my-second-id’]
  • class.detailsTemplateOverride.detailsItemInfos[1].item.firstValue.fields[0].fieldPath = object.imageModulesData[0]

В этом случае первым элементом в разделе сведений о карте будет второе изображение, объявленное в объекте. Второй элемент в разделе сведений о карте – это первое изображение, объявленное в объекте.

Шаблон по умолчанию

Android

Элементы и позиции макета шаблона карты по умолчанию
  1. class.logo
  2. class.localizedIssuerName
    или class.issuerName
  3. См. раздел "Название карточки".
  4. ОТПРАВЛЕНИЕ или ДЕЙСТВИТЕЛЕН С
  5. object.ticketLeg.departureDateTime (дата и время)
    или object.validTimeInterval.start.date
  6. ПРИБЫТИЕ или ДЕЙСТВИТЕЛЬНО ДО
  7. object.ticketLeg.arrivalDateTime (только время)
    или object.validTimeInterval.end.date
  8. ПАССАЖИР
  9. object.passengerNames
  10. CARRIAGE или class.customCarriageLabel
  11. object.ticketLeg.carriage
  12. COACH или class.customCoachLabel
  13. object.ticketLeg.ticketSeat.coach
  14. SEAT или class.customSeatLabel
  15. object.ticketLeg.ticketSeat.seat
    или object.ticketLeg.ticketSeat.seatAssignment
  16. object.barcode.type и object.barcode.value
    или object.ticketNumber
  17. object.barcode.alternateText
  18. object.hexBackgroundColor
    или class.hexBackgroundColor
  19. Маршрут с несколькими пересадками
  20. НОМЕР БИЛЕТА или class.customTicketNumberLabel
  21. object.ticketNumber
  22. СТАТУС БИЛЕТА
  23. object.ticketStatus или object.customTicketStatus
  24. ВЫЛЕТ
  25. object.ticketLeg.departureDateTime
  26. ПРИБЫТИЕ
  27. object.ticketLeg.arrivalDateTime
  28. FARE NAME или class.customFareNameLabel
  29. object.ticketLeg.fareName
  30. PLATFORM или class.customPlatformLabel
  31. object.ticketLeg.platform
  32. ZONE или class.customZoneLabel
  33. object.ticketLeg.zone
  34. FARE CLASS или class.customFareClassLabel
  35. object.ticketLeg.ticketSeat.fareClass
    или object.ticketLeg.ticketSeat.customFareClass
  36. КАТЕГОРИЯ ЛЬГОТЫ
    или class.customConcessionCategoryLabel
  37. object.concessionCategory
    или object.customConcessionCategory
  38. ОГРАНИЧЕНИЯ НА МАРШРУТЕ
    или class.customRouteRestrictionsLabel
  39. object.ticketRestrictions.routeRestrictions
  40. ROUTE RESTRICTIONS DETAILS
    или class.customRouteRestrictionsDetailsLabel
  41. object.ticketRestrictions.routeRestrictionsDetails
  42. ОГРАНИЧЕНИЯ ПО ВРЕМЕНИ
    или class.customTimeRestrictionsLabel
  43. object.ticketRestrictions.timeRestrictions
  44. ДРУГИЕ ОГРАНИЧЕНИЯ
    или class.customOtherRestrictionsLabel
  45. object.ticketRestrictions.otherRestrictions
  46. НОМЕР КВИТАНЦИИ
    или class.customPurchaseReceiptNumberLabel
  47. object.purchaseDetails.purchaseReceiptNumber
  48. ДАТА ПОКУПКИ
  49. object.purchaseDetails.purchaseDateTime
  50. ИДЕНТИФИКАТОР АККАУНТА
  51. object.purchaseDetails.accountId
  52. КОД ПОДТВЕРЖДЕНИЯ
    или class.customConfirmationCodeLabel
  53. object.purchaseDetails.confirmationCode
  54. FACE VALUE или class.customPurchaseFaceValueLabel
  55. object.purchaseDetails.ticketCost.faceValue
  56. PRICE или class.customPurchasePriceLabel
  57. object.purchaseDetails.ticketCost.purchasePrice
  58. СООБЩЕНИЕ О СКИДКЕ
    или class.customDiscountMessageLabel
  59. object.purchaseDetails.ticketCost.discountMessage
  60. class.imageModulesData[0].mainImage
  61. object.imageModulesData[0].mainImage
  62. class.messages[].header
  63. class.messages[].body
  64. object.messages[].header
  65. object.messages[].body
  66. class.textModulesData[0..9].header
  67. class.textModulesData[0..9].body
  68. object.textModulesData[0..9].header
  69. object.textModulesData[0..9].body
  70. class.linksModuleData.uris[].description
  71. object.linksModuleData.uris[].description

Веб

Элементы и позиции макета шаблона карты по умолчанию
  1. class.logo
  2. class.localizedIssuerName
    или class.issuerName
  3. См. раздел "Название карточки".
  4. ОТПРАВЛЕНИЕ или ДЕЙСТВИТЕЛЕН С
  5. object.ticketLeg.departureDateTime (дата и время)
    или object.validTimeInterval.start.date
  6. ПРИБЫТИЕ или ДЕЙСТВИТЕЛЬНО ДО
  7. object.ticketLeg.arrivalDateTime (только время)
    или object.validTimeInterval.end.date
  8. ПАССАЖИР
  9. object.passengerNames
  10. CARRIAGE или class.customCarriageLabel
  11. object.ticketLeg.carriage
  12. COACH или class.customCoachLabel
  13. object.ticketLeg.ticketSeat.coach
  14. SEAT или class.customSeatLabel
  15. object.ticketLeg.ticketSeat.seat
    или object.ticketLeg.ticketSeat.seatAssignment
  16. object.barcode.type и object.barcode.value
    или object.ticketNumber
  17. object.barcode.alternateText
  18. object.hexBackgroundColor
    или class.hexBackgroundColor
  19. Маршрут с несколькими пересадками
  20. НОМЕР БИЛЕТА или class.customTicketNumberLabel
  21. object.ticketNumber
  22. СТАТУС БИЛЕТА
  23. object.ticketStatus или object.customTicketStatus
  24. ВЫЛЕТ
  25. object.ticketLeg.departureDateTime
  26. ПРИБЫТИЕ
  27. object.ticketLeg.arrivalDateTime
  28. FARE NAME или class.customFareNameLabel
  29. object.ticketLeg.fareName
  30. PLATFORM или class.customPlatformLabel
  31. object.ticketLeg.platform
  32. ZONE или class.customZoneLabel
  33. object.ticketLeg.zone
  34. FARE CLASS или class.customFareClassLabel
  35. object.ticketLeg.ticketSeat.fareClass
    или object.ticketLeg.ticketSeat.customFareClass
  36. КАТЕГОРИЯ ЛЬГОТЫ
    или class.customConcessionCategoryLabel
  37. object.concessionCategory
    или object.customConcessionCategory
  38. ОГРАНИЧЕНИЯ НА МАРШРУТЕ
    или class.customRouteRestrictionsLabel
  39. object.ticketRestrictions.routeRestrictions
  40. ROUTE RESTRICTIONS DETAILS
    или class.customRouteRestrictionsDetailsLabel
  41. object.ticketRestrictions.routeRestrictionsDetails
  42. ОГРАНИЧЕНИЯ ПО ВРЕМЕНИ
    или class.customTimeRestrictionsLabel
  43. object.ticketRestrictions.timeRestrictions
  44. ДРУГИЕ ОГРАНИЧЕНИЯ
    или class.customOtherRestrictionsLabel
  45. object.ticketRestrictions.otherRestrictions
  46. НОМЕР КВИТАНЦИИ
    или class.customPurchaseReceiptNumberLabel
  47. object.purchaseDetails.purchaseReceiptNumber
  48. ДАТА ПОКУПКИ
  49. object.purchaseDetails.purchaseDateTime
  50. ИДЕНТИФИКАТОР АККАУНТА
  51. object.purchaseDetails.accountId
  52. КОД ПОДТВЕРЖДЕНИЯ
    или class.customConfirmationCodeLabel
  53. object.purchaseDetails.confirmationCode
  54. FACE VALUE или class.customPurchaseFaceValueLabel
  55. object.purchaseDetails.ticketCost.faceValue
  56. PRICE или class.customPurchasePriceLabel
  57. object.purchaseDetails.ticketCost.purchasePrice
  58. СООБЩЕНИЕ О СКИДКЕ
    или class.customDiscountMessageLabel
  59. object.purchaseDetails.ticketCost.discountMessage
  60. class.imageModulesData[0].mainImage
  61. object.imageModulesData[0].mainImage
  62. class.messages[].header
  63. class.messages[].body
  64. object.messages[].header
  65. object.messages[].body
  66. class.textModulesData[0..9].header
  67. class.textModulesData[0..9].body
  68. object.textModulesData[0..9].header
  69. object.textModulesData[0..9].body
  70. class.linksModuleData.uris[].description
  71. object.linksModuleData.uris[].description

Для полей модуля изображений мы показываем только одно поле модуля изображений из класса и только одно поле модуля изображений из объекта. Если вам нужно больше одного поля модуля изображений на любом уровне, переопределите шаблон по умолчанию.

Для текстовых модулей мы показываем не более 20 полей из класса и 20 полей из объекта. Поля отображаются в том же порядке, в котором они определены в массиве. Если вам нужно больше 20 полей текстового модуля на любом уровне, переопределите шаблон по умолчанию.

Для сообщений мы показываем не более 20 сообщений из класса и 20 сообщений из объекта. Порядок сообщений не гарантируется. Если вам нужно больше 20 сообщений на любом уровне или гарантия для заказов, переопределите шаблон по умолчанию.

В поле модуля ссылок можно указать любое количество URI. URI отображаются сгруппированными в следующем порядке для каждого уровня (класса или объекта):

  1. Координаты на карте
  2. номера телефонов.
  3. Адреса электронной почты
  4. веб-страницы.

Для каждой группы URI отображаются в том же порядке, в котором они определены в массиве. Если вам нужен другой порядок, переопределите шаблон по умолчанию.

Элементы и позиции макета шаблона списка по умолчанию
  1. (object.ticketLeg.originName
      и object.ticketLeg.destinationName)
    или (object.ticketLeg.originStationCode
      и object.ticketLeg.destinationStationCode)
    или object.ticketLeg.originName
  2. object.ticketLeg.departureDateTime
    или object.validTimeInterval.end.date
  3. class.logo
  4. object.hexBackgroundColor
    или class.hexBackgroundColor
  5. <# passes> (сгруппировано)