How to detect collision without physics

722 Views Asked by At

I want to detect when two bodies contact without using didBeginContact() function

I try with CGRectIntersectsRect() without any effect.

class GameScene: SKScene, SKPhysicsContactDelegate {

    // Player
    var _player = SKNode()
    var platform = SKNode()

    let heroCategory: UInt32 = 1 << 0
    let platformCategory: UInt32 = 1 << 1

    override func didMoveToView(view: SKView) {

        /* Setup your scene here */

        // Setup
        self.anchorPoint = CGPointMake(0.5, 0.5)
        self.physicsWorld.gravity = CGVectorMake(0.0, -2.0);
        self.physicsWorld.contactDelegate = self

        // Start populating
        _player = creatPlayer()
        self.addChild(_player)

        platform = creatPlatform(1, atPosition: CGPoint(x: 0, y: -200))
        self.addChild(platform)


        let platformTwo = creatPlatform(2, atPosition: CGPoint(x: 0, y: 200))
        self.addChild(platformTwo)

    }

    func creatPlatform(type: Int, atPosition: CGPoint) -> PlatformNode {

        let node = PlatformNode()
        node.platformType = type
        node.position = atPosition
        let sprite = SKSpriteNode(color: UIColor.redColor(), size: CGSize(width: 200, height: 50))
        node.addChild(sprite)

        node.physicsBody = SKPhysicsBody(rectangleOfSize: sprite.size)
        node.physicsBody?.dynamic = false;
        node.physicsBody?.categoryBitMask = platformCategory
        node.physicsBody?.contactTestBitMask = heroCategory
        node.physicsBody?.collisionBitMask = 0;

        return node

    }

    func creatPlayer() -> SKNode {

        let playerNode = SKNode()
        let sprite = SKSpriteNode(color: UIColor.whiteColor(), size: CGSize(width: 50, height: 50))
        playerNode.addChild(sprite)

        playerNode.physicsBody = SKPhysicsBody(rectangleOfSize: sprite.size)
        playerNode.physicsBody?.dynamic = false
        playerNode.physicsBody?.allowsRotation = false
        playerNode.physicsBody?.restitution = 1.0
        playerNode.physicsBody?.friction = 0.0
        playerNode.physicsBody?.angularDamping = 0.0
        playerNode.physicsBody?.linearDamping = 0.0
        playerNode.physicsBody?.categoryBitMask = heroCategory
        playerNode.physicsBody?.contactTestBitMask = platformCategory
        playerNode.physicsBody?.collisionBitMask = 0;

        return playerNode

    }

    override func touchesBegan(touches: Set<NSObject>, withEvent event: UIEvent) {

        /* Called when a touch begins */
        _player.physicsBody?.dynamic = true

    }

    override func update(currentTime: CFTimeInterval) {

        /* Called before each frame is rendered */
        if(CGRectIntersectsRect(platform.frame, _player.frame)){
            println("Collision")
        }
    }

}

Maybe using CGRectIntersectsRect is a wrong approach, but I can be used instead?

1

There are 1 best solutions below

0
On BEST ANSWER

The frame property

The frame property is a rectangle in the parent’s coordinate system that contains the node’s content, ignoring the node’s children.

Also from docs:

The frame is non-empty if the node’s class draws content.

And because SKNode class does not perform any drawing of its own, and your platform is probably subclass of SKNode and player is SKNode the frame property is always (0,0,0,0).

You can access the real size of a frame in few ways:

  • You can make player and platform as subclasses of SKSpriteNode.
  • You can leave them as they are and access the child SKSpriteNode inside them.
  • You can leave as they are and use calcualteAccumulatedFrame() method.

About calcualteAccumulatedFrame() from docs:

A node’s accumulated frame, retrieved by calling the calculateAccumulatedFrame method, is the largest rectangle that includes the frame of the node and the frames of all its descendants.