| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155 |
- //********************************** Banshee Engine (www.banshee3d.com) **************************************************//
- //**************** Copyright (c) 2016 Marko Pintera ([email protected]). All rights reserved. **********************//
- #include "BsPlayInEditorManager.h"
- #include "BsScriptGameObjectManager.h"
- #include "Utility/BsTime.h"
- #include "Scene/BsSceneManager.h"
- #include "Scene/BsSceneObject.h"
- #include "BsApplication.h"
- #include "Physics/BsPhysics.h"
- #include "Audio/BsAudio.h"
- #include "Animation/BsAnimationManager.h"
- namespace bs
- {
- PlayInEditorManager::PlayInEditorManager()
- :mState(PlayInEditorState::Stopped), mNextState(PlayInEditorState::Stopped),
- mFrameStepActive(false), mScheduledStateChange(false), mPausableTime(0.0f)
- {
- if (!gApplication().isEditor())
- mState = PlayInEditorState::Playing;
- else
- {
- setSystemsPauseState(true);
- gSceneManager().setComponentState(ComponentState::Stopped);
- }
- }
- void PlayInEditorManager::setState(PlayInEditorState state)
- {
- if (!gApplication().isEditor())
- return;
- // Delay state change to next frame as this method could be called in middle of object update, in which case
- // part of the objects before this call would receive different state than other objects.
- mScheduledStateChange = true;
- mNextState = state;
- }
- void PlayInEditorManager::setStateImmediate(PlayInEditorState state)
- {
- if (mState == state)
- return;
- PlayInEditorState oldState = mState;
- mState = state;
- switch (state)
- {
- case PlayInEditorState::Stopped:
- {
- mFrameStepActive = false;
- mPausableTime = 0.0f;
- setSystemsPauseState(true);
- gSceneManager().setComponentState(ComponentState::Stopped);
- mSavedScene->_instantiate();
- gSceneManager()._setRootNode(mSavedScene);
- mSavedScene = nullptr;
- }
- break;
- case PlayInEditorState::Playing:
- {
- if (oldState == PlayInEditorState::Stopped)
- saveSceneInMemory();
- gSceneManager().setComponentState(ComponentState::Running);
- setSystemsPauseState(false);
- gAnimation().setPaused(false);
- }
- break;
- case PlayInEditorState::Paused:
- {
- mFrameStepActive = false;
- setSystemsPauseState(true);
- gAnimation().setPaused(true);
- if (oldState == PlayInEditorState::Stopped)
- saveSceneInMemory();
- gSceneManager().setComponentState(ComponentState::Paused);
- }
- break;
- default:
- break;
- }
- }
- void PlayInEditorManager::frameStep()
- {
- if (!gApplication().isEditor())
- return;
- switch (mState)
- {
- case PlayInEditorState::Stopped:
- case PlayInEditorState::Paused:
- setState(PlayInEditorState::Playing);
- break;
- default:
- break;
- }
- mFrameStepActive = true;
- }
- void PlayInEditorManager::update()
- {
- if (mState == PlayInEditorState::Playing)
- mPausableTime += gTime().getFrameDelta();
- if (mScheduledStateChange)
- {
- setStateImmediate(mNextState);
- mScheduledStateChange = false;
- }
- if (mFrameStepActive)
- {
- setState(PlayInEditorState::Paused);
- mFrameStepActive = false;
- }
- }
- void PlayInEditorManager::saveSceneInMemory()
- {
- mSavedScene = SceneManager::instance().getRootNode()->clone(false);
- // Remove objects with "dont save" flag
- Stack<HSceneObject> todo;
- todo.push(mSavedScene);
- while (!todo.empty())
- {
- HSceneObject current = todo.top();
- todo.pop();
- if (current->hasFlag(SOF_DontSave))
- current->destroy();
- else
- {
- UINT32 numChildren = current->getNumChildren();
- for (UINT32 i = 0; i < numChildren; i++)
- todo.push(current->getChild(i));
- }
- }
- }
- void PlayInEditorManager::setSystemsPauseState(bool paused)
- {
- gPhysics().setPaused(paused);
- gAudio().setPaused(paused);
- }
- }
|