Implement state for MessageState.

This commit is contained in:
J-D-K 2025-11-10 18:39:34 -05:00
parent d8b8375fd5
commit 710f246583
3 changed files with 112 additions and 18 deletions

View File

@ -256,7 +256,7 @@ class ConfirmState final : public BaseState
OPTION_FONT_SIZE,
sdl::text::NO_WRAP,
colors::WHITE,
sm_yes);
sm_no);
}
private:
@ -429,7 +429,7 @@ class ConfirmState final : public BaseState
else if (validCancel) { StateType::create_and_push(m_onCancel, m_taskData); }
else
{
FadeState::create_and_push(colors::DIM_BACKGROUND, colors::ALPHA_FADE_END, colors::ALPHA_FADE_END, nullptr);
FadeState::create_and_push(colors::DIM_BACKGROUND, colors::ALPHA_FADE_END, colors::ALPHA_FADE_BEGIN, nullptr);
}
// Deactivate this state.

View File

@ -16,12 +16,21 @@ class MessageState final : public BaseState
/// @param message Message to display.
MessageState(std::string_view message);
/// @brief Same as above. Moves message instead of copying.
MessageState(std::string &message);
/// @brief Creates and returns a new MessageState. See constructor.
static inline std::shared_ptr<MessageState> create(std::string_view message)
{
return std::make_shared<MessageState>(message);
}
/// @brief Creates and returns a new MessageState. See constructor.
static inline std::shared_ptr<MessageState> create(std::string &message)
{
return std::make_shared<MessageState>(message);
}
/// @brief Same as above, only pushed to the StateManager before return.
static inline std::shared_ptr<MessageState> create_and_push(std::string_view message)
{
@ -30,6 +39,14 @@ class MessageState final : public BaseState
return newState;
}
/// @brief Same as above, only pushed to the StateManager before return.
static inline std::shared_ptr<MessageState> create_and_push(std::string &message)
{
auto newState = MessageState::create(message);
StateManager::push_state(newState);
return newState;
}
/// @brief Same as above, but creates and pushes a transition fade in between.
static inline std::shared_ptr<MessageState> create_push_fade(std::string_view message)
{
@ -39,6 +56,15 @@ class MessageState final : public BaseState
return newState;
}
/// @brief Same as above, but creates and pushes a transition fade in between.
static inline std::shared_ptr<MessageState> create_push_fade(std::string &message)
{
auto newState = MessageState::create(message);
auto fadeState =
FadeState::create_and_push(colors::DIM_BACKGROUND, colors::ALPHA_FADE_BEGIN, colors::ALPHA_FADE_END, newState);
return newState;
}
/// @brief Update override.
void update() override;
@ -46,6 +72,14 @@ class MessageState final : public BaseState
void render() override;
private:
/// @brief States this state can be in.
enum class State
{
Opening,
Displaying,
Closing
};
/// @brief Safe store of the message to display.
std::string m_message{};
@ -55,8 +89,8 @@ class MessageState final : public BaseState
/// @brief Transition.
ui::Transition m_transition{};
/// @brief Bool to signal to close.
bool m_close{};
/// @brief Stores the current state of the current state.
MessageState::State m_state{};
/// @brief This is the OK string.
static inline const char *sm_okText{};
@ -74,7 +108,10 @@ class MessageState final : public BaseState
void initialize_static_members();
/// @brief Updates the dialog according to the transition.
void update_dialog();
void update_dimensions() noexcept;
/// @brief Updates and handles the input.
void update_handle_input() noexcept;
/// @brief Closes and "hides" the dialog.
void close_dialog();

View File

@ -7,11 +7,47 @@
#include "input.hpp"
#include "strings/strings.hpp"
namespace
{
// Initial coordinates.
constexpr int INITIAL_WIDTH_HEIGHT = 32;
// Target
constexpr int TARGET_WIDTH = 720;
constexpr int TARGET_HEIGHT = 256;
}
// ---- Construction ----
MessageState::MessageState(std::string_view message)
: m_message(message)
, m_transition(0, 0, 32, 32, 0, 0, graphics::SCREEN_HEIGHT, 256, ui::Transition::DEFAULT_THRESHOLD)
, m_transition(0,
0,
INITIAL_WIDTH_HEIGHT,
INITIAL_WIDTH_HEIGHT,
0,
0,
TARGET_WIDTH,
TARGET_HEIGHT,
ui::Transition::DEFAULT_THRESHOLD)
, m_state(State::Opening)
{
MessageState::initialize_static_members();
sm_dialogPop->play();
}
MessageState::MessageState(std::string &message)
: m_message(std::move(message))
, m_transition(0,
0,
INITIAL_WIDTH_HEIGHT,
INITIAL_WIDTH_HEIGHT,
0,
0,
TARGET_WIDTH,
TARGET_HEIGHT,
ui::Transition::DEFAULT_THRESHOLD)
, m_state(State::Opening)
{
MessageState::initialize_static_members();
sm_dialogPop->play();
@ -21,17 +57,12 @@ MessageState::MessageState(std::string_view message)
void MessageState::update()
{
m_transition.update();
sm_dialog->set_from_transition(m_transition, true);
if (!m_transition.in_place()) { return; }
// To do: I only use this in one place right now. I'm not sure this guards correctly here?
const bool aPressed = input::button_pressed(HidNpadButton_A);
m_triggerGuard = m_triggerGuard || (aPressed && !m_triggerGuard);
const bool finished = m_triggerGuard && aPressed;
if (finished) { MessageState::close_dialog(); }
else if (m_close && m_transition.in_place()) { MessageState::deactivate_state(); }
switch (m_state)
{
case State::Opening: MessageState::update_dimensions(); break;
case State::Displaying: MessageState::update_handle_input(); break;
case State::Closing: MessageState::update_dimensions(); break;
}
}
void MessageState::render()
@ -65,9 +96,35 @@ void MessageState::initialize_static_members()
sm_dialog->set_from_transition(m_transition, true);
}
void MessageState::update_dimensions() noexcept
{
// Update the dialog.
m_transition.update();
sm_dialog->set_from_transition(m_transition, true);
// Conditions for state shifting.
const bool opened = m_state == State::Opening && m_transition.in_place();
const bool closed = m_state == State::Closing && m_transition.in_place();
if (opened) { m_state = State::Displaying; }
else if (closed) { MessageState::deactivate_state(); }
}
void MessageState::update_handle_input() noexcept
{
// Input bools.
const bool aPressed = input::button_pressed(HidNpadButton_A);
// Handle the triggerguard.
m_triggerGuard = m_triggerGuard || (aPressed && !m_triggerGuard);
// Conditions.
const bool finished = m_triggerGuard && aPressed;
if (finished) { MessageState::close_dialog(); }
}
void MessageState::close_dialog()
{
m_close = true;
m_state = State::Closing;
m_transition.set_target_width(32);
m_transition.set_target_height(32);
}