重构UI架构:分离数据模型和显示逻辑
- 新增 Core 模块:GameObject、LogEntry、AssetItem 数据模型 - 新增 Managers 模块:SceneManager、LogSystem、ProjectManager - Panel 层只负责显示,不再持有数据 - 解耦 HierarchyPanel 和 InspectorPanel 之间的直接依赖
This commit is contained in:
@@ -32,6 +32,9 @@ add_executable(${PROJECT_NAME} WIN32
|
||||
src/main.cpp
|
||||
src/Application.cpp
|
||||
src/Theme.cpp
|
||||
src/Managers/SceneManager.cpp
|
||||
src/Managers/LogSystem.cpp
|
||||
src/Managers/ProjectManager.cpp
|
||||
src/panels/Panel.cpp
|
||||
src/panels/MenuBar.cpp
|
||||
src/panels/HierarchyPanel.cpp
|
||||
|
||||
@@ -48,8 +48,6 @@ bool Application::Initialize(HWND hwnd) {
|
||||
m_consolePanel = std::make_unique<ConsolePanel>();
|
||||
m_projectPanel = std::make_unique<ProjectPanel>();
|
||||
|
||||
m_inspectorPanel->SetHierarchyPanel(m_hierarchyPanel.get());
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
13
ui/src/Core/AssetItem.h
Normal file
13
ui/src/Core/AssetItem.h
Normal file
@@ -0,0 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
|
||||
namespace UI {
|
||||
|
||||
struct AssetItem {
|
||||
std::string name;
|
||||
std::string type;
|
||||
bool isFolder;
|
||||
};
|
||||
|
||||
}
|
||||
61
ui/src/Core/GameObject.h
Normal file
61
ui/src/Core/GameObject.h
Normal file
@@ -0,0 +1,61 @@
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <memory>
|
||||
|
||||
namespace UI {
|
||||
|
||||
class Component {
|
||||
public:
|
||||
virtual ~Component() = default;
|
||||
virtual std::string GetName() const = 0;
|
||||
};
|
||||
|
||||
class TransformComponent : public Component {
|
||||
public:
|
||||
float position[3] = {0.0f, 0.0f, 0.0f};
|
||||
float rotation[3] = {0.0f, 0.0f, 0.0f};
|
||||
float scale[3] = {1.0f, 1.0f, 1.0f};
|
||||
|
||||
std::string GetName() const override { return "Transform"; }
|
||||
};
|
||||
|
||||
class MeshRendererComponent : public Component {
|
||||
public:
|
||||
std::string materialName = "Default-Material";
|
||||
std::string meshName = "";
|
||||
|
||||
std::string GetName() const override { return "Mesh Renderer"; }
|
||||
};
|
||||
|
||||
class GameObject {
|
||||
public:
|
||||
std::string name;
|
||||
std::vector<GameObject> children;
|
||||
std::vector<std::unique_ptr<Component>> components;
|
||||
bool selected = false;
|
||||
|
||||
GameObject() = default;
|
||||
explicit GameObject(const std::string& n) : name(n) {}
|
||||
|
||||
template<typename T, typename... Args>
|
||||
T* AddComponent(Args&&... args) {
|
||||
auto comp = std::make_unique<T>(std::forward<Args>(args)...);
|
||||
T* ptr = comp.get();
|
||||
components.push_back(std::move(comp));
|
||||
return ptr;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T* GetComponent() {
|
||||
for (auto& comp : components) {
|
||||
if (auto casted = dynamic_cast<T*>(comp.get())) {
|
||||
return casted;
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
13
ui/src/Core/LogEntry.h
Normal file
13
ui/src/Core/LogEntry.h
Normal file
@@ -0,0 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
|
||||
namespace UI {
|
||||
|
||||
struct LogEntry {
|
||||
enum class Level { Info, Warning, Error };
|
||||
Level level;
|
||||
std::string message;
|
||||
};
|
||||
|
||||
}
|
||||
19
ui/src/Managers/LogSystem.cpp
Normal file
19
ui/src/Managers/LogSystem.cpp
Normal file
@@ -0,0 +1,19 @@
|
||||
#include "LogSystem.h"
|
||||
|
||||
namespace UI {
|
||||
|
||||
LogSystem& LogSystem::Get() {
|
||||
static LogSystem instance;
|
||||
return instance;
|
||||
}
|
||||
|
||||
void LogSystem::AddLog(LogEntry::Level level, const std::string& message) {
|
||||
m_logs.push_back({level, message});
|
||||
if (m_callback) m_callback();
|
||||
}
|
||||
|
||||
void LogSystem::Clear() {
|
||||
m_logs.clear();
|
||||
}
|
||||
|
||||
}
|
||||
26
ui/src/Managers/LogSystem.h
Normal file
26
ui/src/Managers/LogSystem.h
Normal file
@@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include "Core/LogEntry.h"
|
||||
#include <vector>
|
||||
#include <functional>
|
||||
|
||||
namespace UI {
|
||||
|
||||
class LogSystem {
|
||||
public:
|
||||
static LogSystem& Get();
|
||||
|
||||
void AddLog(LogEntry::Level level, const std::string& message);
|
||||
void Clear();
|
||||
const std::vector<LogEntry>& GetLogs() const { return m_logs; }
|
||||
|
||||
void SetCallback(std::function<void()> callback) { m_callback = callback; }
|
||||
|
||||
private:
|
||||
LogSystem() = default;
|
||||
|
||||
std::vector<LogEntry> m_logs;
|
||||
std::function<void()> m_callback;
|
||||
};
|
||||
|
||||
}
|
||||
23
ui/src/Managers/ProjectManager.cpp
Normal file
23
ui/src/Managers/ProjectManager.cpp
Normal file
@@ -0,0 +1,23 @@
|
||||
#include "ProjectManager.h"
|
||||
|
||||
namespace UI {
|
||||
|
||||
ProjectManager& ProjectManager::Get() {
|
||||
static ProjectManager instance;
|
||||
return instance;
|
||||
}
|
||||
|
||||
void ProjectManager::CreateDemoAssets() {
|
||||
m_items = {
|
||||
{"Cube", "Prefab", false},
|
||||
{"Sphere", "Prefab", false},
|
||||
{"Player", "Prefab", false},
|
||||
{"MainScript", "Script", false},
|
||||
{"DefaultMat", "Material", false},
|
||||
{"Scene1", "Scene", false},
|
||||
{"Textures", "Folder", true},
|
||||
{"Models", "Folder", true},
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
26
ui/src/Managers/ProjectManager.h
Normal file
26
ui/src/Managers/ProjectManager.h
Normal file
@@ -0,0 +1,26 @@
|
||||
#pragma once
|
||||
|
||||
#include "Core/AssetItem.h"
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
namespace UI {
|
||||
|
||||
class ProjectManager {
|
||||
public:
|
||||
static ProjectManager& Get();
|
||||
|
||||
std::vector<AssetItem>& GetItems() { return m_items; }
|
||||
int GetSelectedIndex() const { return m_selectedIndex; }
|
||||
void SetSelectedIndex(int index) { m_selectedIndex = index; }
|
||||
|
||||
void CreateDemoAssets();
|
||||
|
||||
private:
|
||||
ProjectManager() = default;
|
||||
|
||||
std::vector<AssetItem> m_items;
|
||||
int m_selectedIndex = -1;
|
||||
};
|
||||
|
||||
}
|
||||
47
ui/src/Managers/SceneManager.cpp
Normal file
47
ui/src/Managers/SceneManager.cpp
Normal file
@@ -0,0 +1,47 @@
|
||||
#include "SceneManager.h"
|
||||
|
||||
namespace UI {
|
||||
|
||||
SceneManager& SceneManager::Get() {
|
||||
static SceneManager instance;
|
||||
return instance;
|
||||
}
|
||||
|
||||
void SceneManager::SetSelectedObject(GameObject* obj) {
|
||||
if (m_selectedObject) {
|
||||
m_selectedObject->selected = false;
|
||||
}
|
||||
m_selectedObject = obj;
|
||||
if (m_selectedObject) {
|
||||
m_selectedObject->selected = true;
|
||||
}
|
||||
}
|
||||
|
||||
void SceneManager::CreateDemoScene() {
|
||||
m_rootObjects.clear();
|
||||
|
||||
GameObject mainCamera("Main Camera");
|
||||
mainCamera.AddComponent<TransformComponent>();
|
||||
|
||||
GameObject directionalLight("Directional Light");
|
||||
|
||||
GameObject cube("Cube");
|
||||
cube.AddComponent<TransformComponent>();
|
||||
cube.AddComponent<MeshRendererComponent>()->meshName = "Cube Mesh";
|
||||
|
||||
GameObject sphere("Sphere");
|
||||
sphere.AddComponent<TransformComponent>();
|
||||
sphere.AddComponent<MeshRendererComponent>()->meshName = "Sphere Mesh";
|
||||
|
||||
GameObject player("Player");
|
||||
GameObject weapon("Weapon");
|
||||
player.children.push_back(std::move(weapon));
|
||||
|
||||
m_rootObjects.push_back(std::move(mainCamera));
|
||||
m_rootObjects.push_back(std::move(directionalLight));
|
||||
m_rootObjects.push_back(std::move(cube));
|
||||
m_rootObjects.push_back(std::move(sphere));
|
||||
m_rootObjects.push_back(std::move(player));
|
||||
}
|
||||
|
||||
}
|
||||
25
ui/src/Managers/SceneManager.h
Normal file
25
ui/src/Managers/SceneManager.h
Normal file
@@ -0,0 +1,25 @@
|
||||
#pragma once
|
||||
|
||||
#include "Core/GameObject.h"
|
||||
#include <vector>
|
||||
|
||||
namespace UI {
|
||||
|
||||
class SceneManager {
|
||||
public:
|
||||
static SceneManager& Get();
|
||||
|
||||
std::vector<GameObject>& GetRootObjects() { return m_rootObjects; }
|
||||
GameObject* GetSelectedObject() { return m_selectedObject; }
|
||||
void SetSelectedObject(GameObject* obj);
|
||||
|
||||
void CreateDemoScene();
|
||||
|
||||
private:
|
||||
SceneManager() = default;
|
||||
|
||||
std::vector<GameObject> m_rootObjects;
|
||||
GameObject* m_selectedObject = nullptr;
|
||||
};
|
||||
|
||||
}
|
||||
@@ -1,40 +1,42 @@
|
||||
#include "ConsolePanel.h"
|
||||
#include "Managers/LogSystem.h"
|
||||
#include "Core/LogEntry.h"
|
||||
#include <imgui.h>
|
||||
|
||||
namespace UI {
|
||||
|
||||
ConsolePanel::ConsolePanel() : Panel("Console") {
|
||||
m_logs.push_back({LogEntry::Level::Info, "Engine initialized successfully"});
|
||||
m_logs.push_back({LogEntry::Level::Info, "Loading default scene..."});
|
||||
m_logs.push_back({LogEntry::Level::Warning, "Missing material on object 'Cube'"});
|
||||
m_logs.push_back({LogEntry::Level::Error, "Failed to load texture: 'Assets/Textures/missing.png'"});
|
||||
m_logs.push_back({LogEntry::Level::Info, "Scene loaded successfully"});
|
||||
LogSystem::Get().AddLog(LogEntry::Level::Info, "Engine initialized successfully");
|
||||
LogSystem::Get().AddLog(LogEntry::Level::Info, "Loading default scene...");
|
||||
LogSystem::Get().AddLog(LogEntry::Level::Warning, "Missing material on object 'Cube'");
|
||||
LogSystem::Get().AddLog(LogEntry::Level::Error, "Failed to load texture: 'Assets/Textures/missing.png'");
|
||||
LogSystem::Get().AddLog(LogEntry::Level::Info, "Scene loaded successfully");
|
||||
}
|
||||
|
||||
void ConsolePanel::Render() {
|
||||
ImGui::Begin(m_name.c_str(), &m_isOpen, ImGuiWindowFlags_None);
|
||||
|
||||
if (ImGui::Button("Clear")) {
|
||||
Clear();
|
||||
LogSystem::Get().Clear();
|
||||
}
|
||||
ImGui::SameLine();
|
||||
if (ImGui::Button("Info")) {
|
||||
AddLog(LogEntry::Level::Info, "Test info message");
|
||||
LogSystem::Get().AddLog(LogEntry::Level::Info, "Test info message");
|
||||
}
|
||||
ImGui::SameLine();
|
||||
if (ImGui::Button("Warn")) {
|
||||
AddLog(LogEntry::Level::Warning, "Test warning message");
|
||||
LogSystem::Get().AddLog(LogEntry::Level::Warning, "Test warning message");
|
||||
}
|
||||
ImGui::SameLine();
|
||||
if (ImGui::Button("Error")) {
|
||||
AddLog(LogEntry::Level::Error, "Test error message");
|
||||
LogSystem::Get().AddLog(LogEntry::Level::Error, "Test error message");
|
||||
}
|
||||
|
||||
ImGui::Separator();
|
||||
|
||||
ImGui::BeginChild("LogScroll", ImVec2(0, 0), false, ImGuiWindowFlags_HorizontalScrollbar);
|
||||
|
||||
for (const auto& log : m_logs) {
|
||||
for (const auto& log : LogSystem::Get().GetLogs()) {
|
||||
ImVec4 color;
|
||||
const char* prefix;
|
||||
|
||||
@@ -65,13 +67,4 @@ void ConsolePanel::Render() {
|
||||
ImGui::End();
|
||||
}
|
||||
|
||||
void ConsolePanel::AddLog(LogEntry::Level level, const std::string& message) {
|
||||
m_logs.push_back({level, message});
|
||||
m_scrollToBottom = true;
|
||||
}
|
||||
|
||||
void ConsolePanel::Clear() {
|
||||
m_logs.clear();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,27 +1,15 @@
|
||||
#pragma once
|
||||
|
||||
#include "Panel.h"
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
namespace UI {
|
||||
|
||||
struct LogEntry {
|
||||
enum class Level { Info, Warning, Error };
|
||||
Level level;
|
||||
std::string message;
|
||||
};
|
||||
|
||||
class ConsolePanel : public Panel {
|
||||
public:
|
||||
ConsolePanel();
|
||||
void Render() override;
|
||||
void AddLog(LogEntry::Level level, const std::string& message);
|
||||
|
||||
private:
|
||||
void Clear();
|
||||
|
||||
std::vector<LogEntry> m_logs;
|
||||
bool m_scrollToBottom = false;
|
||||
};
|
||||
|
||||
|
||||
@@ -1,42 +1,18 @@
|
||||
#include "HierarchyPanel.h"
|
||||
#include "Managers/SceneManager.h"
|
||||
#include "Core/GameObject.h"
|
||||
#include <imgui.h>
|
||||
|
||||
namespace UI {
|
||||
|
||||
HierarchyPanel::HierarchyPanel() : Panel("Hierarchy") {
|
||||
InitDemoData();
|
||||
}
|
||||
|
||||
void HierarchyPanel::InitDemoData() {
|
||||
GameObject mainCamera;
|
||||
mainCamera.name = "Main Camera";
|
||||
|
||||
GameObject directionalLight;
|
||||
directionalLight.name = "Directional Light";
|
||||
|
||||
GameObject cube;
|
||||
cube.name = "Cube";
|
||||
|
||||
GameObject sphere;
|
||||
sphere.name = "Sphere";
|
||||
|
||||
GameObject player;
|
||||
player.name = "Player";
|
||||
GameObject weapon;
|
||||
weapon.name = "Weapon";
|
||||
player.children.push_back(weapon);
|
||||
|
||||
m_rootObjects.push_back(mainCamera);
|
||||
m_rootObjects.push_back(directionalLight);
|
||||
m_rootObjects.push_back(cube);
|
||||
m_rootObjects.push_back(sphere);
|
||||
m_rootObjects.push_back(player);
|
||||
SceneManager::Get().CreateDemoScene();
|
||||
}
|
||||
|
||||
void HierarchyPanel::Render() {
|
||||
ImGui::Begin(m_name.c_str(), &m_isOpen, ImGuiWindowFlags_None);
|
||||
|
||||
for (auto& obj : m_rootObjects) {
|
||||
for (auto& obj : SceneManager::Get().GetRootObjects()) {
|
||||
RenderGameObject(obj);
|
||||
}
|
||||
|
||||
@@ -57,11 +33,7 @@ void HierarchyPanel::RenderGameObject(GameObject& obj) {
|
||||
bool isOpen = ImGui::TreeNodeEx(obj.name.c_str(), flags);
|
||||
|
||||
if (ImGui::IsItemClicked() && !ImGui::IsItemToggledOpen()) {
|
||||
if (m_selectedObject) {
|
||||
m_selectedObject->selected = false;
|
||||
}
|
||||
obj.selected = true;
|
||||
m_selectedObject = &obj;
|
||||
SceneManager::Get().SetSelectedObject(&obj);
|
||||
}
|
||||
|
||||
if (isOpen) {
|
||||
|
||||
@@ -1,30 +1,16 @@
|
||||
#pragma once
|
||||
|
||||
#include "Panel.h"
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
namespace UI {
|
||||
|
||||
struct GameObject {
|
||||
std::string name;
|
||||
std::vector<GameObject> children;
|
||||
bool isOpen = false;
|
||||
bool selected = false;
|
||||
};
|
||||
|
||||
class HierarchyPanel : public Panel {
|
||||
public:
|
||||
HierarchyPanel();
|
||||
void Render() override;
|
||||
GameObject* GetSelectedObject() { return m_selectedObject; }
|
||||
|
||||
private:
|
||||
void RenderGameObject(GameObject& obj);
|
||||
void InitDemoData();
|
||||
|
||||
std::vector<GameObject> m_rootObjects;
|
||||
GameObject* m_selectedObject = nullptr;
|
||||
void RenderGameObject(class GameObject& obj);
|
||||
};
|
||||
|
||||
}
|
||||
@@ -1,4 +1,6 @@
|
||||
#include "InspectorPanel.h"
|
||||
#include "Managers/SceneManager.h"
|
||||
#include "Core/GameObject.h"
|
||||
#include <imgui.h>
|
||||
|
||||
namespace UI {
|
||||
@@ -8,18 +10,22 @@ InspectorPanel::InspectorPanel() : Panel("Inspector") {}
|
||||
void InspectorPanel::Render() {
|
||||
ImGui::Begin(m_name.c_str(), &m_isOpen, ImGuiWindowFlags_None);
|
||||
|
||||
GameObject* selected = nullptr;
|
||||
if (m_hierarchyPanel) {
|
||||
selected = m_hierarchyPanel->GetSelectedObject();
|
||||
}
|
||||
GameObject* selected = SceneManager::Get().GetSelectedObject();
|
||||
|
||||
if (selected) {
|
||||
ImGui::Text("%s", selected->name.c_str());
|
||||
ImGui::Separator();
|
||||
|
||||
RenderTransformSection();
|
||||
ImGui::Separator();
|
||||
RenderMeshRendererSection();
|
||||
auto transform = selected->GetComponent<TransformComponent>();
|
||||
if (transform) {
|
||||
RenderTransformSection(transform);
|
||||
ImGui::Separator();
|
||||
}
|
||||
|
||||
auto meshRenderer = selected->GetComponent<MeshRendererComponent>();
|
||||
if (meshRenderer) {
|
||||
RenderMeshRendererSection(meshRenderer);
|
||||
}
|
||||
} else {
|
||||
ImGui::Text("No object selected");
|
||||
ImGui::TextColored(ImVec4(0.5f, 0.5f, 0.5f, 1.0f), "Select an object in Hierarchy");
|
||||
@@ -28,44 +34,42 @@ void InspectorPanel::Render() {
|
||||
ImGui::End();
|
||||
}
|
||||
|
||||
void InspectorPanel::RenderTransformSection() {
|
||||
void InspectorPanel::RenderTransformSection(TransformComponent* transform) {
|
||||
if (ImGui::CollapsingHeader("Transform", ImGuiTreeNodeFlags_DefaultOpen)) {
|
||||
ImGui::Indent(10.0f);
|
||||
|
||||
ImGui::Text("Position");
|
||||
ImGui::SameLine(80);
|
||||
ImGui::SetNextItemWidth(180);
|
||||
ImGui::DragFloat3("##Position", m_position, 0.1f);
|
||||
ImGui::DragFloat3("##Position", transform->position, 0.1f);
|
||||
|
||||
ImGui::Text("Rotation");
|
||||
ImGui::SameLine(80);
|
||||
ImGui::SetNextItemWidth(180);
|
||||
ImGui::DragFloat3("##Rotation", m_rotation, 1.0f);
|
||||
ImGui::DragFloat3("##Rotation", transform->rotation, 1.0f);
|
||||
|
||||
ImGui::Text("Scale");
|
||||
ImGui::SameLine(80);
|
||||
ImGui::SetNextItemWidth(180);
|
||||
ImGui::DragFloat3("##Scale", m_scale, 0.1f);
|
||||
ImGui::DragFloat3("##Scale", transform->scale, 0.1f);
|
||||
|
||||
ImGui::Unindent(10.0f);
|
||||
}
|
||||
}
|
||||
|
||||
void InspectorPanel::RenderMeshRendererSection() {
|
||||
void InspectorPanel::RenderMeshRendererSection(MeshRendererComponent* meshRenderer) {
|
||||
if (ImGui::CollapsingHeader("Mesh Renderer", ImGuiTreeNodeFlags_DefaultOpen)) {
|
||||
ImGui::Indent(10.0f);
|
||||
|
||||
ImGui::Text("Material");
|
||||
ImGui::SameLine(80);
|
||||
ImGui::SetNextItemWidth(180);
|
||||
static char materialName[64] = "Default-Material";
|
||||
ImGui::InputText("##Material", materialName, sizeof(materialName));
|
||||
ImGui::InputText("##Material", meshRenderer->materialName.data(), meshRenderer->materialName.capacity());
|
||||
|
||||
ImGui::Text("Mesh");
|
||||
ImGui::SameLine(80);
|
||||
ImGui::SetNextItemWidth(180);
|
||||
static char meshName[64] = "Cube Mesh";
|
||||
ImGui::InputText("##Mesh", meshName, sizeof(meshName));
|
||||
ImGui::InputText("##Mesh", meshRenderer->meshName.data(), meshRenderer->meshName.capacity());
|
||||
|
||||
ImGui::Unindent(10.0f);
|
||||
}
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include "Panel.h"
|
||||
#include "HierarchyPanel.h"
|
||||
|
||||
namespace UI {
|
||||
|
||||
@@ -9,17 +8,10 @@ class InspectorPanel : public Panel {
|
||||
public:
|
||||
InspectorPanel();
|
||||
void Render() override;
|
||||
void SetHierarchyPanel(HierarchyPanel* panel) { m_hierarchyPanel = panel; }
|
||||
|
||||
private:
|
||||
void RenderTransformSection();
|
||||
void RenderMeshRendererSection();
|
||||
|
||||
HierarchyPanel* m_hierarchyPanel = nullptr;
|
||||
|
||||
float m_position[3] = {0.0f, 1.0f, -10.0f};
|
||||
float m_rotation[3] = {0.0f, 0.0f, 0.0f};
|
||||
float m_scale[3] = {1.0f, 1.0f, 1.0f};
|
||||
void RenderTransformSection(class TransformComponent* transform);
|
||||
void RenderMeshRendererSection(class MeshRendererComponent* meshRenderer);
|
||||
};
|
||||
|
||||
}
|
||||
@@ -1,22 +1,13 @@
|
||||
#include "ProjectPanel.h"
|
||||
#include "Managers/ProjectManager.h"
|
||||
#include "Core/AssetItem.h"
|
||||
#include <imgui.h>
|
||||
#include <imgui_internal.h>
|
||||
|
||||
namespace UI {
|
||||
|
||||
ProjectPanel::ProjectPanel() : Panel("Project") {
|
||||
m_folders = {"Assets", "Scenes", "Scripts", "Materials", "Prefabs"};
|
||||
|
||||
m_items = {
|
||||
{"Cube", "Prefab", false},
|
||||
{"Sphere", "Prefab", false},
|
||||
{"Player", "Prefab", false},
|
||||
{"MainScript", "Script", false},
|
||||
{"DefaultMat", "Material", false},
|
||||
{"Scene1", "Scene", false},
|
||||
{"Textures", "Folder", true},
|
||||
{"Models", "Folder", true},
|
||||
};
|
||||
ProjectManager::Get().CreateDemoAssets();
|
||||
}
|
||||
|
||||
void ProjectPanel::Render() {
|
||||
@@ -37,11 +28,12 @@ void ProjectPanel::Render() {
|
||||
int columns = (int)(panelWidth / (buttonWidth + padding));
|
||||
if (columns < 1) columns = 1;
|
||||
|
||||
for (int i = 0; i < m_items.size(); i++) {
|
||||
auto& items = ProjectManager::Get().GetItems();
|
||||
for (int i = 0; i < items.size(); i++) {
|
||||
if (i > 0 && i % columns != 0) {
|
||||
ImGui::SameLine();
|
||||
}
|
||||
RenderAssetItem(m_items[i], i);
|
||||
RenderAssetItem(items[i], i);
|
||||
}
|
||||
|
||||
ImGui::EndChild();
|
||||
@@ -51,14 +43,14 @@ void ProjectPanel::Render() {
|
||||
void ProjectPanel::RenderAssetItem(const AssetItem& item, int index) {
|
||||
ImGui::PushID(index);
|
||||
|
||||
bool isSelected = (m_selectedIndex == index);
|
||||
bool isSelected = (ProjectManager::Get().GetSelectedIndex() == index);
|
||||
if (isSelected) {
|
||||
ImGui::PushStyleColor(ImGuiCol_Button, ImVec4(0.26f, 0.59f, 0.98f, 0.40f));
|
||||
ImGui::PushStyleColor(ImGuiCol_Button, ImVec4(0.40f, 0.40f, 0.40f, 0.50f));
|
||||
}
|
||||
|
||||
ImVec2 buttonSize(80.0f, 90.0f);
|
||||
if (ImGui::Button("##Asset", buttonSize)) {
|
||||
m_selectedIndex = index;
|
||||
ProjectManager::Get().SetSelectedIndex(index);
|
||||
}
|
||||
|
||||
if (isSelected) {
|
||||
|
||||
@@ -1,28 +1,16 @@
|
||||
#pragma once
|
||||
|
||||
#include "Panel.h"
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
namespace UI {
|
||||
|
||||
struct AssetItem {
|
||||
std::string name;
|
||||
std::string type;
|
||||
bool isFolder;
|
||||
};
|
||||
|
||||
class ProjectPanel : public Panel {
|
||||
public:
|
||||
ProjectPanel();
|
||||
void Render() override;
|
||||
|
||||
private:
|
||||
void RenderAssetItem(const AssetItem& item, int index);
|
||||
|
||||
std::vector<std::string> m_folders;
|
||||
std::vector<AssetItem> m_items;
|
||||
int m_selectedIndex = -1;
|
||||
void RenderAssetItem(const struct AssetItem& item, int index);
|
||||
};
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user