bool MrIceBlock::collision_squished(GameObject& object) { switch(ice_state) { case ICESTATE_KICKED: case ICESTATE_NORMAL: squishcount++; if(squishcount >= MAXSQUISHES) { kill_fall(); return true; } set_state(ICESTATE_FLAT); nokick_timer.start(NOKICK_TIME); break; case ICESTATE_FLAT: { MovingObject* movingobject = dynamic_cast<MovingObject*>(&object); if (movingobject && (movingobject->get_pos().x < get_pos().x)) { dir = RIGHT; } else { dir = LEFT; } } if (nokick_timer.check()) set_state(ICESTATE_KICKED); break; case ICESTATE_GRABBED: assert(false); break; } Player* player = dynamic_cast<Player*>(&object); if (player) player->bounce(*this); return true; }
void FlipLevelTransformer::transform_moving_object(float height, MovingObject& object) { Vector pos = object.get_pos(); pos.y = height - pos.y - object.get_bbox().get_height(); object.set_pos(pos); }
void Bomb::ungrab(MovingObject& object, Direction dir_) { this->dir = dir_; // portable objects are usually pushed away from Tux when dropped, but we // don't want that, so we set the position //FIXME: why don't we want that? shouldn't behavior be consistent? set_pos(object.get_pos() + Vector(dir_ == LEFT ? -16 : 16, get_bbox().get_height()*0.66666 - 32)); set_colgroup_active(COLGROUP_MOVING); grabbed = false; }
bool MrIceBlock::collision_squished(GameObject& object) { Player* player = dynamic_cast<Player*>(&object); if(player && (player->does_buttjump || player->is_invincible())) { player->bounce(*this); kill_fall(); return true; } switch(ice_state) { case ICESTATE_KICKED: { BadGuy* badguy = dynamic_cast<BadGuy*>(&object); if (badguy) { badguy->kill_fall(); break; } } // fall through case ICESTATE_NORMAL: { squishcount++; if (squishcount >= MAXSQUISHES) { kill_fall(); return true; } } set_state(ICESTATE_FLAT); nokick_timer.start(NOKICK_TIME); break; case ICESTATE_FLAT: { MovingObject* movingobject = dynamic_cast<MovingObject*>(&object); if (movingobject && (movingobject->get_pos().x < get_pos().x)) { dir = RIGHT; } else { dir = LEFT; } } if (nokick_timer.check()) set_state(ICESTATE_KICKED); break; case ICESTATE_GRABBED: assert(false); break; } if (player) player->bounce(*this); return true; }
bool Snail::collision_squished(GameObject& object) { if (m_frozen) return WalkingBadguy::collision_squished(object); Player* player = dynamic_cast<Player*>(&object); if (player && (player->m_does_buttjump || player->is_invincible())) { kill_fall(); player->bounce(*this); return true; } switch (state) { case STATE_KICKED: case STATE_NORMAL: // Can't stomp in midair if (!on_ground()) break; squishcount++; if (squishcount >= MAX_SNAIL_SQUISHES) { kill_fall(); return true; } SoundManager::current()->play("sounds/stomp.wav", get_pos()); be_flat(); break; case STATE_FLAT: SoundManager::current()->play("sounds/kick.wav", get_pos()); { MovingObject* movingobject = dynamic_cast<MovingObject*>(&object); if (movingobject && (movingobject->get_pos().x < get_pos().x)) { m_dir = Direction::RIGHT; } else { m_dir = Direction::LEFT; } } be_kicked(); break; case STATE_GRABBED: case STATE_KICKED_DELAY: break; } if (player) player->bounce(*this); return true; }
void AngryStone::active_update(float elapsed_time) { BadGuy::active_update(elapsed_time); if (frozen) { return; } switch (state) { case IDLE: { MovingObject* player = get_nearest_player(); if(player) { MovingObject* badguy = this; const Vector playerPos = player->get_pos(); const Vector badguyPos = badguy->get_pos(); float dx = (playerPos.x - badguyPos.x); float dy = (playerPos.y - badguyPos.y); float playerHeight = player->get_bbox().get_height(); float badguyHeight = badguy->get_bbox().get_height(); float playerWidth = player->get_bbox().get_width(); float badguyWidth = badguy->get_bbox().get_width(); if ((dx > -playerWidth) && (dx < badguyWidth)) { if (dy > 0) { attackDirection.x = 0; attackDirection.y = 1; } else { attackDirection.x = 0; attackDirection.y = -1; } if ((attackDirection.x != oldWallDirection.x) || (attackDirection.y != oldWallDirection.y)) { sprite->set_action("charging"); timer.start(CHARGE_TIME); state = CHARGING; } } else if ((dy > -playerHeight) && (dy < badguyHeight)) { if (dx > 0) { attackDirection.x = 1; attackDirection.y = 0; } else { attackDirection.x = -1; attackDirection.y = 0; } if ((attackDirection.x != oldWallDirection.x) || (attackDirection.y != oldWallDirection.y)) { sprite->set_action("charging"); timer.start(CHARGE_TIME); state = CHARGING; } } } } break; case CHARGING: { if (timer.check()) { sprite->set_action("attacking"); timer.start(ATTACK_TIME); state = ATTACKING; physic.enable_gravity(false); physic.set_velocity_x(CHARGE_SPEED * attackDirection.x); physic.set_velocity_y(CHARGE_SPEED * attackDirection.y); oldWallDirection.x = 0; oldWallDirection.y = 0; } } break; case ATTACKING: { if (timer.check()) { timer.start(RECOVER_TIME); state = RECOVERING; sprite->set_action("idle"); physic.enable_gravity(true); physic.set_velocity_x(0); physic.set_velocity_y(0); } } break; case RECOVERING: { if (timer.check()) { state = IDLE; sprite->set_action("idle"); physic.enable_gravity(true); physic.set_velocity_x(0); physic.set_velocity_y(0); } } break; } }