Desenvolver para diferentes tamanhos de tela


O app precisa funcionar bem em dispositivos Wear OS de todos os tamanhos, aproveitando o espaço extra disponível e ainda tendo uma ótima aparência em telas menores. Este guia oferece recomendações para alcançar essa experiência do usuário.

Para saber mais sobre os princípios de design para layouts adaptáveis, leia as orientações de design.

Criar layouts responsivos usando o Material 3

Os layouts precisam ter margens baseadas em porcentagem. Como o Compose funciona por padrão em valores absolutos, use rememberResponsiveColumnPadding da biblioteca Horologist para calcular o padding e transmiti-lo para o parâmetro contentPadding do ScreenScaffold e o parâmetro contentPadding do TransformingLazyColumn.

O snippet de código a seguir usa um componente TransformingLazyColumn para criar conteúdo que fica ótimo em vários tamanhos de tela do Wear OS:

val columnState = rememberTransformingLazyColumnState()
val contentPadding = rememberResponsiveColumnPadding(
    first = ColumnItemType.ListHeader,
    last = ColumnItemType.Button,
)
val transformationSpec = rememberTransformationSpec()
ScreenScaffold(
    scrollState = columnState,
    contentPadding = contentPadding
) { contentPadding ->
    TransformingLazyColumn(
        state = columnState,
        contentPadding = contentPadding
    ) {
        item {
            ListHeader(
                modifier = Modifier.fillMaxWidth().transformedHeight(this, transformationSpec),
                transformation = SurfaceTransformation(transformationSpec)
            ) {
                Text(text = "Header")
            }
        }
        // ... other items
        item {
            Button(
                modifier = Modifier.fillMaxWidth().transformedHeight(this, transformationSpec),
                transformation = SurfaceTransformation(transformationSpec),
                onClick = { /* ... */ },
                icon = {
                    Icon(
                        imageVector = Icons.Default.Build,
                        contentDescription = "build",
                    )
                },
            ) {
                Text(
                    text = "Build",
                    maxLines = 1,
                    overflow = TextOverflow.Ellipsis,
                )
            }
        }
    }
}

Este exemplo também demonstra ScreenScaffold e AppScaffold. Eles coordenam entre o app e telas individuais (rotas de navegação) para garantir o comportamento correto de rolagem e o posicionamento de TimeText.

Para o padding superior e inferior, observe também o seguinte:

  • A especificação do primeiro e do último ItemType, para determinar o padding correto.
  • O uso de ListHeader para o primeiro item da lista, porque os cabeçalhos Text não podem ter preenchimento.

As especificações completas estão disponíveis nos kits de design do Figma. Para mais detalhes e exemplos, consulte:

  • A biblioteca Horologist: fornece ajudantes para criar apps otimizados e diferenciados para Wear OS.
  • O exemplo ComposeStarter: um exemplo que mostra os princípios descritos neste guia.
  • O exemplo do JetCaster: um exemplo mais complexo de como criar um app para funcionar com diferentes tamanhos de tela usando a biblioteca Horologist.

Usar layouts de rolagem no seu app

Use um layout de rolagem, conforme mostrado anteriormente nesta página, como a escolha padrão ao implementar as telas. Isso permite que os usuários acessem os componentes do app independente das preferências de exibição ou do tamanho da tela do dispositivo Wear OS.

O efeito do tamanho do dispositivo e do escalonamento de fonte diferentes

O efeito de diferentes tamanhos de dispositivo e escalonamento de fonte.

Caixas de diálogo

As caixas de diálogo também precisam ser roláveis, a menos que haja um bom motivo para não fazer isso. O componente AlertDialog é responsivo e rolável por padrão se o conteúdo exceder a altura da janela de visualização.

As telas personalizadas podem exigir layouts sem rolagem

Algumas telas ainda podem ser adequadas para layouts sem rolagem. Vários exemplos incluem a tela principal do player em um app de mídia e a tela de treino em um app de condicionamento físico.

Nesses casos, consulte as orientações canônicas fornecidas nos kits de design do Figma e implemente um design responsivo ao tamanho da tela, usando as margens corretas.

Oferecer experiências diferenciadas com pontos de interrupção

Com telas maiores, você pode apresentar mais conteúdo e recursos. Para implementar esse tipo de experiência diferenciada, use pontos de interrupção de tamanho de tela, mostrando um layout diferente quando o tamanho da tela exceder 225 dp:

const val LARGE_DISPLAY_BREAKPOINT = 225

@Composable
fun isLargeDisplay() =
    LocalConfiguration.current.screenWidthDp >= LARGE_DISPLAY_BREAKPOINT

// ...
// ... use in your Composables:
    if (isLargeDisplay()) {
        // Show additional content.
    } else {
        // Show content only for smaller displays.
    }
    // ...

As orientações de design ilustram mais dessas oportunidades.

Testar combinações de tamanhos de tela e de fonte usando visualizações

As visualizações do Compose ajudam você a desenvolver para vários tamanhos de tela do Wear OS. Use as definições de dispositivos e de visualização de escalonamento de fonte para conferir o seguinte:

  • Como suas telas ficam nos extremos de tamanho, por exemplo, a maior fonte combinada com a tela menor.
  • Como sua experiência diferenciada se comporta em pontos de interrupção.

Implemente as visualizações usando WearPreviewDevices e WearPreviewFontScales para todas as telas do app.

@WearPreviewDevices
@WearPreviewFontScales
@Composable
fun ComposeListPreview() {
    ComposeList()
}

Teste de captura de tela

Além dos testes de visualização, os testes de captura de tela permitem testar uma variedade de tamanhos de hardware. Isso é útil principalmente quando esses dispositivos não estão imediatamente disponíveis para você e o problema pode não aparecer em outros tamanhos de tela.

O teste de captura de tela também ajuda a identificar regressões em locais específicos da base de código.

Nossos exemplos usam o Roborazzi para testes de captura de tela:

  1. Configure os arquivos build.gradle do projeto e do app para usar o Roborazzi.
  2. Crie um teste de captura de tela para cada tela que você tem no app. Por exemplo, no exemplo do ComposeStarter, um teste para o GreetingScreen é implementado, conforme mostrado em GreetingScreenTest:
@RunWith(ParameterizedRobolectricTestRunner::class)
class GreetingScreenTest(override val device: WearDevice) : WearScreenshotTest() {
    override val tolerance = 0.02f

    @Test
    fun greetingScreenTest() = runTest {
        AppScaffold {
            GreetingScreen(greetingName = "screenshot", onShowList = {})
        }
    }

    companion object {
        @JvmStatic
        @ParameterizedRobolectricTestRunner.Parameters
        fun devices() = WearDevice.entries
    }
}

Alguns pontos importantes:

  • O WearDevice.entries contém definições para os dispositivos Wear OS mais populares, para que os testes sejam executados em uma faixa representativa de tamanhos de tela.

Gerar imagens douradas

Para gerar imagens para suas telas, execute o seguinte comando em um terminal:

./gradlew recordRoborazziDebug

Verificar imagens

Para verificar as mudanças nas imagens atuais, execute o seguinte comando em um terminal:

./gradlew verifyRoborazziDebug

Para conferir um exemplo completo de teste de captura de tela, consulte o exemplo ComposeStarter.