{"id":16401738,"url":"https://github.com/dev-hwang/geofence_service","last_synced_at":"2025-04-13T09:51:02.482Z","repository":{"id":56831136,"uuid":"334869022","full_name":"Dev-hwang/geofence_service","owner":"Dev-hwang","description":"This plugin is a geofence service with activity recognition API.","archived":false,"fork":false,"pushed_at":"2024-10-11T05:09:20.000Z","size":231,"stargazers_count":37,"open_issues_count":1,"forks_count":18,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-03-27T01:12:19.503Z","etag":null,"topics":["android","circular","flutter","foreground-service","geofence","ios"],"latest_commit_sha":null,"homepage":"https://pub.dev/packages/geofence_service","language":"Dart","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Dev-hwang.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2021-02-01T07:41:51.000Z","updated_at":"2024-10-11T05:09:24.000Z","dependencies_parsed_at":"2024-10-27T11:01:01.081Z","dependency_job_id":"86d40b27-15d2-4cf2-a5d3-d435d39a36b7","html_url":"https://github.com/Dev-hwang/geofence_service","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Dev-hwang%2Fgeofence_service","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Dev-hwang%2Fgeofence_service/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Dev-hwang%2Fgeofence_service/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Dev-hwang%2Fgeofence_service/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Dev-hwang","download_url":"https://codeload.github.com/Dev-hwang/geofence_service/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248695300,"owners_count":21146952,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["android","circular","flutter","foreground-service","geofence","ios"],"created_at":"2024-10-11T05:44:02.532Z","updated_at":"2025-04-13T09:51:02.463Z","avatar_url":"https://github.com/Dev-hwang.png","language":"Dart","funding_links":[],"categories":[],"sub_categories":[],"readme":"# This plugin has been deprecated. You can use [geofencing_api](https://pub.dev/packages/geofencing_api) instead.\n\nThis plugin is a geofence service with activity recognition API. It does not use the Geofence API implemented on the platform. Therefore, battery efficiency cannot be guaranteed. Instead, this plugin can provide more accurate and realtime geo-fencing by navigating your location while your app is alive.\n\n[![pub package](https://img.shields.io/pub/v/geofence_service.svg)](https://pub.dev/packages/geofence_service)\n\n## Features\n\n* `Geofence` can have multiple radius.\n* `Geofence` can see what activity took place when the device entered the radius.\n* `GeofenceService` can perform geo-fencing in real time and catch errors during operation.\n\n**WAIT**: This plugin performs geo-fencing based on a circular geofence. If you want to create a polygon geofence, this [plugin](https://pub.dev/packages/poly_geofence_service) is recommended.\n\n## Getting started\n\nTo use this plugin, add `geofence_service` as a [dependency in your pubspec.yaml file](https://flutter.io/platform-plugins/). For example:\n\n```yaml\ndependencies:\n  geofence_service: ^6.0.0\n```\n\nAfter adding the `geofence_service` plugin to the flutter project, we need to specify the platform-specific permissions and services to use for this plugin to work properly.\n\n### :baby_chick: Android\n\nSince geo-fencing operates based on location, we need to add the following permission to the `AndroidManifest.xml` file. Open the `AndroidManifest.xml` file and specify it between the `\u003cmanifest\u003e` and `\u003capplication\u003e` tags.\n\n```\n\u003cuses-permission android:name=\"android.permission.ACCESS_FINE_LOCATION\" /\u003e\n\u003cuses-permission android:name=\"android.permission.ACCESS_COARSE_LOCATION\" /\u003e\n```\n\nThe biggest feature of this plugin is that it can know user activity while geo-fencing. Please specify the permission usage in `\u003cmanifest\u003e` tag.\n\n```\n\u003cuses-permission android:name=\"android.permission.WAKE_LOCK\" /\u003e\n\u003cuses-permission android:name=\"com.google.android.gms.permission.ACTIVITY_RECOGNITION\" /\u003e\n\u003cuses-permission android:name=\"android.permission.ACTIVITY_RECOGNITION\" /\u003e\n```\n\n### :baby_chick: iOS\n\nLike Android platform, geo-fencing is based on location, we need to add the following description. Open the `ios/Runner/Info.plist` file and specify it inside the `\u003cdict\u003e` tag.\n\n```\n\u003ckey\u003eNSLocationWhenInUseUsageDescription\u003c/key\u003e\n\u003cstring\u003eUsed to provide geofence service.\u003c/string\u003e\n```\n\nTo detect changes in user activity, add the following description.\n\n```\n\u003ckey\u003eNSMotionUsageDescription\u003c/key\u003e\n\u003cstring\u003eUsed to recognize user activity information.\u003c/string\u003e\n```\n\n## How to use\n\n1. Create a `GeofenceService` instance and set options. `GeofenceService.instance.setup()` provides the following options:\n* `interval`: The time interval in milliseconds to check the geofence status. The default is `5000`.\n* `accuracy`: Geo-fencing error range in meters. The default is `100`.\n* `loiteringDelayMs`: Sets the delay between `GeofenceStatus.ENTER` and `GeofenceStatus.DWELL` in milliseconds. The default is `300000`.\n* `statusChangeDelayMs`: Sets the status change delay in milliseconds. `GeofenceStatus.ENTER` and `GeofenceStatus.EXIT` events may be called frequently when the location is near the boundary of the geofence. Use this option to minimize event calls at this time. If the option value is too large, realtime geo-fencing is not possible, so use it carefully. The default is `10000`.\n* `useActivityRecognition`: Whether to use the activity recognition API. The default is `true`.\n* `allowMockLocations`: Whether to allow mock locations. The default is `false`.\n* `printDevLog`: Whether to show the developer log. If this value is set to true, logs for geofence service activities (start, stop, etc.) can be viewed. It does not work in release mode. The default is `false`.\n* `geofenceRadiusSortType`: Sets the sort type of the geofence radius. The default is `GeofenceRadiusSortType.DESC`.\n\n```dart\n// Create a [GeofenceService] instance and set options.\nfinal _geofenceService = GeofenceService.instance.setup(\n    interval: 5000,\n    accuracy: 100,\n    loiteringDelayMs: 60000,\n    statusChangeDelayMs: 10000,\n    useActivityRecognition: true,\n    allowMockLocations: false,\n    printDevLog: false,\n    geofenceRadiusSortType: GeofenceRadiusSortType.DESC);\n```\n\n2. Create a `Geofence` and `GeofenceRadius` list. `Geofence` and `GeofenceRadius` provides the following parameters:\n* `id`: Identifier for `Geofence` and `GeofenceRadius`.\n* `data`: Custom data for `Geofence` and `GeofenceRadius`.\n* `latitude`: The latitude of geofence center.\n* `longitude`: The longitude of geofence center.\n* `radius`: The radius of `Geofence`.\n* `length`: The length of the radius in meters. The best result should be set between 100 and 150 meters in radius. If Wi-FI is available, it can be set up to 20~40m.\n\n```dart\n// Create a [Geofence] list.\nfinal _geofenceList = \u003cGeofence\u003e[\n  Geofence(\n    id: 'place_1',\n    latitude: 35.103422,\n    longitude: 129.036023,\n    radius: [\n      GeofenceRadius(id: 'radius_100m', length: 100),\n      GeofenceRadius(id: 'radius_25m', length: 25),\n      GeofenceRadius(id: 'radius_250m', length: 250),\n      GeofenceRadius(id: 'radius_200m', length: 200),\n    ],\n  ),\n  Geofence(\n    id: 'place_2',\n    latitude: 35.104971,\n    longitude: 129.034851,\n    radius: [\n      GeofenceRadius(id: 'radius_25m', length: 25),\n      GeofenceRadius(id: 'radius_100m', length: 100),\n      GeofenceRadius(id: 'radius_200m', length: 200),\n    ],\n  ),\n];\n```\n\n3. Register the listener and call `GeofenceService.instance.start()`.\n\n```dart\n// This function is to be called when the geofence status is changed.\nFuture\u003cvoid\u003e _onGeofenceStatusChanged(\n    Geofence geofence,\n    GeofenceRadius geofenceRadius,\n    GeofenceStatus geofenceStatus,\n    Location location) async {\n  print('geofence: ${geofence.toJson()}');\n  print('geofenceRadius: ${geofenceRadius.toJson()}');\n  print('geofenceStatus: ${geofenceStatus.toString()}');\n  _geofenceStreamController.sink.add(geofence);\n}\n\n// This function is to be called when the activity has changed.\nvoid _onActivityChanged(Activity prevActivity, Activity currActivity) {\n  print('prevActivity: ${prevActivity.toJson()}');\n  print('currActivity: ${currActivity.toJson()}');\n  _activityStreamController.sink.add(currActivity);\n}\n\n// This function is to be called when the location has changed.\nvoid _onLocationChanged(Location location) {\n  print('location: ${location.toJson()}');\n}\n\n// This function is to be called when a location services status change occurs\n// since the service was started.\nvoid _onLocationServicesStatusChanged(bool status) {\n  print('isLocationServicesEnabled: $status');\n}\n\n// This function is used to handle errors that occur in the service.\nvoid _onError(error) {\n  final errorCode = getErrorCodesFromError(error);\n  if (errorCode == null) {\n    print('Undefined error: $error');\n    return;\n  }\n  \n  print('ErrorCode: $errorCode');\n}\n\n@override\nvoid initState() {\n  super.initState();\n  WidgetsBinding.instance.addPostFrameCallback((_) {\n    _geofenceService.addGeofenceStatusChangeListener(_onGeofenceStatusChanged);\n    _geofenceService.addLocationChangeListener(_onLocationChanged);\n    _geofenceService.addLocationServicesStatusChangeListener(_onLocationServicesStatusChanged);\n    _geofenceService.addActivityChangeListener(_onActivityChanged);\n    _geofenceService.addStreamErrorListener(_onError);\n    _geofenceService.start(_geofenceList).catchError(_onError);\n  });\n}\n```\n\n4. To add or remove `Geofence` while the service is running, use the following function:\n\n```text\n_geofenceService.addGeofence(Object);\n_geofenceService.addGeofenceList(List);\n_geofenceService.removeGeofence(Object);\n_geofenceService.removeGeofenceList(List);\n_geofenceService.removeGeofenceById(String);\n_geofenceService.clearGeofenceList();\n```\n\n5. If you want to pause or resume the service, use the function below.\n\n```text\n_geofenceService.pause();\n_geofenceService.resume();\n```\n\n6. When you are finished using the service, unregister the listener and call `GeofenceService.instance.stop()`.\n\n```text\n_geofenceService.removeGeofenceStatusChangeListener(_onGeofenceStatusChanged);\n_geofenceService.removeLocationChangeListener(_onLocationChanged);\n_geofenceService.removeLocationServicesStatusChangeListener(_onLocationServicesStatusChanged);\n_geofenceService.removeActivityChangeListener(_onActivityChanged);\n_geofenceService.removeStreamErrorListener(_onError);\n_geofenceService.clearAllListeners();\n_geofenceService.stop();\n```\n\n**Note**: When calling the stop function, the listener is not removed, but the added geofence is cleared.\n\n## Models\n\n### :chicken: Geofence\n\nA model representing a geofence.\n\n| Property            | Description                                |\n|---------------------|--------------------------------------------|\n| `id`                | Identifier for `Geofence`.                 |\n| `data`              | Custom data for `Geofence`.                |\n| `latitude`          | The latitude of geofence center.           |\n| `longitude`         | The longitude of geofence center.          |\n| `radius`            | The radius of `Geofence`.                  |\n| `status`            | The status of `Geofence`.                  |\n| `timestamp`         | The timestamp of `Geofence`.               |\n| `remainingDistance` | The remaining distance to the destination. |\n\n### :chicken: GeofenceRadius\n\nA model representing the radius of `Geofence`.\n\n| Property            | Description                                     |\n|---------------------|-------------------------------------------------|\n| `id`                | Identifier for `GeofenceRadius`.                |\n| `data`              | Custom data for `GeofenceRadius`.               |\n| `length`            | The length of the radius in meters.             |\n| `status`            | The status of `GeofenceRadius`.                 |\n| `activity`          | The user activity when geofence status changes. |\n| `speed`             | The passing speed when geofence status changes. |\n| `timestamp`         | The timestamp when geofence status changes.     |\n| `remainingDistance` | The remaining distance to the radius.           |\n\n### :chicken: GeofenceStatus\n\nDefines the type of the geofence status.\n\n| Value   | Description                                                               |\n|---------|---------------------------------------------------------------------------|\n| `ENTER` | Occurs when entering the geofence radius.                                 |\n| `EXIT`  | Occurs when exiting the geofence radius.                                  |\n| `DWELL` | Occurs when the loitering delay elapses after entering the geofence area. |\n\n### :chicken: Activity\n\nA model representing the user's activity.\n\n| Property     | Description                            |\n|--------------|----------------------------------------|\n| `type`       | The type of activity recognized.       |\n| `confidence` | The confidence of activity recognized. |\n\n### :chicken: ActivityType\n\nDefines the type of activity.\n\n| Value        | Description                                                                |\n|--------------|----------------------------------------------------------------------------|\n| `IN_VEHICLE` | The device is in a vehicle, such as a car.                                 |\n| `ON_BICYCLE` | The device is on a bicycle.                                                |\n| `RUNNING`    | The device is on a user who is running. This is a sub-activity of ON_FOOT. |\n| `STILL`      | The device is still (not moving).                                          |\n| `WALKING`    | The device is on a user who is walking. This is a sub-activity of ON_FOOT. |\n| `UNKNOWN`    | Unable to detect the current activity.                                     |\n\n### :chicken: ActivityConfidence\n\nDefines the confidence of activity.\n\n| Value    | Description            |\n|----------|------------------------|\n| `HIGH`   | High accuracy: 75~100  |\n| `MEDIUM` | Medium accuracy: 50~75 |\n| `LOW`    | Low accuracy: 0~50     |\n\n### :chicken: GeofenceRadiusSortType\n\nDefines the sort type of the geofence radius. If you have set multiple radius for one geofence, multiple radius can come in at the same time. At this time, you can control the order in which the radius comes in by referring to the radius meters.\n\n| Value  | Description                          |\n|--------|--------------------------------------|\n| `ASC`  | Sort the meters in ascending order.  |\n| `DESC` | Sort the meters in descending order. |\n\n### :chicken: ErrorCodes\n\nError codes that may occur in the service.\n\n| Value                                                | Description                                                                                                                   |\n|------------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------|\n| `ALREADY_STARTED`                                    | Occurs when the service has already been started but the start function is called.                                            |\n| `LOCATION_SERVICES_DISABLED`                         | Occurs when location services are disabled. When this error occurs, you should notify the user and request activation.        |\n| `LOCATION_PERMISSION_DENIED`                         | Occurs when location permission is denied.                                                                                    |\n| `LOCATION_PERMISSION_PERMANENTLY_DENIED`             | Occurs when location permission is permanently denied. In this case, the user must manually allow the permission.             |\n| `ACTIVITY_RECOGNITION_PERMISSION_DENIED`             | Occurs when activity recognition permission is denied.                                                                        |\n| `ACTIVITY_RECOGNITION_PERMISSION_PERMANENTLY_DENIED` | Occurs when activity recognition permission is permanently denied. In this case, the user must manually allow the permission. |\n\n## Support\n\nIf you find any bugs or issues while using the plugin, please register an issues on [GitHub](https://github.com/Dev-hwang/geofence_service/issues). You can also contact us at \u003chwj930513@naver.com\u003e.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdev-hwang%2Fgeofence_service","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdev-hwang%2Fgeofence_service","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdev-hwang%2Fgeofence_service/lists"}