Extraindo cores predominantes de uma imagem com a classe Palette

Quem é desenvolvedor Android e presta atenção nos detalhes de cada aplicativo que utiliza (diferente de mim que não me apego a detalhes kkkk #brincadeira), já deve ter notado que, em alguns apps, a ToolBar muda de cor de acordo com a Activity em que estamos navegando. Um app onde fica evidente esse comportamento no design é o Youtube. Na tela inicial do YouTube para Android, a ToolBar tem fundo vermelho, porém, quando um canal é acessado, a cor do muda e é escolhida de acordo com o avatar do canal.

A classe Palette é a responsável pela execução dessa “mágica” no design de um app Android. Essa classe facilita a extração das cores predominantes em uma imagem Bitmap, o que dá a possibilidade ao desenvolvedor de estilizar os outros componentes com cores compatíveis, visando um contraste adequado.

Se você desenvolve utilizando o Android Studio, para acrescentar a Palette ao seu projeto, basta adicionar seguinte linha no bloco das dependências:

compile 'com.android.support:palette-v7:+'

Após acrescentar a dependência, já é possível fazer uso da Palette. Para isso, o primeiro passo é criar uma Bitmap a partir do ImageView, como mostra o trecho de código abaixo:

Em seguida, é necessário criar um objeto Palette.Builder utilizando a Bitmap obtida anteriormente. O Palette.Builder será usado para gerar a Palette, a qual poder ser obtida tanto de forma síncrona quanto de forma assíncrona. O código abaixo ilustra essas duas possibilidades:


Quando o método síncrono fornece o retorno ou o assíncrono acaba a AsyncTask, as cores já podem ser obtidas através da Palette. Para manipular essas cores é necessário utilizar um objeto do tipo Swatch. O Swatch contém dados relacionados a um determinado tipo de cor encontrado na imagem. Informações como o valor da cor no RGB e a quantidade de pixels (population) que ela ocupa na imagem estão presentes em um Swatch.

A Palette oferece, por padrão, seis tipos de Swatch: Vibrant, Vibrant Dark, Vibrant Light, Muted, Muted Dark, Muted Light. Porém, podem ser extraídas até 16 cores diferentes de uma imagem. O código abaixo mostra um exemplo de como obter os Swatch padrões através da Palette:

Após obter o Swatch, já é possível atribuir uma cor a um componente escolhido. No trecho de código abaixo, as cores extraídas dos Swatch foram atribuídas à LinearLayout e TextView. É importante esclarecer que uma checagem de valor null dever ser feita, uma vez que a cor encontrada por não ser compatível com nenhum tipo de Swatch.

No código acima, o método getRgb() é usado para obter o valor RBG da cor. Por sua vez, o método getTitleTextColor() serve para obter uma cor para o título que faça contraste com a do Swatch. Na imagem a seguir é possível ver o resultado da extração das cores e a aplicação delas nos respectivos componentes.

exemplo-palette

Um projeto Android contendo o código fonte usado nessa postagem pode ser acessado neste link: Exemplo Palette.

E ai gostou da Palette? Caso você tenha alguma dúvida ou quer complementar o post com alguma informação, deixe um comentário.

7 comentários em “Extraindo cores predominantes de uma imagem com a classe Palette”

    • E ae Modesto, blz?
      A sua pergunta é muito boa! Eu deveria ter feito o projeto exemplo com a possibilidade de escolher a imagem a partir da galeria. xD
      Para responder sua pergunta, fiz uma implementação da mesma Activity que usei no exemplo da Pallete com a modificação para carregar imagens da galeria. Você pode acessar o código nesse link:
      https://gist.github.com/luizmarcus/f911e676ec6afc290cc9
      Não esqueça de adicionar a permissão “android.permission.READ_EXTERNAL_STORAGE” para acessar a galeria no AndroidMainfest do seu projeto.
      Qualquer dúvida é só falar.

      Responder
    • E ae, Felipe! Vlw!
      Para aplicar a transparência totalmente, você pode atribuir Color.transparent ao background. Ex:view.setBackgroundColor(Color.transparent)
      Caso você queira só tornar o rgb 20% transparent, por exemplo, você pode usar o view.setAlpha(0.8)

      Responder

Deixe um comentário para Felipe Cancelar resposta