3

I want to load kml files on google map in flutter. i can't find it on google _maps_flutter plugin. is there any other plugins which can do it in flutter?

Code Runner
  • 868
  • 16
  • 27
  • KML doesn't seem to be supported yet. See these issues: [1](https://github.com/flutter/flutter/issues/33514) [2](https://github.com/flutter/flutter/issues/33563) [3](https://github.com/flutter/flutter/issues/41897) – evan Oct 17 '19 at 14:43

2 Answers2

0

It's been a month, so you may have figured this out, but hopefully, if you haven't this can help.

You can run native code in flutter, so if you can adapt this, it should work. You will need to create a Method Channel to run the native code with something like this.

// Run java code for KML Campus Map Overlay
  Future<void> _showCampusMap() async {
    const platform = MethodChannel(**<YOUR METHOD CHANNEL>**);
    try {
      final campusMapOverlay = await platform.invokeMethod('downloadKmlLayer');
      print(campusMapOverlay);
    } on PlatformException catch (error) {
      print(error);
    }
  }

KML Layer code can be found in the URL below.

https://github.com/googlemaps/android-maps-utils/commit/d606fcde40467abb5fae2ba78b8562a2cd1c517b

Even though I have managed to get native code to work, with simply displaying some text, I haven't figured out how to get the KML Code to work yet.I think the problem lies in it not knowing what mMap is in the onPostExecute method, but it is very possible there is more than I do not know.

    import java.io.Console;    
    import android.os.Bundle;
    import io.flutter.app.FlutterActivity;
    import io.flutter.plugins.GeneratedPluginRegistrant;
    import io.flutter.plugin.common.MethodCall;
    import io.flutter.plugin.common.MethodChannel;
    import io.flutter.plugin.common.MethodChannel.Result;
    import io.flutter.plugin.common.MethodChannel.MethodCallHandler;

    import org.xmlpull.v1.XmlPullParserException;
    import android.os.AsyncTask;
    import java.io.ByteArrayInputStream;
    import java.io.ByteArrayOutputStream;
    import java.io.IOException;
    import java.io.InputStream;
    import java.net.URL;


    public class MainActivity extends FlutterActivity {
      @Override
      protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        GeneratedPluginRegistrant.registerWith(this);

        new MethodChannel(getFlutterView(), "**<YOUR METHOD CHANNEL>**").setMethodCallHandler(new MethodCallHandler() {
          @Override
          public void onMethodCall(MethodCall call, MethodChannel.Result result) {

            if (call.method.equals("retrieveFileFromUrl")) {
              String KMLLayer = retrieveFileFromUrl();
              result.success(KMLLayer);
            }

          }
        });
      }

      private void retrieveFileFromUrl() {
        new DownloadKmlFile("**<YOUR KML LAYER>**")
                .execute();
      }

      private class DownloadKmlFile extends AsyncTask<String, Void, byte[]> {
        private final String mUrl;

        public DownloadKmlFile(String url) {
          mUrl = url;
        }

        protected byte[] doInBackground(String... params) {

          try {
            InputStream is = new URL(mUrl).openStream();
            // Log.d(TAG, "doInBackground: " + mUrl.toString());
            ByteArrayOutputStream buffer = new ByteArrayOutputStream();
            int nRead;
            byte[] data = new byte[16384];
            while ((nRead = is.read(data, 0, data.length)) != -1) {
              buffer.write(data, 0, nRead);
            }
            buffer.flush();
            return buffer.toByteArray();
          } catch (IOException e) {
            e.printStackTrace();
          }
          return null;
        }

        protected void onPostExecute(byte[] byteArr) {
          try {
            KmlLayer kmlLayer = new KmlLayer(mMap, new ByteArrayInputStream(byteArr), getApplicationContext());
            kmlLayer.addLayerToMap();
            // moveCameraToKml(kmlLayer);
          } catch (XmlPullParserException e) {
            e.printStackTrace();
          } catch (IOException e) {
            e.printStackTrace();
          }
        }
      }
    }

You can see here for a bit more details.

https://medium.com/47billion/creating-a-bridge-in-flutter-between-dart-and-native-code-in-java-or-objectivec-5f80fd0cd713

I hope gets you on the right path.

Andrew Stevenson
  • 578
  • 1
  • 9
  • 23
  • Thanks. I haven't get anything yet. But I am busy with something else so I will get look into it later and get back to you and let you know it helps me or not. Again thank you so much for your help – Code Runner Nov 18 '19 at 15:49
  • You're welcome. I'm working on the same thing, but I have 4 errors atm. I'll provide my solution, if I get there, unless you get there first. – Andrew Stevenson Nov 18 '19 at 17:04
  • I haven't yet. I got down to 3 errors, but I'm stuck. This line includes a variable mMap that connects to GoogleMap in JAVA, but I am using google_map_flutter package and I don't know how to link it. I'm unsure whether I need to include all the JAVA map code and dismiss the flutter map code. KmlLayer kmlLayer = new KmlLayer(mMap, new ByteArrayInputStream(byteArr), getApplicationContext()); – Andrew Stevenson Dec 03 '19 at 09:37
  • Somebody has written a custom integration layer for google_maps_flutter and is waiting for permission to share the code. It might be worth you signing in and mentioning that you are interested. https://github.com/flutter/flutter/issues/33563 – Andrew Stevenson Dec 10 '19 at 15:40
  • yeah I sent him the file but he is waiting for confirmation so I don't know when he will get confirmation. So even I am trying to write my own as well but same as you I am confused about how to connect that layer to google_maps_flutter' – Code Runner Dec 10 '19 at 19:33
0

--------NOTE: only for android-------------

This solution won't work for iOS but there is a workaround for android, you can see the solution here in the medium article

Code Runner
  • 868
  • 16
  • 27