void Player::check_water(Map *map) { const Tmx::Tileset *tileset = map->get_tileset(0); const Tmx::PropertySet prop = tileset->GetProperties(); // Check if under water int start = prop.GetNumericProperty("water_start"); int end = prop.GetNumericProperty("water_end"); if (start && check_center(map, start, end)) { set_ay(get_attribute("water_weight")); m_in_water = true; } else { if (m_in_water) { if (m_action == Jump) { set_vy(-get_attribute("water_jump_speed")); } else if (m_action == Catapult) { set_vy(-get_attribute("water_catapult_speed")); } } set_ay(get_attribute("weight")); m_in_water = false; } }
World::World(Map *map, MediaDB *media, WorldDB *db, const char *music) : m_map(map), m_media(media), m_db(db) { // Load attributes m_bg_color = m_map->get_numeric_property("bg_color"); m_offset_x = m_map->get_numeric_property("offset_x"); m_offset_y = m_map->get_numeric_property("offset_y"); m_lock_x = m_map->get_numeric_property("lock_x"); m_lock_y = m_map->get_numeric_property("lock_y"); // Play music if (music) { media->play_music(music); } else { media->play_music(m_map->get_literal_property("music").c_str()); } int num_groups = map->get_num_object_groups(); for (int object_group = 0; object_group < num_groups; object_group++) { const Tmx::ObjectGroup *group = map->get_object_group(object_group); std::string name = group->GetName(); int num_objects = group->GetNumObjects(); for (int i = 0; i < num_objects; i++) { const Tmx::Object *obj = group->GetObject(i); const Tmx::PropertySet prop = obj->GetProperties(); std::string dirname = prop.GetLiteralProperty(std::string("direction")); Object *object = ObjectFactory::create_object( obj->GetName().c_str(), m_media, obj->GetType().c_str(), obj->GetX(), obj->GetY(), obj->GetWidth(), obj->GetHeight(), prop); if (object) { object->world_initialize(this); m_objects.push_back(object); } else { std::cerr << "Warning - Unable to load object: " << i << std::endl; } } } }
void Climber::move_climb(Map *map, int input) { const Tmx::Tileset *tileset = map->get_tileset(0); const Tmx::PropertySet prop = tileset->GetProperties(); int block_id = prop.GetNumericProperty("climb"); if (!m_leave_ready && m_leave_timer.expired(c_leave_time)) { m_leave_ready = true; } switch (m_climb_dir) { case ClimbRight: case ClimbLeft: if (input & PRESS_JUMP) { if (m_leave_ready) { leave_climb(map); } } else if (input & PRESS_DOWN) { animate_climb(); set_action(Move); set_dir(Right); set_vy(check_ahead(map, get_attribute("move_speed"), block_id, block_id)); } else if (input & PRESS_UP) { animate_climb(); set_action(Move); set_dir(Left); set_vy(-check_ahead(map, get_attribute("move_speed"), block_id, block_id)); } else { set_dir(); set_action(Still); set_vy(0); } break; default: break; } Body::move(map); }
Object::Direction ObjectFactory::get_dir(const Tmx::Object *obj) { Object::Direction dir = Object::Right; const Tmx::PropertySet prop = obj->GetProperties(); std::string dirname = prop.GetLiteralProperty(std::string("direction")); if (dirname == std::string("right")) { dir = Object::Right; } else if (dirname == std::string("left")) { dir = Object::Left; } else if (dirname == std::string("up")) { dir = Object::Up; } else if (dirname == std::string("down")) { dir = Object::Down; } return dir; }
void Climber::move(Map *map) { int input = get_input(); if (m_climb_dir == ClimbNone && (m_action == Jump || m_action == Fall)) { const Tmx::Tileset *tileset = map->get_tileset(0); const Tmx::PropertySet prop = tileset->GetProperties(); // Check if on climb block int block_id = prop.GetNumericProperty("climb"); if (block_id) { if (m_dir == Right && (input & PRESS_RIGHT)) { if (check_ahead(map, 1, block_id, block_id) == 0) { set_vx(0); set_ay(0); m_leave_ready = false; m_climb_dir = ClimbRight; } } else if (m_dir == Left && (input & PRESS_LEFT)) { if (check_ahead(map, 1, block_id, block_id) == 0) { set_vx(0); set_ay(0); m_leave_ready = false; m_climb_dir = ClimbLeft; } } } } if (m_climb_dir == ClimbNone) { Knight::move(map); } else { move_climb(map, input); } }
bool Object::check_collision(int x, int y, Map *map, int start, int end) { bool result = false; const Tmx::Tileset *tileset = map->get_tileset(0); const Tmx::PropertySet prop = tileset->GetProperties(); int tile_id = map->get_tile_id(x, y, 0); if (!start) { if (tile_id >= prop.GetNumericProperty("solid_start") && tile_id <= prop.GetNumericProperty("solid_end")) { result = true; } } else { if (!end) { end = start; } if (tile_id >= start && tile_id <= end) { result = true; } } return result; }
Object* ObjectFactory::create_object(const char *name, MediaDB *media, const char *type, int x, int y, const Tmx::Object *obj) { Object *object = 0; Object::Direction dir = Object::Right; if (!type && obj) { type = obj->GetType().c_str(); if (!name) { name = obj->GetName().c_str(); } x = obj->GetX(); y = obj->GetY(); dir = get_dir(obj); } if (strcmp(type, "Player") == 0) { std::string pathname = Object::get_prefix() + std::string(name); TiXmlDocument doc(pathname.c_str()); if (doc.LoadFile()) { search_nodes(&doc); } if (strcmp(priv_object_type, "knight") == 0) { object = new Knight(name, media, x, y, dir); } else if (strcmp(priv_object_type, "climber") == 0) { object = new Climber(name, media, x, y, dir); } else if (strcmp(priv_object_type, "flyer") == 0) { object = new Flyer(name, media, x, y, dir); } else if (strcmp(priv_object_type, "natator") == 0) { object = new Natator(name, media, x, y, dir); } else if (strcmp(priv_object_type, "dragon") == 0) { object = new Dragon(name, media, x, y, dir); } else { object = new Player(name, media, x, y, dir); } } else if (strcmp(type, "Collectable") == 0) { std::string pathname = Object::get_prefix() + std::string(name); TiXmlDocument doc(pathname.c_str()); if (doc.LoadFile()) { search_nodes(&doc); } if (strcmp(priv_object_type, "coin") == 0) { object = new Coin(name, media, x, y); } else if (strcmp(priv_object_type, "heart_container") == 0) { object = new HeartContainer(name, media, x, y); } else if (strcmp(priv_object_type, "heart_refill") == 0) { object = new HeartRefill(name, media, x, y); } else if (strcmp(priv_object_type, "potion") == 0) { object = new Potion(name, media, x, y); } else if (strcmp(priv_object_type, "stone") == 0) { object = new Stone(name, media, x, y); } else if (strcmp(priv_object_type, "fire_refill") == 0) { object = new FireRefill(name, media, x, y); } else if (strcmp(priv_object_type, "tornado_refill") == 0) { object = new TornadoRefill(name, media, x, y); } else if (strcmp(priv_object_type, "arrow_refill") == 0) { object = new ArrowRefill(name, media, x, y); } else if (strcmp(priv_object_type, "boomerang_refill") == 0) { object = new BoomerangRefill(name, media, x, y); } else if (strcmp(priv_object_type, "thunder_refill") == 0) { object = new ThunderRefill(name, media, x, y); } else if (strcmp(priv_object_type, "break_rock") == 0) { object = new BreakRock(name, media, x, y); } else if (strcmp(priv_object_type, "create_rock") == 0) { object = new CreateRock(name, media, x, y); } } else if (strcmp(type, "Item") == 0) { std::string pathname = Object::get_prefix() + std::string(name); TiXmlDocument doc(pathname.c_str()); if (doc.LoadFile()) { search_nodes(&doc); } if (strcmp(priv_object_type, "key") == 0) { object = new Key(name, media, x, y); } else if (strcmp(priv_object_type, "arm") == 0) { object = new Arm(name, media, x, y); } else if (strcmp(priv_object_type, "shield") == 0) { object = new Shield(name, media, x, y); } else if (strcmp(priv_object_type, "armour") == 0) { object = new Armour(name, media, x, y); } } else if (strcmp(type, "Walker") == 0) { object = new Walker(name, media, x, y, dir); } else if (strcmp(type, "Crawler") == 0) { object = new Crawler(name, media, x, y, dir); } else if (strcmp(type, "Erupter") == 0) { object = new Erupter(name, media, x, y, dir); } else if (strcmp(type, "Guardian") == 0) { object = new Guardian(name, media, x, y, dir); } else if (strcmp(type, "Shooter") == 0) { object = new Shooter(name, media, x, y, dir); } else if (strcmp(type, "Diver") == 0) { object = new Diver(name, media, x, y, dir); } else if (strcmp(type, "Hovering") == 0) { if (obj) { object = new Hovering(name, media, x, y, obj->GetWidth(), dir); } } else if (strcmp(type, "Floater") == 0) { object = new Floater(name, media, x, y, dir); } else if (strcmp(type, "Swimmer") == 0) { object = new Swimmer(name, media, x, y, dir); } else if (strcmp(type, "Haunter") == 0) { object = new Haunter(name, media, x, y, obj->GetWidth(), obj->GetHeight(), dir); } else if (strcmp(type, "Waver") == 0) { object = new Waver(name, media, x, y, dir); } else if (strcmp(type, "Dancer") == 0) { object = new Dancer(name, media, x, y, dir); } else if (strcmp(type, "Roller") == 0) { object = new Roller(name, media, x, y, obj->GetPolyline()); } else if (strcmp(type, "Falling") == 0) { object = new Falling(name, media, x, y, dir); } else if (strcmp(type, "Obstacle") == 0) { object = new Obstacle(name, media, x, y, dir); } else if (strcmp(type, "MekaDragon") == 0) { object = new MekaDragon(name, media, x, y, dir); } else if (strcmp(type, "MummyDragon") == 0) { object = new MummyDragon(name, media, x, y, dir); } else if (strcmp(type, "Area") == 0) { if (obj) { const Tmx::PropertySet prop = obj->GetProperties(); std::string tn = prop.GetLiteralProperty(std::string("type")); object = new Area(name, media, tn.c_str(), x, y, obj->GetWidth(), obj->GetHeight()); if (object) { std::string musicname = prop.GetLiteralProperty(std::string("music")); if (musicname != std::string("No such property!")) { object->set_string("music", musicname.c_str()); } } } } else if (strcmp(type, "Chest") == 0) { object = new Chest(name, media, x, y); } if (object) { #ifdef TODO // Causes error now for areas if (!object->get_loaded()) { delete object; object = 0; } #endif // Initialize all attributes in tmx mapfile if (obj) { const Tmx::PropertySet prop = obj->GetProperties(); std::map<std::string, std::string> pmap = prop.GetList(); for (std::map<std::string, std::string>::const_iterator it = pmap.begin(); it != pmap.end(); ++it) { std::string attr_name = it->first; if (attr_name != std::string("direction") && attr_name != std::string("music")) { object->set_attribute(attr_name.c_str(), atoi(it->second.c_str())); } } } object->initialize(); } return object; }
void Player::player_move(Map *map) { Actor::move(map); check_water(map); int input = get_input(); const Tmx::Tileset *tileset = map->get_tileset(0); const Tmx::PropertySet prop = tileset->GetProperties(); // Check if on catapult int catid = prop.GetNumericProperty("catapult"); if (catid && check_below(map, 1, catid, catid) == 0) { if (input & PRESS_RIGHT) { set_vx(get_attribute("move_speed")); } else if (input & PRESS_LEFT) { set_vx(-get_attribute("move_speed")); } set_jump(map, true); } switch(m_action) { case Still: set_vx(0); case Move: // Check for crouch or move if (input & PRESS_DOWN) { set_action(Crouch); } else if (input & PRESS_RIGHT) { animate_move(); set_action(Move); set_vx(get_attribute("move_speed")); } else if (input & PRESS_LEFT) { animate_move(); set_action(Move); set_vx(-get_attribute("move_speed")); } else { set_action(Still); } // Check for jump if (input & PRESS_JUMP) { if (m_jump_ready && m_hit_ground) { if (input & PRESS_RIGHT) { set_vx(get_attribute("move_speed")); } else if (input & PRESS_LEFT) { set_vx(-get_attribute("move_speed")); } set_jump(map, false); } m_jump_ready = false; } else { // Restore jump lock m_jump_ready = true; } Body::move(map); if (get_fall()) { set_action(Fall); } break; case Fall: // Check for change of direction during fall if (input & PRESS_RIGHT) { set_vx(get_attribute("move_speed")); } else if (input & PRESS_LEFT) { set_vx(-get_attribute("move_speed")); } Body::move(map); if (!get_fall()) { m_hit_ground = true; set_action(Still); } break; case Jump: case Catapult: Body::move(map); if (get_fall()) { set_action(Fall); } break; case Crouch: set_vx(0); Body::move(map); if (!get_fall()) { m_hit_ground = true; } if (!(input & PRESS_DOWN)) { set_action(Still); } break; case Hit: if (m_hit_timer.expired(get_attribute("hit_time"))) { set_vx(0); set_lock_direction(false); reset_hit(); } Body::move(map); break; case HitPerish: animate_perish(); set_speed(0, -get_attribute("move_speed")); Body::move(map); if (m_y < -get_image_height()) { set_solid(true); set_invisible(false); set_action(HitPerished); } break; case Attack: case AttackLow: if (animate_attack()) { reset_attack(); } Body::move(map); if (!get_fall()) { m_hit_ground = true; } break; default: Body::move(map); break; } }
void AFP::MapParser::addBackgroundLayers(std::vector <SceneNode*>& sceneLayers, SceneNode& spriteGraph, const sf::FloatRect worldBounds) { /// Initialize the different tiling backround layers for (int i = 0; i < mMap.GetNumImageLayers(); ++i) { SceneNode::Ptr layer(new SceneNode(Category::None)); sceneLayers.push_back(layer.get()); /// Add background layers to spritegraph spriteGraph.attachChild(std::move(layer)); const Tmx::ImageLayer* imageLayer = mMap.GetImageLayer(i); const Tmx::PropertySet layerProperties = imageLayer->GetProperties(); if (layerProperties.HasProperty("repeat") && layerProperties.GetLiteralProperty("repeat") == "true") { /// Set backround texture to be tiled sf::Texture& texture = mTextures.get(imageLayer->GetName()); sf::IntRect textureRect(worldBounds); texture.setRepeated(true); /// Make the texture as big as the world bounds std::unique_ptr<SpriteNode> backgroundSprite( new SpriteNode(texture, textureRect)); backgroundSprite->setPosition( worldBounds.left, worldBounds.top); sceneLayers.back()->attachChild(std::move(backgroundSprite)); } else if (layerProperties.HasProperty("repeatVertical") && layerProperties.GetLiteralProperty("repeatVertical") == "true") { /// Tile texture vertically sf::Texture& texture = mTextures.get(imageLayer->GetName()); sf::IntRect textureRect(0.f, 0.f, worldBounds.width, texture.getSize().y); texture.setRepeated(true); std::unique_ptr<SpriteNode> backgroundSprite( new SpriteNode(texture, textureRect)); if (!layerProperties.HasProperty("height")) { throw std::runtime_error("World::buildScene(): Missing property" " height from vertical image layer!"); } /// Set tiled image to the correct height. In tiled the height is /// set as the number of pixels from the bottom int height = layerProperties.GetNumericProperty("height"); backgroundSprite->setPosition( worldBounds.left, mMap.GetHeight() * mMap.GetTileHeight() - height - texture.getSize().y); sceneLayers.back()->attachChild(std::move(backgroundSprite)); } } }
void Player::player_move(Map *map) { const Tmx::Tileset *tileset = map->get_tileset(0); const Tmx::PropertySet prop = tileset->GetProperties(); // Check if under water int start = prop.GetNumericProperty("water_start"); int end = prop.GetNumericProperty("water_end"); if (start && check_ahead(map, 1, start, end) == 0) { if (!m_water_timer.expired(get_attribute("water_treshold"))) { return; } m_water_timer.reset(); } // Check if on catapult int catid = prop.GetNumericProperty("catapult"); if (catid && check_below(map, 1, catid, catid) == 0) { set_vy(int(-get_attribute("catapult_speed"))); set_action(Jump); } Actor::move(map); set_ay(get_attribute("weight")); int input = get_input(); switch(m_action) { case Still: set_vx(0); case Move: // Check for jump if (input & PRESS_JUMP) { if (m_jump_ready) { m_jump_ready = false; set_action(Jump); if (input & PRESS_RIGHT) { set_speed(get_attribute("jump_forward"), -get_attribute("jump_speed")); } else if (input & PRESS_LEFT) { set_speed(-get_attribute("jump_forward"), -get_attribute("jump_speed")); } else { set_vy(-get_attribute("jump_speed")); } } } else { // Restore jump lock m_jump_ready = true; // Check for crouch or move if (input & PRESS_DOWN) { set_action(Crouch); } else if (input & PRESS_RIGHT) { animate_move(); set_action(Move); set_vx(get_attribute("move_speed")); } else if (input & PRESS_LEFT) { animate_move(); set_action(Move); set_vx(-get_attribute("move_speed")); } else { set_action(Still); set_vx(0); } } Body::move(map); if (get_fall()) { set_action(Fall); } break; case Fall: // Check for change of direction during fall if (input & PRESS_RIGHT) { set_vx(get_attribute("jump_forward")); } else if (input & PRESS_LEFT) { set_vx(-get_attribute("jump_forward")); } Body::move(map); if (!get_fall()) { set_action(Still); } break; case Jump: Body::move(map); if (get_fall()) { set_action(Fall); } break; case Crouch: set_vx(0); Body::move(map); if (!(input & PRESS_DOWN)) { set_action(Still); } break; case Hit: if (m_hit_timer.expired(get_attribute("hit_time"))) { m_hit_timer.reset(); set_vx(0); set_lock_direction(false); m_hit = HitNone; set_action(Still); } Body::move(map); break; default: Body::move(map); break; } }