diff --git a/CHANGELOG.md b/CHANGELOG.md index 6baf32e..2526b62 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,9 @@ +## [0.2.2] - Fixed PlatformException + +* Fixed PlatformException https://github.com/aloisdeniel/flutter_geocoder/issues/29 +* Format code. +* Update deps. + ## [0.2.1] - Fixed issues with Uint8List * Fixed breaking changes in newer SDK versions. diff --git a/android/build.gradle b/android/build.gradle index 4761cf6..c6b622c 100644 --- a/android/build.gradle +++ b/android/build.gradle @@ -10,7 +10,7 @@ buildscript { } dependencies { - classpath 'com.android.tools.build:gradle:3.3.0' + classpath 'com.android.tools.build:gradle:4.0.1' } } @@ -26,8 +26,7 @@ rootProject.allprojects { apply plugin: 'com.android.library' android { - compileSdkVersion 28 - //buildToolsVersion '28.0.3' + compileSdkVersion 29 defaultConfig { minSdkVersion 16 diff --git a/android/gradle/wrapper/gradle-wrapper.properties b/android/gradle/wrapper/gradle-wrapper.properties index bae5290..b451223 100644 --- a/android/gradle/wrapper/gradle-wrapper.properties +++ b/android/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ -#Fri Jun 23 08:50:38 CEST 2017 +#Wed Sep 02 01:21:30 MSK 2020 distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-4.6-all.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-6.1.1-all.zip diff --git a/android/src/main/AndroidManifest.xml b/android/src/main/AndroidManifest.xml index 4895e49..a292f71 100644 --- a/android/src/main/AndroidManifest.xml +++ b/android/src/main/AndroidManifest.xml @@ -1,3 +1,2 @@ - + package="com.yourcompany.geocoder"> diff --git a/android/src/main/java/com/aloisdeniel/geocoder/GeocoderPlugin.java b/android/src/main/java/com/aloisdeniel/geocoder/GeocoderPlugin.java index f7cf971..0003336 100644 --- a/android/src/main/java/com/aloisdeniel/geocoder/GeocoderPlugin.java +++ b/android/src/main/java/com/aloisdeniel/geocoder/GeocoderPlugin.java @@ -6,6 +6,7 @@ import java.util.HashMap; import java.io.IOException; import java.lang.Exception; + import android.content.Context; import android.location.Address; import android.location.Geocoder; @@ -23,7 +24,8 @@ * NotAvailableException */ class NotAvailableException extends Exception { - NotAvailableException() {} + NotAvailableException() { + } } /** @@ -31,203 +33,192 @@ class NotAvailableException extends Exception { */ public class GeocoderPlugin implements MethodCallHandler { - private Geocoder geocoder; - - public GeocoderPlugin(Context context) { - - this.geocoder = new Geocoder(context); - } - - /** - * Plugin registration. - */ - public static void registerWith(Registrar registrar) { - final MethodChannel channel = new MethodChannel(registrar.messenger(), "github.com/aloisdeniel/geocoder"); - channel.setMethodCallHandler(new GeocoderPlugin(registrar.context())); - } - - // MethodChannel.Result wrapper that responds on the platform thread. - private static class MethodResultWrapper implements Result { - private Result methodResult; - private Handler handler; - - MethodResultWrapper(Result result) { - methodResult = result; - handler = new Handler(Looper.getMainLooper()); - } - - @Override - public void success(final Object result) { - handler.post( - new Runnable() { - @Override - public void run() { - methodResult.success(result); - } - }); - } - - @Override - public void error( - final String errorCode, final String errorMessage, final Object errorDetails) { - handler.post( - new Runnable() { - @Override - public void run() { - methodResult.error(errorCode, errorMessage, errorDetails); - } - }); - } + private Geocoder geocoder; - @Override - public void notImplemented() { - handler.post( - new Runnable() { - @Override - public void run() { - methodResult.notImplemented(); - } - }); + public GeocoderPlugin(Context context) { + this.geocoder = new Geocoder(context); } - } - @Override - public void onMethodCall(MethodCall call, Result rawResult) { - Result result = new MethodResultWrapper(rawResult); - - if (call.method.equals("findAddressesFromQuery")) { - String address = (String) call.argument("address"); - findAddressesFromQuery(address, result); - } - else if (call.method.equals("findAddressesFromCoordinates")) { - float latitude = ((Number) call.argument("latitude")).floatValue(); - float longitude = ((Number) call.argument("longitude")).floatValue(); - findAddressesFromCoordinates(latitude,longitude, result); - } else { - result.notImplemented(); + /** + * Plugin registration. + */ + public static void registerWith(Registrar registrar) { + final MethodChannel channel = new MethodChannel(registrar.messenger(), "github.com/aloisdeniel/geocoder"); + channel.setMethodCallHandler(new GeocoderPlugin(registrar.context())); } - } - private void assertPresent() throws NotAvailableException { - if (!geocoder.isPresent()) { - throw new NotAvailableException(); - } - } + // MethodChannel.Result wrapper that responds on the platform thread. + private static class MethodResultWrapper implements Result { + private Result methodResult; + private Handler handler; - private void findAddressesFromQuery(final String address, final Result result) { + MethodResultWrapper(Result result) { + methodResult = result; + handler = new Handler(Looper.getMainLooper()); + } - final GeocoderPlugin plugin = this; - new AsyncTask>() { @Override - protected List
doInBackground(Void... params) { - try { - plugin.assertPresent(); - return geocoder.getFromLocationName(address, 20); - } catch (IOException ex) { - return null; - } catch (NotAvailableException ex) { - return new ArrayList<>(); - } + public void success(final Object result) { + handler.post(new Runnable() { + @Override + public void run() { + methodResult.success(result); + } + }); } @Override - protected void onPostExecute(List
addresses) { - if (addresses != null) { - if (addresses.isEmpty()) - result.error("not_available", "Empty", null); - - else result.success(createAddressMapList(addresses)); - } - else result.error("failed", "Failed", null); + public void error(final String errorCode, final String errorMessage, final Object errorDetails) { + handler.post(new Runnable() { + @Override + public void run() { + methodResult.error(errorCode, errorMessage, errorDetails); + } + }); } - }.execute(); - } - private void findAddressesFromCoordinates(final float latitude, final float longitude, final Result result) { - final GeocoderPlugin plugin = this; - new AsyncTask>() { @Override - protected List
doInBackground(Void... params) { - try { - plugin.assertPresent(); - return geocoder.getFromLocation(latitude, longitude, 20); - } catch (IOException ex) { - return null; - } catch (NotAvailableException ex) { - return new ArrayList<>(); - } + public void notImplemented() { + handler.post(new Runnable() { + @Override + public void run() { + methodResult.notImplemented(); + } + }); } + } - @Override - protected void onPostExecute(List
addresses) { - if (addresses != null) { - if (addresses.isEmpty()) - result.error("not_available", "Empty", null); + @Override + public void onMethodCall(MethodCall call, Result rawResult) { + Result result = new MethodResultWrapper(rawResult); + + if (call.method.equals("findAddressesFromQuery")) { + String address = (String) call.argument("address"); + findAddressesFromQuery(address, result); + } else if (call.method.equals("findAddressesFromCoordinates")) { + float latitude = ((Number) call.argument("latitude")).floatValue(); + float longitude = ((Number) call.argument("longitude")).floatValue(); + findAddressesFromCoordinates(latitude, longitude, result); + } else { + result.notImplemented(); + } + } - else result.success(createAddressMapList(addresses)); - } - else result.error("failed", "Failed", null); + private void assertPresent() throws NotAvailableException { + if (!Geocoder.isPresent()) { + throw new NotAvailableException(); } - }.execute(); - } + } + + private void findAddressesFromQuery(final String address, final Result result) { - private Map createCoordinatesMap(Address address) { + final GeocoderPlugin plugin = this; + new AsyncTask>() { + @Override + protected List
doInBackground(Void... params) { + try { + plugin.assertPresent(); + return geocoder.getFromLocationName(address, 20); + } catch (IOException ex) { + result.error("failed", "IOException", null); + return null; + } catch (NotAvailableException ex) { + result.error("not_available", "NotAvailableException", null); + return null; + } + } - if(address == null) - return null; + @Override + protected void onPostExecute(List
addresses) { + if (addresses != null) { + result.success(createAddressMapList(addresses)); + } + } + }.execute(); + } - Map result = new HashMap(); + private void findAddressesFromCoordinates(final float latitude, final float longitude, final Result result) { + final GeocoderPlugin plugin = this; + new AsyncTask>() { + @Override + protected List
doInBackground(Void... params) { + try { + plugin.assertPresent(); + return geocoder.getFromLocation(latitude, longitude, 20); + } catch (IOException ex) { + result.error("failed", "IOException", null); + return null; + } catch (NotAvailableException ex) { + result.error("not_available", "NotAvailableException", null); + return null; + } + } - result.put("latitude", address.getLatitude()); - result.put("longitude", address.getLongitude()); + @Override + protected void onPostExecute(List
addresses) { + if (addresses != null) { + result.success(createAddressMapList(addresses)); + } + } + }.execute(); + } - return result; - } + private Map createCoordinatesMap(Address address) { + if (address == null) { + return null; + } - private Map createAddressMap(Address address) { + Map result = new HashMap<>(); - if(address == null) - return null; + result.put("latitude", address.getLatitude()); + result.put("longitude", address.getLongitude()); - // Creating formatted address - StringBuilder sb = new StringBuilder(); - for (int i = 0; i <= address.getMaxAddressLineIndex(); i++) { - if (i > 0) { - sb.append(", "); - } - sb.append(address.getAddressLine(i)); + return result; } - Map result = new HashMap(); - - result.put("coordinates", createCoordinatesMap(address)); - result.put("featureName", address.getFeatureName()); - result.put("countryName", address.getCountryName()); - result.put("countryCode", address.getCountryCode()); - result.put("locality", address.getLocality()); - result.put("subLocality", address.getSubLocality()); - result.put("thoroughfare", address.getThoroughfare()); - result.put("subThoroughfare", address.getSubThoroughfare()); - result.put("adminArea", address.getAdminArea()); - result.put("subAdminArea", address.getSubAdminArea()); - result.put("addressLine", sb.toString()); - result.put("postalCode", address.getPostalCode()); + private Map createAddressMap(Address address) { + if (address == null) { + return null; + } - return result; - } + // Creating formatted address + StringBuilder sb = new StringBuilder(); + for (int i = 0; i <= address.getMaxAddressLineIndex(); i++) { + if (i > 0) { + sb.append(", "); + } + sb.append(address.getAddressLine(i)); + } - private List> createAddressMapList(List
addresses) { + Map result = new HashMap<>(); + + result.put("coordinates", createCoordinatesMap(address)); + result.put("featureName", address.getFeatureName()); + result.put("countryName", address.getCountryName()); + result.put("countryCode", address.getCountryCode()); + result.put("locality", address.getLocality()); + result.put("subLocality", address.getSubLocality()); + result.put("thoroughfare", address.getThoroughfare()); + result.put("subThoroughfare", address.getSubThoroughfare()); + result.put("adminArea", address.getAdminArea()); + result.put("subAdminArea", address.getSubAdminArea()); + result.put("addressLine", sb.toString()); + result.put("postalCode", address.getPostalCode()); + + return result; + } - if(addresses == null) - return new ArrayList>(); + private List> createAddressMapList(List
addresses) { + if (addresses == null) { + return new ArrayList<>(); + } - List> result = new ArrayList>(addresses.size()); + List> result = new ArrayList<>(addresses.size()); + for (Address address : addresses) { + result.add(createAddressMap(address)); + } - for (Address address : addresses) { - result.add(createAddressMap(address)); + return result; } - - return result; - } } diff --git a/example/android/gradle.properties b/example/android/gradle.properties index 8bd86f6..7be3d8b 100644 --- a/example/android/gradle.properties +++ b/example/android/gradle.properties @@ -1 +1,2 @@ org.gradle.jvmargs=-Xmx1536M +android.enableR8=true diff --git a/example/lib/main.dart b/example/lib/main.dart index 967240c..12eebe0 100644 --- a/example/lib/main.dart +++ b/example/lib/main.dart @@ -17,7 +17,7 @@ class AppState extends InheritedWidget { Key key, this.mode, Widget child, - }) : assert(mode != null), + }) : assert(mode != null), assert(child != null), super(key: key, child: child); @@ -32,7 +32,6 @@ class AppState extends InheritedWidget { } class GeocodeView extends StatefulWidget { - GeocodeView(); @override @@ -40,7 +39,6 @@ class GeocodeView extends StatefulWidget { } class _GeocodeViewState extends State { - _GeocodeViewState(); final TextEditingController _controller = new TextEditingController(); @@ -50,22 +48,19 @@ class _GeocodeViewState extends State { bool isLoading = false; Future search() async { - this.setState(() { this.isLoading = true; }); - try{ + try { var geocoding = AppState.of(context).mode; var results = await geocoding.findAddressesFromQuery(_controller.text); this.setState(() { this.results = results; }); - } - catch(e) { - print("Error occured: $e"); - } - finally { + } catch (e) { + print("Error occurred: $e"); + } finally { this.setState(() { this.isLoading = false; }); @@ -75,30 +70,32 @@ class _GeocodeViewState extends State { @override Widget build(BuildContext context) { return new Column( - children: [ - new Card( - child: new Padding( - padding: const EdgeInsets.all(10.0), - child: new Row( - children: [ - new Expanded( - child: new TextField( - controller: _controller, - decoration: new InputDecoration(hintText: "Enter an address"), - ), + children: [ + new Card( + child: new Padding( + padding: const EdgeInsets.all(10.0), + child: new Row( + children: [ + new Expanded( + child: new TextField( + controller: _controller, + decoration: + new InputDecoration(hintText: "Enter an address"), ), - new IconButton(icon: new Icon(Icons.search), onPressed: () => search()) - ], - ), + ), + new IconButton( + icon: new Icon(Icons.search), onPressed: () => search()) + ], ), ), - new Expanded(child: new AddressListView(this.isLoading, this.results)), - ]); + ), + new Expanded(child: new AddressListView(this.isLoading, this.results)), + ], + ); } } class ReverseGeocodeView extends StatefulWidget { - ReverseGeocodeView(); @override @@ -106,8 +103,8 @@ class ReverseGeocodeView extends StatefulWidget { } class _ReverseGeocodeViewState extends State { - - final TextEditingController _controllerLongitude = new TextEditingController(); + final TextEditingController _controllerLongitude = + new TextEditingController(); final TextEditingController _controllerLatitude = new TextEditingController(); _ReverseGeocodeViewState(); @@ -117,25 +114,23 @@ class _ReverseGeocodeViewState extends State { bool isLoading = false; Future search() async { - - this.setState(() { this.isLoading = true; }); - try{ + try { var geocoding = AppState.of(context).mode; var longitude = double.parse(_controllerLongitude.text); var latitude = double.parse(_controllerLatitude.text); - var results = await geocoding.findAddressesFromCoordinates(new Coordinates(latitude, longitude)); + var results = await geocoding.findAddressesFromCoordinates( + Coordinates(latitude, longitude), + ); this.setState(() { this.results = results; }); - } - catch(e) { - print("Error occured: $e"); - } - finally { + } catch (e) { + print("Error occurred: ${e.toString()}"); + } finally { this.setState(() { this.isLoading = false; }); @@ -145,43 +140,44 @@ class _ReverseGeocodeViewState extends State { @override Widget build(BuildContext context) { return new Column( - children: [ - new Card( - child: new Padding( - padding: const EdgeInsets.all(10.0), - child: new Row( - children: [ - new Expanded( - child: new Column( - children: [ - new TextField( - controller: _controllerLatitude, - decoration: new InputDecoration(hintText: "Latitude"), - ), - new TextField( - controller: _controllerLongitude, - decoration: new InputDecoration(hintText: "Longitude"), - ), - ], - ), + children: [ + new Card( + child: new Padding( + padding: const EdgeInsets.all(10.0), + child: new Row( + children: [ + new Expanded( + child: new Column( + children: [ + new TextField( + controller: _controllerLatitude, + decoration: new InputDecoration(hintText: "Latitude"), + ), + new TextField( + controller: _controllerLongitude, + decoration: new InputDecoration(hintText: "Longitude"), + ), + ], ), - new IconButton(icon: new Icon(Icons.search), onPressed: () => search()) - ], - ), + ), + new IconButton( + icon: new Icon(Icons.search), onPressed: () => search()) + ], ), ), - new Expanded(child: new AddressListView(this.isLoading, this.results)), - ]); + ), + new Expanded(child: new AddressListView(this.isLoading, this.results)), + ], + ); } } class _MyAppState extends State { - Geocoding geocoding = Geocoder.local; final Map modes = { - "Local" : Geocoder.local, - "Google (distant)" : Geocoder.google(""), + "Local": Geocoder.local, + "Google (distant)": Geocoder.google(""), }; void _changeMode(Geocoding mode) { @@ -201,37 +197,41 @@ class _MyAppState extends State { appBar: new AppBar( title: new Text('Geocoder'), actions: [ - new PopupMenuButton( // overflow menu + new PopupMenuButton( + // overflow menu onSelected: _changeMode, itemBuilder: (BuildContext context) { - return modes.keys.map((String mode) { - return new CheckedPopupMenuItem( - checked: modes[mode] == this.geocoding, - value: modes[mode], - child: new Text(mode), - ); - }).toList(); + return modes.keys.map( + (String mode) { + return new CheckedPopupMenuItem( + checked: modes[mode] == this.geocoding, + value: modes[mode], + child: new Text(mode), + ); + }, + ).toList(); }, ), ], bottom: new TabBar( - tabs: [ - new Tab( + tabs: [ + new Tab( text: "Query", icon: new Icon(Icons.search), ), - new Tab( - text: "Coordinates", - icon: new Icon(Icons.pin_drop), - ), + new Tab( + text: "Coordinates", + icon: new Icon(Icons.pin_drop), + ), ], ), ), body: new TabBarView( - children: [ - new GeocodeView(), - new ReverseGeocodeView(), - ]), + children: [ + new GeocodeView(), + new ReverseGeocodeView(), + ], + ), ), ), ), diff --git a/example/lib/widgets.dart b/example/lib/widgets.dart index c3217f8..279114b 100644 --- a/example/lib/widgets.dart +++ b/example/lib/widgets.dart @@ -1,40 +1,48 @@ import 'package:flutter/material.dart'; import 'package:geocoder/model.dart'; - class AddressTile extends StatelessWidget { - final Address address; AddressTile(this.address); - final titleStyle = const TextStyle(fontSize: 15.0, fontWeight: FontWeight.bold); + final titleStyle = const TextStyle( + fontSize: 15.0, + fontWeight: FontWeight.bold, + ); @override Widget build(BuildContext context) { return new Padding( - padding: const EdgeInsets.all(10.0), - child: new Column( - crossAxisAlignment: CrossAxisAlignment.start, - children: [ - new ErrorLabel("feature name", this.address.featureName, fontSize: 15.0, isBold: true, ), - new ErrorLabel("address lines", this.address.addressLine), - new ErrorLabel("country name", this.address.countryName), - new ErrorLabel("locality", this.address.locality), - new ErrorLabel("sub-locality", this.address.subLocality), - new ErrorLabel("admin-area", this.address.adminArea), - new ErrorLabel("sub-admin-area", this.address.subAdminArea), - new ErrorLabel("thoroughfare", this.address.thoroughfare), - new ErrorLabel("sub-thoroughfare", this.address.subThoroughfare), - new ErrorLabel("postal code", this.address.postalCode), - this.address.coordinates != null ? new ErrorLabel("", this.address.coordinates.toString()) : new ErrorLabel("coordinates", null), - ]), - ); + padding: const EdgeInsets.all(10.0), + child: new Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + new ErrorLabel( + "feature name", + this.address.featureName, + fontSize: 15.0, + isBold: true, + ), + new ErrorLabel("address lines", this.address.addressLine), + new ErrorLabel("country name", this.address.countryName), + new ErrorLabel("locality", this.address.locality), + new ErrorLabel("sub-locality", this.address.subLocality), + new ErrorLabel("admin-area", this.address.adminArea), + new ErrorLabel("sub-admin-area", this.address.subAdminArea), + new ErrorLabel("thoroughfare", this.address.thoroughfare), + new ErrorLabel("sub-thoroughfare", this.address.subThoroughfare), + new ErrorLabel("postal code", this.address.postalCode), + this.address.coordinates != null + ? new ErrorLabel("", this.address.coordinates.toString()) + : new ErrorLabel("coordinates", null), + ], + ), + ); } } class AddressListView extends StatelessWidget { - final List
addresses; final bool isLoading; @@ -43,30 +51,33 @@ class AddressListView extends StatelessWidget { @override Widget build(BuildContext context) { - - if(this.isLoading) { + if (this.isLoading) { return new Center(child: new CircularProgressIndicator()); } return new ListView.builder( itemCount: this.addresses.length, - itemBuilder: (c,i) => new AddressTile(this.addresses[i]), + itemBuilder: (c, i) => new AddressTile(this.addresses[i]), ); } } class ErrorLabel extends StatelessWidget { - final String name, text; final TextStyle descriptionStyle; - ErrorLabel(this.name, String text, { double fontSize = 9.0, bool isBold = false}) : - this.text = text ?? "Unknown $name", - this.descriptionStyle = new TextStyle(fontSize: fontSize, fontWeight: isBold ? FontWeight.bold : FontWeight.normal, color: text == null ? Colors.red : Colors.black); + ErrorLabel(this.name, String text, + {double fontSize = 9.0, bool isBold = false}) + : this.text = text ?? "Unknown $name", + this.descriptionStyle = new TextStyle( + fontSize: fontSize, + fontWeight: isBold ? FontWeight.bold : FontWeight.normal, + color: text == null ? Colors.red : Colors.black, + ); @override Widget build(BuildContext context) { return new Text(this.text, style: descriptionStyle); } -} \ No newline at end of file +} diff --git a/example/pubspec.yaml b/example/pubspec.yaml index 2358988..e52752a 100644 --- a/example/pubspec.yaml +++ b/example/pubspec.yaml @@ -4,56 +4,13 @@ description: Demonstrates how to use the geocoder plugin. dependencies: flutter: sdk: flutter - - # The following adds the Cupertino Icons font to your application. - # Use with the CupertinoIcons class for iOS style icons. - cupertino_icons: ^0.1.0 + cupertino_icons: ^0.1.3 dev_dependencies: flutter_test: sdk: flutter - geocoder: path: ../ -# For information on the generic Dart part of this file, see the -# following page: https://www.dartlang.org/tools/pub/pubspec - -# The following section is specific to Flutter. flutter: - - # The following line ensures that the Material Icons font is - # included with your application, so that you can use the icons in - # the material Icons class. - uses-material-design: true - - # To add assets to your application, add an assets section, like this: - # assets: - # - images/a_dot_burr.jpeg - # - images/a_dot_ham.jpeg - - # An image asset can refer to one or more resolution-specific "variants", see - # https://flutter.io/assets-and-images/#resolution-aware. - - # For details regarding adding assets from package dependencies, see - # https://flutter.io/assets-and-images/#from-packages - - # To add custom fonts to your application, add a fonts section here, - # in this "flutter" section. Each entry in this list should have a - # "family" key with the font family name, and a "fonts" key with a - # list giving the asset and other descriptors for the font. For - # example: - # fonts: - # - family: Schyler - # fonts: - # - asset: fonts/Schyler-Regular.ttf - # - asset: fonts/Schyler-Italic.ttf - # style: italic - # - family: Trajan Pro - # fonts: - # - asset: fonts/TrajanPro.ttf - # - asset: fonts/TrajanPro_Bold.ttf - # weight: 700 - # - # For details regarding fonts from package dependencies, - # see https://flutter.io/custom-fonts/#from-packages + uses-material-design: true \ No newline at end of file diff --git a/lib/geocoder.dart b/lib/geocoder.dart index 33a277f..7dca227 100644 --- a/lib/geocoder.dart +++ b/lib/geocoder.dart @@ -6,5 +6,7 @@ export 'model.dart'; class Geocoder { static final Geocoding local = LocalGeocoding(); - static Geocoding google(String apiKey, { String language }) => GoogleGeocoding(apiKey, language: language); + + static Geocoding google(String apiKey, {String language}) => + GoogleGeocoding(apiKey, language: language); } diff --git a/lib/model.dart b/lib/model.dart index f45e835..e1862b1 100644 --- a/lib/model.dart +++ b/lib/model.dart @@ -2,7 +2,6 @@ import 'package:meta/meta.dart'; @immutable class Coordinates { - /// The geographic coordinate that specifies the north–south position of a point on the Earth's surface. final double latitude; @@ -12,15 +11,15 @@ class Coordinates { Coordinates(this.latitude, this.longitude); /// Creates coordinates from a map containing its properties. - Coordinates.fromMap(Map map) : - this.latitude = map["latitude"], + Coordinates.fromMap(Map map) + : this.latitude = map["latitude"], this.longitude = map["longitude"]; /// Creates a map from the coordinates properties. Map toMap() => { - "latitude": this.latitude, - "longitude": this.longitude, - }; + "latitude": this.latitude, + "longitude": this.longitude, + }; String toString() => "{$latitude,$longitude}"; } @@ -63,11 +62,23 @@ class Address { /// The sub-thoroughfare name of the address final String subThoroughfare; - Address({this.coordinates, this.addressLine, this.countryName, this.countryCode, this.featureName, this.postalCode, this.adminArea, this.subAdminArea, this.locality, this.subLocality, this.thoroughfare, this.subThoroughfare}); + Address( + {this.coordinates, + this.addressLine, + this.countryName, + this.countryCode, + this.featureName, + this.postalCode, + this.adminArea, + this.subAdminArea, + this.locality, + this.subLocality, + this.thoroughfare, + this.subThoroughfare}); /// Creates an address from a map containing its properties. - Address.fromMap(Map map) : - this.coordinates = new Coordinates.fromMap(map["coordinates"]), + Address.fromMap(Map map) + : this.coordinates = new Coordinates.fromMap(map["coordinates"]), this.addressLine = map["addressLine"], this.countryName = map["countryName"], this.countryCode = map["countryCode"], @@ -82,17 +93,17 @@ class Address { /// Creates a map from the address properties. Map toMap() => { - "coordinates": this.coordinates.toMap(), - "addressLine": this.addressLine, - "countryName": this.countryName, - "countryCode": this.countryCode, - "featureName": this.featureName, - "postalCode": this.postalCode, - "locality": this.locality, - "subLocality": this.subLocality, - "adminArea": this.adminArea, - "subAdminArea": this.subAdminArea, - "thoroughfare": this.thoroughfare, - "subThoroughfare": this.subThoroughfare, - }; -} \ No newline at end of file + "coordinates": this.coordinates.toMap(), + "addressLine": this.addressLine, + "countryName": this.countryName, + "countryCode": this.countryCode, + "featureName": this.featureName, + "postalCode": this.postalCode, + "locality": this.locality, + "subLocality": this.subLocality, + "adminArea": this.adminArea, + "subAdminArea": this.subAdminArea, + "thoroughfare": this.thoroughfare, + "subThoroughfare": this.subThoroughfare, + }; +} diff --git a/lib/services/base.dart b/lib/services/base.dart index a4d8103..4bf88a9 100644 --- a/lib/services/base.dart +++ b/lib/services/base.dart @@ -3,10 +3,9 @@ import 'dart:async'; import 'package:geocoder/model.dart'; abstract class Geocoding { - /// Search corresponding addresses from given [coordinates]. Future> findAddressesFromCoordinates(Coordinates coordinates); /// Search for addresses that matches que given [address] query. Future> findAddressesFromQuery(String address); -} \ No newline at end of file +} diff --git a/lib/services/distant_google.dart b/lib/services/distant_google.dart index 7f2195f..f8c848d 100644 --- a/lib/services/distant_google.dart +++ b/lib/services/distant_google.dart @@ -8,7 +8,6 @@ import 'package:geocoder/services/base.dart'; /// Geocoding and reverse geocoding through requests to Google APIs. class GoogleGeocoding implements Geocoding { - static const _host = 'https://maps.google.com/maps/api/geocode/json'; final String apiKey; @@ -16,15 +15,20 @@ class GoogleGeocoding implements Geocoding { final HttpClient _httpClient; - GoogleGeocoding(this.apiKey, { this.language }) : - _httpClient = HttpClient(), - assert(apiKey != null, "apiKey must not be null"); + GoogleGeocoding(this.apiKey, {this.language}) + : _httpClient = HttpClient(), + assert(apiKey != null, "apiKey must not be null"); - Future> findAddressesFromCoordinates(Coordinates coordinates) async { - final url = '$_host?key=$apiKey${language != null ? '&language='+language : ''}&latlng=${coordinates.latitude},${coordinates.longitude}'; + @override + Future> findAddressesFromCoordinates( + Coordinates coordinates, + ) async { + final url = + '$_host?key=$apiKey${language != null ? '&language=' + language : ''}&latlng=${coordinates.latitude},${coordinates.longitude}'; return _send(url); } + @override Future> findAddressesFromQuery(String address) async { var encoded = Uri.encodeComponent(address); final url = '$_host?key=$apiKey&address=$encoded'; @@ -42,30 +46,27 @@ class GoogleGeocoding implements Geocoding { var results = data["results"]; - if(results == null) - return null; + if (results == null) return null; - return results.map(_convertAddress) - .map
((map) => Address.fromMap(map)) - .toList(); + return results + .map(_convertAddress) + .map
((map) => Address.fromMap(map)) + .toList(); } Map _convertCoordinates(dynamic geometry) { - if(geometry == null) - return null; + if (geometry == null) return null; var location = geometry["location"]; - if(location == null) - return null; + if (location == null) return null; return { - "latitude" : location["lat"], - "longitude" : location["lng"], + "latitude": location["lat"], + "longitude": location["lng"], }; } Map _convertAddress(dynamic data) { - Map result = Map(); result["coordinates"] = _convertCoordinates(data["geometry"]); @@ -74,45 +75,33 @@ class GoogleGeocoding implements Geocoding { var addressComponents = data["address_components"]; addressComponents.forEach((item) { - List types = item["types"]; - if(types.contains("route")) { - + if (types.contains("route")) { result["thoroughfare"] = item["long_name"]; - } - else if(types.contains("street_number")) { - + } else if (types.contains("street_number")) { result["subThoroughfare"] = item["long_name"]; - } - else if(types.contains("country")) { + } else if (types.contains("country")) { result["countryName"] = item["long_name"]; result["countryCode"] = item["short_name"]; - } - else if(types.contains("locality")) { + } else if (types.contains("locality")) { result["locality"] = item["long_name"]; - } - else if(types.contains("postal_code")) { + } else if (types.contains("postal_code")) { result["postalCode"] = item["long_name"]; - } - else if(types.contains("postal_code")) { + } else if (types.contains("postal_code")) { result["postalCode"] = item["long_name"]; - } - else if(types.contains("administrative_area_level_1")) { + } else if (types.contains("administrative_area_level_1")) { result["adminArea"] = item["long_name"]; - } - else if(types.contains("administrative_area_level_2")) { + } else if (types.contains("administrative_area_level_2")) { result["subAdminArea"] = item["long_name"]; - } - else if(types.contains("sublocality") || types.contains("sublocality_level_1")) { + } else if (types.contains("sublocality") || + types.contains("sublocality_level_1")) { result["subLocality"] = item["long_name"]; - } - else if(types.contains("premise")) { + } else if (types.contains("premise")) { result["featureName"] = item["long_name"]; } result["featureName"] = result["featureName"] ?? result["addressLine"]; - }); return result; diff --git a/lib/services/local.dart b/lib/services/local.dart index 8d924ab..4a6df4e 100644 --- a/lib/services/local.dart +++ b/lib/services/local.dart @@ -4,18 +4,27 @@ import 'package:flutter/services.dart'; import 'package:geocoder/model.dart'; import 'package:geocoder/services/base.dart'; - /// Geocoding and reverse geocoding through built-lin local platform services. class LocalGeocoding implements Geocoding { - static const MethodChannel _channel = MethodChannel('github.com/aloisdeniel/geocoder'); + static const MethodChannel _channel = MethodChannel( + 'github.com/aloisdeniel/geocoder', + ); - Future> findAddressesFromCoordinates(Coordinates coordinates) async { - Iterable addresses = await _channel.invokeMethod('findAddressesFromCoordinates', coordinates.toMap()); + Future> findAddressesFromCoordinates( + Coordinates coordinates, + ) async { + Iterable addresses = await _channel.invokeMethod( + 'findAddressesFromCoordinates', + coordinates.toMap(), + ); return addresses.map((x) => Address.fromMap(x)).toList(); } Future> findAddressesFromQuery(String address) async { - Iterable coordinates = await _channel.invokeMethod('findAddressesFromQuery', { "address" : address }); + Iterable coordinates = await _channel.invokeMethod( + 'findAddressesFromQuery', + {"address": address}, + ); return coordinates.map((x) => Address.fromMap(x)).toList(); } -} \ No newline at end of file +} diff --git a/pubspec.yaml b/pubspec.yaml index 10a252c..49fc490 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -1,14 +1,14 @@ name: geocoder description: Forward and reverse geocoding. -version: 0.2.1 +version: 0.2.2 author: Aloïs Deniel homepage: https://github.com/aloisdeniel/flutter_geocoder environment: - sdk: ">=2.0.0 <3.0.0" + sdk: ">=2.0.0 <3.0.0" dependencies: - meta: ^1.1.6 + meta: ^1.2.2 flutter: sdk: flutter