ios - bug with regular collisions in spriteKit -
im making simple jumping game. when "hero" collides ground calls didbegincontact
, make jump. pretty basic doesn't work because after while (sometimes sooner, later...) stop working can see. know if im doing wrong or if there better way it, or if there known bug in spritekit id never heard of... image gif. if can't see movement open in new tab
@interface xyzworld1() @property (nonatomic) skspritenode *hero; @property (nonatomic) skspritenode *groundphysics; @end @implementation xyzworld1 static const uint32_t ground = 0x2 << 2; static const uint32_t bee = 0x3 << 3;
method create ground:
-(skspritenode*)creategroundxpos:(float)x ypos:(float)y width:(cgfloat)width height:(cgfloat)height { skspritenode *ground = [skspritenode spritenodewithcolor:[uicolor colorwithhue:1 saturation:1 brightness:1 alpha:1] size:cgsizemake(width, height)]; skphysicsbody *groundfisica =[skphysicsbody bodywithrectangleofsize:ground.size]; [ground setname:@"ground"]; [groundfisica setdynamic:no]; [groundfisica setaffectedbygravity:no]; [groundfisica setallowsrotation:no]; [groundfisica setrestitution:0]; [groundfisica setusesprecisecollisiondetection:yes]; [groundfisica setcategorybitmask:ground]; [groundfisica setcontacttestbitmask:bee]; [groundfisica setcollisionbitmask:bee]; ground.physicsbody = groundfisica; [ground setposition:cgpointmake(x, y)]; return ground; }
method create hero
-(skspritenode*)crearhero { sktexture *temp = _herowalkingframes[0]; skspritenode *hero = [skspritenode spritenodewithtexture:temp]; hero.name = @"hero"; hero.zposition = 1; if(is_iphone_5){ [hero setposition:cgpointmake(100, 280)]; } else { [hero setposition:cgpointmake(100, 220)]; } [hero setsize:cgsizemake(25, 25)]; hero.physicsbody = [skphysicsbody bodywithrectangleofsize:cgsizemake(23, 24)]; [hero.physicsbody setdensity:0.95]; [hero.physicsbody setdynamic:yes]; [hero.physicsbody setaffectedbygravity:yes]; [hero.physicsbody setallowsrotation:no]; [hero.physicsbody setusesprecisecollisiondetection:yes]; [hero.physicsbody setrestitution:0]; [hero.physicsbody setvelocity:cgvectormake(0, 0)]; return hero; }
method preload stuff before game starts:
-(void)preloadassets { //hero _herowalkingframes = [self cargararrayatlas:@"astrojump.atlas" imagename:@"astronautajump_000"]; _hero = [self crearhero]; _hero.physicsbody.categorybitmask = bee; _hero.physicsbody.collisionbitmask = bee | cubico | ground | bicho ; _hero.physicsbody.contacttestbitmask = bee | cubico | ground | bicho ; //ground _groundphysics = [self creategroundxpos:100 ypos:142 width:42 height:23.25]; }
method called when 2 bodies first contact each other:
-(void) didbegincontact:(skphysicscontact *)contact { //if hero collides ground if((contact.bodya.categorybitmask == bee && contact.bodyb.categorybitmask == ground) || (contact.bodya.categorybitmask == ground && contact.bodyb.categorybitmask == bee) ) { if(_jumping == no && _groundphysics.position.y+_groundphysics.size.height/2<=_hero.position.y-11.5) { [self jumping]; } } }
method called jump:
-(void)jumping{ //play sound file [self runaction:self.jumpsound withkey:@"jumpsound"]; if(is_iphone_5){ _diferencia=(164 * 9)/_hero.position.y; }else{ _diferencia=(164 * 7)/_hero.position.y; } [_hero.physicsbody applyimpulse:cgvectormake(0,_diferencia)]; _jumping = yes; [_hero removeactionforkey:@"astrojump"]; [self astrojump]; } -(void)astrojump { //runaction animation method [_hero runaction:[skaction animatewithtextures:_herowalkingframes timeperframe:0.05f resize:no restore:no] withkey:@"astrojump"]; return; }
the boolean (self.jumping) if sentence, in update
, initgamecontent
:
-(void)update:(cftimeinterval)currenttime { if(_hero.physicsbody.velocity.dy < 0 )_jumping = no; } -(void)initgamecontent { _jumping = no;
you might want make sure reset players position above ground when contact ground detected. otherwise player still in contact ground when [self jumping];
called can result in player being "stuck". i've seen similar issues in games when doing collision detection. code below shows resolve issue.
if (_jumping == no && _groundphysics.position.y+_groundphysics.size.height/2<=_hero.position.y-11.5) { _hero.position.y = _groundphysics.position.y + _groundphysics.size.height/2 + 1; [self jumping]; }
Comments
Post a Comment