boxShadow e filter: Sombras e Efeitos Visuais Unificados no React Native 0.76

Como as novas props de estilo boxShadow e filter, introduzidas no React Native 0.76 com a Nova Arquitetura, substituem as props de sombra separadas de iOS/Android por uma sintaxe única inspirada no CSS da web.

Até a versão 0.75, estilizar sombras no React Native era um exercício de paciência: um conjunto de props só para iOS (shadowColor, shadowOffset, shadowOpacity, shadowRadius), mais a prop elevation para Android, que produzia um resultado visual completamente diferente e não aceitava cor customizada. Com o React Native 0.76, a Nova Arquitetura passou a suportar duas props de estilo inspiradas diretamente no CSS da web: boxShadow e filter, finalmente unificando sombras e efeitos gráficos entre as duas plataformas.

O jeito antigo (props separadas por plataforma)

Para ter uma sombra parecida em iOS e Android, era preciso duplicar a lógica de estilo e aceitar que o resultado nunca seria idêntico:

<View
    style={{
        shadowColor: '#000',
        shadowOffset: { width: 0, height: 4 },
        shadowOpacity: 0.3,
        shadowRadius: 6,
        elevation: 8, // comportamento diferente no Android
    }}
/>

Além da duplicação, essa abordagem não funcionava em Views sem cor de fundo no Android e não suportava sombra interna (inset) nem spread.

Como funciona o boxShadow

A prop boxShadow aceita uma string no mesmo formato do CSS box-shadow da web, ou um objeto (ou array de objetos, para múltiplas sombras) com as mesmas informações:

// Forma string, igual ao CSS da web
<View style={{ boxShadow: '5px 5px 10px 0px rgba(255, 0, 0, 0.5)' }} />

// Forma objeto, mais fácil de compor com variáveis
<View
    style={{
        boxShadow: {
            offsetX: 5,
            offsetY: 5,
            blurRadius: 10,
            spreadDistance: 0,
            color: 'rgba(255, 0, 0, 0.5)',
        },
    }}
/>

As duas formas produzem o mesmo resultado. A forma objeto é mais prática quando os valores vêm de um tema ou de props do componente, já que evita montar a string manualmente.

Sombras múltiplas e sombra interna

Passando um array, dá para empilhar mais de uma sombra na mesma View — e usando inset: true, a sombra passa a ser projetada para dentro do elemento em vez de para fora:

<View
    style={{
        borderRadius: 12,
        boxShadow: [
            { offsetX: 0, offsetY: 2, blurRadius: 4, color: 'rgba(0,0,0,0.2)' },
            { offsetX: 0, offsetY: 0, blurRadius: 6, spreadDistance: -2, color: 'rgba(0,0,0,0.3)', inset: true },
        ],
    }}
/>

Como funciona o filter

A prop filter aplica efeitos gráficos ao componente inteiro, com a mesma lista de funções do CSS filter da web: brightness, contrast, grayscale, hueRotate, invert, opacity, saturate, sepia, blur e dropShadow. Também aceita string ou array de objetos:

// Forma string
<Image source={foto} style={{ filter: 'grayscale(1) brightness(0.8)' }} />

// Forma array de objetos, combinando múltiplos efeitos
<Image
    source={foto}
    style={{
        filter: [{ grayscale: 1 }, { brightness: 0.8 }, { blur: 2 }],
    }}
/>

Esse exemplo deixa a imagem em tons de cinza, reduz o brilho e aplica um leve desfoque — tudo sem precisar de uma lib nativa de processamento de imagem ou de capturar a view com react-native-view-shot para editar os pixels.

dropShadow: sombra que segue a silhueta

Diferente de boxShadow, que projeta uma sombra retangular (respeitando borderRadius), a função dropShadow do filter gera uma sombra que acompanha o contorno real dos pixels não transparentes — ideal para ícones e imagens com fundo transparente:

<Image
    source={require('./logo-transparente.png')}
    style={{
        filter: [{ dropShadow: '0 4px 6px rgba(0, 0, 0, 0.4)' }],
    }}
/>

Casos de uso

Cuidados

As duas props só funcionam com a Nova Arquitetura habilitada (Fabric) — em apps ainda rodando na arquitetura antiga, elas são ignoradas silenciosamente. blur e dropShadow dentro de filter exigem Android 12+; sombras normais via boxShadow pedem Android 9+, e sombras internas (inset: true) pedem Android 10+. A cor padrão da sombra também diverge da web: no React Native, sem especificar color, o padrão é preto, enquanto no CSS da web o padrão herda a cor do texto do elemento.

Compatibilidade

boxShadow e filter foram introduzidos no React Native 0.76 (outubro de 2024), exigindo a Nova Arquitetura habilitada no projeto. Não há como usá-los na arquitetura antiga (bridge clássica) nem via Expo Go em versões anteriores ao suporte completo da Nova Arquitetura no SDK correspondente.

documentação oficial

Conclusão

Com boxShadow e filter, o React Native encerra anos de divergência entre as props de sombra do iOS e a elevation do Android, adotando a sintaxe já conhecida do CSS da web. É uma das mudanças mais práticas da Nova Arquitetura: menos código condicional por plataforma e efeitos visuais que antes exigiam bibliotecas nativas extras.

Tecnologia:
react

Deixe seu Comentário!

Dúvida, sugestão ou só um "valeu!" — tudo é bem-vindo por aqui.

Comentário
Nome
Email
lock Seu e-mail não será publicado.