Changeset View
Changeset View
Standalone View
Standalone View
source/simulation2/components/CCmpCinemaManager.cpp
/* Copyright (C) 2016 Wildfire Games. | /* Copyright (C) 2017 Wildfire Games. | ||||
* This file is part of 0 A.D. | * This file is part of 0 A.D. | ||||
* | * | ||||
* 0 A.D. is free software: you can redistribute it and/or modify | * 0 A.D. is free software: you can redistribute it and/or modify | ||||
* it under the terms of the GNU General Public License as published by | * it under the terms of the GNU General Public License as published by | ||||
* the Free Software Foundation, either version 2 of the License, or | * the Free Software Foundation, either version 2 of the License, or | ||||
* (at your option) any later version. | * (at your option) any later version. | ||||
* | * | ||||
* 0 A.D. is distributed in the hope that it will be useful, | * 0 A.D. is distributed in the hope that it will be useful, | ||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||||
* GNU General Public License for more details. | * GNU General Public License for more details. | ||||
* | * | ||||
* You should have received a copy of the GNU General Public License | * You should have received a copy of the GNU General Public License | ||||
* along with 0 A.D. If not, see <http://www.gnu.org/licenses/>. | * along with 0 A.D. If not, see <http://www.gnu.org/licenses/>. | ||||
*/ | */ | ||||
#include "precompiled.h" | #include "precompiled.h" | ||||
#include "simulation2/system/Component.h" | #include "simulation2/system/Component.h" | ||||
#include "ICmpCinemaManager.h" | #include "ICmpCinemaManager.h" | ||||
#include "graphics/GameView.h" | #include "graphics/GameView.h" | ||||
#include "graphics/CinemaManager.h" | #include "graphics/CinemaManager.h" | ||||
#include "gui/CGUI.h" | |||||
#include "gui/GUIManager.h" | |||||
#include "gui/IGUIObject.h" | |||||
#include "ps/CLogger.h" | #include "ps/CLogger.h" | ||||
#include "ps/Game.h" | #include "ps/Game.h" | ||||
#include "simulation2/components/ICmpOverlayRenderer.h" | |||||
#include "simulation2/components/ICmpRangeManager.h" | |||||
#include "simulation2/components/ICmpSelectable.h" | |||||
#include "simulation2/components/ICmpTerritoryManager.h" | |||||
#include "simulation2/MessageTypes.h" | #include "simulation2/MessageTypes.h" | ||||
#include "simulation2/Simulation2.h" | #include "simulation2/Simulation2.h" | ||||
#include "renderer/Renderer.h" | |||||
class CCmpCinemaManager : public ICmpCinemaManager | class CCmpCinemaManager : public ICmpCinemaManager | ||||
{ | { | ||||
public: | public: | ||||
static void ClassInit(CComponentManager& componentManager) | static void ClassInit(CComponentManager& componentManager) | ||||
{ | { | ||||
componentManager.SubscribeToMessageType(MT_Update); | componentManager.SubscribeToMessageType(MT_Update); | ||||
} | } | ||||
DEFAULT_COMPONENT_ALLOCATOR(CinemaManager) | DEFAULT_COMPONENT_ALLOCATOR(CinemaManager) | ||||
static std::string GetSchema() | static std::string GetSchema() | ||||
{ | { | ||||
return "<a:component type='system'/>" | return "<a:component type='system'/>" | ||||
elexis: Those three lines should be one until extended IMO | |||||
"<empty/>" | "<empty/>" | ||||
; | ; | ||||
} | } | ||||
virtual void Init(const CParamNode& UNUSED(paramNode)) | virtual void Init(const CParamNode& UNUSED(paramNode)) | ||||
{ | { | ||||
// ... | m_Enabled = false; | ||||
m_Paused = false; | |||||
m_MapRevealed = false; | |||||
m_ElapsedTime = fixed::Zero(); | |||||
m_TotalTime = fixed::Zero(); | |||||
m_CurrentPathElapsedTime = fixed::Zero(); | |||||
} | } | ||||
virtual void Deinit() | virtual void Deinit() | ||||
{ | { | ||||
// ... | // ... | ||||
Not Done Inline ActionsWhat information do these thee dots provide that an empty function doesn't imply? elexis: What information do these thee dots provide that an empty function doesn't imply? | |||||
} | } | ||||
virtual void Serialize(ISerializer& serialize) | virtual void Serialize(ISerializer& serialize) | ||||
{ | { | ||||
if (!g_Game || !g_Game->GetView()) | serialize.Bool("MapRevealed", m_MapRevealed); | ||||
return; | serialize.NumberU32_Unbounded("NumberOfPaths", m_Paths.size()); | ||||
for (auto it : m_Paths) | |||||
elexisUnsubmitted Done Inline Actionsuse the actual type instead of auto elexis: use the actual type instead of auto | |||||
CinematicSimulationData* p_CinematicSimulationData = g_Game->GetView()->GetCinema()->GetCinematicSimulationData(); | |||||
serialize.Bool("MapRevealed", p_CinematicSimulationData->m_MapRevealed); | |||||
serialize.NumberU32_Unbounded("NumberOfPaths", p_CinematicSimulationData->m_Paths.size()); | |||||
for (auto it : p_CinematicSimulationData->m_Paths) | |||||
{ | { | ||||
CCinemaPath& path = it.second; | CCinemaPath& path = it.second; | ||||
const CCinemaData* data = path.GetData(); | const CCinemaData* data = path.GetData(); | ||||
// TODO: maybe implement String_Unbounded | // TODO: maybe implement String_Unbounded | ||||
serialize.String("PathName", data->m_Name, 1, 2048); | serialize.String("PathName", data->m_Name, 1, 2048); | ||||
serialize.String("PathOrientation", data->m_Orientation, 1, 2048); | serialize.String("PathOrientation", data->m_Orientation, 1, 2048); | ||||
serialize.String("PathMode", data->m_Mode, 1, 2048); | serialize.String("PathMode", data->m_Mode, 1, 2048); | ||||
Show All 33 Lines | for (auto it : m_Paths) | ||||
serialize.NumberFixed_Unbounded("PositionY", targetNodes[i].Position.Y); | serialize.NumberFixed_Unbounded("PositionY", targetNodes[i].Position.Y); | ||||
serialize.NumberFixed_Unbounded("PositionZ", targetNodes[i].Position.Z); | serialize.NumberFixed_Unbounded("PositionZ", targetNodes[i].Position.Z); | ||||
} | } | ||||
} | } | ||||
} | } | ||||
virtual void Deserialize(const CParamNode& UNUSED(paramNode), IDeserializer& deserialize) | virtual void Deserialize(const CParamNode& UNUSED(paramNode), IDeserializer& deserialize) | ||||
{ | { | ||||
if (!g_Game || !g_Game->GetView()) | deserialize.Bool("MapRevealed", m_MapRevealed); | ||||
return; | |||||
CinematicSimulationData* p_CinematicSimulationData = g_Game->GetView()->GetCinema()->GetCinematicSimulationData(); | |||||
deserialize.Bool("MapRevealed", p_CinematicSimulationData->m_MapRevealed); | |||||
uint32_t numberOfPaths = 0; | uint32_t numberOfPaths = 0; | ||||
deserialize.NumberU32_Unbounded("NumberOfPaths", numberOfPaths); | deserialize.NumberU32_Unbounded("NumberOfPaths", numberOfPaths); | ||||
for (uint32_t i = 0; i < numberOfPaths; ++i) | for (uint32_t i = 0; i < numberOfPaths; ++i) | ||||
{ | { | ||||
CCinemaData data; | CCinemaData data; | ||||
deserialize.String("PathName", data.m_Name, 1, 2048); | deserialize.String("PathName", data.m_Name, 1, 2048); | ||||
deserialize.String("PathOrientation", data.m_Orientation, 1, 2048); | deserialize.String("PathOrientation", data.m_Orientation, 1, 2048); | ||||
Show All 34 Lines | for (uint32_t i = 0; i < numberOfPaths; ++i) | ||||
deserialize.NumberFixed_Unbounded("PositionY", node.Position.Y); | deserialize.NumberFixed_Unbounded("PositionY", node.Position.Y); | ||||
deserialize.NumberFixed_Unbounded("PositionZ", node.Position.Z); | deserialize.NumberFixed_Unbounded("PositionZ", node.Position.Z); | ||||
targetSpline.AddNode(node.Position, CFixedVector3D(), node.Distance); | targetSpline.AddNode(node.Position, CFixedVector3D(), node.Distance); | ||||
} | } | ||||
} | } | ||||
// Construct cinema path with data gathered | // Construct cinema path with data gathered | ||||
CCinemaPath path(data, pathSpline, targetSpline); | m_Paths[data.m_Name] = CCinemaPath(data, pathSpline, targetSpline); | ||||
p_CinematicSimulationData->m_Paths[data.m_Name] = path; | |||||
} | } | ||||
g_Game->GetView()->GetCinema()->SetEnabled(p_CinematicSimulationData->m_Enabled); | SetEnabled(m_Enabled); | ||||
} | } | ||||
virtual void HandleMessage(const CMessage& msg, bool UNUSED(global)) | virtual void HandleMessage(const CMessage& msg, bool UNUSED(global)) | ||||
{ | { | ||||
if (!g_Game || !g_Game->GetView()) | |||||
return; | |||||
switch (msg.GetType()) | switch (msg.GetType()) | ||||
{ | { | ||||
case MT_Update: | case MT_Update: | ||||
{ | { | ||||
const CMessageUpdate &msgData = static_cast<const CMessageUpdate&>(msg); | const CMessageUpdate &msgData = static_cast<const CMessageUpdate&>(msg); | ||||
CinematicSimulationData* pCinematicSimulationData = g_Game->GetView()->GetCinema()->GetCinematicSimulationData(); | if (!m_Enabled) | ||||
if (!pCinematicSimulationData->m_Enabled) | |||||
break; | break; | ||||
pCinematicSimulationData->m_ElapsedTime += msgData.turnLength; | m_ElapsedTime += msgData.turnLength; | ||||
pCinematicSimulationData->m_CurrentPathElapsedTime += msgData.turnLength; | m_CurrentPathElapsedTime += msgData.turnLength; | ||||
if (pCinematicSimulationData->m_CurrentPathElapsedTime >= pCinematicSimulationData->m_PathQueue.front().GetDuration()) | if (m_CurrentPathElapsedTime >= m_PathQueue.front().GetDuration()) | ||||
{ | { | ||||
CMessageCinemaPathEnded msgCinemaPathEnded(pCinematicSimulationData->m_PathQueue.front().GetName()); | CMessageCinemaPathEnded msgCinemaPathEnded(m_PathQueue.front().GetName()); | ||||
pCinematicSimulationData->m_PathQueue.pop_front(); | m_PathQueue.pop_front(); | ||||
g_Game->GetSimulation2()->PostMessage(SYSTEM_ENTITY, msgCinemaPathEnded); | GetSimContext().GetComponentManager().PostMessage(SYSTEM_ENTITY, msgCinemaPathEnded); | ||||
pCinematicSimulationData->m_CurrentPathElapsedTime = fixed::Zero(); | m_CurrentPathElapsedTime = fixed::Zero(); | ||||
if (!pCinematicSimulationData->m_PathQueue.empty()) | if (!m_PathQueue.empty()) | ||||
pCinematicSimulationData->m_PathQueue.front().Reset(); | m_PathQueue.front().Reset(); | ||||
} | } | ||||
if (pCinematicSimulationData->m_ElapsedTime >= pCinematicSimulationData->m_TotalTime) | if (m_ElapsedTime >= m_TotalTime) | ||||
{ | { | ||||
pCinematicSimulationData->m_CurrentPathElapsedTime = fixed::Zero(); | m_CurrentPathElapsedTime = fixed::Zero(); | ||||
pCinematicSimulationData->m_ElapsedTime = fixed::Zero(); | m_ElapsedTime = fixed::Zero(); | ||||
pCinematicSimulationData->m_TotalTime = fixed::Zero(); | m_TotalTime = fixed::Zero(); | ||||
g_Game->GetView()->GetCinema()->SetEnabled(false); | SetEnabled(false); | ||||
g_Game->GetSimulation2()->PostMessage(SYSTEM_ENTITY, CMessageCinemaQueueEnded()); | GetSimContext().GetComponentManager().PostMessage(SYSTEM_ENTITY, CMessageCinemaQueueEnded()); | ||||
} | } | ||||
break; | break; | ||||
} | } | ||||
default: | default: | ||||
break; | break; | ||||
} | } | ||||
} | } | ||||
virtual void AddPath(const CStrW& name, const CCinemaPath& path) | |||||
{ | |||||
if (m_Paths.find(name) != m_Paths.end()) | |||||
{ | |||||
LOGWARNING("Path with name '%s' already exists", name.ToUTF8()); | |||||
return; | |||||
} | |||||
m_Paths[name] = path; | |||||
} | |||||
virtual void AddCinemaPathToQueue(const CStrW& name) | virtual void AddCinemaPathToQueue(const CStrW& name) | ||||
{ | { | ||||
if (!g_Game || !g_Game->GetView()) | if (!HasPath(name)) | ||||
{ | |||||
LOGWARNING("Path with name '%s' doesn't exist", name.ToUTF8()); | |||||
return; | return; | ||||
g_Game->GetView()->GetCinema()->AddPathToQueue(name); | } | ||||
CinematicSimulationData* pCinematicSimulationData = g_Game->GetView()->GetCinema()->GetCinematicSimulationData(); | m_PathQueue.push_back(m_Paths[name]); | ||||
if (pCinematicSimulationData->m_PathQueue.size() == 1) | |||||
pCinematicSimulationData->m_PathQueue.front().Reset(); | if (m_PathQueue.size() == 1) | ||||
pCinematicSimulationData->m_TotalTime += pCinematicSimulationData->m_Paths[name].GetDuration(); | m_PathQueue.front().Reset(); | ||||
m_TotalTime += m_Paths[name].GetDuration(); | |||||
} | } | ||||
virtual void Play() | virtual void Play() | ||||
{ | { | ||||
if (!g_Game || !g_Game->GetView()) | SetEnabled(true); | ||||
return; | |||||
g_Game->GetView()->GetCinema()->Play(); | |||||
g_Game->GetView()->GetCinema()->SetEnabled(true); | |||||
} | } | ||||
virtual void Stop() | virtual void Stop() | ||||
{ | { | ||||
if (!g_Game || !g_Game->GetView()) | SetEnabled(false); | ||||
} | |||||
virtual bool HasPath(const CStrW& name) const | |||||
{ | |||||
return m_Paths.find(name) != m_Paths.end(); | |||||
} | |||||
virtual void ClearQueue() | |||||
{ | |||||
m_PathQueue.clear(); | |||||
} | |||||
virtual const std::map<CStrW, CCinemaPath>& GetPaths() const | |||||
{ | |||||
return m_Paths; | |||||
} | |||||
virtual void SetPaths(const std::map<CStrW, CCinemaPath>& newPaths) | |||||
{ | |||||
m_Paths = newPaths; | |||||
} | |||||
virtual const std::list<CCinemaPath>& GetQueue() const | |||||
{ | |||||
return m_PathQueue; | |||||
} | |||||
virtual bool IsEnabled() const | |||||
{ | |||||
return m_Enabled; | |||||
} | |||||
virtual bool IsPaused() const | |||||
{ | |||||
return m_Paused; | |||||
} | |||||
virtual void SetEnabled(bool enabled) | |||||
{ | |||||
if (m_PathQueue.empty() && enabled) | |||||
enabled = false; | |||||
if (m_Enabled == enabled) | |||||
return; | return; | ||||
g_Game->GetView()->GetCinema()->Stop(); | |||||
g_Game->GetView()->GetCinema()->SetEnabled(false); | // Overlay visibility | ||||
g_Renderer.SetOptionBool(CRenderer::Option::OPT_SILHOUETTES, !enabled); | |||||
elexisUnsubmitted Done Inline ActionsThis entirely crashes everything in non-visual replay mode (at least here on linux). Also the comment seems unneeded. Also this call is (still) bugged because it will enable silouettes after finishing the path, even if the user option is to disable silhouettes. Hoping to get a fix for that afterwards. elexis: This entirely crashes everything in non-visual replay mode (at least here on linux).
Just needs… | |||||
CmpPtr<ICmpRangeManager> cmpRangeManager(GetSimContext().GetSystemEntity()); | |||||
CmpPtr<ICmpTerritoryManager> cmpTerritoryManager(GetSimContext().GetSystemEntity()); | |||||
if (cmpRangeManager) | |||||
{ | |||||
if (enabled) | |||||
m_MapRevealed = cmpRangeManager->GetLosRevealAll(-1); | |||||
// TODO: improve m_MapRevealed state and without fade in | |||||
cmpRangeManager->SetLosRevealAll(-1, enabled); | |||||
} | |||||
if (cmpTerritoryManager) | |||||
cmpTerritoryManager->SetVisibility(!enabled); | |||||
ICmpSelectable::SetOverrideVisibility(!enabled); | |||||
ICmpOverlayRenderer::SetOverrideVisibility(!enabled); | |||||
m_Enabled = enabled; | |||||
} | } | ||||
virtual void PlayQueue(const float deltaRealTime, CCamera* camera) | |||||
{ | |||||
if (m_PathQueue.empty()) | |||||
return; | |||||
m_PathQueue.front().Play(deltaRealTime, camera); | |||||
} | |||||
private: | |||||
bool m_Enabled; | |||||
bool m_Paused; | |||||
std::map<CStrW, CCinemaPath> m_Paths; | |||||
std::list<CCinemaPath> m_PathQueue; | |||||
// States before playing | |||||
bool m_MapRevealed; | |||||
fixed m_ElapsedTime, m_TotalTime, m_CurrentPathElapsedTime; | |||||
Not Done Inline ActionsEach member on an own line elexis: Each member on an own line | |||||
}; | }; | ||||
REGISTER_COMPONENT_TYPE(CinemaManager) | REGISTER_COMPONENT_TYPE(CinemaManager) |
Wildfire Games · Phabricator
Those three lines should be one until extended IMO