Note that there are some explanatory texts on larger screens.

plurals
  1. POUnderstanding SpriteKit : Moving Sprites
    primarykey
    data
    text
    <p>This is my first post and I am trying to use Apple's <code>SpriteKit</code> framework.</p> <p>I believe I have a misunderstanding of how to move sprites using the framework. I have a simple example where I would like to move a <code>hero</code> in a simple <code>UP</code>, <code>DOWN</code>, <code>LEFT</code>, <code>RIGHT</code> direction based on the a tap location, respective to the "hero" location. Once the hero hits a <code>block</code> the "hero" should stop.</p> <p>For testing purposes I am just trying to tap above the "hero" hit the wall of blocks on the top of the screen. Then after the collision occurs, tap below the "hero". I was expecting the "hero" to move toward the wall of blocks on the bottom row; however it seem that the "hero" continues to move UP and through the top wall. I am sure I am making a fundamental flaw, I would appreciate any help. </p> <p>Thanks </p> <p>Here is the sample scene I wrote:</p> <pre><code>static inline CGPoint CGPointSubtract(const CGPoint a, const CGPoint b) { return CGPointMake(a.x - b.x, a.y - b.y); } typedef enum DIRECTION_e { UP, DOWN, LEFT, RIGHT } DIRECTION_t; typedef NS_OPTIONS(uint32_t, CNPhysicsCategory) { PhysicsCategoryBlock = 1 &lt;&lt; 0, PhysicsCategoryHero = 1 &lt;&lt; 1 }; @interface LevelScene () @property (nonatomic) SKSpriteNode * hero; @property (nonatomic) BOOL inMotion; @end @implementation LevelScene -(id) initWithSize:(CGSize)size { if (self = [super initWithSize:size]) { self.physicsWorld.gravity = CGVectorMake(0,0); self.physicsWorld.contactDelegate = self; [self createLevel]; [self createHero]; self.inMotion = NO; } return self; } - (void) createHero { [self addHeroAtRow:5 column:2]; } - (void) createLevel { self.backgroundColor = [SKColor blackColor]; self.scaleMode = SKSceneScaleModeAspectFit; [self addBlockAtRow:1 column:1]; [self addBlockAtRow:1 column:2]; [self addBlockAtRow:1 column:3]; [self addBlockAtRow:10 column:1]; [self addBlockAtRow:10 column:2]; [self addBlockAtRow:10 column:3]; } - (void) addBlockAtRow:(NSInteger)row column:(NSInteger)column { SKSpriteNode *block = [[SKSpriteNode alloc] initWithColor:[SKColor brownColor] size:CGSizeMake(64,64)]; block.position = CGPointMake(32 + (column * 64), 32 + ((11-row) * 64)); block.name = @"block"; block.physicsBody = [SKPhysicsBody bodyWithRectangleOfSize:block.size]; block.physicsBody.dynamic = NO; block.physicsBody.categoryBitMask = PhysicsCategoryBlock; block.physicsBody.collisionBitMask = PhysicsCategoryBlock | PhysicsCategoryHero; block.physicsBody.contactTestBitMask = PhysicsCategoryBlock | PhysicsCategoryHero; [self addChild:block]; } - (void) addHeroAtRow:(NSInteger)row column:(NSInteger)column { self.hero = [[SKSpriteNode alloc] initWithColor:[SKColor redColor] size:CGSizeMake(64,64)]; self.hero.position = CGPointMake(32 + (column * 64), 32 + ((11-row) * 64)); self.hero.name = @"hero"; self.hero.physicsBody = [SKPhysicsBody bodyWithRectangleOfSize:CGSizeMake(self.hero.size.width/2, self.hero.size.height/2)]; self.hero.physicsBody.usesPreciseCollisionDetection = YES; self.hero.physicsBody.dynamic = YES; self.hero.physicsBody.categoryBitMask = PhysicsCategoryHero; self.hero.physicsBody.collisionBitMask = PhysicsCategoryHero | PhysicsCategoryBlock; self.hero.physicsBody.contactTestBitMask = PhysicsCategoryHero | PhysicsCategoryBlock; [self addChild:self.hero]; NSLog(@"ADDING HERO: %f, %f", self.hero.position.x, self.hero.position.y); } - (void)didBeginContact:(SKPhysicsContact *)contact { if (contact.bodyA.categoryBitMask == PhysicsCategoryBlock &amp;&amp; contact.bodyB.categoryBitMask == PhysicsCategoryHero) { [self.hero removeAllActions]; self.hero.position = contact.bodyB.node.position; NSLog(@"COLLISION: %f, %f", self.hero.position.x, self.hero.position.y); self.inMotion = NO; } else if (contact.bodyB.categoryBitMask == PhysicsCategoryBlock &amp;&amp; contact.bodyA.categoryBitMask == PhysicsCategoryHero) { [self.hero removeAllActions]; self.hero.position = contact.bodyA.node.position; NSLog(@"COLLISION: %f, %f", self.hero.position.x, self.hero.position.y); self.inMotion = NO; } } - (void) moveHeroTowardDirection:(DIRECTION_t)direction { CGPoint location; switch (direction) { case UP: { location = CGPointMake(self.hero.position.x, self.hero.position.y + 600); } break; case DOWN: { location = CGPointMake(self.hero.position.x, self.hero.position.y + -600); } break; case LEFT: { location = CGPointMake(self.hero.position.x + -600, self.hero.position.y); } break; case RIGHT: { location = CGPointMake(self.hero.position.x + 600, self.hero.position.y); } break; default: return; } NSLog(@"MOVE POSITION: %f, %f", location.x, location.y); SKAction *action = [SKAction moveTo:location duration:10]; [self.hero runAction:action]; } -(void) touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event { if (self.inMotion) return; self.inMotion = YES; UITouch *touch = [touches anyObject]; CGPoint touchLocation = [touch locationInView:self.view]; CGPoint diff = CGPointSubtract(self.hero.position, touchLocation); NSLog(@"TOUCH POSITION: %f, %f", touchLocation.x, touchLocation.y); NSLog(@"HERO POSITION: %f, %f", self.hero.position.x, self.hero.position.y); NSLog(@"DIFF POSITION: %f, %f", diff.x, diff.y); // // Magnitude to find out which direction is dominate // if (abs(diff.x) &gt; abs(diff.y)) { if (touchLocation.x &gt; self.hero.position.x) { NSLog(@"LEFT"); [self moveHeroTowardDirection:LEFT]; } else { NSLog(@"RIGHT"); [self moveHeroTowardDirection:RIGHT]; } } else { if (touchLocation.y &lt; self.hero.position.y) { NSLog(@"UP"); [self moveHeroTowardDirection:UP]; } else { NSLog(@"DOWN"); [self moveHeroTowardDirection:DOWN]; } } } @end </code></pre>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload