Pular para o conteúdo
Carioca Taxi Engenharia
MobileAndroid

GPS em segundo plano no Android sem perder o motorista

O celular do taxista passa o dia com a tela apagada, preso no painel, entrando em túneis. O que o Android faz com a localização nessas horas, e o que fizemos para continuar sabendo onde o carro está.

Jacques Ben BilombeDesenvolvedor, Carioca Taxi
· 5 min de leitura

Este é o 3º artigo da série “Construindo o Carioca Taxi”.

Para o passageiro, o app é aberto, usado e fechado. Para o motorista, o app fica ligado o dia inteiro: o celular preso no painel, a tela apagando, o Waze ou o Google Maps na frente, a bateria esquentando. E durante todo esse tempo precisamos saber onde o carro está: para oferecer a corrida ao motorista mais perto e para mostrar ao passageiro o táxi chegando.

O Android, com razão, faz de tudo para economizar bateria. O problema é que, para ele, um app com a tela apagada é justamente o primeiro candidato a perder o GPS. Este é o terceiro artigo da série.

O básico que precisa estar certo

Serviço em primeiro plano

No Android moderno, a única forma confiável de receber a localização com a tela apagada é um serviço em primeiro plano: o app declara que está fazendo algo que o usuário sabe, e o sistema mostra uma notificação fixa enquanto isso acontece. A nossa diz "Você está online. Localização ativa." Ela é a promessa de que o app não some quando a tela apaga.

"Permitir o tempo todo"

A permissão de localização tem dois níveis: só com o app aberto, ou o tempo todo. O segundo, a partir do Android 11, não pode ser pedido numa janelinha. O sistema leva o usuário para as Configurações. A Play Store também exige que o app explique antes, com as próprias palavras, por que precisa disso.

Então não pedimos a permissão de surpresa. Antes de o motorista ficar online pela primeira vez, ele passa pela tela Preparar o aparelho, que confere cada item, explica e só então abre o pedido do sistema:

  • a localização "o tempo todo";
  • as notificações;
  • a economia de energia desligada.

O vilão que não estava no código

Durante os testes, a localização com a tela apagada passou a chegar a cada 7 segundos em vez de a cada segundo, e com o triplo do erro de posição. Gastamos várias rodadas de teste investigando o nosso código e o da biblioteca de localização. A causa estava no celular: a Economia de energia estava ligada.

Figura 1: O mesmo celular, o mesmo trajeto, com a tela apagada. A economia de energia muda tudo.
Figura 1: O mesmo celular, o mesmo trajeto, com a tela apagada. A economia de energia muda tudo.

Com a Economia de energia ligada, o Android adota a política "GPS desligado com a tela apagada" e passa a entregar posições aproximadas, bem de vez em quando. E o detalhe que mais surpreendeu: colocar o app na lista de exceções da bateria não muda isso. Conferimos com o app comprovadamente isento e a economia ligada, e o resultado foi o mesmo.

A lição foi de processo: antes de investigar o código, confira o estado do aparelho. Por isso a economia de energia virou um dos itens da tela Preparar o aparelho, que avisa o motorista quando ela está ligada.

Do lado do servidor: quando o silêncio é informação

Mesmo com tudo certo, o sinal vai cair: túnel, garagem, celular desligado, rede ruim. A pergunta passa a ser quanto tempo sem posição significa "não sei onde ele está".

Figura 2: O "sinal perdido". Um alarme por motorista, sem consultar o banco a cada segundo.
Figura 2: O "sinal perdido". Um alarme por motorista, sem consultar o banco a cada segundo.

Cada motorista tem um pequeno objeto no servidor (um Durable Object, como contamos no primeiro artigo) que guarda a hora da última posição e mantém um único alarme. Se o alarme dispara e nenhuma posição nova chegou em 20 segundos, o estado vira "sinal perdido". O passageiro vê isso no app, e o carro para de "andar" no mapa por estimativa. Quando uma posição chega, volta ao normal.

O alarme só é reagendado quando dispara, e a hora da última posição vai para o disco no máximo a cada 5 segundos. Um motorista mandando posição o tempo todo custa quase nada.

Para as horas online, que entram nos ganhos e na performance do motorista, há outra regra. Uma sessão sem nenhuma posição por 10 minutos é fechada na hora da última posição recebida, porque o app morreu ou o celular desligou. Mas o servidor não tira o motorista do ar sozinho por isso. Quem decide ficar online é o motorista. Se o servidor o desligasse, ele pararia de receber corridas sem saber por quê.

Túneis: estimar com cuidado

No Rio, perder o GPS é rotina: Rebouças, Santa Bárbara, Túnel Novo. Na navegação dentro do nosso app, o carro precisa seguir no mapa sem o GPS, mas sem inventar movimento quando o trânsito parou dentro do túnel.

Usamos o acelerômetro só durante a navegação. Não para calcular a posição (isso acumula erro muito rápido), mas para responder uma pergunta mais simples: o carro está balançando ou está parado?

  • Balançando: o carro segue na mesma velocidade de antes, pela rota, até o sinal voltar.
  • Quieto por dois segundos: o carro para no mapa.
  • Na dúvida: fazemos o de sempre.

A medida que usamos não depende de como o celular está preso: é quanto o tamanho da aceleração varia em dois segundos. Os limites ainda são estimativas, e só a rua vai confirmá-los. Esse é um dos ajustes que fazemos depois das primeiras corridas reais.

Testar no celular, não só no emulador

Tudo o que contamos aqui só aparece num aparelho de verdade, num uso de verdade:

  • economia de energia;
  • tela apagada por meia hora;
  • uma tela dobrável com dois displays, em que o print de tela sai preto se você pedir o display errado.

Por isso nenhuma mudança no app do motorista é dada como pronta sem passar por um celular físico. E, de preferência, por um segundo celular de outra marca, porque cada fabricante tem a sua própria ideia de "economizar bateria".

Considerações finais

GPS em segundo plano não é um recurso que se liga. É um acordo com o sistema operacional, que tem os próprios interesses, e com o motorista, que precisa entender por que o app pede o que pede. O que funcionou para nós:

  • fazer o básico certo: serviço em primeiro plano e permissão explicada;
  • conferir o estado do aparelho antes de culpar o código;
  • tratar o silêncio como informação, do lado do servidor;
  • estimar só o que dá para estimar com segurança.

Este é o último artigo desta primeira série. Se você também trabalha com localização em apps Android e passou por algo parecido, queremos ouvir.