예제 #1
0
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;
    }

}
예제 #2
0
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;
            }
        }
    }
}
예제 #3
0
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);
}
예제 #4
0
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;
}
예제 #5
0
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);
    }
}
예제 #6
0
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;
}
예제 #7
0
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;
}
예제 #8
0
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;
    }
}
예제 #9
0
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));

        }

    }

}
예제 #10
0
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;
    }
}