casi acabat el Player pero -> canvi de PC
This commit is contained in:
@@ -29,6 +29,7 @@ Player::Player(const Data& player)
|
|||||||
// Pinta el jugador en pantalla
|
// Pinta el jugador en pantalla
|
||||||
void Player::render() {
|
void Player::render() {
|
||||||
sprite_->render(1, color_);
|
sprite_->render(1, color_);
|
||||||
|
Screen::get()->getRendererSurface()->putPixel(under_right_foot_.x, under_right_foot_.y, 6);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Actualiza las variables del objeto
|
// Actualiza las variables del objeto
|
||||||
@@ -103,17 +104,14 @@ void Player::transitionToState(State state) {
|
|||||||
fall_sound_ctrl_.reset();
|
fall_sound_ctrl_.reset();
|
||||||
current_slope_ = nullptr;
|
current_slope_ = nullptr;
|
||||||
break;
|
break;
|
||||||
case State::ON_SLOPE: {
|
case State::ON_SLOPE:
|
||||||
std::cout << "ON_SLOPE\n";
|
std::cout << "ON_SLOPE\n";
|
||||||
vy_ = 0;
|
vy_ = 0;
|
||||||
handleDeathByFalling();
|
handleDeathByFalling();
|
||||||
jump_sound_ctrl_.reset();
|
jump_sound_ctrl_.reset();
|
||||||
fall_sound_ctrl_.reset();
|
fall_sound_ctrl_.reset();
|
||||||
const LineDiagonal* SLOPE_LEFT = room_->getSlopeAtPoint(under_left_foot_);
|
updateCurrentSlope();
|
||||||
const LineDiagonal* SLOPE_RIGHT = room_->getSlopeAtPoint(under_right_foot_);
|
|
||||||
current_slope_ = SLOPE_LEFT ? SLOPE_LEFT : SLOPE_RIGHT;
|
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
case State::JUMPING:
|
case State::JUMPING:
|
||||||
std::cout << "JUMPING\n";
|
std::cout << "JUMPING\n";
|
||||||
// Puede saltar desde ON_GROUND o ON_SLOPE
|
// Puede saltar desde ON_GROUND o ON_SLOPE
|
||||||
@@ -167,8 +165,10 @@ void Player::updateOnGround(float delta_time) {
|
|||||||
|
|
||||||
// Actualización lógica del estado ON_SLOPE
|
// Actualización lógica del estado ON_SLOPE
|
||||||
void Player::updateOnSlope(float delta_time) {
|
void Player::updateOnSlope(float delta_time) {
|
||||||
(void)delta_time; // No usado en este método, pero se mantiene por consistencia
|
(void)delta_time; // No usado en este método, pero se mantiene por consistencia
|
||||||
handleShouldFall(); // Verifica si debe caer (no tiene suelo)
|
|
||||||
|
// NOTA: No llamamos handleShouldFall() aquí porque moveOnSlope() ya maneja
|
||||||
|
// todas las condiciones de salida de la rampa (out of bounds, transición a superficie plana)
|
||||||
|
|
||||||
// Verifica si el jugador quiere saltar
|
// Verifica si el jugador quiere saltar
|
||||||
if (wannaJump) { transitionToState(State::JUMPING); }
|
if (wannaJump) { transitionToState(State::JUMPING); }
|
||||||
@@ -225,14 +225,7 @@ void Player::moveOnGround(float delta_time) {
|
|||||||
const int SLOPE_Y = vx_ < 0.0F ? room_->checkLeftSlopes(SIDE) : room_->checkRightSlopes(SIDE);
|
const int SLOPE_Y = vx_ < 0.0F ? room_->checkLeftSlopes(SIDE) : room_->checkRightSlopes(SIDE);
|
||||||
if (SLOPE_Y != Collision::NONE) {
|
if (SLOPE_Y != Collision::NONE) {
|
||||||
// Hay rampa: sube al jugador para pegarlo a la rampa
|
// Hay rampa: sube al jugador para pegarlo a la rampa
|
||||||
// Esta es la nueva posición "ideal" a la que nos queremos teletransportar
|
y_ = SLOPE_Y - HEIGHT;
|
||||||
const float NEW_Y = SLOPE_Y - HEIGHT;
|
|
||||||
|
|
||||||
// Solo aplicamos el "snap" si es para SUBIR (new_y < y_)
|
|
||||||
if (NEW_Y < y_) {
|
|
||||||
y_ = std::max(NEW_Y, y_ - 1.0F);
|
|
||||||
}
|
|
||||||
|
|
||||||
transitionToState(State::ON_SLOPE);
|
transitionToState(State::ON_SLOPE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -244,9 +237,88 @@ void Player::moveOnSlope(float delta_time) {
|
|||||||
|
|
||||||
if (vx_ == 0.0F) { return; }
|
if (vx_ == 0.0F) { return; }
|
||||||
|
|
||||||
// Implementar aqui el desplazamiento en x_ e y_ en funcion de la velocidad y la ecuacion de la recta
|
// Verificar que tenemos una rampa válida
|
||||||
// Son LineDiagonal, de 45º. La linea esta en current_slope_ (comprobar que no sea nullptr)
|
if (current_slope_ == nullptr) {
|
||||||
|
transitionToState(State::FALLING);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Determinar el tipo de rampa
|
||||||
|
const bool IS_LEFT_SLOPE = isLeftSlope();
|
||||||
|
|
||||||
|
// Movimiento horizontal con colisión lateral
|
||||||
|
const float DISPLACEMENT = vx_ * delta_time;
|
||||||
|
if (vx_ < 0.0F) {
|
||||||
|
const SDL_FRect PROJECTION = getProjection(Direction::LEFT, DISPLACEMENT);
|
||||||
|
const int POS = room_->checkRightSurfaces(PROJECTION);
|
||||||
|
if (POS == Collision::NONE) {
|
||||||
|
x_ += DISPLACEMENT;
|
||||||
|
} else {
|
||||||
|
x_ = POS + 1;
|
||||||
|
}
|
||||||
|
} else if (vx_ > 0.0F) {
|
||||||
|
const SDL_FRect PROJECTION = getProjection(Direction::RIGHT, DISPLACEMENT);
|
||||||
|
const int POS = room_->checkLeftSurfaces(PROJECTION);
|
||||||
|
if (POS == Collision::NONE) {
|
||||||
|
x_ += DISPLACEMENT;
|
||||||
|
} else {
|
||||||
|
x_ = POS - WIDTH;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualizar posición de los pies para cálculos
|
||||||
|
updateFeet();
|
||||||
|
|
||||||
|
// Seleccionar el pie apropiado según el tipo de rampa
|
||||||
|
// Left slopes (forma \) colisionan con el pie izquierdo
|
||||||
|
// Right slopes (forma /) colisionan con el pie derecho
|
||||||
|
const float FOOT_X = IS_LEFT_SLOPE ? under_left_foot_.x : under_right_foot_.x;
|
||||||
|
|
||||||
|
// Calcular la Y del pie basado en la ecuación de la rampa (45 grados)
|
||||||
|
// Left slope (\): y aumenta con x -> y = y1 + (x - x1)
|
||||||
|
// Right slope (/): y disminuye con x -> y = y1 - (x - x1)
|
||||||
|
float foot_y = 0.0F;
|
||||||
|
if (IS_LEFT_SLOPE) {
|
||||||
|
foot_y = current_slope_->y1 + (FOOT_X - current_slope_->x1);
|
||||||
|
} else {
|
||||||
|
foot_y = current_slope_->y1 - (FOOT_X - current_slope_->x1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Ajustar la posición Y del jugador (restar HEIGHT porque foot_y es la posición del pie)
|
||||||
|
y_ = foot_y - HEIGHT;
|
||||||
|
|
||||||
|
// Verificar si el pie ha salido de los límites horizontales de la rampa
|
||||||
|
// Usar min/max porque LEFT slopes tienen x1<x2 pero RIGHT slopes tienen x1>x2
|
||||||
|
const int MIN_X = std::min(current_slope_->x1, current_slope_->x2);
|
||||||
|
const int MAX_X = std::max(current_slope_->x1, current_slope_->x2);
|
||||||
|
const bool OUT_OF_BOUNDS = (FOOT_X < MIN_X) || (FOOT_X > MAX_X);
|
||||||
|
|
||||||
|
if (OUT_OF_BOUNDS) {
|
||||||
|
// Determinar si estamos saliendo por arriba o por abajo de la rampa
|
||||||
|
const bool EXITING_DOWNWARD = (FOOT_X > current_slope_->x2 && IS_LEFT_SLOPE) ||
|
||||||
|
(FOOT_X < current_slope_->x1 && !IS_LEFT_SLOPE);
|
||||||
|
|
||||||
|
if (EXITING_DOWNWARD) {
|
||||||
|
// Salida por abajo: bajar 1 pixel para ayudar detección de suelo
|
||||||
|
y_ += 1.0F;
|
||||||
|
}
|
||||||
|
// Si sale por arriba, mantener altura (ya está en foot_y - HEIGHT)
|
||||||
|
|
||||||
|
// El jugador ya no está en la rampa, limpiar referencia
|
||||||
|
current_slope_ = nullptr;
|
||||||
|
|
||||||
|
// Verificar si hay soporte debajo (suelo plano, conveyor belt, u otra slope)
|
||||||
|
if (isOnFloor()) {
|
||||||
|
// Hay soporte: transición a ON_GROUND (podría ser superficie, conveyor u otra rampa)
|
||||||
|
transitionToState(State::ON_GROUND);
|
||||||
|
} else {
|
||||||
|
// Sin soporte: empezar a caer
|
||||||
|
transitionToState(State::FALLING);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Verificar transición a superficie plana
|
||||||
if (isOnTopSurface()) {
|
if (isOnTopSurface()) {
|
||||||
transitionToState(State::ON_GROUND);
|
transitionToState(State::ON_GROUND);
|
||||||
return;
|
return;
|
||||||
@@ -509,15 +581,65 @@ auto Player::isOnConveyorBelt() -> bool {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Comprueba si el jugador está sobre una rampa
|
// Comprueba si el jugador está sobre una rampa
|
||||||
|
// Retorna true SOLO si un pie está en rampa Y el otro pie está volando (sin soporte)
|
||||||
auto Player::isOnSlope() -> bool {
|
auto Player::isOnSlope() -> bool {
|
||||||
bool on_slope = false;
|
|
||||||
updateFeet();
|
updateFeet();
|
||||||
|
|
||||||
// Comprueba las rampas
|
// Verificar qué pie está en qué tipo de rampa
|
||||||
on_slope |= room_->checkLeftSlopes(under_left_foot_);
|
const bool LEFT_FOOT_ON_LEFT_SLOPE = room_->checkLeftSlopes(under_left_foot_);
|
||||||
on_slope |= room_->checkRightSlopes(under_right_foot_);
|
const bool RIGHT_FOOT_ON_RIGHT_SLOPE = room_->checkRightSlopes(under_right_foot_);
|
||||||
|
|
||||||
return on_slope;
|
// Verificar si cada pie está "volando" (sin soporte: ni top surface ni conveyor belt)
|
||||||
|
const bool LEFT_FOOT_FLYING = !(room_->checkTopSurfaces(under_left_foot_) ||
|
||||||
|
room_->checkConveyorBelts(under_left_foot_));
|
||||||
|
const bool RIGHT_FOOT_FLYING = !(room_->checkTopSurfaces(under_right_foot_) ||
|
||||||
|
room_->checkConveyorBelts(under_right_foot_));
|
||||||
|
|
||||||
|
// Retornar true si UN pie en rampa Y el OTRO volando
|
||||||
|
return (LEFT_FOOT_ON_LEFT_SLOPE && RIGHT_FOOT_FLYING) ||
|
||||||
|
(RIGHT_FOOT_ON_RIGHT_SLOPE && LEFT_FOOT_FLYING);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprueba si current_slope_ es una rampa izquierda (ascendente a la izquierda)
|
||||||
|
// Las rampas izquierdas tienen forma \ con x1 < x2 (x aumenta de izq a der)
|
||||||
|
auto Player::isLeftSlope() -> bool {
|
||||||
|
if (current_slope_ == nullptr) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
// Left slopes (\): x1 < x2 (x aumenta de izquierda a derecha)
|
||||||
|
// Right slopes (/): x1 > x2 (x decrece de izquierda a derecha)
|
||||||
|
return current_slope_->x1 < current_slope_->x2;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza current_slope_ con la rampa correcta según el pie que toca
|
||||||
|
void Player::updateCurrentSlope() {
|
||||||
|
updateFeet();
|
||||||
|
|
||||||
|
// Left slopes (\) ascendentes a izquierda tocan el pie izquierdo
|
||||||
|
if (room_->checkLeftSlopes(under_left_foot_)) {
|
||||||
|
current_slope_ = room_->getSlopeAtPoint(under_left_foot_);
|
||||||
|
}
|
||||||
|
// Right slopes (/) ascendentes a derecha tocan el pie derecho
|
||||||
|
else if (room_->checkRightSlopes(under_right_foot_)) {
|
||||||
|
current_slope_ = room_->getSlopeAtPoint(under_right_foot_);
|
||||||
|
}
|
||||||
|
// Fallback para casos edge
|
||||||
|
else {
|
||||||
|
current_slope_ = room_->getSlopeAtPoint(under_left_foot_);
|
||||||
|
if (current_slope_ == nullptr) {
|
||||||
|
current_slope_ = room_->getSlopeAtPoint(under_right_foot_);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Debug output
|
||||||
|
if (current_slope_ != nullptr) {
|
||||||
|
const char* TYPE = isLeftSlope() ? "Left \\" : "Right /";
|
||||||
|
std::cout << "[SLOPE] " << TYPE
|
||||||
|
<< " from (" << current_slope_->x1 << "," << current_slope_->y1 << ")"
|
||||||
|
<< " to (" << current_slope_->x2 << "," << current_slope_->y2 << ")\n";
|
||||||
|
} else {
|
||||||
|
std::cout << "[SLOPE] nullptr\n";
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Comprueba que el jugador no toque ningun tile de los que matan
|
// Comprueba que el jugador no toque ningun tile de los que matan
|
||||||
|
|||||||
@@ -189,6 +189,8 @@ class Player {
|
|||||||
auto isOnTopSurface() -> bool; // Comprueba si el jugador está sobre una superficie
|
auto isOnTopSurface() -> bool; // Comprueba si el jugador está sobre una superficie
|
||||||
auto isOnConveyorBelt() -> bool; // Comprueba si el jugador esta sobre una cinta transportadora
|
auto isOnConveyorBelt() -> bool; // Comprueba si el jugador esta sobre una cinta transportadora
|
||||||
auto isOnSlope() -> bool; // Comprueba si el jugador está sobre una rampa
|
auto isOnSlope() -> bool; // Comprueba si el jugador está sobre una rampa
|
||||||
|
auto isLeftSlope() -> bool; // Comprueba si current_slope_ es una rampa izquierda (ascendente a la izquierda)
|
||||||
|
void updateCurrentSlope(); // Actualiza current_slope_ con la rampa correcta y muestra debug info
|
||||||
|
|
||||||
// --- Funciones de actualización de geometría ---
|
// --- Funciones de actualización de geometría ---
|
||||||
void syncSpriteAndCollider(); // Actualiza collider_box y collision points
|
void syncSpriteAndCollider(); // Actualiza collider_box y collision points
|
||||||
|
|||||||
Reference in New Issue
Block a user