Configurar sua versão

O sistema de compilação do Android compila os recursos e o código-fonte do app e os empacota em APKs que você pode testar, implantar, assinar e distribuir. O Android Studio usa o Gradle, um kit de ferramentas de compilação avançado, para automatizar e gerenciar o processo de compilação, permitindo que você defina configurações de compilação personalizadas e flexíveis. Cada configuração de compilação pode definir o próprio conjunto de códigos e recursos, reutilizando as partes comuns em todas as versões do app. O Android Plugin for Gradle funciona com o kit de ferramentas de compilação para fornecer processos e configurações ajustáveis que são específicas para compilar e testar aplicativos para Android.

O Gradle e o plug-in do Android são executados de forma independente do Android Studio. Isso significa que você pode compilar seus apps Android pelo Android Studio, pela linha de comando do seu computador ou em computadores em que o Android Studio não esteja instalado (como servidores de integração contínua). Se você não estiver usando o Android Studio, veja como compilar e executar seu app pela linha de comando. A saída da compilação é a mesma, esteja você compilando o projeto em uma linha de comando, em um computador remoto ou usando o Android Studio.

Observação: como o Gradle e o plug-in do Android são executados de forma independente do Android Studio, é necessário atualizar as ferramentas de compilação separadamente. Leia as notas da versão para saber como atualizar o Gradle e o plug-in do Android.

A flexibilidade do sistema de compilação do Android permite realizar configurações de compilação personalizadas sem modificar os arquivos dos recursos principais do app. Esta seção ajuda a entender como o sistema de compilação do Android funciona e como ele pode ajudar a personalizar e automatizar várias configurações de compilação. Se quiser saber mais sobre como implantar seu app, consulte Programar e executar no Android Studio. Para começar a criar configurações de compilação personalizadas imediatamente usando o Android Studio, consulte Configurar variantes de compilação.

O processo de compilação

O processo de compilação envolve muitas ferramentas e processos que convertem seu projeto em um Pacote de Aplicativo Android (APK, na sigla em inglês). Como esse processo é bastante flexível, é útil entender como ele funciona.

Figura 1. Processo de compilação de um módulo típico de app Android.

O processo de compilação de um módulo típico de app Android, conforme é mostrado na figura 1, segue as seguintes etapas gerais:

  1. Os compiladores convertem seu código-fonte em arquivos DEX (Dalvik Executable), que incluem o bytecode que é executado em dispositivos Android e todo o restante em recursos compilados.
  2. O APK Packager combina os arquivos DEX e os recursos compilados em um único APK. No entanto, para que seu app possa ser instalado e implantado em um dispositivo Android, o APK precisa ser assinado.
  3. O APK Packager assina o APK usando o keystore de lançamento ou de depuração:
    1. Se você estiver compilando uma versão de depuração do seu app, ou seja, um app apenas para teste e geração de perfis, o Packager vai assiná-lo com o keystore de depuração. O Android Studio configura novos projetos automaticamente com um keystore de depuração.
    2. Se você estiver compilando uma versão de lançamento do app que pretende lançar externamente, o Packager vai assiná-lo usando o keystore de lançamento. Para criar um keystore de lançamento, veja como assinar seu app no Android Studio.
  4. Antes de gerar seu APK final, o Packager usa a ferramenta zipalign para otimizar seu app para usar menos memória quando ele for executado em um dispositivo.

No final do processo de compilação, você tem um APK de depuração ou de lançamento que pode ser usando para implantar, testar ou lançar o app para usuários externos.

Configurações de compilação personalizadas

O Gradle e o plug-in do Android ajudam a configurar os seguintes aspectos da sua compilação:

Tipos de compilação
Os tipos de compilação definem certas propriedades que o Gradle usa ao compilar e empacotar seu app. Geralmente, eles são configurados para diferentes fases do ciclo de desenvolvimento. Por exemplo, o tipo de compilação de depuração oferece opções de depuração e assina o APK com a chave de depuração, enquanto o tipo de compilação de lançamento pode reduzir, ofuscar e assinar seu APK com uma chave de lançamento para distribuição. É necessário definir pelo menos um tipo de compilação para compilar seu app. Por padrão, o Android Studio cria os tipos de compilação de depuração e de lançamento. Para começar a personalizar as configurações de empacotamento do app, veja como Configurar tipos de compilação.
Variações de produtos
As variações de produtos representam diferentes versões do seu app que você pode lançar para os usuários, por exemplo, versões gratuita e paga do app. Você pode personalizar os tipos de produtos para usar códigos e recursos diferentes, compartilhando e reutilizando as partes comuns a todas as versões do seu app. Os tipos de produto são opcionais, e você precisa criá-los manualmente. Para começar a criar diferentes versões do app, veja como Configurar variações de produtos.
Variantes de compilação
Uma variante de compilação é um produto cruzado de um tipo de versão e variação de produto e é a configuração que o Gradle usa para criar seu app. Usando variantes de compilação, você pode criar a versão de depuração de variações de produtos durante o desenvolvimento ou versões de lançamento assinadas dos aromas de produtos para distribuição. Apesar de não ser necessário configurar as variantes de compilação diretamente, é preciso configurar os tipos de compilação e as variações de produtos que as compõem. A criação de outros tipos de compilação ou variações de produtos também faz com que outras variantes de compilação sejam criadas. Para saber como criar e gerenciar variantes de compilação, leia a visão geral de como Configurar variantes de compilação.
Entradas do manifesto
Você pode especificar valores para algumas propriedades do arquivo de manifesto na configuração da variante de compilação. Esses valores de compilação modificam os valores existentes no arquivo de manifesto. Isso é útil se você quer gerar vários APKs para seus módulos, com cada arquivo .apk tendo valores diferentes para nome do app, versão mínima do SDK ou versão de destino do SDK. Quando há vários manifestos, o Gradle combina as configurações de manifesto.
Dependências
O sistema de compilação gerencia as dependências do projeto por meio do seu sistema de arquivos local e de repositórios remotos. Isso evita a necessidade de pesquisar, fazer o download e copiar manualmente pacotes binários das suas dependências para o diretório do projeto. Para saber mais, consulte Adicionar dependências de compilação.
Assinaturas
O sistema de compilação permite especificar configurações de assinatura nas definições da compilação e pode assinar seus APKs automaticamente durante o processo de compilação. O sistema assina a versão de depuração com uma chave e um certificado padrão, usando credenciais conhecidas para evitar solicitações de senha no momento da compilação. O sistema não assina a versão de lançamento a menos que você defina explicitamente uma configuração de assinatura para essa compilação. Se você não tem uma chave de lançamento, pode gerar uma conforme a descrição apresentada em Assinar o app.
Redução de código e recursos
O sistema de compilação permite especificar um arquivo de regras do ProGuard diferente para cada variante de compilação. Ao criar seu app, o sistema de compilação aplica o conjunto adequado de regras para reduzir seu código e recursos usando as ferramentas de redução integradas, como o R8.
Suporte a vários APKs
O sistema de compilação permite compilar automaticamente diferentes APKs, cada um contendo apenas os códigos e recursos necessários para uma densidade de tela ou Interface binária do aplicativo (ABI, na sigla em inglês) específica. Para saber mais, consulte Compilar vários APKs.

Arquivos de configuração de compilação

Para criar configurações de compilação personalizadas, você precisa alterar um ou mais arquivos de configuração de compilação, ou arquivos build.gradle. Esses arquivos de texto simples usam a Domain Specific Language (DSL) para descrever e manipular a lógica de compilação que usa Groovy, que é uma linguagem dinâmica para a Java Virtual Machine (JVM). Não é preciso conhecer Groovy para começar a configurar sua compilação porque o plug-in do Android para Gradle introduz a maioria dos elementos DSL necessários. Para saber mais sobre a DSL do plug-in do Android, leia a documentação de referência da DSL.

Ao iniciar um novo projeto, o Android Studio cria automaticamente alguns desses arquivos para você, conforme é mostrado na figura 2, e os preenche com base em padrões razoáveis.

Figura 2. Estrutura de projeto padrão de um módulo de app para Android.

Existem alguns arquivos de configuração de compilação do Gradle que fazem parte da estrutura de projeto padrão de um app para Android. Antes de começar a configurar sua compilação, é importante entender o escopo e o propósito de cada um desses arquivos e os elementos DSL que eles devem definir.

Arquivo de configurações do Gradle

O arquivo settings.gradle, localizado no diretório raiz do projeto, informa ao Gradle os módulos que serão incluídos ao compilar seu app. Para a maioria dos projetos, o arquivo é simples e inclui apenas o seguinte:

    include ‘:app’
    

Entretanto, projetos com vários módulos precisam especificar cada módulo a ser incluído na compilação final.

Arquivo de compilação de nível superior

O arquivo build.gradle de nível superior, localizado no diretório raiz do projeto, define configurações de compilação que se aplicam a todos os módulos do seu projeto. Por padrão, o arquivo de compilação de nível superior usa o bloco buildscript para definir os repositórios e as dependências do Gradle que são comuns a todos os módulos do projeto. O exemplo de código a seguir descreve as configurações padrão e os elementos de DSL encontrados no arquivo build.gradle de nível superior após a criação de um novo projeto.

    /**
     * The buildscript block is where you configure the repositories and
     * dependencies for Gradle itself—meaning, you should not include dependencies
     * for your modules here. For example, this block includes the Android plugin for
     * Gradle as a dependency because it provides the additional instructions Gradle
     * needs to build Android app modules.
     */

    buildscript {

        /**
         * The repositories block configures the repositories Gradle uses to
         * search or download the dependencies. Gradle pre-configures support for remote
         * repositories such as JCenter, Maven Central, and Ivy. You can also use local
         * repositories or define your own remote repositories. The code below defines
         * JCenter as the repository Gradle should use to look for its dependencies.
         *
         * New projects created using Android Studio 3.0 and higher also include
         * Google's Maven repository.
         */

        repositories {
            google()
            jcenter()
        }

        /**
         * The dependencies block configures the dependencies Gradle needs to use
         * to build your project. The following line adds Android plugin for Gradle
         * version 3.5.2 as a classpath dependency.
         */

        dependencies {
            classpath 'com.android.tools.build:gradle:3.5.2'
        }
    }

    /**
     * The allprojects block is where you configure the repositories and
     * dependencies used by all modules in your project, such as third-party plugins
     * or libraries. However, you should configure module-specific dependencies in
     * each module-level build.gradle file. For new projects, Android Studio
     * includes JCenter and Google's Maven repository by default, but it does not
     * configure any dependencies (unless you select a template that requires some).
     */

    allprojects {
       repositories {
           google()
           jcenter()
       }
    }
    

Configurar propriedades para todo o projeto

Para projetos do Android que incluem diversos módulos, pode ser útil definir certas propriedades no nível do projeto e compartilhá-las em todos os módulos. Você pode fazer isso adicionando propriedades adicionais ao bloco ext no arquivo build.gradle de nível superior.

    buildscript {...}

    allprojects {...}

    // This block encapsulates custom properties and makes them available to all
    // modules in the project.
    ext {
        // The following are only a few examples of the types of properties you can define.
        compileSdkVersion = 28
        // You can also create properties to specify versions for dependencies.
        // Having consistent versions between modules can avoid conflicts with behavior.
        supportLibVersion = "28.0.0"
        ...
    }
    ...
    

Para acessar essas propriedades a partir de um módulo no mesmo projeto, use a seguinte sintaxe no arquivo build.gradle do módulo (saiba mais sobre esse arquivo na seção abaixo):

    android {
      // Use the following syntax to access properties you defined at the project level:
      // rootProject.ext.property_name
      compileSdkVersion rootProject.ext.compileSdkVersion
      ...
    }
    ...
    dependencies {
        implementation "com.android.support:appcompat-v7:${rootProject.ext.supportLibVersion}"
        ...
    }
    

Observação: embora o Gradle permita definir propriedades de todo o projeto no nível do módulo, evite fazer isso, uma vez que essa ação faz com que os módulos que compartilham essas propriedades sejam vinculados. A vinculação de módulos dificulta a exportação posterior de um módulo como projeto independente e impede que o Gradle utilize a execução paralela de projetos para agilizar as compilações que têm vários módulos.

Arquivo de compilação de módulo

O arquivo build.gradle de módulo, localizado em cada diretório project/module/, permite definir configurações de compilação para o módulo específico em que ele se encontra. A definição dessas configurações de compilação permite disponibilizar opções de empacotamento personalizadas, como tipos de compilação e variações de produtos extras, além de modificar as configurações no manifesto de app main/ ou no arquivo build.gradle de nível superior.

Este arquivo build.gradle de exemplo de módulo do app para Android descreve alguns elementos DSL básicos e configurações que você precisa conhecer.

    /**
     * The first line in the build configuration applies the Android plugin for
     * Gradle to this build and makes the android block available to specify
     * Android-specific build options.
     */

    apply plugin: 'com.android.application'

    /**
     * The android block is where you configure all your Android-specific
     * build options.
     */

    android {

      /**
       * compileSdkVersion specifies the Android API level Gradle should use to
       * compile your app. This means your app can use the API features included in
       * this API level and lower.
       */

      compileSdkVersion 28

      /**
       * buildToolsVersion specifies the version of the SDK build tools, command-line
       * utilities, and compiler that Gradle should use to build your app. You need to
       * download the build tools using the SDK Manager.
       *
       * This property is optional because the plugin uses a recommended version of
       * the build tools by default.
       */

      buildToolsVersion "29.0.0"

      /**
       * The defaultConfig block encapsulates default settings and entries for all
       * build variants, and can override some attributes in main/AndroidManifest.xml
       * dynamically from the build system. You can configure product flavors to override
       * these values for different versions of your app.
       */

      defaultConfig {

        /**
         * applicationId uniquely identifies the package for publishing.
         * However, your source code should still reference the package name
         * defined by the package attribute in the main/AndroidManifest.xml file.
         */

        applicationId 'com.example.myapp'

        // Defines the minimum API level required to run the app.
        minSdkVersion 15

        // Specifies the API level used to test the app.
        targetSdkVersion 28

        // Defines the version number of your app.
        versionCode 1

        // Defines a user-friendly version name for your app.
        versionName "1.0"
      }

      /**
       * The buildTypes block is where you can configure multiple build types.
       * By default, the build system defines two build types: debug and release. The
       * debug build type is not explicitly shown in the default build configuration,
       * but it includes debugging tools and is signed with the debug key. The release
       * build type applies Proguard settings and is not signed by default.
       */

      buildTypes {

        /**
         * By default, Android Studio configures the release build type to enable code
         * shrinking, using minifyEnabled, and specifies the default Proguard rules file.
         */

        release {
            minifyEnabled true // Enables code shrinking for the release build type.
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
      }

      /**
       * The productFlavors block is where you can configure multiple product flavors.
       * This allows you to create different versions of your app that can
       * override the defaultConfig block with their own settings. Product flavors
       * are optional, and the build system does not create them by default.
       *
       * This example creates a free and paid product flavor. Each product flavor
       * then specifies its own application ID, so that they can exist on the Google
       * Play Store, or an Android device, simultaneously.
       *
       * If you declare product flavors, you must also declare flavor dimensions
       * and assign each flavor to a flavor dimension.
       */

      flavorDimensions "tier"
      productFlavors {
        free {
          dimension "tier"
          applicationId 'com.example.myapp.free'
        }

        paid {
          dimension "tier"
          applicationId 'com.example.myapp.paid'
        }
      }

      /**
       * The splits block is where you can configure different APK builds that
       * each contain only code and resources for a supported screen density or
       * ABI. You'll also need to configure your build so that each APK has a
       * different versionCode.
       */

      splits {
        // Settings to build multiple APKs based on screen density.
        density {

          // Enable or disable building multiple APKs.
          enable false

          // Exclude these densities when building multiple APKs.
          exclude "ldpi", "tvdpi", "xxxhdpi", "400dpi", "560dpi"
        }
      }
    }

    /**
     * The dependencies block in the module-level build configuration file
     * specifies dependencies required to build only the module itself.
     * To learn more, go to Add build dependencies.
     */

    dependencies {
        implementation project(":lib")
        implementation 'com.android.support:appcompat-v7:28.0.0'
        implementation fileTree(dir: 'libs', include: ['*.jar'])
    }
    

Arquivos de propriedades do Gradle

O Gradle também contém dois arquivos de propriedades, localizados no diretório raiz do seu projeto, úteis para especificar configurações para o próprio kit de ferramentas de compilação do Gradle:

gradle.properties
Nesse arquivo, é possível definir configurações do Gradle para todo o projeto, como o tamanho máximo de heap do daemon do Gradle. Para saber mais, consulte o Ambiente de compilação.
local.properties
Configura as propriedades de ambiente local do sistema de compilação, incluindo o seguinte:
  • ndk.dir: caminho para o NDK. Essa propriedade está obsoleta. Todas as versões do NDK transferidas por download serão instaladas no diretório ndk do Android SDK.
  • sdk.dir: caminho para o SDK.
  • cmake.dir: caminho para o CMake.
  • ndk.symlinkdir: a partir do Android Studio 3.5, cria um link simbólico para o NDK que pode ser mais curto que o caminho NDK instalado.

Remapear o NDK para um caminho mais curto (somente Windows)

O problema mais comum com caminhos longos do Windows é que ferramentas (como ld.exe) na pasta NDK instalada acabam com caminhos muito profundos, mas as ferramentas não têm boa compatibilidade com caminhos longos.

Em local.properties, é possível pode definir a propriedade ndk.symlinkdir para solicitar que o plug-in do Gradle crie um link simbólico para o NDK. O caminho desse link simbólico pode ser menor que a pasta existente do NDK. Por exemplo, ndk.symlinkdir = C:\ resultará no seguinte link simbólico: C:\ndk\19.0.5232133

Como sincronizar o projeto com arquivos do Gradle

Quando você altera os arquivos de configuração de compilação do seu projeto, o Android Studio exige a sincronização dos arquivos para permitir a importação das alterações e a execução de algumas verificações, garantindo que as configurações não criem erros de compilação.

Para sincronizar os arquivos do projeto, clique em Sync Now na barra de notificações que aparece quando você faz alterações, conforme mostrado na Figura 3, ou clique em Sync Project na barra de menu. Se o Android Studio perceber erros na sua configuração, por exemplo, se o código-fonte usar recursos de API que só estão disponíveis em um nível de API superior à sua compileSdkVersion, a janela Messages será exibida com uma descrição do problema.

Figura 3. Sincronização do projeto com arquivos de configuração de compilação no Android Studio.

Conjuntos de origem

O Android Studio agrupa o código-fonte e os recursos de maneira lógica para cada módulo, criando conjuntos de origem. O conjunto de origem main/ de um módulo contém os códigos e os recursos usados por todas as variantes de compilação dele. Outros diretórios de conjuntos de origem são opcionais, e o Android Studio não os cria automaticamente quando você configura novas variantes de compilação. Entretanto, a criação de conjuntos de origem, semelhante ao main/, ajuda a organizar os arquivos e recursos que o Gradle usará somente ao compilar certas versões do app:

src/main/
Esse conjunto de origem inclui os códigos e recursos comuns a todas as variantes de compilação.
src/buildType/
Crie esse conjunto de origem para incluir os códigos e recursos exclusivos de uma variante de compilação específica.
src/productFlavor/
Crie esse conjunto de origem para incluir os códigos e recursos exclusivos de uma variação específica de produto.

Observação: se você configurar sua compilação para combinar diversas variações de produtos, poderá criar diretórios de conjuntos de origem para cada combinação de variações de produtos entre as dimensões de variações: src/productFlavor1ProductFlavor2/

src/productFlavorBuildType/
Crie esse conjunto de origem para incluir os códigos e recursos exclusivos de uma variante de compilação específica.

Por exemplo, para gerar a versão "fullDebug" do app, o sistema de compilação combina códigos, configurações e recursos dos seguintes conjuntos de origem:

  • src/fullDebug/ (o conjunto de origem da variante de compilação)
  • src/debug/ (o conjunto de origem do tipo de compilação)
  • src/full/ (o conjunto de origem da variação de produto)
  • src/main/ (o conjunto de origem principal)

Observação: ao criar um novo arquivo ou diretório no Android Studio usando as opções de menu File > New, você pode criá-lo para um conjunto de origem específico. Os conjuntos de origem disponíveis para escolha se baseiam nas suas configurações de compilação, e o Android Studio cria os diretórios necessários automaticamente caso eles ainda não existam.

Se conjuntos de origem diferentes contiverem outras versões do mesmo arquivo, o Gradle usará a seguinte ordem de prioridade para decidir qual arquivo usar (os conjuntos de origem à esquerda modificam os arquivos e as configurações dos conjuntos de origem à direita):

variante de compilação > tipo de compilação > variação de produtos > conjunto de origem principal > dependências de biblioteca

Isso permite que o Gradle use arquivos específicos à variante de compilação que você está tentando compilar reutilizando atividades, lógica de app e recursos comuns a outras versões do seu app. Ao combinar diversos manifestos, o Gradle usa a mesma ordem de prioridade. Portanto, cada variante de compilação pode definir diferentes componentes ou permissões no manifesto final. Para saber mais sobre como criar conjuntos de origem personalizados, acesse Criar conjuntos de origem para variantes de compilação.