barus's diary

とても真面目なblogですにゃ

Swift4(Xcode9)でiPhoneアプリのブロック崩し作成する

MacBook Air買ったった・・。

やることは一つ、iPhoneアプリを作ること。

 

参考書を見ながら、初心者が最初にやるHello!表示する儀式も無事通過しd( ̄  ̄)

f:id:hatakeka:20180115102238p:plain

 

ググっていると、ブロック崩しのサンプルを見つけた。( ̄+ー ̄)

f:id:hatakeka:20180115101330g:plain

 

ブロック崩しWindows環境でも作ったことがない。そう簡単に出来るのかな?と思いつつやってみると簡単に出来た。ボールの衝突判定やら、壁の衝突、ボールの移動処理もろもろが、SpriteKitクラスにパッケージ化されていて拍子抜けした。(´Д` )

 

今回は、iPhoneアプリブロック崩しを紹介する。

 

環境は、macOS 10、 Swift4、  Xcode9

 

 

 

MAC購入は初めてなので、何も分からない。

とりあえず、amazonで以下の参考書3冊購入した。

 

 

[asin:479739417X:image:large]

たった2日でマスターできる iOSアプリ開発集中講座 Xcode 9/Swift 4対応 Swift4 iPhoneX ミニゲームアプリ開発入門

 

 

軽く書籍の感想を書く。

 

1冊目、「絶対に挫折しないiPhoneアプリ」は、初めてXcodeを触る場合に役立った。ボタン、テキストをペタペタ貼ってイベントを拾うところはVisualStduioと同じだ。残りのページは必要になった時に読もうと思う。 

 

_(:3 」∠)_三3

 

2冊目、「たった2日でマスターできるiOSアプリ」では、検索バーからWEBにアクセスしてデータを引っ張ってくるサンプルをチョロと動かした。これは応用範囲は広そうだ。残りのページは必要になった時に読もうと思う。

 

  _(:3 」∠)_三3

 

3冊目、「Swift4のミニゲームアプリ開発入門」初心者には取っ付きにくいが、後々一番やくに立ちそうな内容ではあったが。読まずにそっと閉じ。(著者が元京都大学教授で定年退職されている方で、物理シミュレーションに精通してる。)

 

     _(:3 」∠)_三3

 

 

ふむ、ぶっちゃけ、書籍だけでは物足りない。というか、自分が今求めている方向性とちょっと違う。なので「swift sample」でググってみた。

 

 

色々とヒットした。

以下、Xcode9 , swift4の環境で動作したのを紹介する。 

①パズル

GitHub - austinzheng/swift-2048: 2048 for Swift

 

②横ゲー。(ファミコンのマリオみたいなもの)

GitHub - fullstackio/FlappySwift: swift implementation of flappy bird. More at fullstackedu.com

 

ブロック崩し

How To Make a Breakout Game with SpriteKit and Swift: Part 1

How To Make a Breakout Game with SpriteKit and Swift: Part 2

 

Youtube ブロック崩し

https://www.youtube.com/watch?v=B_XBzBc63DA

 

 

いずれもとても参考になる。この中で、超初心者にも分かりやすいのが④のYoutubeの動画であった。こんなに簡単にブロック崩しが作れるんだと感動した。

 

 

 

ブロック崩しの作り方

 

プロジェクトを作成する

プロジェクトはGameを選択する。

f:id:hatakeka:20180115123948p:plain

 

素材の準備

GameScene.sksをクリックしてColor Spriteをドラッグ&ドロップし、ブロックを9つコピーアンドペーストで作成し、パドルも同様に作成する。ボールはこの画像「ball.png」 f:id:hatakeka:20180115112004p:plain  を利用した。フォルダから、Assets.xcassetsにドラッグ&ドロップで作成する。Color SpriteのTextureに画像名「ball」を入力するとボールの画像が表示される。 

f:id:hatakeka:20180115173212p:plain

 

 

以上で、素材の準備が完了した。

f:id:hatakeka:20180115111744p:plain

次にそれぞれの設定を行う。 

 

  • ブロックの設定

commandキー押しながらブロックを選択して、

Nameをbrickとした。

Physics DefinitionのBody TypeをBounding rectangleにし

Dynamic,Allows Rotation,Pinned,Affected By Gravity

のチェックを外す。

Friction, Restitution をそれぞれ0

Category MASK   1 

Collision  MASK   2

Filed        MASK   0

Contact   MASK   2

f:id:hatakeka:20180115105922p:plain

 

  • ボールを跳ね返すバーの設定

Nameをpaddleとした。以下、brickと同じ。

Physics DefinitionのBody TypeをBounding rectangleにし

Dynamic,Allows Rotation,Pinned,Affected By Gravity

のチェックを外す。

Friction, Restitution をそれぞれ0

Category MASK   1 

Collision  MASK   2

Filed        MASK   0

Contact   MASK   2

f:id:hatakeka:20180115105927p:plain

 

  • ボールの設定 

Nameをballとした。(赤い文字は上のpaddle,brickと異なるところ)

Physics DefinitionのBody TypeをBounding rectangleにし

Dynamicのチェックはしたまま、Allows Rotation,Pinned,Affected By Gravityのチェックを外す。

Friction, Restitution をそれぞれ0

Category MASK   2

Collision  MASK   1

Filed        MASK   0

Contact   MASK   1

f:id:hatakeka:20180115105931p:plain

 

以上で、素材の設定は済んだのでこれを動かすソースが以下。

 

GameScene.swift 

//
//  GameScene.swift
//  BreakOut_sample
//
//  Created by su5file on 2018/01/15.
//  Copyright © 2018年 su5file. All rights reserved.
//

import SpriteKit
import GameplayKit

class GameScene: SKScene , SKPhysicsContactDelegate {
    
    var ball:SKSpriteNode!
    var paddle:SKSpriteNode!
    
    override func didMove(to view: SKView) {
        //withname にはGameScene.sksで作成した名前
        ball   = self.childNode(withName: "ball") as! SKSpriteNode
        paddle = self.childNode(withName: "paddle") as! SKSpriteNode
        
        //ボールの飛んでいく方向
        ball.physicsBody?.applyImpulse(CGVector(dx: 50, dy: 50))
        
        //壁にボールがぶつかった時、跳ねかえる
        let border = SKPhysicsBody(edgeLoopFrom: (view.scene?.frame)!)
        border.friction = 0
        self.physicsBody = border
        
        //SKPhysicsContactDelegate をクラス参照に入れてないとエラーとなる
        self.physicsWorld.contactDelegate = self
        
    }
    
    //パドル
    override func touchesBegan(_ touches: Set, with event: UIEvent?) {
        for touch in touches
        {
            let toucLocation = touch.location(in: self)
            paddle.position.x = toucLocation.x
        }
    }
    
    //パドル
    override func touchesMoved(_ touches: Set, with event: UIEvent?) {
        for touch in touches
        {
            let toucLocation = touch.location(in: self)
            paddle.position.x = toucLocation.x
        }
    }
    
    //ボールがブロックに当たると消える。
    func didBegin(_ contact : SKPhysicsContact)
    {
        let bodyAName = contact.bodyA.node?.name;
        let bodyBName = contact.bodyB.node?.name;
        
        if bodyAName == "ball" && bodyBName == "brick" ||
            bodyAName == "brick" && bodyBName == "ball"
        {
            if bodyAName == "brick"
            {
                contact.bodyA.node?.removeFromParent()
            }
            else if bodyBName == "brick"
            {
                contact.bodyB.node?.removeFromParent()
            }
        }
        
    }

 

 

 たったこれだけで、command+Rで動かすと以下のようになる。

f:id:hatakeka:20180115101330g:plain

 

 ぶっちゃけ、ソースコードの意味をあまりよく理解せずに、取り敢えず動かした感じだが(´Д` )。今回は動いたことだけで満足である。

 

 どうやら、SpriteKitクラスが重要らしいことがわかった。アマゾンで「SpriteKit」で書籍をググると、2015年発行の本があることはあるが、バージョンが古くて自分の環境では動かなそうなので、購入はパスした。

 

 

 

 

 

 以上。

 

参考URL

https://www.youtube.com/watch?v=B_XBzBc63DA