Editor now uses separate stacks; 1 set of stacks when in play and another set of stacks otherwise.

CommandStack now uses SHDeque
This commit is contained in:
Sri Sham Haran 2022-11-12 18:22:45 +08:00
parent 3402992189
commit 78ca464c65
4 changed files with 141 additions and 22 deletions

View File

@ -10,63 +10,102 @@
namespace SHADE namespace SHADE
{ {
SHCommandManager::CommandStack SHCommandManager::undoStack{};
SHCommandManager::CommandStack SHCommandManager::redoStack{}; SHCommandManager::CommandStack SHCommandManager::undoStack(defaultStackSize);
SHCommandManager::CommandStack SHCommandManager::redoStack(defaultStackSize);
SHCommandManager::CommandStack SHCommandManager::secondaryUndoStack(defaultStackSize);
SHCommandManager::CommandStack SHCommandManager::secondaryRedoStack(defaultStackSize);
SHCommandManager::CommandStackPtr SHCommandManager::pCurrUndoStack(&undoStack);
SHCommandManager::CommandStackPtr SHCommandManager::pCurrRedoStack(&redoStack);
void SHCommandManager::PerformCommand(BaseCommandPtr commandPtr, bool const& overrideValue) void SHCommandManager::PerformCommand(BaseCommandPtr commandPtr, bool const& overrideValue)
{ {
redoStack = CommandStack(); *pCurrRedoStack = CommandStack(defaultStackSize);
commandPtr->Execute(); commandPtr->Execute();
if (overrideValue && !undoStack.empty()) if (overrideValue && !pCurrUndoStack->Empty())
{ {
undoStack.top()->Merge(commandPtr); pCurrUndoStack->Top()->Merge(commandPtr);
} }
else else
{ {
undoStack.push(commandPtr); pCurrUndoStack->Push(commandPtr);
} }
} }
void SHCommandManager::RegisterCommand(BaseCommandPtr commandPtr) void SHCommandManager::RegisterCommand(BaseCommandPtr commandPtr)
{ {
undoStack.push(commandPtr); pCurrUndoStack->Push(commandPtr);
} }
void SHCommandManager::UndoCommand() void SHCommandManager::UndoCommand()
{ {
if (undoStack.empty()) if (pCurrUndoStack->Empty())
return; return;
undoStack.top()->Undo(); pCurrUndoStack->Top()->Undo();
redoStack.push(undoStack.top()); pCurrRedoStack->Push(pCurrUndoStack->Top());
undoStack.pop(); pCurrUndoStack->Pop();
} }
void SHCommandManager::RedoCommand() void SHCommandManager::RedoCommand()
{ {
if (redoStack.empty()) if (pCurrRedoStack->Empty())
return; return;
redoStack.top()->Execute(); pCurrRedoStack->Top()->Execute();
undoStack.push(redoStack.top()); pCurrUndoStack->Push(pCurrRedoStack->Top());
redoStack.pop(); pCurrRedoStack->Pop();
} }
std::size_t SHCommandManager::GetUndoStackSize() std::size_t SHCommandManager::GetUndoStackSize()
{ {
return undoStack.size(); return pCurrUndoStack->Size();
} }
std::size_t SHCommandManager::GetRedoStackSize() std::size_t SHCommandManager::GetRedoStackSize()
{ {
return redoStack.size(); return pCurrRedoStack->Size();
} }
void SHCommandManager::PopLatestCommandFromRedoStack() void SHCommandManager::PopLatestCommandFromRedoStack()
{ {
redoStack.pop(); pCurrRedoStack->Pop();
} }
void SHCommandManager::PopLatestCommandFromUndoStack() void SHCommandManager::PopLatestCommandFromUndoStack()
{ {
undoStack.pop(); pCurrUndoStack->Pop();
} }
void SHCommandManager::SwapStacks()
{
if (pCurrUndoStack == &undoStack)
{
pCurrUndoStack = &secondaryUndoStack;
}
else
{
secondaryUndoStack.Clear();
pCurrUndoStack = &undoStack;
}
if (pCurrRedoStack == &redoStack)
{
pCurrRedoStack = &secondaryRedoStack;
}
else
{
secondaryRedoStack.Clear();
pCurrRedoStack = &redoStack;
}
}
void SHCommandManager::ClearAll()
{
undoStack.Clear();
redoStack.Clear();
secondaryUndoStack.Clear();
secondaryRedoStack.Clear();
}
}//namespace SHADE }//namespace SHADE

View File

@ -10,6 +10,7 @@
//#==============================================================# //#==============================================================#
#include "SHCommand.hpp" #include "SHCommand.hpp"
#include "SH_API.h" #include "SH_API.h"
#include "Tools/SHDeque.h"
namespace SHADE namespace SHADE
{ {
@ -22,7 +23,8 @@ namespace SHADE
using BaseCommandPtr = std::shared_ptr<SHBaseCommand>; using BaseCommandPtr = std::shared_ptr<SHBaseCommand>;
template<typename T> template<typename T>
using SHCommandPtr = std::shared_ptr<SHCommand<T>>; using SHCommandPtr = std::shared_ptr<SHCommand<T>>;
using CommandStack = std::stack<BaseCommandPtr>; using CommandStack = SHDeque<BaseCommandPtr>;
using CommandStackPtr = CommandStack*;
static void PerformCommand(BaseCommandPtr commandPtr, bool const& overrideValue = false); static void PerformCommand(BaseCommandPtr commandPtr, bool const& overrideValue = false);
static void RegisterCommand(BaseCommandPtr commandPtr); static void RegisterCommand(BaseCommandPtr commandPtr);
@ -34,8 +36,17 @@ namespace SHADE
static void PopLatestCommandFromRedoStack(); static void PopLatestCommandFromRedoStack();
static void PopLatestCommandFromUndoStack(); static void PopLatestCommandFromUndoStack();
static void SwapStacks();
static void ClearAll();
static constexpr CommandStack::SizeType defaultStackSize = 100;
private: private:
static CommandStackPtr pCurrUndoStack;
static CommandStackPtr pCurrRedoStack;
static CommandStack undoStack; static CommandStack undoStack;
static CommandStack secondaryUndoStack;
static CommandStack redoStack; static CommandStack redoStack;
static CommandStack secondaryRedoStack;
}; };
}//namespace SHADE }//namespace SHADE

View File

@ -228,7 +228,7 @@ namespace SHADE
.previousState = editor->editorState .previousState = editor->editorState
}; };
editor->editorState = SHEditor::State::PLAY; editor->editorState = SHEditor::State::PLAY;
SHCommandManager::SwapStacks();
SHEventManager::BroadcastEvent<SHEditorStateChangeEvent>(STATE_CHANGE_EVENT, SH_EDITOR_ON_PLAY_EVENT); SHEventManager::BroadcastEvent<SHEditorStateChangeEvent>(STATE_CHANGE_EVENT, SH_EDITOR_ON_PLAY_EVENT);
} }
} }
@ -253,7 +253,7 @@ namespace SHADE
.previousState = editor->editorState .previousState = editor->editorState
}; };
editor->editorState = SHEditor::State::STOP; editor->editorState = SHEditor::State::STOP;
SHCommandManager::SwapStacks();
SHEventManager::BroadcastEvent<SHEditorStateChangeEvent>(STATE_CHANGE_EVENT, SH_EDITOR_ON_STOP_EVENT); SHEventManager::BroadcastEvent<SHEditorStateChangeEvent>(STATE_CHANGE_EVENT, SH_EDITOR_ON_STOP_EVENT);
editor->LoadScene(SHSceneManager::GetCurrentSceneAssetID()); editor->LoadScene(SHSceneManager::GetCurrentSceneAssetID());
} }

View File

@ -0,0 +1,69 @@
#pragma once
#pragma once
#include "SH_API.h"
#include <deque>
namespace SHADE
{
template<typename T>
class SH_API SHDeque
{
public:
using ValueType = T;
using Pointer = T*;
using ValueRef = T&;
using ValueConstRef = T const&;
using SizeType = uint32_t;
using ContainerType = std::deque<ValueType>;
using ContainerTypeConstRef = std::deque<ValueType>;
SHDeque(SizeType n) : max_size(n) {}
ContainerTypeConstRef const& GetDeque() const
{
return deque;
}
void Push(ValueConstRef obj)
{
if (deque.size() < max_size)
deque.push_front(std::move(obj));
else
{
deque.pop_back();
deque.push_front(std::move(obj));
}
}
bool Empty()
{
return deque.empty();
}
void Pop()
{
deque.pop_front();
}
ValueConstRef Top()
{
return deque.front();
}
SizeType Size() const noexcept
{
return deque.size();
}
void Clear()
{
deque.clear();
}
private:
int max_size;
ContainerType deque{};
};
}