初始化后如何从函数中获取值?
Posted
技术标签:
【中文标题】初始化后如何从函数中获取值?【英文标题】:How to get value from function after it has already been initialised? 【发布时间】:2017-09-18 10:30:16 【问题描述】:我从 Firebase 获取我的坐标,然后将它们放在我的地图上,但问题是我的 Firebase 获取指令发生在地图初始化标记之后,在我的坐标中给出 nil
。
如何从 Firebase 中获取值并将它们作为标记?
var fetchLat: Double!
var fetchLong: Double!
我在这里从 Firebase 获取值
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation])
let camera = GMSCameraPosition.camera(withLatitude: latPass, longitude: longPass, zoom: 5)
let mapView = GMSMapView.map(withFrame: CGRect.zero, camera: camera)
view = mapView
mapView.settings.scrollGestures = true
mapView.settings.zoomGestures = true
mapView.settings.myLocationButton = true
let dataBaseRef=FIRDatabase.database().reference()
dataBaseRef.child("LocationTest").queryOrderedByKey().observe(.childAdded, with: (snapshot) in
let postDict = snapshot.value as? [String : AnyObject] ?? [:]
var fetchLat = postDict["lat"] as! Double
var fetchLong = postDict["long"] as! Double
)
我把它们放在地图上
let friendLocator = [
Locator(name: "Virat", long: fetchLong, lat: fetchLat),
]
for friend in friendLocator
let friendMarker = GMSMarker()
friendMarker.position=CLLocationCoordinate2D(latitude: friend.lat, longitude: friend.long)
friendMarker.title=friend.name
friendMarker.map=mapView
mapView.selectedMarker=friendMarker
因为地图初始化是在从 Firebase 获取值之前完成的,所以在获取值之后如何设置标记?
【问题讨论】:
为什么在 didUpdateLocations 中调用 firebase 获取请求。 @Pushpendra 因为我在didUpdateLocations
中添加了我的标记
@naveen-saini : view = mapView 那里的视图是什么? Self.view 或单独的 UIView 变量名为 view ??
@SandeepBhandari 只是self.view
@naveen-saini :这意味着你的 self.view 是 GMSMapView 类型,那么你不需要在另一个函数中引用 mapView ,你可以简单地说 self.view.selectedMarker=friendMarker
【参考方案1】:
如果在地图上显示用户的 ViewController 与 LocationManager
的代理相同,那么,
在您的 ViewController 中创建一个属性,
var friendLocator : [Locator] = [Locator]()
创建一个在地图上绘制用户的函数
func locateFriends()
if self.view is GMSMapView
for friend in friendLocator
let friendMarker = GMSMarker()
friendMarker.position=CLLocationCoordinate2D(latitude: friend.lat, longitude: friend.long)
friendMarker.title=friend.name
friendMarker.map= (self.view as! GMSMapView)
(self.view as! GMSMapView).selectedMarker=friendMarker
最后将新找到的定位器实例追加到didUpdateLocations
delegate中的数组
extension ViewController : UIPageViewControllerDelegate
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation])
let dataBaseRef=FIRDatabase.database().reference()
dataBaseRef.child("LocationTest").queryOrderedByKey().observe(.childAdded, with: (snapshot) in
let postDict = snapshot.value as? [String : AnyObject] ?? [:]
var fetchLat = postDict["lat"] as! Double
var fetchLong = postDict["long"] as! Double
let locator = Locator(name: "Virat", long: fetchLong, lat: fetchLat)
//do some sort of duplicate check before blindly adding new locator to array
self.friendLocator.append(locator)
self.locateFriends()
)
如果在地图上显示用户的 ViewController 不同,则 UILocationManager 委托使用相同的逻辑,但使用delegate
模式通知 ViewController 新的定位器对象并重新加载地图。
编辑:
重新格式化 OP 的代码
import MapKit
import UIKit
import CoreLocation
import GoogleMaps
import GooglePlaces
import GoogleMapsCore
import Firebase
import FirebaseDatabase
struct postStruct
let lat: Double!
let long: Double!
class ViewController: UIViewController,MKMapViewDelegate, CLLocationManagerDelegate, UISearchBarDelegate
var viratPin=CustomPointAnnotation()
var posts=[postStruct]()
var mapView : GMSMapView? = nil
var friendLocator : [Locator] = [Locator]()
@IBOutlet weak var searchBar: UISearchBar!
@IBOutlet weak var searchSupporter: UIView!
@IBAction func dismissKeyboard(_ sender: Any)
searchBar.resignFirstResponder()
struct Locator
let name: String
let long: CLLocationDegrees
let lat: CLLocationDegrees
class CustomPointAnnotation: MKPointAnnotation
var imageName: String!
let manager = CLLocationManager()
var myLocation: CLLocationCoordinate2D?
var friend1: CLLocationCoordinate2D?
var arbokPin = CustomPointAnnotation()
var location=0
var latPass: Double!
var longPass: Double!
var fetchLat: Double!
var fetchLong: Double!
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation])
var location=locations[0]
let span:MKCoordinateSpan=MKCoordinateSpanMake(0.01, 0.01)
var myLocation:CLLocationCoordinate2D=CLLocationCoordinate2DMake(location.coordinate.latitude, location.coordinate.longitude)
let region:MKCoordinateRegion=MKCoordinateRegionMake(myLocation, span)
latPass=location.coordinate.latitude
longPass=location.coordinate.longitude
post()
self.configureMapView()
let dataBaseRef=FIRDatabase.database().reference()
dataBaseRef.child("LocationTest").queryOrderedByKey().observe(.childAdded, with: (snapshot) in
let postDict = snapshot.value as? [String : AnyObject] ?? [:]
var fetchLat = postDict["lat"] as! Double
var fetchLong = postDict["long"] as! Double
let locator = Locator(name: "You", long: fetchLong, lat: fetchLat)
self.friendLocator.append(locator)
self.locateFriend()
)
manager.stopUpdatingLocation()
self.view = mapView
func configureMapView()
let camera = GMSCameraPosition.camera(withLatitude: latPass, longitude: longPass, zoom: 5)
self.mapView = GMSMapView.map(withFrame: CGRect.zero, camera: camera)
view = mapView
mapView.settings.scrollGestures = true
mapView.settings.zoomGestures = true
mapView.settings.myLocationButton = true
mapView.addSubview(searchBar)
mapView.addSubview(searchSupporter)
mapView.bringSubview(toFront: searchBar)
for gesture in mapView.gestureRecognizers!
mapView.removeGestureRecognizer(gesture)
func locateFriend()
for friend in friendLocator
let friendMarker = GMSMarker()
friendMarker.position=CLLocationCoordinate2D(latitude: friend.lat, longitude: friend.long)
friendMarker.title=friend.name
friendMarker.map=mapView
mapView.selectedMarker=friendMarker
if friend.name=="Virat"
friendMarker.icon=UIImage(named: "ViratPin.png")
else if friend.name=="Naveen"
friendMarker.icon=UIImage(named: "naveenPin.png")
else if friend.name=="You"
friendMarker.icon=UIImage(named: "currentLocation.png")
do
mapView.mapStyle = try GMSMapStyle(jsonString: kMapStyle)
catch
NSLog("One or more of the map styles failed to load. \(error)")
override func viewDidLoad()
super.viewDidLoad()
manager.delegate=self
manager.desiredAccuracy=kCLLocationAccuracyBest
manager.requestWhenInUseAuthorization()
manager.startUpdatingLocation()
searchBar.isUserInteractionEnabled=true
searchBar.delegate=self
searchSupporter.alpha=0
func searchBarTextDidBeginEditing(_ searchBar : UISearchBar)
self.searchSupporter.alpha=0.8
print("yes")
func searchBarTextDidEndEditing(_ searchBar: UISearchBar)
searchSupporter.alpha=0
print("no")
func searchBarSearchButtonClicked(_ searchBar: UISearchBar)
print(searchBar.text!)
override var prefersStatusBarHidden: Bool
return true
func post()
let post : [String: Double]=["lat":latPass, "long":longPass]
let dataBaseRef=FIRDatabase.database().reference()
//dataBaseRef.child("Location").childByAutoId().setValue(post)
dataBaseRef.child("Location").child("id").setValue(post)
【讨论】:
我的mapView
是在didUpdateLocations
中初始化的,所以我不能在另一个函数中使用它。
@naveen-saini : 我在 didUpdateLocations 中没有看到任何地图初始化代码
@naveen-saini :如果它在 didUpdateLocations 中初始化,您可以为 map 创建一个可选变量,并使其成为您的 ViewController 的实例属性,并在您的 didUpdateLocations 中将其用作 self.mapView,最后在locateFriends 函数在添加 GMSMarker 之前检查 self.mapView != nil thats all
@naveen-saini : 给我一秒钟
@naveen-saini : 立即查看以上是关于初始化后如何从函数中获取值?的主要内容,如果未能解决你的问题,请参考以下文章
Kotlin集合操作 ⑤ ( Map 集合 | 获取 Map 值 | Map 遍历 | 可变 Map 集合 )