Personalizando aplicativos

Agora que os componentes e recursos da biblioteca Car UI estão nos aplicativos, para personalizar esses aplicativos, os OEMs devem fornecer duas sobreposições:

  • Sobreposição de tempo de construção. Esta sobreposição adicionaria quaisquer recursos necessários para os RROs. Isso inclui:

    • Drawables
    • Estilos (por exemplo, aparências de texto)
    • Recursos compartilhados (por exemplo, cores)

  • Sobreposição RRO. Esta pasta contém os recursos usados ​​para gerar um RRO por aplicativo de destino. Esses recursos só podem se referir a:

    • Valores definidos dentro do mesmo RRO (por exemplo, para uma cor seria um valor hexadecimal).
    • Recursos de estrutura do Android (por exemplo, @android:color/accent ).
    • Um recurso definido na sobreposição de tempo de compilação acima.

Estrutura geral

A estrutura de sobreposição de customização proposta é a seguinte:

  • <path-to-OEM-overlays>/

    • overlay/framework/base/core/res/ . Recursos de sobreposição de tempo de compilação

    • rro/

      • Android.mk . Makefile usado para gerar os RROs para cada pacote de destino com base nos recursos contidos nesta pasta.

      • AndroidManifest.xml . Um modelo de arquivo de manifesto usado pelo makefile acima.

      • res/ . Sobreposições de tempo de execução a serem aplicadas a todos os aplicativos de destino.

Os OEMs podem ter mais de uma dessas estruturas, dependendo do número de marcas que desejam tratar em um único destino de construção (consulte Manipulação de várias marcas ).

Sobreposições de recursos de tempo de execução

A pasta RRO na pasta de sobreposição OEM deve conter recursos a serem aplicados a todos os aplicativos de destino. Os RROs têm limitações que afetam sua capacidade de sobrepor recursos compostos. Em resumo, uma RRO:

  • Não pode se referir a identificadores de recursos definidos no APK de destino ou no próprio RRO. Isso significa que os RROs não podem adicionar novos identificadores, como novos drawables, cores ou estilos.

  • Pode consulte os identificadores de recursos definidos na estrutura, sejam esses recursos definidos em /frameworks/base/core/res ou por meio de uma sobreposição de tempo de compilação. Esses identificadores devem ser referidos usando o android: name-space:

    • Para RROs DeviceDefault públicos , use android
      Por exemplo, @android:style/TextAppearance.DeviceDefault.Large

    • Para todos os outros (não público ou recursos adicionados por meio de sobreposição de tempo de compilação), use *android
      Por exemplo, @*android/style:TextAppearance.OEM.Brand1.Title

Além dos recursos, a pasta RRO deve conter:

  • AndroidManifest.xml . No exemplo abaixo, RRO_PACKAGE_NAME e TARGET_PACKAGE_NAME são espaços reservados para os makefiles:

    <?xml version=“1.0” encoding=“utf-8”?>
    <manifest xmlns:android=“http://schemas.android.com/apk/res/android”
        package=“{{RRO_PACKAGE_NAME}}” />
        <application android:hasCode=“false” />
        <overlay android:priority=“10”
            android:targetPackage=“{{TARGET_PACKAGE_NAME}}”
            android:requiredSystemPropertyName=“ro.product.sku”
            android:requiredSystemPropertyValue=“<your-product-sku>” />
    </manifest>
    
  • Android.mk em que oem no seguinte makefile define o prefixo que todos os RROs gerados teriam.
      LOCAL_PATH := $(call my-dir)
      include $(CLEAR_VARS)
      CAR_UI_RRO_SET_NAME := oem
      CAR_UI_RESOURCE_DIR := $(LOCAL_PATH)/res
      CAR_UI_RRO_TARGETS := $(CAR_UI_RRO_PACKAGE_NAMES)
      include packages/apps/Car/libs/car-ui-lib/generate_rros.mk
      

Configurando Sobreposições RRO

Um novo arquivo de configuração é suportado, overlayable.xml , que você pode usar para definir os controles de acesso. Por exemplo, você pode especificar quem pode sobrepor recursos, bem como quais recursos podem ser sobrepostos. Como resultado, os recursos agora podem ser agrupados de diferentes maneiras para torná-los disponíveis para serem sobrepostos por diferentes RROs.

Para configurar o controle de acesso RRO:

  1. Na pasta res/values , crie overlayable.xml .
  2. Crie as tags de recurso <overlayable> .
  3. Defina o atributo name para a tag <overlayable> , que deve ser único no pacote. Cada sobreposição pode segmentar apenas um grupo sobreposto.
  4. Defina a tag <policy> dentro de <overlayable> .
  5. Defina os grupos de recursos que podem ser sobrepostos. Por exemplo:
      <resources>
          <overlayable name="OverlayableResources">
              <policy type="public">
                  <item type="string" name="app_title" />
              </policy>
          </overlayable>
      </resources>
      

Para aplicar as seguintes alterações ao seu projeto RRO:

  1. Na pasta res/xml , crie overlays.xml . Consulte a entrada no exemplo de código abaixo para overlay .
  2. Defina os recursos a serem substituídos.
  3. Adicione android:resourcesMap="@xml/overlays" à tag <overlay> em AndroidManifest.xml . Por exemplo, no exemplo de código abaixo, consulte a entrada para <overlay> .
  4. Defina android:isStatic=”true” para uma sobreposição estática. Cada sobreposição pode segmentar apenas um dos grupos que podem ser sobrepostos.

Considere o seguinte exemplo. A primeira seção pertence a AndroidManifest.xml enquanto a segunda seção pertence a overlays.xml .

  <manifest xmlns:android="http://schemas.android.com/apk/res/android"
      package="com.android.car.ui.rro"
      android:versionCode="1"
      android:versionName="1.0">
      <overlay android:targetName="OverlayableResources"
               android:resourcesMap="@xml/overlays"
               android:targetPackage="com.android.car.ui"
               android:priority="1"
               android:isStatic="false" />
  </manifest>
  <overlay>
      <item target="string/app_title" value="@ string/app_title" />
  </overlay>
  

Com uma ressalva, os RROs existentes anteriormente continuarão funcionando no Android 10. A ressalva é que, para serem instalados com o PackageManagerRRO, os pacotes devem ser pré-instalados ou assinados com a mesma chave do aplicativo de destino. No Android 10, os arquivos de layout podem ser sobrepostos. No entanto, isso requer o uso de requireViewById() ao obter a exibição em vez de findViewById() . No Android 10, essa alteração foi implementada em car-ui-lib para dar suporte a sobreposições de layout.

A próxima versão principal do Android permitirá que você sobreponha um arquivo de layout e defina novos recursos no pacote RRO e faça referência a eles internamente.

Adicionando recursos específicos de OEM

Para superar as limitações de RRO que impedem a adição de recursos OEM:

  • Estenda as estruturas/base usando uma sobreposição de tempo de construção , adicionando todos os recursos necessários.
  • Consulte esses recursos dos RROs OEM usando *android: namespace.

Por exemplo, veja a seguir uma maneira de adicionar um desenhável específico do OEM e usá-lo em um RRO:

  • <path-to-OEM-overlays>

    • overlay/framework/base/core/res/res/drawable/

      • oem_background_drawable.xml

    • rro/res/values

      • drawables.xml

        <resources>
            <item type="drawable" name="car_ui_toolbar_background">
                @*android:drawable/oem_background_drawable
            </item>
        </resources>
        

Lidando com várias marcas

Os arquivos de manifesto RRO têm uma sintaxe para permitir que sejam aplicados condicionalmente com base nas propriedades do sistema. Para lidar com várias marcas em uma única imagem de sistema, os OEMs podem usar isso da seguinte maneira (consulte Estrutura geral ).

<?xml version=“1.0” encoding=“utf-8”?>
<manifest xmlns:android=“http://schemas.android.com/apk/res/android”
    package=“{{RRO_PACKAGE_NAME}}”/>
    <application android:hasCode=“false”/>
    <overlay android:priority=“10”
        android:targetPackage=“{{TARGET_PACKAGE_NAME}}”
        android:requiredSystemPropertyName=“ro.product.sku”
        android:requiredSystemPropertyValue=“<your-product-sku>”/>
</manifest>

A sintaxe para android:requiredSystemPropertyName e android:requiredSystemPropertyValue faria com que esse RRO fosse ativado somente se a propriedade do sistema correspondente correspondesse ao valor fornecido. Os OEMs podem então definir vários desses RROs, todos eles ativados estaticamente e ter apenas um ativo por vez.

Adicionando a biblioteca Car UI a um alvo

Para incorporar a biblioteca Car UI a um alvo Android, você deve incluir o seguinte trecho de código:

# Include build-time overlays
    PRODUCT_PACKAGE_OVERLAYS += \
      <path-to-oem-overlays>/overlay
    # Define package names to generate RROs for
    CAR_UI_RRO_PACKAGE_NAMES += \
      com.android.car.ui.paintbooth \
      com.android.car.media \
      com.android.car.dialer \
      com.android.car.linkviewer \
      com.android.car.settings \
      com.android.car.systemupdater \
      com.google.android.apps.automotive.inputmethod \
      com.google.android.apps.automotive.templates.host \
      ...
    # Include generated RROs
    PRODUCT_PACKAGES += \
      oem-com-android-car-ui-paintbooth \
      oem-com-android-car-media \
      oem-com-android-car-dialer \
      oem-com-android-car-linkviewer \
      oem-com-android-car-settings \
      oem-com-android-car-systemupdater \
      oem-com-google-android-apps-automotive-inputmethod \
      oem-com-google-android-apps-automotive-templates-host \
      ...
  • Faz com que <path-to-OEM-overlays>/rro/Android.mk gere um RRO para cada um dos pacotes nomeados em CAR_UI_RRO_PACKAGE_NAMES .

  • Inclui os RROs gerados em PRODUCT_PACKAGES .

  • Inclui uma sobreposição de tempo de compilação em PRODUCT_PACKAGE_OVERLAYS para adicionar recursos específicos de OEM.

Para saber quais pacotes suportam car-ui-lib , veja Lista de pacotes contendo car-ui-lib .