window_message: animació d'entrada i eixida de la finestra
This commit is contained in:
@@ -35,48 +35,53 @@ void WindowMessage::render() {
|
||||
config_.border_color.b, config_.border_color.a);
|
||||
SDL_RenderRect(renderer, &rect_);
|
||||
|
||||
float current_y = rect_.y + config_.padding;
|
||||
float available_width = getAvailableTextWidth();
|
||||
// Solo mostrar contenido si no estamos en animación de show/hide
|
||||
if (shouldShowContent()) {
|
||||
float current_y = rect_.y + config_.padding;
|
||||
float available_width = getAvailableTextWidth();
|
||||
|
||||
// Dibujar título si existe
|
||||
if (!title_.empty()) {
|
||||
std::string visible_title = getTruncatedText(title_, available_width);
|
||||
text_renderer_->writeStyle(
|
||||
rect_.x + rect_.w / 2.0f,
|
||||
current_y,
|
||||
visible_title,
|
||||
title_style_);
|
||||
current_y += text_renderer_->getCharacterSize() + config_.title_separator_spacing;
|
||||
// Dibujar título si existe
|
||||
if (!title_.empty()) {
|
||||
std::string visible_title = getTruncatedText(title_, available_width);
|
||||
if (!visible_title.empty()) {
|
||||
text_renderer_->writeStyle(
|
||||
rect_.x + rect_.w / 2.0f,
|
||||
current_y,
|
||||
visible_title,
|
||||
title_style_);
|
||||
}
|
||||
current_y += text_renderer_->getCharacterSize() + config_.title_separator_spacing;
|
||||
|
||||
// Línea separadora debajo del título (solo si hay título visible)
|
||||
if (!visible_title.empty()) {
|
||||
SDL_SetRenderDrawColor(renderer, config_.border_color.r, config_.border_color.g,
|
||||
config_.border_color.b, config_.border_color.a);
|
||||
SDL_RenderLine(renderer,
|
||||
rect_.x + config_.padding,
|
||||
current_y - config_.title_separator_spacing / 2.0f,
|
||||
rect_.x + rect_.w - config_.padding,
|
||||
current_y - config_.title_separator_spacing / 2.0f);
|
||||
// Línea separadora debajo del título (solo si hay título visible)
|
||||
if (!visible_title.empty()) {
|
||||
SDL_SetRenderDrawColor(renderer, config_.border_color.r, config_.border_color.g,
|
||||
config_.border_color.b, config_.border_color.a);
|
||||
SDL_RenderLine(renderer,
|
||||
rect_.x + config_.padding,
|
||||
current_y - config_.title_separator_spacing / 2.0f,
|
||||
rect_.x + rect_.w - config_.padding,
|
||||
current_y - config_.title_separator_spacing / 2.0f);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Dibujar textos
|
||||
for (const auto& text : texts_) {
|
||||
std::string visible_text = getTruncatedText(text, available_width);
|
||||
if (!visible_text.empty()) {
|
||||
text_renderer_->writeStyle(
|
||||
rect_.x + rect_.w / 2.0f,
|
||||
current_y,
|
||||
visible_text,
|
||||
text_style_);
|
||||
// Dibujar textos
|
||||
for (const auto& text : texts_) {
|
||||
std::string visible_text = getTruncatedText(text, available_width);
|
||||
if (!visible_text.empty()) {
|
||||
text_renderer_->writeStyle(
|
||||
rect_.x + rect_.w / 2.0f,
|
||||
current_y,
|
||||
visible_text,
|
||||
text_style_);
|
||||
}
|
||||
current_y += text_renderer_->getCharacterSize() + config_.line_spacing;
|
||||
}
|
||||
current_y += text_renderer_->getCharacterSize() + config_.line_spacing;
|
||||
}
|
||||
}
|
||||
|
||||
void WindowMessage::update() {
|
||||
// Actualizar animación de redimensionado
|
||||
if (resize_animation_.active) {
|
||||
// Actualizar animaciones
|
||||
if (show_hide_animation_.active || resize_animation_.active) {
|
||||
// Aquí necesitarías el delta_time del game loop
|
||||
// Por ahora usamos un valor fijo, pero idealmente se pasaría como parámetro
|
||||
float delta_time = 1.0f / 60.0f; // Asumiendo 60 FPS
|
||||
@@ -85,12 +90,37 @@ void WindowMessage::update() {
|
||||
}
|
||||
|
||||
void WindowMessage::show() {
|
||||
ensureTextFits();
|
||||
if (visible_) {
|
||||
return; // Ya visible
|
||||
}
|
||||
|
||||
visible_ = true;
|
||||
ensureTextFits();
|
||||
|
||||
// Detener cualquier animación anterior
|
||||
resize_animation_.stop();
|
||||
|
||||
// Iniciar animación de mostrar desde tamaño 0
|
||||
show_hide_animation_.startShow(rect_.w, rect_.h);
|
||||
rect_.w = 0.0f;
|
||||
rect_.h = 0.0f;
|
||||
updatePosition(); // Reposicionar con tamaño 0
|
||||
}
|
||||
|
||||
void WindowMessage::hide() {
|
||||
visible_ = false;
|
||||
if (!visible_) {
|
||||
return; // Ya oculto
|
||||
}
|
||||
|
||||
// Detener cualquier animación anterior
|
||||
resize_animation_.stop();
|
||||
|
||||
// Guardar el tamaño actual para la animación
|
||||
show_hide_animation_.target_width = rect_.w;
|
||||
show_hide_animation_.target_height = rect_.h;
|
||||
|
||||
// Iniciar animación de ocultar hacia tamaño 0
|
||||
show_hide_animation_.startHide();
|
||||
}
|
||||
|
||||
void WindowMessage::setTitle(const std::string& title) {
|
||||
@@ -137,6 +167,10 @@ void WindowMessage::centerOnScreen() {
|
||||
}
|
||||
|
||||
void WindowMessage::autoSize() {
|
||||
if (show_hide_animation_.active) {
|
||||
return; // No redimensionar durante show/hide
|
||||
}
|
||||
|
||||
if (resize_animation_.active) {
|
||||
resize_animation_.stop(); // Detener animación anterior
|
||||
}
|
||||
@@ -263,13 +297,63 @@ void WindowMessage::triggerAutoResize() {
|
||||
}
|
||||
|
||||
void WindowMessage::updateAnimation(float delta_time) {
|
||||
if (show_hide_animation_.active) {
|
||||
updateShowHideAnimation(delta_time);
|
||||
}
|
||||
|
||||
if (resize_animation_.active) {
|
||||
updateResizeAnimation(delta_time);
|
||||
}
|
||||
}
|
||||
|
||||
void WindowMessage::updateShowHideAnimation(float delta_time) {
|
||||
if (!show_hide_animation_.active) {
|
||||
return;
|
||||
}
|
||||
|
||||
show_hide_animation_.elapsed += delta_time;
|
||||
|
||||
if (show_hide_animation_.isFinished(config_.animation_duration)) {
|
||||
// Animación terminada
|
||||
if (show_hide_animation_.type == ShowHideAnimation::Type::SHOWING) {
|
||||
// Mostrar completado
|
||||
rect_.w = show_hide_animation_.target_width;
|
||||
rect_.h = show_hide_animation_.target_height;
|
||||
} else if (show_hide_animation_.type == ShowHideAnimation::Type::HIDING) {
|
||||
// Ocultar completado
|
||||
rect_.w = 0.0f;
|
||||
rect_.h = 0.0f;
|
||||
visible_ = false;
|
||||
}
|
||||
|
||||
show_hide_animation_.stop();
|
||||
updatePosition();
|
||||
} else {
|
||||
// Interpolar el tamaño
|
||||
float progress = easeOut(show_hide_animation_.getProgress(config_.animation_duration));
|
||||
|
||||
if (show_hide_animation_.type == ShowHideAnimation::Type::SHOWING) {
|
||||
// Crecer desde 0 hasta el tamaño objetivo
|
||||
rect_.w = show_hide_animation_.target_width * progress;
|
||||
rect_.h = show_hide_animation_.target_height * progress;
|
||||
} else if (show_hide_animation_.type == ShowHideAnimation::Type::HIDING) {
|
||||
// Decrecer desde el tamaño actual hasta 0
|
||||
rect_.w = show_hide_animation_.target_width * (1.0f - progress);
|
||||
rect_.h = show_hide_animation_.target_height * (1.0f - progress);
|
||||
}
|
||||
|
||||
updatePosition(); // Mantener la posición centrada durante la animación
|
||||
}
|
||||
}
|
||||
|
||||
void WindowMessage::updateResizeAnimation(float delta_time) {
|
||||
if (!resize_animation_.active) {
|
||||
return;
|
||||
}
|
||||
|
||||
resize_animation_.elapsed += delta_time;
|
||||
|
||||
if (resize_animation_.isFinished()) {
|
||||
if (resize_animation_.isFinished(config_.animation_duration)) {
|
||||
// Animación terminada
|
||||
rect_.w = resize_animation_.target_width;
|
||||
rect_.h = resize_animation_.target_height;
|
||||
@@ -277,7 +361,7 @@ void WindowMessage::updateAnimation(float delta_time) {
|
||||
updatePosition();
|
||||
} else {
|
||||
// Interpolar el tamaño
|
||||
float progress = easeOut(resize_animation_.getProgress());
|
||||
float progress = easeOut(resize_animation_.getProgress(config_.animation_duration));
|
||||
|
||||
rect_.w = resize_animation_.start_width +
|
||||
(resize_animation_.target_width - resize_animation_.start_width) * progress;
|
||||
@@ -288,6 +372,11 @@ void WindowMessage::updateAnimation(float delta_time) {
|
||||
}
|
||||
}
|
||||
|
||||
auto WindowMessage::shouldShowContent() const -> bool {
|
||||
// No mostrar contenido durante animaciones de show/hide
|
||||
return !show_hide_animation_.active;
|
||||
}
|
||||
|
||||
auto WindowMessage::easeOut(float t) const -> float {
|
||||
// Función de suavizado ease-out cuadrática
|
||||
return 1.0f - (1.0f - t) * (1.0f - t);
|
||||
|
||||
Reference in New Issue
Block a user