Index: ps/trunk/binaries/data/mods/public/simulation/components/RangeVisualization.js
===================================================================
--- ps/trunk/binaries/data/mods/public/simulation/components/RangeVisualization.js
+++ ps/trunk/binaries/data/mods/public/simulation/components/RangeVisualization.js
@@ -70,11 +70,11 @@
RangeVisualization.prototype.RegenerateRangeVisualizations = function(forceUpdate)
{
- let cmpSelectable = Engine.QueryInterface(this.entity, IID_Selectable);
- if (!cmpSelectable)
+ let cmpRangeOverlayRenderer = Engine.QueryInterface(this.entity, IID_RangeOverlayRenderer);
+ if (!cmpRangeOverlayRenderer)
return;
- cmpSelectable.ResetRangeOverlays();
+ cmpRangeOverlayRenderer.ResetRangeOverlays();
if (!this.enabled && !forceUpdate)
return;
@@ -83,7 +83,7 @@
for (let rangeOverlayType of this.rangeVisualizations.keys())
if (this.enabledRangeTypes[rangeOverlayType])
for (let rangeOverlay of this.rangeVisualizations.get(rangeOverlayType))
- cmpSelectable.AddRangeOverlay(
+ cmpRangeOverlayRenderer.AddRangeOverlay(
rangeOverlay.radius,
rangeOverlay.texture,
rangeOverlay.textureMask,
Index: ps/trunk/binaries/data/mods/public/simulation/templates/template_structure.xml
===================================================================
--- ps/trunk/binaries/data/mods/public/simulation/templates/template_structure.xml
+++ ps/trunk/binaries/data/mods/public/simulation/templates/template_structure.xml
@@ -100,6 +100,7 @@
round
default
+
2.0
Index: ps/trunk/binaries/data/mods/public/simulation/templates/template_unit.xml
===================================================================
--- ps/trunk/binaries/data/mods/public/simulation/templates/template_unit.xml
+++ ps/trunk/binaries/data/mods/public/simulation/templates/template_unit.xml
@@ -66,6 +66,7 @@
false
+
2.0
Index: ps/trunk/source/simulation2/TypeList.h
===================================================================
--- ps/trunk/source/simulation2/TypeList.h
+++ ps/trunk/source/simulation2/TypeList.h
@@ -150,6 +150,9 @@
INTERFACE(RangeManager)
COMPONENT(RangeManager)
+INTERFACE(RangeOverlayRenderer)
+COMPONENT(RangeOverlayRenderer)
+
INTERFACE(Selectable)
COMPONENT(Selectable)
Index: ps/trunk/source/simulation2/components/CCmpRangeOverlayRenderer.cpp
===================================================================
--- ps/trunk/source/simulation2/components/CCmpRangeOverlayRenderer.cpp
+++ ps/trunk/source/simulation2/components/CCmpRangeOverlayRenderer.cpp
@@ -0,0 +1,216 @@
+/* Copyright (C) 2017 Wildfire Games.
+ * This file is part of 0 A.D.
+ *
+ * 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
+ * the Free Software Foundation, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 0 A.D. is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with 0 A.D. If not, see .
+ */
+
+#include "precompiled.h"
+
+#include "ICmpRangeOverlayRenderer.h"
+
+#include "graphics/Overlay.h"
+#include "graphics/TextureManager.h"
+#include "renderer/Renderer.h"
+#include "simulation2/MessageTypes.h"
+#include "simulation2/components/ICmpPlayer.h"
+#include "simulation2/components/ICmpPlayerManager.h"
+#include "simulation2/components/ICmpPosition.h"
+#include "simulation2/helpers/Render.h"
+#include "simulation2/system/Component.h"
+
+class CCmpRangeOverlayRenderer : public ICmpRangeOverlayRenderer
+{
+public:
+ static void ClassInit(CComponentManager& componentManager)
+ {
+ componentManager.SubscribeToMessageType(MT_OwnershipChanged);
+ }
+
+ DEFAULT_COMPONENT_ALLOCATOR(RangeOverlayRenderer)
+
+ CCmpRangeOverlayRenderer() : m_RangeOverlayData()
+ {
+ m_Color = CColor(0, 0, 0, 0);
+ }
+
+ ~CCmpRangeOverlayRenderer()
+ {
+ for (const RangeOverlayData& rangeOverlay : m_RangeOverlayData)
+ delete rangeOverlay.second;
+ }
+
+ static std::string GetSchema()
+ {
+ return "";
+ }
+
+ virtual void Init(const CParamNode& UNUSED(paramNode))
+ {
+ m_EnabledInterpolate = false;
+ m_EnabledRenderSubmit = false;
+ m_Enabled = false;
+ UpdateMessageSubscriptions();
+ }
+
+ virtual void Deinit() { }
+
+ virtual void Serialize(ISerializer& UNUSED(serialize))
+ {
+ }
+
+ virtual void Deserialize(const CParamNode& paramNode, IDeserializer& UNUSED(deserialize))
+ {
+ Init(paramNode);
+ }
+
+ void ResetRangeOverlays()
+ {
+ for (const RangeOverlayData& rangeOverlay : m_RangeOverlayData)
+ delete rangeOverlay.second;
+ m_RangeOverlayData.clear();
+ UpdateMessageSubscriptions();
+ m_Enabled = false;
+ }
+
+ virtual void AddRangeOverlay(float radius, const std::string& texture, const std::string& textureMask, float thickness)
+ {
+ if (!CRenderer::IsInitialised())
+ return;
+
+ SOverlayDescriptor rangeOverlayDescriptor;
+ SOverlayTexturedLine* rangeOverlay = nullptr;
+ rangeOverlayDescriptor.m_Radius = radius;
+ rangeOverlayDescriptor.m_LineTexture = CStrIntern(TEXTUREBASEPATH + texture);
+ rangeOverlayDescriptor.m_LineTextureMask = CStrIntern(TEXTUREBASEPATH + textureMask);
+ rangeOverlayDescriptor.m_LineThickness = thickness;
+
+ m_RangeOverlayData.push_back({ rangeOverlayDescriptor, rangeOverlay });
+ m_Enabled = true;
+ UpdateMessageSubscriptions();
+ }
+
+ void HandleMessage(const CMessage& msg, bool UNUSED(global))
+ {
+ switch (msg.GetType())
+ {
+ case MT_Interpolate:
+ {
+ const CMessageInterpolate& msgData = static_cast (msg);
+
+ for (RangeOverlayData& rangeOverlay : m_RangeOverlayData)
+ {
+ delete rangeOverlay.second;
+ rangeOverlay.second = new SOverlayTexturedLine;
+ UpdateRangeOverlay(&rangeOverlay.first, *rangeOverlay.second, msgData.offset);
+ }
+
+ UpdateMessageSubscriptions();
+
+ break;
+ }
+ case MT_OwnershipChanged:
+ {
+ const CMessageOwnershipChanged& msgData = static_cast (msg);
+ if (msgData.to == INVALID_PLAYER)
+ break;
+
+ CmpPtr cmpPlayerManager(GetSystemEntity());
+ if (!cmpPlayerManager)
+ break;
+
+ CmpPtr cmpPlayer(GetSimContext(), cmpPlayerManager->GetPlayerByID(msgData.to));
+ if (!cmpPlayer)
+ break;
+
+ CColor color = cmpPlayer->GetColor();
+ m_Color = color;
+ break;
+ }
+ case MT_RenderSubmit:
+ {
+ const CMessageRenderSubmit& msgData = static_cast (msg);
+ RenderSubmit(msgData.collector);
+ break;
+ }
+ }
+ }
+
+ void UpdateMessageSubscriptions()
+ {
+ bool needInterpolate = false;
+ bool needRenderSubmit = false;
+
+ if (m_Enabled)
+ {
+ needInterpolate = true;
+ needRenderSubmit = true;
+ }
+
+ if (needInterpolate != m_EnabledInterpolate)
+ {
+ GetSimContext().GetComponentManager().DynamicSubscriptionNonsync(MT_Interpolate, this, needInterpolate);
+ m_EnabledInterpolate = needInterpolate;
+ m_Enabled = needInterpolate;
+ }
+
+ if (needRenderSubmit != m_EnabledRenderSubmit)
+ {
+ GetSimContext().GetComponentManager().DynamicSubscriptionNonsync(MT_RenderSubmit, this, needRenderSubmit);
+ m_EnabledRenderSubmit = needRenderSubmit;
+ m_Enabled = needRenderSubmit;
+ }
+ }
+
+ void RenderSubmit(SceneCollector& collector)
+ {
+ if (!m_RangeOverlayData.size())
+ return;
+
+ for (const RangeOverlayData& rangeOverlay : m_RangeOverlayData)
+ if (rangeOverlay.second)
+ collector.Submit(rangeOverlay.second);
+ }
+
+private:
+ void UpdateRangeOverlay(const SOverlayDescriptor* overlayDescriptor, SOverlayTexturedLine& overlay, float frameOffset)
+ {
+ if (!CRenderer::IsInitialised())
+ return;
+
+ CmpPtr cmpPosition(GetEntityHandle());
+ if (!cmpPosition || !cmpPosition->IsInWorld())
+ return;
+
+ float rotY;
+ CVector2D origin;
+ cmpPosition->GetInterpolatedPosition2D(frameOffset, origin.X, origin.Y, rotY);
+
+ overlay.m_SimContext = &GetSimContext();
+ overlay.m_Color = m_Color;
+ overlay.CreateOverlayTexture(overlayDescriptor);
+
+ SimRender::ConstructTexturedLineCircle(overlay, origin, overlayDescriptor->m_Radius);
+ }
+
+ bool m_EnabledInterpolate;
+ bool m_EnabledRenderSubmit;
+ bool m_Enabled;
+
+ const char* TEXTUREBASEPATH = "art/textures/selection/";
+ typedef std::pair RangeOverlayData;
+ std::vector m_RangeOverlayData;
+ CColor m_Color;
+};
+
+REGISTER_COMPONENT_TYPE(RangeOverlayRenderer)
Index: ps/trunk/source/simulation2/components/CCmpSelectable.cpp
===================================================================
--- ps/trunk/source/simulation2/components/CCmpSelectable.cpp
+++ ps/trunk/source/simulation2/components/CCmpSelectable.cpp
@@ -65,7 +65,7 @@
CCmpSelectable()
: m_DebugBoundingBoxOverlay(NULL), m_DebugSelectionBoxOverlay(NULL),
- m_BuildingOverlay(NULL), m_UnitOverlay(NULL), m_RangeOverlayData(),
+ m_BuildingOverlay(NULL), m_UnitOverlay(NULL),
m_FadeBaselineAlpha(0.f), m_FadeDeltaAlpha(0.f), m_FadeProgress(0.f),
m_Selected(false), m_Cached(false), m_Visible(false)
{
@@ -78,8 +78,6 @@
delete m_DebugSelectionBoxOverlay;
delete m_BuildingOverlay;
delete m_UnitOverlay;
- for (RangeOverlayData& rangeOverlay : m_RangeOverlayData)
- delete rangeOverlay.second;
}
static std::string GetSchema()
@@ -194,22 +192,6 @@
SetSelectionHighlightAlpha(color.a);
}
- virtual void AddRangeOverlay(float radius, const std::string& texture, const std::string& textureMask, float thickness)
- {
- if (!CRenderer::IsInitialised())
- return;
-
- SOverlayDescriptor rangeOverlayDescriptor;
- SOverlayTexturedLine* rangeOverlay = nullptr;
-
- rangeOverlayDescriptor.m_Radius = radius;
- rangeOverlayDescriptor.m_LineTexture = CStrIntern(TEXTUREBASEPATH + texture);
- rangeOverlayDescriptor.m_LineTextureMask = CStrIntern(TEXTUREBASEPATH + textureMask);
- rangeOverlayDescriptor.m_LineThickness = thickness;
-
- m_RangeOverlayData.push_back({rangeOverlayDescriptor, rangeOverlay});
- }
-
virtual void SetSelectionHighlightAlpha(float alpha)
{
alpha = std::max(m_AlphaMin, alpha);
@@ -238,7 +220,7 @@
/**
* Draw a textured line overlay. The selection overlays for structures are based solely on footprint shape.
*/
- void UpdateTexturedLineOverlay(const SOverlayDescriptor* overlayDescriptor, SOverlayTexturedLine& overlay, float frameOffset, bool buildingOverlay);
+ void UpdateTexturedLineOverlay(const SOverlayDescriptor* overlayDescriptor, SOverlayTexturedLine& overlay, float frameOffset);
/**
* Called from the interpolation handler; responsible for ensuring the dynamic overlay (provided we're
@@ -260,11 +242,6 @@
void UpdateMessageSubscriptions();
/**
- * Delete all range overlays.
- */
- void ResetRangeOverlays();
-
- /**
* Set the color of the current owner.
*/
void UpdatePlayerColor();
@@ -274,10 +251,6 @@
SOverlayTexturedLine* m_BuildingOverlay;
SOverlayQuad* m_UnitOverlay;
- // Holds the data for all range overlays
- typedef std::pair RangeOverlayData;
- std::vector m_RangeOverlayData;
-
SOverlayLine* m_DebugBoundingBoxOverlay;
SOverlayLine* m_DebugSelectionBoxOverlay;
@@ -345,17 +318,8 @@
// update dynamic overlay only when visible
if (m_Color.a > 0)
- {
UpdateDynamicOverlay(msgData.offset);
- for (RangeOverlayData& rangeOverlay : m_RangeOverlayData)
- {
- delete rangeOverlay.second;
- rangeOverlay.second = new SOverlayTexturedLine;
- UpdateTexturedLineOverlay(&rangeOverlay.first, *rangeOverlay.second, msgData.offset, false);
- }
- }
-
UpdateMessageSubscriptions();
break;
@@ -439,15 +403,6 @@
SetSelectionHighlight(color, m_Selected);
}
-void CCmpSelectable::ResetRangeOverlays()
-{
- for (RangeOverlayData& rangeOverlay : m_RangeOverlayData)
- delete rangeOverlay.second;
- m_RangeOverlayData.clear();
-
- UpdateMessageSubscriptions();
-}
-
void CCmpSelectable::UpdateMessageSubscriptions()
{
bool needInterpolate = false;
@@ -477,7 +432,7 @@
SAFE_DELETE(m_BuildingOverlay);
}
-void CCmpSelectable::UpdateTexturedLineOverlay(const SOverlayDescriptor* overlayDescriptor, SOverlayTexturedLine& overlay, float frameOffset, bool buildingOverlay)
+void CCmpSelectable::UpdateTexturedLineOverlay(const SOverlayDescriptor* overlayDescriptor, SOverlayTexturedLine& overlay, float frameOffset)
{
if (!CRenderer::IsInitialised())
return;
@@ -499,10 +454,10 @@
overlay.m_Color = m_Color;
overlay.CreateOverlayTexture(overlayDescriptor);
- if (buildingOverlay && fpShape == ICmpFootprint::SQUARE)
+ if (fpShape == ICmpFootprint::SQUARE)
SimRender::ConstructTexturedLineBox(overlay, origin, cmpPosition->GetRotation(), fpSize0_fixed.ToFloat(), fpSize1_fixed.ToFloat());
else
- SimRender::ConstructTexturedLineCircle(overlay, origin, buildingOverlay ? fpSize0_fixed.ToFloat() : overlayDescriptor->m_Radius);
+ SimRender::ConstructTexturedLineCircle(overlay, origin, fpSize0_fixed.ToFloat());
}
void CCmpSelectable::UpdateDynamicOverlay(float frameOffset)
@@ -615,7 +570,7 @@
// (see InvalidateStaticOverlay). Since they are expected to change rarely (if ever) during
// normal gameplay, this saves us doing all the work below on each frame.
m_BuildingOverlay = new SOverlayTexturedLine;
- UpdateTexturedLineOverlay(&m_OverlayDescriptor, *m_BuildingOverlay, 0, true);
+ UpdateTexturedLineOverlay(&m_OverlayDescriptor, *m_BuildingOverlay, 0);
}
m_BuildingOverlay->m_Color = m_Color; // done separately so alpha changes don't require a full update call
collector.Submit(m_BuildingOverlay);
@@ -630,10 +585,6 @@
default:
break;
}
-
- for (const RangeOverlayData& rangeOverlay : m_RangeOverlayData)
- if (rangeOverlay.second)
- collector.Submit(rangeOverlay.second);
}
// Render bounding box debug overlays if we have a positive target alpha value. This ensures
Index: ps/trunk/source/simulation2/components/ICmpRangeOverlayRenderer.h
===================================================================
--- ps/trunk/source/simulation2/components/ICmpRangeOverlayRenderer.h
+++ ps/trunk/source/simulation2/components/ICmpRangeOverlayRenderer.h
@@ -0,0 +1,40 @@
+/* Copyright (C) 2017 Wildfire Games.
+ * This file is part of 0 A.D.
+ *
+ * 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
+ * the Free Software Foundation, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 0 A.D. is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with 0 A.D. If not, see .
+ */
+
+#ifndef INCLUDED_ICMPRANGEOVERLAYRENDERER
+#define INCLUDED_ICMPRANGEOVERLAYRENDERER
+
+#include "ps/CStrIntern.h"
+#include "simulation2/system/Interface.h"
+
+class ICmpRangeOverlayRenderer : public IComponent
+{
+public:
+ /**
+ * Add a range overlay to this entity, for example for an aura or attack.
+ */
+ virtual void AddRangeOverlay(float radius, const std::string& texture, const std::string& textureMask, float thickness) = 0;
+
+ /**
+ * Delete all range overlays.
+ */
+ virtual void ResetRangeOverlays() = 0;
+
+ DECLARE_INTERFACE_TYPE(RangeOverlayRenderer)
+};
+
+#endif // INCLUDED_ICMPRANGEOVERLAYRENDERER
Index: ps/trunk/source/simulation2/components/ICmpRangeOverlayRenderer.cpp
===================================================================
--- ps/trunk/source/simulation2/components/ICmpRangeOverlayRenderer.cpp
+++ ps/trunk/source/simulation2/components/ICmpRangeOverlayRenderer.cpp
@@ -0,0 +1,26 @@
+/* Copyright (C) 2017 Wildfire Games.
+ * This file is part of 0 A.D.
+ *
+ * 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
+ * the Free Software Foundation, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 0 A.D. is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with 0 A.D. If not, see .
+ */
+
+#include "precompiled.h"
+
+#include "ICmpRangeOverlayRenderer.h"
+#include "simulation2/system/InterfaceScripted.h"
+
+BEGIN_INTERFACE_WRAPPER(RangeOverlayRenderer)
+DEFINE_INTERFACE_METHOD_4("AddRangeOverlay", void, ICmpRangeOverlayRenderer, AddRangeOverlay, float, std::string, std::string, float)
+DEFINE_INTERFACE_METHOD_0("ResetRangeOverlays", void, ICmpRangeOverlayRenderer, ResetRangeOverlays)
+END_INTERFACE_WRAPPER(RangeOverlayRenderer)
Index: ps/trunk/source/simulation2/components/ICmpSelectable.h
===================================================================
--- ps/trunk/source/simulation2/components/ICmpSelectable.h
+++ ps/trunk/source/simulation2/components/ICmpSelectable.h
@@ -39,16 +39,6 @@
virtual void SetSelectionHighlight(const CColor& color, bool selected) = 0;
/**
- * Add a range overlay to this entity, for example for an aura or attack.
- */
- virtual void AddRangeOverlay(float radius, const std::string& texture, const std::string& textureMask, float thickness) = 0;
-
- /**
- * Delete all range overlays.
- */
- virtual void ResetRangeOverlays() = 0;
-
- /**
* Enables or disables rendering of an entity's selectable.
* @param visible Whether the selectable should be visible.
*/
Index: ps/trunk/source/simulation2/components/ICmpSelectable.cpp
===================================================================
--- ps/trunk/source/simulation2/components/ICmpSelectable.cpp
+++ ps/trunk/source/simulation2/components/ICmpSelectable.cpp
@@ -25,8 +25,6 @@
BEGIN_INTERFACE_WRAPPER(Selectable)
DEFINE_INTERFACE_METHOD_2("SetSelectionHighlight", void, ICmpSelectable, SetSelectionHighlight, CColor, bool)
-DEFINE_INTERFACE_METHOD_4("AddRangeOverlay", void, ICmpSelectable, AddRangeOverlay, float, std::string, std::string, float)
-DEFINE_INTERFACE_METHOD_0("ResetRangeOverlays", void, ICmpSelectable, ResetRangeOverlays)
END_INTERFACE_WRAPPER(Selectable)
bool ICmpSelectable::ms_EnableDebugOverlays = false;