Configurar uma cerca geográfica

Uma Geofence define um limite geográfico circular à volta de um ponto de interesse. A sua aplicação recebe notificações quando o utilizador entra ou sai do limite. As geofences são úteis para lembretes baseados na localização, alertas, check-ins e entrega de conteúdos contextuais.

Este artigo mostra como criar um geofence, monitorizar alterações de estado e gerir eventos de geofence numa aplicação do SDK de Aplicações Windows (WinUI 3).

Prerequisites

  • Um projeto WinUI 3 criado a partir do modelo Blank App, Packaged (WinUI 3 in Desktop).
  • A capacidade de Localização declarada no manifesto do pacote. Consulte Obter a localização do utilizador para instruções.

Solicitar acesso à localização

Chame Geolocator.RequestAccessAsync antes de criar ou monitorizar cercas geográficas.

using Windows.Devices.Geolocation;
using Windows.Devices.Geolocation.Geofencing;

var accessStatus = await Geolocator.RequestAccessAsync();
if (accessStatus != GeolocationAccessStatus.Allowed)
{
    StatusText.Text = "Location access is required for geofencing.";
    return;
}

Criar uma geofence

Defina uma geocerca especificando um identificador, um centro geográfico, um raio em metros e quais as transições de estado a monitorizar (entrada, saída ou remoção).

var position = new BasicGeoposition
{
    Latitude = 47.6062,
    Longitude = -122.3321
};

var geocircle = new Geocircle(position, 200); // 200-meter radius

var geofence = new Geofence(
    "SeattleDowntown",                          // Unique identifier
    geocircle,                                  // Geographic boundary
    MonitoredGeofenceStates.Entered |           // States to monitor
    MonitoredGeofenceStates.Exited,
    false,                                      // Single use: false = persistent
    TimeSpan.FromSeconds(10)                    // Dwell time before triggering
);

GeofenceMonitor.Current.Geofences.Add(geofence);

Parâmetros de geocerca

Parâmetro Descrição
id Um fio único que identifica a geofence. Utilize isto para distinguir eventos de diferentes cercas geográficas.
geoshape Um Geocírculo que define a fronteira. Apenas os limites circulares são suportados.
monitoredStates Que transições monitorizar: Entered, Exited ou Removed. Combine com o operador |.
singleUse Se true, o geofence é ativado uma vez e é removido automaticamente.
dwellTime Quanto tempo o utilizador deve permanecer dentro (ou fora) do limite antes de o evento ser acionado. Ajuda a filtrar os cruzamentos breves.

Monitorizar eventos de geofence em primeiro plano

Subscreva o evento GeofenceMonitor.Current.GeofenceStateChanged para receber notificações enquanto a sua aplicação estiver a funcionar.

GeofenceMonitor.Current.GeofenceStateChanged += OnGeofenceStateChanged;

Leia os relatórios e atualize a interface. O evento é acionado numa thread em segundo plano, por isso use DispatcherQueue para encaminhar as atualizações da IU.

private void OnGeofenceStateChanged(GeofenceMonitor sender, object args)
{
    var reports = sender.ReadReports();

    DispatcherQueue.TryEnqueue(() =>
    {
        foreach (var report in reports)
        {
            var state = report.NewState;
            var id = report.Geofence.Id;

            switch (state)
            {
                case GeofenceState.Entered:
                    StatusText.Text = $"Entered geofence: {id}";
                    break;
                case GeofenceState.Exited:
                    StatusText.Text = $"Exited geofence: {id}";
                    break;
                case GeofenceState.Removed:
                    StatusText.Text = $"Geofence removed: {id}";
                    // Re-add the geofence if it was removed due to expiration
                    break;
            }
        }
    });
}

Monitorizar as alterações no estado da geocerca

Utilize GeofenceMonitor.Current.StatusChanged para detetar quando a monitorização da geofence está desativada — por exemplo, quando o utilizador desativa os serviços de localização.

GeofenceMonitor.Current.StatusChanged += (sender, args) =>
{
    DispatcherQueue.TryEnqueue(() =>
    {
        var status = sender.Status;
        if (status == GeofenceMonitorStatus.Disabled)
        {
            StatusText.Text = "Geofence monitoring is disabled. Check location settings.";
        }
    });
};

Sugestão

Ao usar geofences, monitorize as alterações de permissões através do GeofenceMonitor.StatusChanged em vez do Geolocator.StatusChanged. Um valor GeofenceMonitorStatus de Disabled é equivalente a um PositionStatus de Disabled, mas GeofenceMonitorStatus fornece mais contexto para cenários de geofencing.

Eliminar uma delimitação geográfica

Remova uma geocerca localizando-a na coleção GeofenceMonitor.Current.Geofences.

var geofences = GeofenceMonitor.Current.Geofences;
var target = geofences.FirstOrDefault(g => g.Id == "SeattleDowntown");

if (target != null)
{
    geofences.Remove(target);
}

Melhores práticas

  • Defina um tempo de permanência razoável. Um tempo de permanência de pelo menos 10 segundos ajuda a filtrar o jitter do GPS e evita falsos gatilhos nas bordas dos limites.
  • Use um raio de pelo menos 50 metros. A precisão do GPS varia consoante o dispositivo e o ambiente. Um raio inferior a 50 metros pode produzir resultados pouco fiáveis.
  • Verifique o acesso à internet se necessário. Se a sua aplicação realizar operações de rede quando ocorre um evento de geofence (como enviar uma notificação para um servidor), verifique a conectividade antes de criar a geofence.
  • Trate o estado Removed. Geofences podem ser removidas pelo sistema se expirarem ou se o sistema estiver sob pressão de recursos. Verifique se existe GeofenceState.Removed e recrie a delimitação geográfica, caso o seu cenário o exija.
  • Não monitorize o primeiro plano e o fundo simultaneamente para a mesma geofence, a menos que seja necessário. Se o fizeres, anula o registo da escuta em primeiro plano quando a aplicação for suspensa e volta a registá-la quando for retomada.