【iOS/SwiftUI】GoogleMapに現在地を表示する

SwiftUIに戻る

目次

概要

前回はGoogleMapの導入方法を記載した。
今度は自分の現在地を表示させよう。現在地という特性上、スクリーンショットやデモ動画はないので、その点ご了承いただきたい。

ソースコード

import SwiftUI

@main
struct TestApp: App {
    @UIApplicationDelegateAdaptor(AppDelegate.self) var appDelegate
    
    var body: some Scene {
        WindowGroup {
            GoogleMapView()
        }
    }
}
import SwiftUI
import ExternalAccessory

struct GoogleMapView: View {
    var body: some View {
        VStack {
            ZStack {
                CustomMapView()
            }
            Text("GoogleMap Test")
        }
        .onAppear {
            print("表示されたよ")
        }
    }
}
import SwiftUI
import GoogleMaps

struct CustomMapView: UIViewRepresentable {
    let mapView = GMSMapView()
    @State var locationManager = CLLocationManager()
    
    func makeCoordinator() -> LocationCoordinator {
        return LocationCoordinator(mapView: self)
    }
    
    func makeUIView(context: Context) -> GMSMapView {
        mapView.isMyLocationEnabled = true
        locationManager.delegate = context.coordinator
        locationManager.requestWhenInUseAuthorization()
        locationManager.distanceFilter = 50
        locationManager.startUpdatingLocation()
        return mapView
    }

    func updateUIView(_ mapView: GMSMapView, context: Context) {
    }
}

final class LocationCoordinator: NSObject {
    var parent: CustomMapView
    
    init(mapView: CustomMapView) {
        parent = mapView
    }
}

extension LocationCoordinator: CLLocationManagerDelegate {
    func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
        guard let userLocation = locations.last else { return }
        let camera = GMSCameraPosition.camera(
            withLatitude: userLocation.coordinate.latitude,
            longitude: userLocation.coordinate.longitude,
            zoom: 15.0
        )
        parent.mapView.animate(to: camera)
        parent.locationManager.stopUpdatingLocation()
    }
}

詳細

info.plist

info.plistに「Privacy – Location When In Use Usage Description」の項目を追加する。
この項目は位置情報を取得する際にダイアログに表示される文言を記載する。

これをやらなくては現在地を取得できないから注意だ。

CustomMapView.swift

CustomMapView

こちらは位置情報取得などの処理部分とView部分の橋渡し的な感じになっている。
以下のようにdelegateをcontext.coordinator(LocationCoordinatorクラス)に設定するため、位置情報の更新などに行われる処理はLocationCoordinatorクラスで行われるようにする。requestWhenInUseAuthorizationで端末から位置情報を取得できるようにする。

locationManager.delegate = context.coordinator
locationManager.requestWhenInUseAuthorization()
locationManager.distanceFilter = 50
locationManager.startUpdatingLocation()

LocationCoordinatorクラス

ここでは位置情報の取得をデリゲートメソッドを使用することで取得している。
locationManagerメソッドで位置情報を取得して橋渡し役であるmapView(parent)に渡し、そこから画面に反映させるようにしている。

GMSCameraPositionを使用して、中心位置やズームを設定する。

参考ページ

SwiftUIに戻る