/** * \brief Returns the path an entity should follow to take these stairs. * * When an entity collides with the stairs (usually the hero), * it can call this function to know the path it should take to make the * appropriate movement. * * \param way The way you are taking these stairs. * \return The corresponding path to make. */ std::string Stairs::get_path(Way way) { // Determine the movement direction. int initial_direction = get_direction() * 2; std::string path = ""; int nb_steps; if (is_inside_floor()) { nb_steps = 5; } else { nb_steps = (get_direction() == 1) ? 1 : 2; } for (int i = 0; i < nb_steps; i++) { path += '0' + initial_direction; } if (!is_inside_floor()) { // Second direction to take for each subtype of stairs // (assuming the direction is north). static const int second_directions[] = { 0, 4, 2, 2 }; int second_direction = second_directions[subtype]; if (get_direction() == 3) { // Direction south. second_direction = (second_direction + 4) % 8; } char c = '0' + second_direction; path = path + c; if (subtype == SPIRAL_UPSTAIRS || subtype == SPIRAL_DOWNSTAIRS) { path = path + c; } } if (way == REVERSE_WAY) { std::string inverse_path = ""; std::string::reverse_iterator it; int direction = 0; for (it = path.rbegin(); it != path.rend(); it++) { direction = *it - '0'; direction = (direction + 4) % 8; inverse_path += '0' + direction; } path = inverse_path; // path += '0' + direction; } return path; }
/** * @brief Creates a new stairs entity. * @param name name of the entity to create * @param layer layer of the entity to create on the map * @param x x coordinate of the entity to create * @param y y coordinate of the entity to create * @param direction direction of the stairs (0 to 3) * @param subtype the subtype of stairs */ Stairs::Stairs(const std::string &name, Layer layer, int x, int y, int direction, Subtype subtype): Detector(COLLISION_FACING_POINT_ANY | COLLISION_RECTANGLE, name, layer, x, y, 16, 16), subtype(subtype), enabled(true) { Debug::check_assertion(!is_inside_floor() || layer != LAYER_HIGH, "Cannot put single floor stairs on the high layer"); set_direction(direction); if (!is_inside_floor()) { set_size(16, 8); if (direction == 3) { // down set_origin(0, -8); } } }
/** * \brief Creates a new stairs entity. * \param name Name of the entity to create. * \param layer Layer of the entity to create on the map. * \param xy Coordinates of the entity to create. * \param direction Direction of the stairs (0 to 3). * \param subtype The subtype of stairs. */ Stairs::Stairs( const std::string& name, Layer layer, const Point& xy, int direction, Subtype subtype): Detector(COLLISION_TOUCHING | COLLISION_OVERLAPPING, name, layer, xy, Size(16, 16)), subtype(subtype) { Debug::check_assertion(!is_inside_floor() || layer != LAYER_HIGH, "Cannot put single floor stairs on the high layer"); set_direction(direction); if (!is_inside_floor()) { set_size(16, 8); if (direction == 3) { // Down. set_origin(0, -8); } } }
/** * @brief Plays a sound corresponding to these stairs. * * When an entity collides with the stairs (usually the hero), * it can call this function to play the appropriate stairs sound. * * @param way the way you are taking these stairs */ void Stairs::play_sound(Way way) { SoundId sound_id; if (is_inside_floor()) { // choose the sound depending on whether we are going upstairs or downstairs sound_id = (way == NORMAL_WAY) ? "stairs_up_end" : "stairs_down_end"; } else { // choose the sound depending on whether we are on the old floor or the new floor, and // going upstairs or downstairs if (subtype == SPIRAL_UPSTAIRS || subtype == STRAIGHT_UPSTAIRS) { sound_id = (way == NORMAL_WAY) ? "stairs_up_start" : "stairs_down_end"; } else { sound_id = (way == NORMAL_WAY) ? "stairs_down_start" : "stairs_up_end"; } } Sound::play(sound_id); }
/** * \brief Plays a sound corresponding to these stairs. * * When an entity collides with the stairs (usually the hero), * it can call this function to play the appropriate stairs sound. * * \param way The way you are taking these stairs. */ void Stairs::play_sound(Way way) { std::string sound_id; if (is_inside_floor()) { // Choose the sound depending on whether we are going // upstairs or downstairs. sound_id = (way == NORMAL_WAY) ? "stairs_up_end" : "stairs_down_end"; } else { // Choose the sound depending on whether we are on the old floor or the // new floor, and going upstairs or downstairs. if (subtype == SPIRAL_UPSTAIRS || subtype == STRAIGHT_UPSTAIRS) { sound_id = (way == NORMAL_WAY) ? "stairs_up_start" : "stairs_down_end"; } else { sound_id = (way == NORMAL_WAY) ? "stairs_down_start" : "stairs_up_end"; } } if (Sound::exists(sound_id)) { Sound::play(sound_id); } }
/** * \brief Returns whether this entity can have collisions with entities even * if they are not on the same layer. * \return \c true if this entity can collide with entities that are on * another layer. */ bool Stairs::has_layer_independent_collisions() const { return is_inside_floor(); }