如何制作Pokemon Go for iOS —第1部分:地图和位置

在本系列文章中,我们将借助Swift 3为iOS编写一个简单的’Pokemon Go’克隆。如果您使用的是Swift的当前公共版本,则可能要考虑使用Xcode 8,它带来了Swift 2.3和Swift 3。 如果值得使用Swift 3,则可以在这里了解。 不要犹豫,使用旧版本的Swift来完成本教程,您当然可以!

如果您没有上述工具,则可以考虑从AppStore下载Xcode。 这样,您便可以开始使用Swift 2(撰写本文时)。

因此,首先让我们启动Xcode-beta(Xcode 8)并创建一个新项目。 我们要创建一个单一视图应用程序,因为我们要从一个普通的白色项目开始。

然后输入项目名称,在这种情况下将是pokemongo。 您可以随意命名,因为稍后将显示实​​际的名称。 我们要使用的语言显然是Swift ,而不是Objective-C。 对于设备,您可以选择自己喜欢的任何东西,仅iPhone或iPad,或两者都通用。 在单击下一步之前,请不要忘记选中“ 使用核心数据” ,我们需要它来将数据存储在手机上。

单击下一步后,将显示您的项目摘要。 将显示名称更改为“ Pokemon Go”,并将部署目标更改为您选择的版本,在我的情况下为10.0,因为Swift 3仅在iOS 10上运行。此外,请取消选中除Portrait之外的所有其他设备方向

我们几乎都准备出发。 最后一步是转到窗口左侧的文件浏览器中的 ViewController.swift ,并删除所有不必要的注释和函数,因为这将清理我们的代码(好的代码仅具有必要的功能!)

现在我们已经准备就绪,可以从实际项目开始。 转到Main.storyboard ,然后在右侧区域的最低框中选择第三个图标,然后搜索Map Kit View 。 将其拖放到您的项目中并调整其大小。 仍然在选择“地图视图”的情况下,单击画布底部灯条右侧的倒数第二个项目,可以在其中找到已拖动了地图视图的视图控制器。
确保未选择“约束到边距”并将其(如果尚未设置),所有约束都设置为0。最后,点击底部的“添加约束”,从现在开始,我们的画布将适应所有屏幕尺寸。

现在,我们想使用代码访问“地图视图”,因此需要创建一个出口。 因此,我们必须单击右上角带有两个相互干扰的圆圈的图标。 您应该会看到第二个窗口,其中包含我们的视图控制器的代码。 现在,在代码画布中的viewDidLoad-functionViewController之间 ,按住控件并从Map View中拖放。 要输入名称,请输入mapView (Swift主要使用驼峰式大小写,这意味着您从小字开始,每当一个单词被一个空格隔开时,您只需将“新”单词的首字母大写)。

完成所有这些之后,单击右上角的左对齐图标,然后选择ViewController.swift文件。 您应该在mapView出口旁边找到一个警告图标。 这是因为尚未导入框架 (功能等的集合)。 在显示导入UIKit的位置下方, 导入MapKit

现在我们知道这个特定的ViewController实际上只会显示地图,为了简洁起见,我们应该将ViewController重命名为MapViewController。 为此,首先在代码中将其重命名,然后在文件浏览器中,最后转到Main.storyboard,单击ViewController(不是地图视图),然后在右侧单击显示类的箭头,然后选择MapViewController。

下一步,我们必须为该位置做一些事情。 首先,像导入MapKit一样导入 CoreLocation。 然后名为class的部分下面创建一个名为locationManager 的变量 ,其类型为CLLocationManager 。 这需要用!展开,因为我们没有对其进行初始化。 然而。
在viewDidLoad函数的super.ViewDidLoad()下面,我们必须初始化位置管理器。 为此,请按名称进行调用,然后用等号表示CLLocationManager并在其后添加()。 括号代表没有参数的初始化程序,这意味着我们不需要传递数据。
在该部分下面,再次致电位置管理器,以便我们可以设置所需的精度。 我们说locationManager.desiredAccuracy并用等号将其分配给kCLLocationAccurcacyBest
我们在viewDidLoad函数中需要做的最后一件事是委托。 委托通常提供事件的功能,例如何时发生更改,正在单击或正在单击。 我们说locationManager.delegate并为其分配值self (屏幕截图中缺少委托)。
最后,我们必须遵循名为CLLocationManagerDelegate的委托的协议 。 为此,请转到已编写MapViewController的类声明的位置(用花括号将其关闭),然后为上述协议MapViewController创建扩展 。 必须使用花括号将其打开和关闭(就像之前的类声明一样)。 介于两者之间的所有内容(即代码所在的位置)都称为body

现在,在扩展程序主体中,我们想创建一个函数来帮助我们的应用程序知道是否允许我们使用用户的位置。 我们需要这样做,因为Apple不允许我们未经请求就获取位置。 因此,我们将创建此函数并将其命名为isLocationUseAllowed ,而无需任何参数。 在该函数的主体中,我们打开 CLLocationManagerauthorizationStatus (如果您喜欢if语句,请执行此操作,但是它绝对不如switch语句干净)。

我们要添加的第一种情况是在实际打开应用程序时允许它。 有两种情况允许使用,无论何时使用和始终使用。 就我们而言,我们不需要永远拥有它。 记住,我们不想强迫用户执行实际上不需要做的事情。
我们输入关键词大小写 ,然后输入.authorizedWhenInUse

之所以只有一个点,然后再授权当使用,是因为我们打开了相同的类型。
例如,您有一天的类型,并且要求您打开这种类型的一天。 你会这样写:

切换TypeOfDay {
case TypeOfDay.night://做事
}

你看,这里我可以写TypeOfDay,但是我不需要,因为我实际上是在打开它。 很明显,因此,我可以只输入.night。

之后,我们需要添加冒号 ,并且在这种情况下,将执行紧随其后的所有操作。 在这种情况下,我们希望获取用户的位置,因为他们允许我们获取位置。 我们调用locationManager并开始更新位置
下一种情况是不确定时 (请注意,屏幕截图再次错误)。 我们希望向用户请求津贴,并通过致电位置管理器为使用该应用程序的请求授权
下一种情况是被限制或拒绝。 您可以添加两个案例,并用逗号分隔它们,然后在其中我们要发出警报,然后说用户已拒绝让我们获取位置。
最后一种情况是默认情况。 这意味着,当所提到的情况都不是这种情况时,将执行此操作,这对我们来说是一个错误。
转到viewDidLoad-function并调用isLocationUseAllowed ,因此它始终在启动应用程序时执行。

接下来,关闭该功能并在locationManager中键入下面的内容。 您应该获得一个功能列表,选择一个名为didUpdateLocations的功能 。 在参数中,您会看到[CLLocation]类型的位置。 方括号表示这是一个数组 ,表示一个装有许多此类物品的盒子(因此,本例中的种类/类型为CLLocation),其中盒子中的第一项是最新位置。 我们只说_而不是var和名称来创建一个临时变量 ,然后调用位置 ,获取第一个并获取其坐标 。 稍后,我们将使用它来更改用户在地图上的位置以及地图中心。

在项目的顶部,我们要在locationManager变量下拥有用户的location 。 我们创建一个CLLocationCoordinate2D类型的变量 ,并对其进行解包,因为它将在以后初始化。 现在,我们打开变量的主体(可以的),并添加一个名为属性观察器的东西。 在主体内部,我们添加了观察者didSet ,它在变量的值更改时执行(还有willSet,在值更改之前执行)。 在didSet主体内部,调用mapView并将其中心设置为用户的location 。 地图上变化的动画应随动画变化而变化,因此我们对动画说是“ 真” (“真”和“假”是布尔值/布尔值)。
回到扩展中的didUpdateLocations函数中,我们想更改临时变量并将其分配给userLocation。
在viewDidLoad 集合内,将地图视图的 用户位置 显示true

现在我们都准备好了! 仅需完成另一件事-这很简单。 转到Info.plist并将鼠标悬停在列表中的一项上,然后单击加号以添加新项。 对于“ 隐私-使用中的位置使用情况”中密钥类型以及消息中的类型,您希望用户在被询问是否允许使用时看到他们。 请注意,如果您不使用Swift 3 ,则密钥为NSLocationWhenInUseUsageDescription

现在,通过点击左上角的播放按钮来启动应用程序时,您将看到到目前为止所有工作都已执行。

在下一部分中,我们将学习面向对象的编程以及如何用它们的类型,健康点和其他所有东西来对Pokemon进行建模。

如果在编程或执行时遇到任何问题,请保持冷静,并在文章中滚动查看是否有问题。 否则,请随时在任何社交网络上问我。