接上文
本節是這個系列的最后一節了。本節中,將增加蛇的方向,增加用戶交互操作,增加開始暫停等等。
1 增加方向
在手機屏幕上,貪吃蛇的移動方向只有四種,上,下,左,右。我們將這四種方向,定義成一個枚舉。創建一個新的文件,Direciton.swift(file->new-file,過程不贅述)。
在Direction.swift中添加如下代碼:
enum Direction {
case UP
case DOWN
case LEFT
case RIGHT
}
之后我們在Snake.swift中添加Direction的擴展,在擴展中,我們定義兩個函數,walk()和changeDirection()。分別描述蛇的前進和方向的變化。對于walk函數,傳入的參數為當前蛇頭的坐標,我們根據當前的方向,修改坐標。對于changeDirection函數,傳入參數有兩個,分別為蛇頭的當前坐標和用戶的點擊坐標(根據點擊坐標決定蛇的新方向),代碼如下:
extension Direction {
func walk(inout point: CGPoint) {
switch self {
case .UP: point.y -= CGFloat(30)
case .DOWN: point.y += CGFloat(30)
case .LEFT: point.x -= CGFloat(30)
case .RIGHT: point.x += CGFloat(30)
}
}
mutating func changeDirection(cur: CGPoint, target: CGPoint) {
switch self {
case .UP: self = cur.x > target.x ? .LEFT : .RIGHT
case .DOWN: self = cur.x > target.x ? .LEFT : .RIGHT
case .LEFT: self = cur.y > target.y ? .UP : .DOWN
case .RIGHT: self = cur.y > target.y ? .UP : .DOWN
}
}
}
之后在Snake中添加對Direction屬性,在 weak var mainView: UIView!下面添加如下代碼:
var direction = Direction.RIGHT
然后修改Snake.walk函數,刪除原來的代碼,改為如下代碼:
direction.walk(&head.frame.origin)
并在Snake中添加修改方向的操作
func changeDirection(point: CGPoint) {
direction.changeDirection(head.frame.origin, target: point)
}
完成以上操作后,我們還需要添加貪吃蛇吃掉食物的操作。當貪吃蛇吃掉一個食物時,需要增加一段身體,因此繼續在Snake中添加如下代碼:
func eat() {
body.addOne(mainView)
}
2 增加用戶交互
有了方向修改操作后,我們需要用戶通過點擊屏幕來觸發修改蛇的運動方向。在左側導航欄中點擊Main.storyboard,在右下角的filter中輸入tap,找到Tap Gesture,將其拖到我們的view中。
操作完成后,會在Main.storyboard中出現手勢操作的標識,如下:
點擊手勢操作標識,并按住control鍵,拖動到SnakeViewController的walk后面,Connection選擇action,Type選擇UITapGesture...,Name填寫changeDirection,之后點擊connect如圖所示:
在changeDirection中添加如下代碼:
@IBAction func changeDirection(sender: UITapGestureRecognizer) {
let tapPoint = sender.locationInView(self.view)
snake.changeDirection(tapPoint)
}
之后點擊運行,當貪吃蛇運行過程中,我們點擊屏幕,可以發現小蛇根據我們的點擊位置,自動的改變方向了。
3 增加開始暫停
點擊Main.storyboard,在右下角的filter中輸入bar button item,找到Bar Button Item,拖動到導航欄的左下角位置,如圖:
點擊新的item,在右側的屬性欄里,將Title修改為『暫停』
點擊新增加的item button,并按住control鍵,和上面的操作一樣,增加pause函數。當用戶點擊暫停時,我們將當前的定時器暫停,當用戶再次點擊時恢復,并修改title,代碼如下:
var isPause = false
@IBAction func pause(sender: UIBarButtonItem) {
isPause = !isPause
if (isPause) {
sender.title = "開始"
timer.fireDate = NSDate.distantFuture()
} else {
sender.title = "暫停"
timer.fireDate = NSDate.distantPast()
}
}
點擊左上角的運行,我們可以發現當點擊『暫停』時,小蛇就停住了,再次點擊『開始』時,又動了起來。
4 增加吃食物判斷邏輯
當蛇頭的坐標和食物的坐標相同時,我們判定吃食成功,則觸發兩個操作,a 修改食物的坐標,b 增加蛇的長度。將SnakeViewController.walk的定義修改成如下代碼:
var score = 0 //記錄分數
func walk() {
if food.frame.origin == snake.head.frame.origin {
food.changeFood(food)
snake.eat()
score += 10
navigationItem.title = String(score)
}
snake.walk()
}
我們同時增加了一個計分操作,如代碼中所示。
點擊左上角的運行,當小蛇完成吃食操作時,它的長度增加了。
5 邊界處理
目前為止,貪吃蛇已基本全部完成了。但是當它到了屏幕的邊界時,會繼續往前,這樣就脫離我們的視線了。因此我們增加邏輯,當碰觸屏幕邊緣時,修改蛇的坐標,讓它從另一邊重新出現。在左側找到ListBodyItem,在SnakeHead中增加touchEdge函數,代碼如下:
func touchEdge(){
if (frame.origin.x < 0) {
frame.origin.x = 330
} else if (frame.origin.x > 330) {
frame.origin.x = 0
} else if (frame.origin.y < 60) {
frame.origin.y = 630
} else if (frame.origin.y > 630) {
frame.origin.y = 60
}
}

之后在Snake的walk中增加對touchEdge的調用,如下:
func walk() {
direction.walk(&head.frame.origin)
head.touchEdge()
}
點擊左上角的運行,現在當小蛇到達屏幕邊緣時,會『神奇』的從另一邊出現了。
最終的效果圖:
項目的github如下:
總結:
1 swift蠻好用的
2 iOS做界面開發的學習曲線挺平滑的
3 素材真的很難找,適配屏幕調整圖片尺寸很費勁