設定地理柵欄

地理圍欄是以某個興趣點為中心所劃定的圓形地理邊界。 當使用者進入或離開邊界時,應用程式會收到通知。 地理圍欄對於以位置為基礎的提醒、警示、簽到,以及依情境提供內容都很有用。

本文說明如何在 Windows 應用程式 SDK(WinUI 3)應用程式中建立地理圍欄、監控狀態變化,以及處理地理圍欄事件。

先決條件

  • 這是一個由 Blank App, Packaged(桌面版 WinUI 3) 範本建立的 WinUI 3 專案。
  • 套件資訊清單中宣告的 位置 功能。 請參閱 「取得使用者位置 」以獲得指示。

請求位置存取權限

在建立或監控地理圍欄前,請先聯絡 Geolocator.RequestAccessAsync 。

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;
}

建立地理柵欄

定義地理圍欄時,請指定識別碼、地理中心、半徑(公尺)以及要監控的狀態轉換(輸入、退出或移除)。

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);

地質柵參數

Parameter 說明
id 用來識別地理圍欄的唯一字串。 使用此功能來區分來自不同地理圍欄的事件。
geoshape 一個定義邊界的 地圓 圖。 僅支援圓形邊界。
monitoredStates 哪個轉換會被監控: Entered、、 Exited或 Removed。 與 | 運算子結合。
singleUse 若 true,地理柵欄會觸發一次,並自動刪除。
dwellTime 使用者必須在邊界內(或外)停留多久,事件才會被觸發。 有助於過濾短暫的過河。

在前景中監控地理圍欄事件

訂閱 GeofenceMonitor.Current.GeofenceStateChanged 事件,即可在應用程式運行時接收通知。

GeofenceMonitor.Current.GeofenceStateChanged += OnGeofenceStateChanged;

閱讀報告並更新使用者介面。 事件會在背景執行緒觸發,所以用 DispatcherQueue 來執行 UI 更新。

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;
            }
        }
    });
}

監控地理圍欄狀態變更

使用 GeofenceMonitor.Current.StatusChanged 來偵測地理圍欄監控是否被停用——例如當使用者關閉位置服務時。

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

Tip

使用地理圍欄時,請透過 GeofenceMonitor.StatusChanged 監控權限變更,而非 Geolocator.StatusChanged。 GeofenceMonitorStatus 的值為 Disabled 時,相當於 PositionStatus 的值為 Disabled,但 GeofenceMonitorStatus 可為地理圍欄情境提供更多脈絡。

移除地理圍欄

在 GeofenceMonitor.Current.Geofences 集合中找到地理圍欄,移除它。

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

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

最佳做法

  • 設定合理的停留時間。 至少 10 秒的停留時間有助於過濾 GPS 抖動,並防止邊界邊緣的誤觸發。
  • 使用至少 50 公尺的半徑。 GPS 的準確度會因裝置和環境而異。 半徑小於50公尺的結果可能不可靠。
  • 如果需要,請檢查網路連線。 如果您的應用程式在地理圍欄事件觸發時執行網路操作(例如向伺服器發送通知),請在建立地理圍欄前先驗證連線性。
  • 處理 Removed 狀態。 若地防柵過期或系統面臨資源壓力,系統可將其移除。 請檢查 GeofenceState.Removed,並在您的情境需要時重新建立地理圍欄。
  • 除非必要,不要同時監控同一個地理圍欄的前景和背景。 如果有,請在應用程式暫停時取消註冊前景監聽器,恢復時再重新註冊。