Pplware

Android: Aceleração gráfica por hardware explicada

A explicação não é recente, mas torna-se pertinente considerando o último artigo do Francisco Franco, Porque razão será o iOS mais fluido e sólido que o Android?. Dianne Hackborn, Framework Engineer do Android, na Google, explica como é que a renderização da interface do Android se processa e desmistifica a aceleração gráfica usando o GPU.

Frustrada pela “desinformação” acerca da renderização dos gráficos no Android, Dianne Hackborn decidiu colocar no seu perfil  Google+ alguns factos acerca da forma como o Android renderiza a interface desde a sua primeira versão até à mais recente, o Ice Cream Sandwich.

O Android sempre usou alguma aceleração gráfica por hardware

Dianne afirma que o Android, desde a sua primeira versão, 1.0, sempre usou alguma aceleração gráfica por hardware para compor as janelas. Ou seja, animações como o aparecimento de menus, transições entre actividades, pop-ups e caixas de diálogo, etc. sempre utilizaram aceleração por hardware.

O Android usa aceleração por software para renderizar o conteúdo das janelas

O Android usa, desde sempre, software para renderizar os conteúdos de cada janela. No exemplo de interface, em baixo, há 4 janelas: a barra de estado, o wallpaper, o launcher no topo do wallpaper e o menu.

Se uma destas janelas actualiza os seu conteúdo, como o realce de um item, então o software é usado para desenhar o novo conteúdo dessa janela (antes do Android 3.0). No entanto, nenhuma das outras janelas são redesenhadas de novo, e a re-composição das janelas é feita usando o hardware.

Para desenhar dentro de uma janela, não é precisa necessariamente aceleração por hardware para conseguir 60 fps. Isto depende muito do número de píxeis do ecrã e da velocidade do CPU. Por exemplo, o Nexus S não tem qualquer dificuldade em renderizar a 60 fps a interface normal do Android, como deslizar listas no seu ecrã a 800×480 píxeis. No entanto, o “Droid” original empancava com uma resolução similar.

A aceleração total por hardware foi introduzida no Android 3.0

A implementação desta aceleração no Android 4.0 não é mais completa do que no Android 3.0. Aliás, no Android 3.0, basta activar a propriedade android:handwareAccelerated=”true” para permitir a aceleração por hardware, e a partir daí é o GPU que entra em acção.

A principal mudança no Android 4.0 refere-se ao facto das aplicações que são especificamente destinadas ao Android 4.0 terem esta propriedade, a aceleração por hardware, activa por omissão.

E porque é que esta propriedade não é activa por omissão para todas as aplicações? Alguns tipos de operações de desenho não são bem suportadas por todo o hardware, prejudicando o comportamento da aplicação quando esta pede que parte da sua interface seja actualizada. Se se forçasse a aceleração por hardware nas aplicações já existentes, grande parte delas deixariam de funcionar, com efeitos mais ou menos visíveis.

O OpenGL pode causar um grande overhead, não deve ser cegamente utilizado

Por exemplo, nos drivers PVR de dispositivos como o Nexus S e o Galaxy Nexus, a simples utilização do OpenGL num processo gasta cerca de 8MB de RAM. Dado que o nosso overhead de processo é cerca de 2MB, é bastante considerável. Essa RAM a mais retira outras coisas, como o número de processos em segundo plano que é possível manter, atrasando potencialmente coisas como a troca entre apps.

Por causa do overhead  do OpenGL, há quem não goste de o usar para o desenho da UI. Por exemplo, tornar o Android 4.0 fluido no Nexus S, envolveu desligar a aceleração gráfica por hardware para algumas partes da interface, para não perder os tais 8MB de RAM no processo de sistema, outros 8MB no processo do telefone, outros 8MB no processo da interface de sistema, etc. Dianne refere “Confiem em mim, não notação a diferença – não há vantagem naquele dispositivo em usar o OpenGL para desenhar algo como a barra de estado, mesmo com aquelas animações bonitas”.

A aceleração por hardware não resolve todos os problemas, até os pode criar

A aceleração gráfica por hardware não é bala de prata para uma interface altamente fluída. Tem havido muito esforço neste sentido, como o agendamento melhorado das threads em primeiro plano vs. segundo plano, desde o Android 1.6, a reescrita do sistema de input no 2.3, modo strict, o garbage collection concorrente, loaders, etc. Para atingir 60 fps, há apenas  20 ms para tratar de cada frame. Isto é muito pouco tempo. Tocar apenas no sistema de armazenamento flash na thread que corre a interface pode, em muitos casos, introduzir um atraso muito maior do que os tais 20 ms, especialmente se se escrever no armazenamento.

Um exemplo relativamente recente: notou-se que o ICS no Nexus S é de facto menos fluído quando se deslocam listas, em comparação com o Gingerbread. Descobriu-se que se deve a pequenas mudanças no timing no ICS; enquanto a app recebia eventos de toque e desenhava no ecrã, ia buscar o próximo evento ligeiramente antes deste estar pronto, causando a perda de uma frame enquanto se seguia o dedo, mesmo com o ecrã a ser desenhado a 60 fps. Isto foi corrigido entretanto.

A fluidez do browser no Android vs. iOS

Quando as pessoas comparam o scrolling nos browsers do Android e do iOS, as grandes diferenças apontadas não são devido à aceleração gráfica por hardware. Originalmente o Android seguiu um caminho diferente para renderizar as páginas web e assumiu diferentes compromissos: a página é mostrada como uma lista, que é continuamente renderizada para o ecrã, em vez de usar as chamadas “tiles”. Isto permite que o scrolling e o zooming nunca mostrem artefactos de tiles que ainda não foram desenhados. A desvantagem reside no facto de, quando a página web se torna mais complicada, os fps baixam.

Por isso, desde o Android 3.0, o browser usa tiles, para se seja possível manter uma taxa de fps constante enquanto se faz scroll, ou zoom, com a desvantagem de serem mostrados artefactos quando as novas tiles não são renderizadas a tempo. A tiles em si, são renderizadas usando software, o que Dianne acredita acontecer também no iOS.

Dianne afirma, no entanto, que esta abordagem baseada em tiles também podia ter sido usada antes do Android 3.0 sem aceleração por hardware. Tal como mencionado em cima, o CPU do Nexus S consegue desenhar facilmente as tiles de uma janela a 60 fps.

A aceleração por hardware é limitada ao GPU, mas existem truques

Consideremos um exemplo interessante, os tablets com o chip Tegra 2: o GPU consegue tocar cada pixel de um ecrã 1280×800 cerca de 2.5 vezes a 60 fps. Agora consideremos o ecrã principal do Android 3.0 onde se muda para a lista de todas as apps: é preciso desenhar o fundo (1 vez todos os píxeis), depois a camada de atalhos e widgets (vamos ser simpáticos, 0.5 vezes todos os píxeis), depois o fundo preto de todas as apps (1 vez todos os píxeis), e os ícones e etiquetas de todas as apps (0.5 vezes todos os píxeis).

Com isto já demos cabo do orçamento por pixel, e ainda nem compusemos as janelas separadas para o ecrã final. Para conseguir uma animação a 60 fps, o Android 3.0 e posteriores usam alguns truques. Um grande truque é tentar colocar todas as janelas sobreposições em vez de as copiar para o framebuffer com o GPU.

Mesmo assim, ultrapassamos o orçamento, mas há outro truque: porque o wallpaper do Android está numa janela à parte, podemos aumentar aumentar esta janela para além do ecrã para acomodar todo o bitmap. Agora, quando se faz scroll, o movimento do fundo não requer nenhum desenho, apenas mover a sua janela… e porque esta janela está numa sobreposição, não precisa sequer de ser composta para o ecrã com o GPU.

A importância do barramento de memória

À medida que as resoluções de ecrã crescem, atingir os 60 fps na interface está intimamente relacionado com a velocidade do GPU e a largura de banda do barramento de memória. De facto, para ter uma melhor ideia acerca de uma peça de hardware, vale a pena olhar para a largura de banda do barramento de memória. Muitas vezes o CPU consegue ser bem mais rápido que o barramento de memória.

A fluidez do Samsung Galaxy Nexus vs. Galaxy S II

Há quem que diga que o SGS2 é bem mais fluido que o Galaxy Nexus. Quando se comparam dispositivos deve-se olhar para todos os factores. Por exemplo, o ecrã do SGS2 tem 480×800 píxeis de resolução, enquanto que o Galaxy Nexus tem 720×1280. Se o Nexus S já atingia 60 fps com os seus 480×800, o CPU do SGS2 ainda melhor.

A grande diferença entre estes dois ecrãs é que o Galaxy Nexus tem 2.4 vezes mais píxeis para serem desenhados do que o SGS2. Isto que dizer que para conseguir a mesma eficiência a desenhar o ecrã, é preciso um CPU que corra um single core a 2.4 vezes da velocidade (e renderizar uma interface para uma única app não é paralelizável, por isso cores múltiplos não fazem a magia).

É exactamente aqui que a aceleração por hardware se torna importante: à medida que o número de píxeis aumenta, os GPUs conseguem escalar muito melhor para lidar com os mesmos, dado que são mais especializados na sua tarefa. De facto, este foi o principal incentivo para implementar o desenho acelerado por hardware no Android – a 720×1280 estamos muito para além do ponto em que os CPUs ARM actuais conseguem 60 fps.

É esta a razão pela qual se deve ter cuidado quando se fazem comparações entre o Galaxy Nexus e dispositivos como o SGS2 – se usa uma aplicação de terceiros, há uma grande possibilidade dela não ter activa sequer a aceleração por hardware, e por isso, a comparação usa a renderização por CPU no Galaxy Nexus, o que não é justo tendo em conta a sua necessidade de tocar em 2.4 vezes mais píxeis do que o SGS2 precisa.

Outra vantagem na utilização do GPU

Outra grande vantagem é possibilidade de utilizar efeitos de desenho que outrora não eram possíveis. Por exemplo, quando se desenha um bitmap em software, não se pode fazer tudo excepto aplicar um offset. Escalar um desenho torna a renderização bem mais lenta. Num GPU, aplicar transformações bem mais pesadas que simples escalas é basicamente”grátis”. É por isso que os novos temas Holo no Android têm imagens de fundo – com o desenho acelerado por hardware, podemos suportar o desenho (e escala) dessas imagens. De facto, se a aceleração por hardware não está activa por uma app, as imagens segundo plano são desligadas[via].

Qual a sua opinião acerca da aceleração gráfica por hardware?
Acha que é um dos factores que distingue a fluidez Android vs. iOS?

Exit mobile version