Muitos aplicativos têm um recurso que desconecta você automaticamente após um determinado período de inatividade. No entanto, alguns desses aplicativos desconectam você com base na inatividade da API, enquanto outros implementam um temporizador de logoff substituindo os controles UIView. Neste artigo, exploraremos uma maneira melhor de obter esse comportamento usando o método hitTest. E alguns aplicativos desconectam você com base na diferença de horário entre o último login/chamada de API com a hora atual. O problema com a última abordagem é que você pode manter sua sessão constantemente ativa definindo manualmente seu horário em um dispositivo para o ponto de login.
O problema com a primeira abordagem é que alguns usuários podem ser desconectados, mesmo que estejam apenas rolando pelo conteúdo e não fazendo nenhuma solicitação ao back-end. Imagine um usuário que lê os termos e condições de um determinado produto bancário antes de abrir e está sendo desconectado. Nós definitivamente queremos evitar isso.
O problema com a segunda abordagem é que pode ser difícil implementar o recurso de logoff por inatividade em uma base de código existente, especialmente se o aplicativo tiver uma base de código grande com exibições personalizadas.
É aqui que o método hitTest pode ser muito útil.
Podemos usar um hack com o método hitTest para prevalecer dos problemas listados.
Vamos supor que já temos uma versão implementada de uma classe responsável por rastrear o tempo de atividade de um usuário.
Vamos expressá-lo com a seguinte API:
protocol IUserActivity { func resetInactiveTime() }
extension UIWindow { open override func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? { userActivity.resetInactiveTime() return super.hitTest(point, with: event) } }
E é isso! Agora, esse método será acionado em todos os eventos interativos que o usuário fizer em uma tela, como tocar, rolar e outras atividades de gesto.
Você também pode declarar uma subclasse de uma UIWindow e substituir um método hitTest lá.
Os eventos de toque no iOS geralmente se originam das interações do usuário com a tela sensível ao toque do dispositivo.
Quando o usuário toca na tela, o hardware detecta o toque e gera um fluxo de dados brutos de toque que inclui informações como localização, pressão e duração do toque.
Esses dados brutos de toque são então processados pelo sistema operacional e transformados em eventos de toque de alto nível que podem ser manipulados pelo UIKit. O sistema operacional determina a qual objeto UIWindow o evento de toque corresponde com base no local do toque e na hierarquia de exibição e, em seguida, envia o evento de toque para o objeto UIResponder desse objeto para processamento.
Quando ocorre um evento de toque, o sistema operacional iOS usa um algoritmo de teste de ocorrência para determinar a qual objeto UIView ou UIWindow o evento de toque corresponde.
O algoritmo de teste de acesso começa no objeto UIWindow de nível superior e verifica recursivamente cada subvisualização na hierarquia de visualização até encontrar a visualização mais profunda que contém o ponto de contato. Ele faz isso verificando se o ponto de contato está dentro do quadro de cada subvisualização.
O teste de acerto usa um algoritmo de travessia de pré-ordem reversa em profundidade. Em outras palavras, o algoritmo visita primeiro o nó raiz e depois percorre suas subárvores dos índices mais altos para os mais baixos.
Esse tipo de travessia permite reduzir o número de iterações de travessia e interromper o processo de pesquisa assim que a primeira visão descendente mais profunda que contém o ponto de contato for encontrada.
Isso é possível porque uma subvisualização é sempre renderizada na frente de sua supervisualização, e uma visualização irmã é sempre renderizada na frente de suas visualizações irmãs com um índice inferior na matriz de subvisualizações. Quando várias exibições sobrepostas contêm um ponto específico, a exibição mais profunda na subárvore mais à direita será a exibição mais à frente (1) .
Como podemos ver, o algoritmo transversal sempre começa a partir do objeto UIWindow, independentemente de qual visualização ou controle o usuário está interagindo.
E definitivamente podemos usar isso para nosso propósito apenas interceptando esses eventos no método hitTest da classe UIWindow!
É isso! Deixe-me saber o que você pensa nos comentários abaixo.