refactor(editor): Complete architecture refactoring
- SceneManager: remove singleton, use dependency injection via EditorContext - SelectionManager: already interface-based via ISelectionManager - Panel: now receives IEditorContext for accessing managers - HierarchyPanel: migrated to use IEditorContext instead of singletons - Add ISceneManager interface and SceneManagerImpl - EditorContextImpl: holds all editor subsystems Architecture now follows dependency injection pattern: Application -> EditorContext -> SceneManager/SelectionManager EditorLayer -> Panels (receive context via SetContext) All Manager singletons removed: EditorSceneManager::Get(), SelectionManager::Get()
This commit is contained in:
@@ -3,6 +3,7 @@
|
||||
#include "IEditorContext.h"
|
||||
#include "EventBus.h"
|
||||
#include "SelectionManagerImpl.h"
|
||||
#include "Managers/SceneManager.h"
|
||||
#include <string>
|
||||
#include <memory>
|
||||
|
||||
@@ -13,7 +14,9 @@ class EditorContextImpl : public IEditorContext {
|
||||
public:
|
||||
EditorContextImpl()
|
||||
: m_eventBus(std::make_unique<EventBus>())
|
||||
, m_selectionManager(std::make_unique<SelectionManagerImpl>(*m_eventBus)) {
|
||||
, m_selectionManager(std::make_unique<SelectionManagerImpl>(*m_eventBus))
|
||||
, m_sceneManager(std::make_unique<SceneManager>()) {
|
||||
m_sceneManager->SetSelectionManager(m_selectionManager.get());
|
||||
}
|
||||
|
||||
EventBus& GetEventBus() override {
|
||||
@@ -24,6 +27,14 @@ public:
|
||||
return *m_selectionManager;
|
||||
}
|
||||
|
||||
void* GetSceneManager() override {
|
||||
return m_sceneManager.get();
|
||||
}
|
||||
|
||||
SceneManager& GetSceneManagerConcrete() {
|
||||
return *m_sceneManager;
|
||||
}
|
||||
|
||||
void SetProjectPath(const std::string& path) override {
|
||||
m_projectPath = path;
|
||||
}
|
||||
@@ -35,6 +46,7 @@ public:
|
||||
private:
|
||||
std::unique_ptr<EventBus> m_eventBus;
|
||||
std::unique_ptr<SelectionManagerImpl> m_selectionManager;
|
||||
std::unique_ptr<SceneManager> m_sceneManager;
|
||||
std::string m_projectPath;
|
||||
};
|
||||
|
||||
|
||||
@@ -15,6 +15,7 @@ public:
|
||||
|
||||
virtual EventBus& GetEventBus() = 0;
|
||||
virtual ISelectionManager& GetSelectionManager() = 0;
|
||||
virtual void* GetSceneManager() = 0;
|
||||
|
||||
virtual void SetProjectPath(const std::string& path) = 0;
|
||||
virtual const std::string& GetProjectPath() const = 0;
|
||||
|
||||
44
editor/src/Core/ISceneManager.h
Normal file
44
editor/src/Core/ISceneManager.h
Normal file
@@ -0,0 +1,44 @@
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <cstdint>
|
||||
|
||||
namespace XCEngine {
|
||||
namespace Editor {
|
||||
|
||||
using GameObjectID = uint64_t;
|
||||
|
||||
class IGameObject {
|
||||
public:
|
||||
virtual ~IGameObject() = default;
|
||||
virtual GameObjectID GetID() const = 0;
|
||||
virtual const std::string& GetName() const = 0;
|
||||
virtual void SetName(const std::string& name) = 0;
|
||||
virtual IGameObject* GetParent() const = 0;
|
||||
virtual void SetParent(IGameObject* parent) = 0;
|
||||
virtual size_t GetChildCount() const = 0;
|
||||
virtual IGameObject* GetChild(size_t index) const = 0;
|
||||
virtual void DetachFromParent() = 0;
|
||||
virtual const std::vector<IGameObject*>& GetChildren() const = 0;
|
||||
};
|
||||
|
||||
class ISceneManager {
|
||||
public:
|
||||
virtual ~ISceneManager() = default;
|
||||
|
||||
virtual IGameObject* CreateEntity(const std::string& name, IGameObject* parent = nullptr) = 0;
|
||||
virtual void DeleteEntity(GameObjectID id) = 0;
|
||||
virtual void RenameEntity(GameObjectID id, const std::string& newName) = 0;
|
||||
virtual void CopyEntity(GameObjectID id) = 0;
|
||||
virtual GameObjectID PasteEntity(GameObjectID parent = 0) = 0;
|
||||
virtual GameObjectID DuplicateEntity(GameObjectID id) = 0;
|
||||
virtual void MoveEntity(GameObjectID id, GameObjectID newParent) = 0;
|
||||
virtual IGameObject* GetEntity(GameObjectID id) = 0;
|
||||
virtual const std::vector<IGameObject*>& GetRootEntities() const = 0;
|
||||
virtual bool HasClipboardData() const = 0;
|
||||
virtual void CreateDemoScene() = 0;
|
||||
};
|
||||
|
||||
}
|
||||
}
|
||||
59
editor/src/Core/SceneManagerImpl.h
Normal file
59
editor/src/Core/SceneManagerImpl.h
Normal file
@@ -0,0 +1,59 @@
|
||||
#pragma once
|
||||
|
||||
#include "ISceneManager.h"
|
||||
#include <unordered_map>
|
||||
#include <vector>
|
||||
#include <memory>
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <algorithm>
|
||||
|
||||
namespace XCEngine {
|
||||
namespace Editor {
|
||||
|
||||
class MathVector3 {
|
||||
public:
|
||||
float x, y, z;
|
||||
};
|
||||
|
||||
class MathQuaternion {
|
||||
public:
|
||||
float x, y, z, w;
|
||||
};
|
||||
|
||||
class SceneManagerImpl : public ISceneManager {
|
||||
public:
|
||||
SceneManagerImpl();
|
||||
|
||||
IGameObject* CreateEntity(const std::string& name, IGameObject* parent = nullptr) override;
|
||||
void DeleteEntity(GameObjectID id) override;
|
||||
void RenameEntity(GameObjectID id, const std::string& newName) override;
|
||||
void CopyEntity(GameObjectID id) override;
|
||||
GameObjectID PasteEntity(GameObjectID parent = 0) override;
|
||||
GameObjectID DuplicateEntity(GameObjectID id) override;
|
||||
void MoveEntity(GameObjectID id, GameObjectID newParent) override;
|
||||
IGameObject* GetEntity(GameObjectID id) override;
|
||||
const std::vector<IGameObject*>& GetRootEntities() const override;
|
||||
bool HasClipboardData() const override;
|
||||
void CreateDemoScene() override;
|
||||
|
||||
private:
|
||||
struct ClipboardData {
|
||||
std::string name;
|
||||
MathVector3 localPosition = {0, 0, 0};
|
||||
MathQuaternion localRotation = {0, 0, 0, 1};
|
||||
MathVector3 localScale = {1, 1, 1};
|
||||
std::vector<ClipboardData> children;
|
||||
};
|
||||
|
||||
ClipboardData CopyEntityRecursive(GameObjectID id);
|
||||
GameObjectID PasteEntityRecursive(const ClipboardData& data, GameObjectID parent);
|
||||
IGameObject* CastToIGameObject(GameObject* go);
|
||||
|
||||
GameObjectID m_nextId = 1;
|
||||
std::vector<IGameObject*> m_rootEntities;
|
||||
std::optional<ClipboardData> m_clipboard;
|
||||
};
|
||||
|
||||
}
|
||||
}
|
||||
@@ -33,6 +33,14 @@ void EditorLayer::onAttach() {
|
||||
m_consolePanel = std::make_unique<ConsolePanel>();
|
||||
m_projectPanel = std::make_unique<ProjectPanel>();
|
||||
|
||||
m_menuBar->SetContext(m_context.get());
|
||||
m_hierarchyPanel->SetContext(m_context.get());
|
||||
m_sceneViewPanel->SetContext(m_context.get());
|
||||
m_gameViewPanel->SetContext(m_context.get());
|
||||
m_inspectorPanel->SetContext(m_context.get());
|
||||
m_consolePanel->SetContext(m_context.get());
|
||||
m_projectPanel->SetContext(m_context.get());
|
||||
|
||||
m_menuBar->OnAttach();
|
||||
m_hierarchyPanel->OnAttach();
|
||||
m_sceneViewPanel->OnAttach();
|
||||
|
||||
@@ -5,7 +5,13 @@
|
||||
namespace XCEngine {
|
||||
namespace Editor {
|
||||
|
||||
::XCEngine::Components::GameObject* EditorSceneManager::CreateEntity(const std::string& name, ::XCEngine::Components::GameObject* parent) {
|
||||
SceneManager::SceneManager() = default;
|
||||
|
||||
void SceneManager::SetSelectionManager(ISelectionManager* selectionManager) {
|
||||
m_selectionManager = selectionManager;
|
||||
}
|
||||
|
||||
::XCEngine::Components::GameObject* SceneManager::CreateEntity(const std::string& name, ::XCEngine::Components::GameObject* parent) {
|
||||
if (!m_scene) {
|
||||
m_scene = new ::XCEngine::Components::Scene("EditorScene");
|
||||
}
|
||||
@@ -20,7 +26,7 @@ namespace Editor {
|
||||
return entity;
|
||||
}
|
||||
|
||||
void EditorSceneManager::DeleteEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
void SceneManager::DeleteEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
if (!m_scene) return;
|
||||
|
||||
::XCEngine::Components::GameObject* entity = m_scene->Find(std::to_string(id));
|
||||
@@ -35,15 +41,15 @@ void EditorSceneManager::DeleteEntity(::XCEngine::Components::GameObject::ID id)
|
||||
m_rootEntities.erase(std::remove(m_rootEntities.begin(), m_rootEntities.end(), entity), m_rootEntities.end());
|
||||
}
|
||||
|
||||
if (SelectionManager::Get().GetSelectedEntity() == entity) {
|
||||
SelectionManager::Get().ClearSelection();
|
||||
if (m_selectionManager && m_selectionManager->GetSelectedEntity() == entity->GetID()) {
|
||||
m_selectionManager->ClearSelection();
|
||||
}
|
||||
|
||||
m_scene->DestroyGameObject(entity);
|
||||
OnEntityDeleted.Invoke(id);
|
||||
}
|
||||
|
||||
EditorSceneManager::ClipboardData EditorSceneManager::CopyEntityRecursive(const ::XCEngine::Components::GameObject* entity) {
|
||||
SceneManager::ClipboardData SceneManager::CopyEntityRecursive(const ::XCEngine::Components::GameObject* entity) {
|
||||
ClipboardData data;
|
||||
data.name = entity->GetName();
|
||||
|
||||
@@ -60,7 +66,7 @@ EditorSceneManager::ClipboardData EditorSceneManager::CopyEntityRecursive(const
|
||||
return data;
|
||||
}
|
||||
|
||||
void EditorSceneManager::CopyEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
void SceneManager::CopyEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
if (!m_scene) return;
|
||||
|
||||
::XCEngine::Components::GameObject* entity = m_scene->Find(std::to_string(id));
|
||||
@@ -69,7 +75,7 @@ void EditorSceneManager::CopyEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
m_clipboard = CopyEntityRecursive(entity);
|
||||
}
|
||||
|
||||
::XCEngine::Components::GameObject::ID EditorSceneManager::PasteEntityRecursive(const ClipboardData& data, ::XCEngine::Components::GameObject::ID parent) {
|
||||
::XCEngine::Components::GameObject::ID SceneManager::PasteEntityRecursive(const ClipboardData& data, ::XCEngine::Components::GameObject::ID parent) {
|
||||
::XCEngine::Components::GameObject* parentObj = nullptr;
|
||||
if (parent != 0) {
|
||||
parentObj = m_scene->Find(std::to_string(parent));
|
||||
@@ -94,12 +100,12 @@ void EditorSceneManager::CopyEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
return newEntity->GetID();
|
||||
}
|
||||
|
||||
::XCEngine::Components::GameObject::ID EditorSceneManager::PasteEntity(::XCEngine::Components::GameObject::ID parent) {
|
||||
::XCEngine::Components::GameObject::ID SceneManager::PasteEntity(::XCEngine::Components::GameObject::ID parent) {
|
||||
if (!m_clipboard || !m_scene) return 0;
|
||||
return PasteEntityRecursive(*m_clipboard, parent);
|
||||
}
|
||||
|
||||
::XCEngine::Components::GameObject::ID EditorSceneManager::DuplicateEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
::XCEngine::Components::GameObject::ID SceneManager::DuplicateEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
if (!m_scene) return 0;
|
||||
|
||||
::XCEngine::Components::GameObject* entity = m_scene->Find(std::to_string(id));
|
||||
@@ -113,22 +119,32 @@ void EditorSceneManager::CopyEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
return PasteEntity(parentId);
|
||||
}
|
||||
|
||||
void EditorSceneManager::MoveEntity(::XCEngine::Components::GameObject::ID id, ::XCEngine::Components::GameObject::ID newParentId) {
|
||||
void SceneManager::RenameEntity(::XCEngine::Components::GameObject::ID id, const std::string& newName) {
|
||||
if (!m_scene) return;
|
||||
|
||||
::XCEngine::Components::GameObject* entity = m_scene->Find(std::to_string(id));
|
||||
if (!entity) return;
|
||||
::XCEngine::Components::GameObject* obj = m_scene->Find(std::to_string(id));
|
||||
if (!obj) return;
|
||||
|
||||
obj->SetName(newName);
|
||||
OnEntityChanged.Invoke(id);
|
||||
}
|
||||
|
||||
void SceneManager::MoveEntity(::XCEngine::Components::GameObject::ID id, ::XCEngine::Components::GameObject::ID newParentId) {
|
||||
if (!m_scene) return;
|
||||
|
||||
::XCEngine::Components::GameObject* obj = m_scene->Find(std::to_string(id));
|
||||
if (!obj) return;
|
||||
|
||||
::XCEngine::Components::GameObject* newParent = nullptr;
|
||||
if (newParentId != 0) {
|
||||
newParent = m_scene->Find(std::to_string(newParentId));
|
||||
}
|
||||
|
||||
entity->SetParent(newParent);
|
||||
obj->SetParent(newParent);
|
||||
OnEntityChanged.Invoke(id);
|
||||
}
|
||||
|
||||
void EditorSceneManager::CreateDemoScene() {
|
||||
void SceneManager::CreateDemoScene() {
|
||||
if (m_scene) {
|
||||
delete m_scene;
|
||||
}
|
||||
@@ -143,7 +159,6 @@ void EditorSceneManager::CreateDemoScene() {
|
||||
|
||||
::XCEngine::Components::GameObject* cube = CreateEntity("Cube", nullptr);
|
||||
cube->AddComponent<::XCEngine::Components::TransformComponent>();
|
||||
// MeshRendererComponent 需要添加到 Engine
|
||||
|
||||
::XCEngine::Components::GameObject* sphere = CreateEntity("Sphere", nullptr);
|
||||
sphere->AddComponent<::XCEngine::Components::TransformComponent>();
|
||||
|
||||
@@ -4,6 +4,8 @@
|
||||
#include <vector>
|
||||
#include <memory>
|
||||
#include <optional>
|
||||
#include <string>
|
||||
#include <cstdint>
|
||||
|
||||
#include <XCEngine/Core/Event.h>
|
||||
#include <XCEngine/Core/Math/Vector3.h>
|
||||
@@ -11,16 +13,17 @@
|
||||
#include <XCEngine/Components/GameObject.h>
|
||||
#include <XCEngine/Scene/Scene.h>
|
||||
|
||||
#include "Core/ISelectionManager.h"
|
||||
|
||||
namespace XCEngine {
|
||||
namespace Editor {
|
||||
|
||||
class EditorSceneManager {
|
||||
public:
|
||||
static EditorSceneManager& Get() {
|
||||
static EditorSceneManager instance;
|
||||
return instance;
|
||||
}
|
||||
class ISelectionManager;
|
||||
|
||||
class SceneManager {
|
||||
public:
|
||||
SceneManager();
|
||||
|
||||
::XCEngine::Components::GameObject* CreateEntity(const std::string& name, ::XCEngine::Components::GameObject* parent = nullptr);
|
||||
|
||||
::XCEngine::Components::GameObject* GetEntity(::XCEngine::Components::GameObject::ID id) {
|
||||
@@ -37,12 +40,7 @@ public:
|
||||
|
||||
void DeleteEntity(::XCEngine::Components::GameObject::ID id);
|
||||
|
||||
void RenameEntity(::XCEngine::Components::GameObject::ID id, const std::string& newName) {
|
||||
if (auto* entity = GetEntity(id)) {
|
||||
entity->SetName(newName);
|
||||
OnEntityChanged.Invoke(id);
|
||||
}
|
||||
}
|
||||
void RenameEntity(::XCEngine::Components::GameObject::ID id, const std::string& newName);
|
||||
|
||||
void CopyEntity(::XCEngine::Components::GameObject::ID id);
|
||||
::XCEngine::Components::GameObject::ID PasteEntity(::XCEngine::Components::GameObject::ID parent = 0);
|
||||
@@ -52,6 +50,8 @@ public:
|
||||
void CreateDemoScene();
|
||||
|
||||
bool HasClipboardData() const { return m_clipboard.has_value(); }
|
||||
|
||||
void SetSelectionManager(ISelectionManager* selectionManager);
|
||||
|
||||
::XCEngine::Core::Event<::XCEngine::Components::GameObject::ID> OnEntityCreated;
|
||||
::XCEngine::Core::Event<::XCEngine::Components::GameObject::ID> OnEntityDeleted;
|
||||
@@ -59,8 +59,6 @@ public:
|
||||
::XCEngine::Core::Event<> OnSceneChanged;
|
||||
|
||||
private:
|
||||
EditorSceneManager() = default;
|
||||
|
||||
struct ClipboardData {
|
||||
std::string name;
|
||||
Math::Vector3 localPosition = Math::Vector3::Zero();
|
||||
@@ -75,6 +73,7 @@ private:
|
||||
::XCEngine::Components::Scene* m_scene = nullptr;
|
||||
std::vector<::XCEngine::Components::GameObject*> m_rootEntities;
|
||||
std::optional<ClipboardData> m_clipboard;
|
||||
ISelectionManager* m_selectionManager = nullptr;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
#include "HierarchyPanel.h"
|
||||
#include "Managers/SceneManager.h"
|
||||
#include "Managers/SelectionManager.h"
|
||||
#include "Core/IEditorContext.h"
|
||||
#include <XCEngine/Core/Math/Vector3.h>
|
||||
#include <XCEngine/Core/Math/Quaternion.h>
|
||||
#include <imgui.h>
|
||||
@@ -10,14 +9,14 @@ namespace XCEngine {
|
||||
namespace Editor {
|
||||
|
||||
HierarchyPanel::HierarchyPanel() : Panel("Hierarchy") {
|
||||
EditorSceneManager::Get().CreateDemoScene();
|
||||
|
||||
m_selectionHandlerId = SelectionManager::Get().OnSelectionChanged.Subscribe([this](uint64_t) {
|
||||
});
|
||||
}
|
||||
|
||||
HierarchyPanel::~HierarchyPanel() {
|
||||
SelectionManager::Get().OnSelectionChanged.Unsubscribe(m_selectionHandlerId);
|
||||
}
|
||||
|
||||
void HierarchyPanel::OnAttach() {
|
||||
auto* sceneManager = static_cast<SceneManager*>(m_context->GetSceneManager());
|
||||
sceneManager->CreateDemoScene();
|
||||
}
|
||||
|
||||
void HierarchyPanel::Render() {
|
||||
@@ -33,7 +32,8 @@ void HierarchyPanel::Render() {
|
||||
|
||||
ImGui::BeginChild("EntityList");
|
||||
|
||||
auto rootEntities = EditorSceneManager::Get().GetRootEntities();
|
||||
auto& sceneManager = *static_cast<SceneManager*>(m_context->GetSceneManager());
|
||||
auto rootEntities = sceneManager.GetRootEntities();
|
||||
SortEntities(const_cast<std::vector<::XCEngine::Components::GameObject*>&>(rootEntities));
|
||||
|
||||
for (auto* gameObject : rootEntities) {
|
||||
@@ -42,7 +42,7 @@ void HierarchyPanel::Render() {
|
||||
|
||||
if (ImGui::IsWindowHovered() && ImGui::IsMouseDown(0) && !ImGui::IsAnyItemHovered()) {
|
||||
if (!m_renaming) {
|
||||
SelectionManager::Get().ClearSelection();
|
||||
m_context->GetSelectionManager().ClearSelection();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -56,7 +56,8 @@ void HierarchyPanel::Render() {
|
||||
if (const ImGuiPayload* payload = ImGui::AcceptDragDropPayload("ENTITY_PTR")) {
|
||||
::XCEngine::Components::GameObject* sourceGameObject = *(::XCEngine::Components::GameObject**)payload->Data;
|
||||
if (sourceGameObject && sourceGameObject->GetParent() != nullptr) {
|
||||
EditorSceneManager::Get().MoveEntity(sourceGameObject->GetID(), 0);
|
||||
auto& sceneManager = *static_cast<SceneManager*>(m_context->GetSceneManager());
|
||||
sceneManager.MoveEntity(sourceGameObject->GetID(), 0);
|
||||
}
|
||||
}
|
||||
ImGui::EndDragDropTarget();
|
||||
@@ -94,7 +95,7 @@ void HierarchyPanel::RenderEntity(::XCEngine::Components::GameObject* gameObject
|
||||
flags |= ImGuiTreeNodeFlags_Leaf;
|
||||
}
|
||||
|
||||
if (SelectionManager::Get().IsSelected(gameObject)) {
|
||||
if (m_context->GetSelectionManager().IsSelected(gameObject->GetID())) {
|
||||
flags |= ImGuiTreeNodeFlags_Selected;
|
||||
}
|
||||
|
||||
@@ -107,7 +108,7 @@ void HierarchyPanel::RenderEntity(::XCEngine::Components::GameObject* gameObject
|
||||
ImGui::SetNextItemWidth(-1);
|
||||
if (ImGui::InputText("##Rename", m_renameBuffer, sizeof(m_renameBuffer), ImGuiInputTextFlags_EnterReturnsTrue | ImGuiInputTextFlags_AutoSelectAll)) {
|
||||
if (strlen(m_renameBuffer) > 0) {
|
||||
EditorSceneManager::Get().RenameEntity(gameObject->GetID(), m_renameBuffer);
|
||||
static_cast<SceneManager*>(m_context->GetSceneManager())->RenameEntity(gameObject->GetID(), m_renameBuffer);
|
||||
}
|
||||
m_renaming = false;
|
||||
m_renamingEntity = nullptr;
|
||||
@@ -115,7 +116,7 @@ void HierarchyPanel::RenderEntity(::XCEngine::Components::GameObject* gameObject
|
||||
|
||||
if (!ImGui::IsItemActive() && ImGui::IsMouseClicked(0)) {
|
||||
if (strlen(m_renameBuffer) > 0) {
|
||||
EditorSceneManager::Get().RenameEntity(gameObject->GetID(), m_renameBuffer);
|
||||
static_cast<SceneManager*>(m_context->GetSceneManager())->RenameEntity(gameObject->GetID(), m_renameBuffer);
|
||||
}
|
||||
m_renaming = false;
|
||||
m_renamingEntity = nullptr;
|
||||
@@ -126,11 +127,11 @@ void HierarchyPanel::RenderEntity(::XCEngine::Components::GameObject* gameObject
|
||||
if (ImGui::IsItemClicked() && !ImGui::IsItemToggledOpen()) {
|
||||
ImGuiIO& io = ImGui::GetIO();
|
||||
if (io.KeyCtrl) {
|
||||
if (!SelectionManager::Get().IsSelected(gameObject)) {
|
||||
SelectionManager::Get().AddToSelection(gameObject);
|
||||
if (!m_context->GetSelectionManager().IsSelected(gameObject->GetID())) {
|
||||
m_context->GetSelectionManager().AddToSelection(gameObject->GetID());
|
||||
}
|
||||
} else {
|
||||
SelectionManager::Get().SetSelectedEntity(gameObject);
|
||||
m_context->GetSelectionManager().SetSelectedEntity(gameObject->GetID());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -160,8 +161,8 @@ void HierarchyPanel::RenderEntity(::XCEngine::Components::GameObject* gameObject
|
||||
}
|
||||
|
||||
void HierarchyPanel::RenderContextMenu(::XCEngine::Components::GameObject* gameObject) {
|
||||
auto& sceneManager = EditorSceneManager::Get();
|
||||
auto& selectionManager = SelectionManager::Get();
|
||||
auto& sceneManager = *static_cast<SceneManager*>(m_context->GetSceneManager());
|
||||
auto& selectionManager = m_context->GetSelectionManager();
|
||||
|
||||
if (ImGui::BeginMenu("Create")) {
|
||||
RenderCreateMenu(gameObject);
|
||||
@@ -170,7 +171,7 @@ void HierarchyPanel::RenderContextMenu(::XCEngine::Components::GameObject* gameO
|
||||
|
||||
if (gameObject != nullptr && ImGui::MenuItem("Create Child")) {
|
||||
auto* child = sceneManager.CreateEntity("GameObject", gameObject);
|
||||
selectionManager.SetSelectedEntity(child);
|
||||
selectionManager.SetSelectedEntity(child->GetID());
|
||||
}
|
||||
|
||||
ImGui::Separator();
|
||||
@@ -212,12 +213,12 @@ void HierarchyPanel::RenderContextMenu(::XCEngine::Components::GameObject* gameO
|
||||
}
|
||||
|
||||
void HierarchyPanel::RenderCreateMenu(::XCEngine::Components::GameObject* parent) {
|
||||
auto& sceneManager = EditorSceneManager::Get();
|
||||
auto& selectionManager = SelectionManager::Get();
|
||||
auto& sceneManager = *static_cast<SceneManager*>(m_context->GetSceneManager());
|
||||
auto& selectionManager = m_context->GetSelectionManager();
|
||||
|
||||
if (ImGui::MenuItem("Empty Object")) {
|
||||
auto* newEntity = sceneManager.CreateEntity("GameObject", parent);
|
||||
selectionManager.SetSelectedEntity(newEntity);
|
||||
selectionManager.SetSelectedEntity(newEntity->GetID());
|
||||
}
|
||||
|
||||
ImGui::Separator();
|
||||
@@ -225,12 +226,12 @@ void HierarchyPanel::RenderCreateMenu(::XCEngine::Components::GameObject* parent
|
||||
if (ImGui::MenuItem("Camera")) {
|
||||
auto* newEntity = sceneManager.CreateEntity("Camera", parent);
|
||||
newEntity->AddComponent<::XCEngine::Components::TransformComponent>();
|
||||
selectionManager.SetSelectedEntity(newEntity);
|
||||
selectionManager.SetSelectedEntity(newEntity->GetID());
|
||||
}
|
||||
|
||||
if (ImGui::MenuItem("Light")) {
|
||||
auto* newEntity = sceneManager.CreateEntity("Light", parent);
|
||||
selectionManager.SetSelectedEntity(newEntity);
|
||||
selectionManager.SetSelectedEntity(newEntity->GetID());
|
||||
}
|
||||
|
||||
ImGui::Separator();
|
||||
@@ -238,24 +239,24 @@ void HierarchyPanel::RenderCreateMenu(::XCEngine::Components::GameObject* parent
|
||||
if (ImGui::MenuItem("Cube")) {
|
||||
auto* newEntity = sceneManager.CreateEntity("Cube", parent);
|
||||
newEntity->AddComponent<::XCEngine::Components::TransformComponent>();
|
||||
selectionManager.SetSelectedEntity(newEntity);
|
||||
selectionManager.SetSelectedEntity(newEntity->GetID());
|
||||
}
|
||||
|
||||
if (ImGui::MenuItem("Sphere")) {
|
||||
auto* newEntity = sceneManager.CreateEntity("Sphere", parent);
|
||||
newEntity->AddComponent<::XCEngine::Components::TransformComponent>();
|
||||
selectionManager.SetSelectedEntity(newEntity);
|
||||
selectionManager.SetSelectedEntity(newEntity->GetID());
|
||||
}
|
||||
|
||||
if (ImGui::MenuItem("Plane")) {
|
||||
auto* newEntity = sceneManager.CreateEntity("Plane", parent);
|
||||
newEntity->AddComponent<::XCEngine::Components::TransformComponent>();
|
||||
selectionManager.SetSelectedEntity(newEntity);
|
||||
selectionManager.SetSelectedEntity(newEntity->GetID());
|
||||
}
|
||||
}
|
||||
|
||||
void HierarchyPanel::HandleDragDrop(::XCEngine::Components::GameObject* gameObject) {
|
||||
auto& sceneManager = EditorSceneManager::Get();
|
||||
auto& sceneManager = *static_cast<SceneManager*>(m_context->GetSceneManager());
|
||||
|
||||
if (ImGui::BeginDragDropSource(ImGuiDragDropFlags_None)) {
|
||||
ImGui::SetDragDropPayload("ENTITY_PTR", &gameObject, sizeof(::XCEngine::Components::GameObject*));
|
||||
@@ -296,10 +297,10 @@ void HierarchyPanel::HandleDragDrop(::XCEngine::Components::GameObject* gameObje
|
||||
}
|
||||
|
||||
void HierarchyPanel::HandleKeyboardShortcuts() {
|
||||
auto& sceneManager = EditorSceneManager::Get();
|
||||
auto& selectionManager = SelectionManager::Get();
|
||||
auto& sceneManager = *static_cast<SceneManager*>(m_context->GetSceneManager());
|
||||
auto& selectionManager = m_context->GetSelectionManager();
|
||||
|
||||
::XCEngine::Components::GameObject* selectedGameObject = selectionManager.GetSelectedEntity();
|
||||
::XCEngine::Components::GameObject* selectedGameObject = sceneManager.GetEntity(selectionManager.GetSelectedEntity());
|
||||
|
||||
if (ImGui::IsWindowFocused()) {
|
||||
if (ImGui::IsKeyPressed(ImGuiKey_Delete)) {
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
|
||||
#include "Panel.h"
|
||||
#include <XCEngine/Components/GameObject.h>
|
||||
#include "Managers/SceneManager.h"
|
||||
|
||||
namespace XCEngine {
|
||||
namespace Editor {
|
||||
@@ -13,6 +14,7 @@ public:
|
||||
HierarchyPanel();
|
||||
~HierarchyPanel();
|
||||
|
||||
void OnAttach() override;
|
||||
void Render() override;
|
||||
|
||||
private:
|
||||
@@ -25,8 +27,6 @@ private:
|
||||
bool PassesFilter(::XCEngine::Components::GameObject* gameObject, const std::string& filter);
|
||||
void SortEntities(std::vector<::XCEngine::Components::GameObject*>& entities);
|
||||
|
||||
uint64_t m_selectionHandlerId = 0;
|
||||
|
||||
char m_searchBuffer[256] = "";
|
||||
bool m_renaming = false;
|
||||
::XCEngine::Components::GameObject* m_renamingEntity = nullptr;
|
||||
|
||||
@@ -5,6 +5,8 @@
|
||||
namespace XCEngine {
|
||||
namespace Editor {
|
||||
|
||||
class IEditorContext;
|
||||
|
||||
class Panel {
|
||||
public:
|
||||
Panel(const std::string& name);
|
||||
@@ -21,9 +23,13 @@ public:
|
||||
void SetOpen(bool open) { m_isOpen = open; }
|
||||
void Toggle() { m_isOpen = !m_isOpen; }
|
||||
|
||||
void SetContext(IEditorContext* context) { m_context = context; }
|
||||
IEditorContext* GetContext() const { return m_context; }
|
||||
|
||||
protected:
|
||||
std::string m_name;
|
||||
bool m_isOpen;
|
||||
IEditorContext* m_context = nullptr;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user