Skip to content

Commit 3baa367

Browse files
committed
✨ Refactor CreditsScene: implement UI panel with dynamic layout, enhance rendering with UI components, and streamline event handling for improved user experience
1 parent f0a898d commit 3baa367

3 files changed

Lines changed: 134 additions & 29 deletions

File tree

include/core/scenes/credits_scene.hpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
#pragma once
22

33
#include "core/scenes/game_scene.hpp"
4+
#include <memory>
5+
6+
import engine;
47

58
namespace towerforge::core {
69
class CreditsScene : public GameScene {
@@ -18,5 +21,13 @@ namespace towerforge::core {
1821
void Render() override;
1922

2023
void HandleMouseEvent(const engine::ui::MouseEvent &event) override;
24+
25+
private:
26+
std::unique_ptr<engine::ui::elements::Panel> main_panel_;
27+
std::uint32_t last_screen_width_ = 0;
28+
std::uint32_t last_screen_height_ = 0;
29+
30+
void BuildUI();
31+
void UpdateLayout();
2132
};
2233
}

src/core/game.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -150,8 +150,8 @@ namespace towerforge::core {
150150
case GameState::Credits:
151151
if (!credits_scene_) {
152152
credits_scene_ = std::make_unique<CreditsScene>(this);
153-
credits_scene_->Initialize();
154153
}
154+
credits_scene_->Initialize();
155155
active_scene_ = credits_scene_.get();
156156
break;
157157

src/core/scenes/credits_scene.cpp

Lines changed: 122 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -1,56 +1,150 @@
11
#include "core/scenes/credits_scene.hpp"
22
#include "core/game.h"
3+
#include "ui/ui_theme.h"
34
#include <raylib.h>
45

6+
import engine;
7+
58
namespace towerforge::core {
69
CreditsScene::CreditsScene(Game *game)
710
: GameScene(game) {
811
}
912

1013
void CreditsScene::Initialize() {
11-
// Nothing to initialize
14+
BuildUI();
1215
}
1316

1417
void CreditsScene::Shutdown() {
15-
// Nothing to clean up
16-
}
17-
18-
void CreditsScene::Update(const float delta_time) {
18+
main_panel_.reset();
1919
}
2020

21-
void CreditsScene::Render() {
22-
ClearBackground(Color{20, 20, 30, 255});
21+
void CreditsScene::BuildUI() {
22+
using namespace engine::ui::components;
23+
using namespace engine::ui::elements;
2324

2425
std::uint32_t screen_width;
2526
std::uint32_t screen_height;
2627
engine::rendering::GetRenderer().GetFramebufferSize(screen_width, screen_height);
28+
last_screen_width_ = screen_width;
29+
last_screen_height_ = screen_height;
30+
31+
constexpr int PANEL_WIDTH = 600;
32+
constexpr int PANEL_HEIGHT = 400;
33+
const float panel_x = static_cast<float>((screen_width - PANEL_WIDTH) / 2);
34+
const float panel_y = static_cast<float>((screen_height - PANEL_HEIGHT) / 2);
35+
36+
// Create main panel
37+
main_panel_ = std::make_unique<Panel>();
38+
main_panel_->SetRelativePosition(panel_x, panel_y);
39+
main_panel_->SetSize(static_cast<float>(PANEL_WIDTH), static_cast<float>(PANEL_HEIGHT));
40+
main_panel_->SetBackgroundColor(ui::UITheme::ToEngineColor(ColorAlpha(ui::UITheme::BACKGROUND_PANEL, 0.95f)));
41+
main_panel_->SetBorderColor(ui::UITheme::ToEngineColor(ui::UITheme::PRIMARY));
42+
main_panel_->SetPadding(ui::UITheme::PADDING_LARGE);
43+
44+
// Create content container with vertical layout
45+
auto content = engine::ui::ContainerBuilder()
46+
.Size(PANEL_WIDTH - ui::UITheme::PADDING_LARGE * 2, PANEL_HEIGHT - ui::UITheme::PADDING_LARGE * 2)
47+
.Opacity(0)
48+
.Layout(std::make_unique<VerticalLayout>(ui::UITheme::MARGIN_MEDIUM, Alignment::Center))
49+
.Build();
50+
51+
// Title
52+
auto title = std::make_unique<Text>(
53+
0.0f, 0.0f,
54+
"CREDITS",
55+
ui::UITheme::FONT_SIZE_TITLE,
56+
ui::UITheme::ToEngineColor(GOLD)
57+
);
58+
content->AddChild(std::move(title));
59+
60+
// Version
61+
auto version = std::make_unique<Text>(
62+
0.0f, 0.0f,
63+
"TowerForge v0.1.0",
64+
ui::UITheme::FONT_SIZE_LARGE,
65+
ui::UITheme::ToEngineColor(WHITE)
66+
);
67+
content->AddChild(std::move(version));
68+
69+
// Description
70+
auto description = std::make_unique<Text>(
71+
0.0f, 0.0f,
72+
"A modern SimTower-inspired skyscraper simulation",
73+
ui::UITheme::FONT_SIZE_NORMAL,
74+
ui::UITheme::ToEngineColor(LIGHTGRAY)
75+
);
76+
content->AddChild(std::move(description));
77+
78+
// Divider
79+
auto divider = std::make_unique<Divider>();
80+
divider->SetColor(ui::UITheme::ToEngineColor(ui::UITheme::PRIMARY));
81+
divider->SetSize(static_cast<float>(PANEL_WIDTH - ui::UITheme::PADDING_LARGE * 4), 2.0f);
82+
content->AddChild(std::move(divider));
83+
84+
// Built with header
85+
auto built_with = std::make_unique<Text>(
86+
0.0f, 0.0f,
87+
"Built with:",
88+
ui::UITheme::FONT_SIZE_NORMAL,
89+
ui::UITheme::ToEngineColor(LIGHTGRAY)
90+
);
91+
content->AddChild(std::move(built_with));
92+
93+
// Technologies
94+
const char *technologies[] = {"C++20", "Raylib (rendering)", "Flecs (ECS framework)"};
95+
for (const auto *tech: technologies) {
96+
auto tech_text = std::make_unique<Text>(
97+
0.0f, 0.0f,
98+
std::string("- ") + tech,
99+
ui::UITheme::FONT_SIZE_NORMAL,
100+
ui::UITheme::ToEngineColor(WHITE)
101+
);
102+
content->AddChild(std::move(tech_text));
103+
}
104+
105+
// Spacer
106+
auto spacer = std::make_unique<Panel>();
107+
spacer->SetSize(1.0f, static_cast<float>(ui::UITheme::MARGIN_LARGE));
108+
spacer->SetBackgroundColor({0, 0, 0, 0});
109+
content->AddChild(std::move(spacer));
27110

28-
int y = 100;
111+
// Return instruction
112+
auto return_text = std::make_unique<Text>(
113+
0.0f, 0.0f,
114+
"Press ESC or ENTER to return to menu",
115+
ui::UITheme::FONT_SIZE_SMALL,
116+
ui::UITheme::ToEngineColor(GRAY)
117+
);
118+
content->AddChild(std::move(return_text));
29119

30-
DrawText("CREDITS", (screen_width - MeasureText("CREDITS", 40)) / 2, y, 40, GOLD);
31-
y += 80;
120+
main_panel_->AddChild(std::move(content));
32121

33-
DrawText("TowerForge v0.1.0", (screen_width - MeasureText("TowerForge v0.1.0", 24)) / 2, y, 24, WHITE);
34-
y += 50;
122+
main_panel_->InvalidateComponents();
123+
main_panel_->UpdateComponentsRecursive();
124+
}
35125

36-
DrawText("A modern SimTower-inspired skyscraper simulation",
37-
(screen_width - MeasureText("A modern SimTower-inspired skyscraper simulation", 18)) / 2,
38-
y, 18, LIGHTGRAY);
39-
y += 60;
126+
void CreditsScene::UpdateLayout() {
127+
std::uint32_t screen_width;
128+
std::uint32_t screen_height;
129+
engine::rendering::GetRenderer().GetFramebufferSize(screen_width, screen_height);
40130

41-
DrawText("Built with:", (screen_width - MeasureText("Built with:", 20)) / 2, y, 20, LIGHTGRAY);
42-
y += 40;
43-
DrawText("- C++20", (screen_width - MeasureText("- C++20", 18)) / 2, y, 18, WHITE);
44-
y += 30;
45-
DrawText("- Raylib (rendering)", (screen_width - MeasureText("- Raylib (rendering)", 18)) / 2, y, 18, WHITE);
46-
y += 30;
47-
DrawText("- Flecs (ECS framework)", (screen_width - MeasureText("- Flecs (ECS framework)", 18)) / 2, y, 18,
48-
WHITE);
49-
y += 60;
131+
if (screen_width != last_screen_width_ || screen_height != last_screen_height_) {
132+
BuildUI();
133+
}
134+
}
50135

51-
DrawText("Press ESC or ENTER to return to menu",
52-
(screen_width - MeasureText("Press ESC or ENTER to return to menu", 16)) / 2,
53-
y, 16, GRAY);
136+
void CreditsScene::Update(const float delta_time) {
137+
UpdateLayout();
138+
}
139+
140+
void CreditsScene::Render() {
141+
ClearBackground(Color{20, 20, 30, 255});
142+
143+
engine::ui::BatchRenderer::BeginFrame();
144+
if (main_panel_) {
145+
main_panel_->Render();
146+
}
147+
engine::ui::BatchRenderer::EndFrame();
54148
}
55149

56150
void CreditsScene::HandleMouseEvent(const engine::ui::MouseEvent &event) {

0 commit comments

Comments
 (0)