Browse Source

Fix an MSVC compile bug and some minor work on the scene

Panagiotis Christopoulos Charitos 5 years ago
parent
commit
0ce447278c

+ 4 - 0
anki/renderer/RenderQueue.h

@@ -384,6 +384,10 @@ public:
 	WeakArray<GenericGpuComputeJobQueueElement> m_genericGpuComputeJobs;
 	WeakArray<RayTracingInstanceQueueElement> m_rayTracingInstances;
 
+	/// Contains the ray tracing elements. The rest of the members are unused. It's separate to avoid multithreading
+	/// bugs.
+	RenderQueue* m_rayTracingQueue = nullptr;
+
 	/// Applies only if the RenderQueue holds shadow casters. It's the max timesamp of all shadow casters
 	Timestamp m_shadowRenderablesLastUpdateTimestamp = 0;
 

+ 32 - 19
anki/scene/SceneNode.h

@@ -137,7 +137,7 @@ public:
 		auto end = m_components.getEnd();
 		for(; !err && it != end; ++it)
 		{
-			if(it->m_type == TComponent::CLASS_TYPE)
+			if(it->getComponentType() == TComponent::CLASS_TYPE)
 			{
 				const SceneComponent* comp = *it;
 				err = func(static_cast<const TComponent&>(*comp));
@@ -156,7 +156,7 @@ public:
 		auto end = m_components.getEnd();
 		for(; !err && it != end; ++it)
 		{
-			if(it->m_type == TComponent::CLASS_TYPE)
+			if(it->getComponentType() == TComponent::CLASS_TYPE)
 			{
 				SceneComponent* comp = *it;
 				err = func(static_cast<TComponent&>(*comp));
@@ -172,7 +172,7 @@ public:
 	{
 		for(const ComponentsArrayElement& el : m_components)
 		{
-			if(el.m_type == TComponent::CLASS_TYPE)
+			if(el.getComponentType() == TComponent::CLASS_TYPE)
 			{
 				const SceneComponent* comp = el;
 				return static_cast<const TComponent*>(comp);
@@ -213,7 +213,7 @@ public:
 		I32 inth = I32(nth);
 		for(const ComponentsArrayElement& el : m_components)
 		{
-			if(el.m_type == TComponent::CLASS_TYPE && inth-- == 0)
+			if(el.getComponentType() == TComponent::CLASS_TYPE && inth-- == 0)
 			{
 				const SceneComponent* comp = el;
 				return static_cast<const TComponent*>(comp);
@@ -234,7 +234,7 @@ public:
 	template<typename TComponent>
 	TComponent& getComponentAt(U32 idx)
 	{
-		ANKI_ASSERT(m_components[idx].m_type == TComponent::CLASS_TYPE);
+		ANKI_ASSERT(m_components[idx].getComponentType() == TComponent::CLASS_TYPE);
 		SceneComponent* c = m_components[idx];
 		return *static_cast<TComponent*>(c);
 	}
@@ -243,7 +243,7 @@ public:
 	template<typename TComponent>
 	const TComponent& getComponentAt(U32 idx) const
 	{
-		ANKI_ASSERT(m_components[idx].m_type == TComponent::CLASS_TYPE);
+		ANKI_ASSERT(m_components[idx].getComponentType() == TComponent::CLASS_TYPE);
 		const SceneComponent* c = m_components[idx];
 		return *static_cast<const TComponent*>(c);
 	}
@@ -271,47 +271,60 @@ private:
 	class ComponentsArrayElement
 	{
 	public:
-		SceneComponentType m_type : 8;
-		PtrSize m_ptr : 56;
+		PtrSize m_combo; ///< Encodes the SceneComponentType in the high 8bits and the SceneComponent* to the remaining.
 
 		ComponentsArrayElement(SceneComponent* comp)
-			: m_type(comp->getType())
-			, m_ptr(ptrToNumber(comp))
 		{
-			ANKI_ASSERT((ptrToNumber(comp) & (PtrSize(0xFF) << PtrSize(56))) == 0);
+			set(comp);
 		}
 
 		ComponentsArrayElement(const ComponentsArrayElement& b)
-			: m_type(b.m_type)
-			, m_ptr(b.m_ptr)
+			: m_combo(b.m_combo)
 		{
 		}
 
 		ComponentsArrayElement& operator=(const ComponentsArrayElement& b)
 		{
-			m_type = b.m_type;
-			m_ptr = b.m_ptr;
+			m_combo = b.m_combo;
 			return *this;
 		}
 
 		operator SceneComponent*()
 		{
-			return numberToPtr<SceneComponent*>(m_ptr);
+			return getPtr();
 		}
 
 		operator const SceneComponent*() const
 		{
-			return numberToPtr<const SceneComponent*>(m_ptr);
+			return getPtr();
 		}
 
 		const SceneComponent* operator->() const
 		{
-			return numberToPtr<const SceneComponent*>(m_ptr);
+			return getPtr();
 		}
 
 		SceneComponent* operator->()
 		{
-			return numberToPtr<SceneComponent*>(m_ptr);
+			return getPtr();
+		}
+
+		SceneComponentType getComponentType() const
+		{
+			return SceneComponentType(m_combo & 0xFF);
+		}
+
+	private:
+		void set(SceneComponent* comp)
+		{
+			m_combo = ptrToNumber(comp) << 8;
+			m_combo |= PtrSize(comp->getType());
+			ANKI_ASSERT(getPtr() == comp);
+		}
+
+		SceneComponent* getPtr() const
+		{
+			return numberToPtr<SceneComponent*>(m_combo >> 8);
 		}
 	};
 

+ 34 - 23
anki/scene/Visibility.cpp

@@ -51,7 +51,7 @@ void VisibilityContext::submitNewWork(const FrustumComponent& frc, RenderQueue&
 	ANKI_TRACE_SCOPED_EVENT(SCENE_VIS_SUBMIT_WORK);
 
 	// Check enabled and make sure that the results are null (this can happen on multiple on circular viewing)
-	if(ANKI_UNLIKELY(!frc.anyVisibilityTestEnabled()))
+	if(ANKI_UNLIKELY(frc.getEnabledVisibilityTests() == FrustumComponentVisibilityTestFlag::NONE))
 	{
 		return;
 	}
@@ -106,7 +106,7 @@ void VisibilityContext::submitNewWork(const FrustumComponent& frc, RenderQueue&
 
 	// Software rasterizer task
 	ThreadHiveSemaphore* prepareRasterizerSem = nullptr;
-	if(frc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::OCCLUDERS) && frc.hasCoverageBuffer())
+	if(!!(frc.getEnabledVisibilityTests() & FrustumComponentVisibilityTestFlag::OCCLUDERS) && frc.hasCoverageBuffer())
 	{
 		// Gather triangles task
 		ThreadHiveTask fillDepthTask =
@@ -118,7 +118,7 @@ void VisibilityContext::submitNewWork(const FrustumComponent& frc, RenderQueue&
 		prepareRasterizerSem = fillDepthTask.m_signalSemaphore;
 	}
 
-	if(frc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::OCCLUDERS))
+	if(!!(frc.getEnabledVisibilityTests() & FrustumComponentVisibilityTestFlag::OCCLUDERS))
 	{
 		rqueue.m_fillCoverageBufferCallback = FrustumComponent::fillCoverageBufferCallback;
 		rqueue.m_fillCoverageBufferCallbackUserData = static_cast<void*>(const_cast<FrustumComponent*>(&frc));
@@ -228,7 +228,8 @@ void VisibilityTestTask::test(ThreadHive& hive, U32 taskId)
 	ANKI_TRACE_SCOPED_EVENT(SCENE_VIS_TEST);
 
 	const FrustumComponent& testedFrc = *m_frcCtx->m_frc;
-	ANKI_ASSERT(testedFrc.anyVisibilityTestEnabled());
+	const FrustumComponentVisibilityTestFlag enabledVisibilityTests = testedFrc.getEnabledVisibilityTests();
+	ANKI_ASSERT(enabledVisibilityTests != FrustumComponentVisibilityTestFlag::NONE);
 
 	const SceneNode& testedNode = testedFrc.getSceneNode();
 	auto alloc = m_frcCtx->m_visCtx->m_scene->getFrameAllocator();
@@ -237,33 +238,31 @@ void VisibilityTestTask::test(ThreadHive& hive, U32 taskId)
 	timestamp = testedNode.getComponentMaxTimestamp();
 
 	const Bool wantsRenderComponents =
-		testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::RENDER_COMPONENTS);
+		!!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::RENDER_COMPONENTS);
 
-	const Bool wantsLightComponents =
-		testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::LIGHT_COMPONENTS);
+	const Bool wantsLightComponents = !!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::LIGHT_COMPONENTS);
 
 	const Bool wantsFlareComponents =
-		testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::LENS_FLARE_COMPONENTS);
+		!!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::LENS_FLARE_COMPONENTS);
 
-	const Bool wantsShadowCasters =
-		testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::SHADOW_CASTERS);
+	const Bool wantsShadowCasters = !!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::SHADOW_CASTERS);
 
 	const Bool wantsReflectionProbes =
-		testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::REFLECTION_PROBES);
+		!!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::REFLECTION_PROBES);
 
-	const Bool wantsDecals = testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::DECALS);
+	const Bool wantsDecals = !!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::DECALS);
 
 	const Bool wantsFogDensityComponents =
-		testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::FOG_DENSITY_COMPONENTS);
+		!!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::FOG_DENSITY_COMPONENTS);
 
 	const Bool wantsGiProbeCoponents =
-		testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::GLOBAL_ILLUMINATION_PROBES);
+		!!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::GLOBAL_ILLUMINATION_PROBES);
 
-	const Bool wantsEarlyZ = testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::EARLY_Z)
+	const Bool wantsEarlyZ = !!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::EARLY_Z)
 							 && m_frcCtx->m_visCtx->m_earlyZDist > 0.0f;
 
 	const Bool wantsGenericComputeJobCoponents =
-		testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::GENERIC_COMPUTE_JOB_COMPONENTS);
+		!!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::GENERIC_COMPUTE_JOB_COMPONENTS);
 
 	// Iterate
 	RenderQueueView& result = m_frcCtx->m_queueViews[taskId];
@@ -415,7 +414,7 @@ void VisibilityTestTask::test(ThreadHive& hive, U32 taskId)
 				lc->setupPointLightQueueElement(*el);
 
 				if(castsShadow
-				   && testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::POINT_LIGHT_SHADOWS_ENABLED))
+				   && !!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::POINT_LIGHT_SHADOWS_ENABLED))
 				{
 					RenderQueue* a = alloc.newArray<RenderQueue>(6);
 					nextQueues = WeakArray<RenderQueue>(a, 6);
@@ -443,7 +442,7 @@ void VisibilityTestTask::test(ThreadHive& hive, U32 taskId)
 				lc->setupSpotLightQueueElement(*el);
 
 				if(castsShadow
-				   && testedFrc.visibilityTestsEnabled(FrustumComponentVisibilityTestFlag::SPOT_LIGHT_SHADOWS_ENABLED))
+				   && !!(enabledVisibilityTests & FrustumComponentVisibilityTestFlag::SPOT_LIGHT_SHADOWS_ENABLED))
 				{
 					RenderQueue* a = alloc.newInstance<RenderQueue>();
 					nextQueues = WeakArray<RenderQueue>(a, 1);
@@ -468,15 +467,15 @@ void VisibilityTestTask::test(ThreadHive& hive, U32 taskId)
 				{
 					cascadeCount = 0;
 				}
-				else if(testedFrc.visibilityTestsEnabled(
-							FrustumComponentVisibilityTestFlag::DIRECTIONAL_LIGHT_SHADOWS_1_CASCADE))
+				else if(!!(enabledVisibilityTests
+						   & FrustumComponentVisibilityTestFlag::DIRECTIONAL_LIGHT_SHADOWS_1_CASCADE))
 				{
 					cascadeCount = 1;
 				}
 				else
 				{
-					ANKI_ASSERT(testedFrc.visibilityTestsEnabled(
-						FrustumComponentVisibilityTestFlag::DIRECTIONAL_LIGHT_SHADOWS_ALL_CASCADES));
+					ANKI_ASSERT(!!(enabledVisibilityTests
+								   & FrustumComponentVisibilityTestFlag::DIRECTIONAL_LIGHT_SHADOWS_ALL_CASCADES));
 					cascadeCount = MAX_SHADOW_CASCADES;
 				}
 				ANKI_ASSERT(cascadeCount <= MAX_SHADOW_CASCADES);
@@ -823,7 +822,19 @@ void SceneGraph::doVisibilityTests(SceneNode& fsn, SceneGraph& scene, RenderQueu
 	VisibilityContext ctx;
 	ctx.m_scene = &scene;
 	ctx.m_earlyZDist = scene.getConfig().m_earlyZDistance;
-	ctx.submitNewWork(fsn.getFirstComponentOfType<FrustumComponent>(), rqueue, hive);
+	const FrustumComponent& mainFrustum = fsn.getFirstComponentOfType<FrustumComponent>();
+	ctx.submitNewWork(mainFrustum, rqueue, hive);
+
+	const FrustumComponent* extendedFrustum = fsn.tryGetNthComponentOfType<FrustumComponent>(1);
+	if(extendedFrustum)
+	{
+		// This is the frustum for RT.
+		ANKI_ASSERT(
+			!(extendedFrustum->getEnabledVisibilityTests() & ~FrustumComponentVisibilityTestFlag::ALL_RAY_TRACING));
+
+		rqueue.m_rayTracingQueue = scene.getFrameAllocator().newInstance<RenderQueue>();
+		ctx.submitNewWork(*extendedFrustum, *rqueue.m_rayTracingQueue, hive);
+	}
 
 	hive.waitAllTasks();
 	ctx.m_testedFrcs.destroy(scene.getFrameAllocator());

+ 5 - 8
anki/scene/components/FrustumComponent.h

@@ -51,7 +51,9 @@ enum class FrustumComponentVisibilityTestFlag : U32
 		  | RAY_TRACING_REFLECTIONS | RAY_TRACING_PATH_TRACING,
 
 	ALL_SHADOWS_ENABLED =
-		POINT_LIGHT_SHADOWS_ENABLED | SPOT_LIGHT_SHADOWS_ENABLED | DIRECTIONAL_LIGHT_SHADOWS_ALL_CASCADES
+		POINT_LIGHT_SHADOWS_ENABLED | SPOT_LIGHT_SHADOWS_ENABLED | DIRECTIONAL_LIGHT_SHADOWS_ALL_CASCADES,
+
+	ALL_RAY_TRACING = RAY_TRACING_SHADOWS | RAY_TRACING_GI | RAY_TRACING_REFLECTIONS | RAY_TRACING_PATH_TRACING
 };
 ANKI_ENUM_ALLOW_NUMERIC_OPERATIONS(FrustumComponentVisibilityTestFlag)
 
@@ -209,14 +211,9 @@ public:
 
 	void setEnabledVisibilityTests(FrustumComponentVisibilityTestFlag bits);
 
-	Bool visibilityTestsEnabled(FrustumComponentVisibilityTestFlag bits) const
-	{
-		return !!(m_flags & bits);
-	}
-
-	Bool anyVisibilityTestEnabled() const
+	FrustumComponentVisibilityTestFlag getEnabledVisibilityTests() const
 	{
-		return !!(m_flags & FrustumComponentVisibilityTestFlag::ALL);
+		return m_flags;
 	}
 
 	/// The type is FillCoverageBufferCallback.