Files
HelloVulkan/App/main.cpp
T
atdunbg 394bfd3d0c refactor: 实体句柄表皮——实体自己管理组件的 API 形态
- 新增 EntityHandle:e.AddComponent<T>() / e.GetComponent<T>() /
  e.Destroy() / e.GetUUID(),转发 entt registry,零存储开销
- Scene::CreateEntity 返回 EntityHandle;Scene 层组件接口保留
  (给渲染器/系统批量遍历用)
- 语义分层:应用层"实体管组件"(句柄表皮),
  数据层组件存储仍集中在 registry(ECS 性能根基)
2026-09-22 13:59:18 +08:00

136 lines
3.9 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
//
// Created by atdunbg on 2026/9/20.
//
// SandboxApp:第一个基于 Application 框架的程序。
//
// main 的全部职责:定义一个 Application 派生类并运行它。
// 窗口、渲染器、事件泵、帧计时、场景容器全部由框架管理;
// 这里只写"程序逻辑":创建实体、逐帧更新组件、事件响应。
//
#include <Engine/Core/Application.h>
#include <Engine/Core/Log.h>
#include <Engine/Core/Stats.h>
#include <Engine/ECS/Scene.h>
#include <Engine/ECS/EntityHandle.h>
#include <Engine/ECS/Components.h>
#include <Engine/Assets/AssetManager.h>
#include <glm/glm.hpp>
#include <glm/gtc/matrix_transform.hpp>
#include <GLFW/glfw3.h>
using namespace Engine;
using namespace Engine::ECS;
class SandboxApp final : public Application
{
public:
SandboxApp()
: Application("HelloVulkan", 1280, 720)
{
}
protected:
// ---- 生命周期 ----
void OnInit() override
{
Scene& scene = GetScene();
// 模型资产(AssetManager 负责加载/缓存/生命周期,返回句柄)
auto backpack = GetAssets().LoadModel("assets/models/backpack/backpack.obj");
// 相机实体(primary = 当前渲染视角)
m_Camera = scene.CreateEntity("MainCamera");
auto& camera = m_Camera.AddComponent<CameraComponent>();
camera.primary = true;
camera.camera.SetPosition(glm::vec3(0.0f, 0.0f, 7.0f));
// 背包实体 × 3
for (int i = 0; i < 3; ++i) {
auto e = scene.CreateEntity("Backpack" + std::to_string(i));
e.AddComponent<TransformComponent>().world = glm::translate(
glm::mat4(1.0f),
glm::vec3((i - 1) * 1.5f, 0.0f, 0.0f));
e.AddComponent<MeshRendererComponent>(MeshRendererComponent{backpack});
m_Spinners.push_back(e);
}
// 灯光实体
scene.CreateEntity("KeyLight")
.AddComponent<LightComponent>(
LightComponent{glm::vec3(-0.5f, -1.0f, -0.3f),
glm::vec4(1.0f, 0.95f, 0.9f, 1.0f)});
scene.CreateEntity("FillLight")
.AddComponent<LightComponent>(
LightComponent{glm::vec3(0.5f, -0.5f, 0.3f),
glm::vec4(0.3f, 0.5f, 1.0f, 0.8f)});
}
void OnUpdate(f32 deltaTime) override
{
m_Time += deltaTime;
// 相机(WASD/Space/Shift 移动)
m_Camera.GetComponent<CameraComponent>()
.camera.Update(GetWindow(), deltaTime);
// 旋转动画:直接写实体组件
for (size_t i = 0; i < m_Spinners.size(); ++i) {
f32 angle = m_Time * glm::radians(60.0f) + static_cast<f32>(i) * 0.7f;
auto& transform = m_Spinners[i].GetComponent<TransformComponent>();
glm::mat4 t = glm::translate(
glm::mat4(1.0f),
glm::vec3((static_cast<f32>(i) - 1.0f) * 1.5f, 0.0f, 0.0f));
glm::mat4 r = glm::rotate(glm::mat4(1.0f), angle, glm::vec3(0.0f, 1.0f, 0.0f));
glm::mat4 s = glm::scale(glm::mat4(1.0f), glm::vec3(0.5f));
transform.world = t * r * s;
}
}
// ---- 事件 ----
void OnKeyPress(const Event& event) override
{
if (event.key == GLFW_KEY_F1) {
STATS.PrintComparison();
}
if (event.key == GLFW_KEY_ESCAPE) {
Close();
}
}
void OnWindowResize(const Event& event) override
{
ENGINE_INFO("App: window resized to {}x{}", event.width, event.height);
}
private:
EntityHandle m_Camera{}; // Scene::CreateEntity 之前为空
std::vector<EntityHandle> m_Spinners;
f32 m_Time = 0.0f;
};
int main()
{
SandboxApp app;
try {
app.Run();
}
catch (const std::exception& e) {
ENGINE_FATAL("Exception: {}", e.what());
return -1;
}
return 0;
}