Selaa lähdekoodia

Use ListAllocFree in SceneNode and some bug fixes

Panagiotis Christopoulos Charitos 10 vuotta sitten
vanhempi
sitoutus
1816a994f6

+ 5 - 7
include/anki/scene/SceneGraph.h

@@ -3,8 +3,7 @@
 // Code licensed under the BSD License.
 // http://www.anki3d.org/LICENSE
 
-#ifndef ANKI_SCENE_SCENE_GRAPH_H
-#define ANKI_SCENE_SCENE_GRAPH_H
+#pragma once
 
 #include "anki/scene/Common.h"
 #include "anki/scene/SceneNode.h"
@@ -127,9 +126,9 @@ public:
 	template<typename Func>
 	ANKI_USE_RESULT Error iterateSceneNodes(Func func)
 	{
-		for(SceneNode* psn : m_nodes)
+		for(SceneNode& psn : m_nodes)
 		{
-			Error err = func(*psn);
+			Error err = func(psn);
 			if(err)
 			{
 				return err;
@@ -204,7 +203,7 @@ private:
 	SceneAllocator<U8> m_alloc;
 	SceneFrameAllocator<U8> m_frameAlloc;
 
-	List<SceneNode*> m_nodes;
+	ListAllocFree<SceneNode> m_nodes;
 	U32 m_nodesCount = 0;
 	//SceneDictionary<SceneNode*> m_dict;
 
@@ -276,7 +275,7 @@ Error SceneGraph::iterateSceneNodes(PtrSize begin, PtrSize end, Func func)
 	while(count-- != 0)
 	{
 		ANKI_ASSERT(it != m_nodes.getEnd());
-		Error err = func(*(*it));
+		Error err = func(*it);
 		if(err)
 		{
 			return err;
@@ -291,4 +290,3 @@ Error SceneGraph::iterateSceneNodes(PtrSize begin, PtrSize end, Func func)
 
 } // end namespace anki
 
-#endif

+ 3 - 1
include/anki/scene/SceneNode.h

@@ -9,6 +9,7 @@
 #include "anki/util/Hierarchy.h"
 #include "anki/util/Rtti.h"
 #include "anki/util/Bitset.h"
+#include "anki/util/List.h"
 #include "anki/util/Enum.h"
 #include "anki/scene/SceneComponent.h"
 
@@ -21,7 +22,8 @@ class ResourceManager;
 /// @{
 
 /// Interface class backbone of scene
-class SceneNode: public Hierarchy<SceneNode>
+class SceneNode: public Hierarchy<SceneNode>,
+	public ListAllocFreeEnabled<SceneNode>
 {
 public:
 	using Base = Hierarchy<SceneNode>;

+ 1 - 1
include/anki/util/File.h

@@ -137,7 +137,7 @@ private:
 	void* m_file = nullptr; ///< A native file type
 	Type m_type = Type::NONE;
 	OpenFlag m_flags = OpenFlag::NONE; ///< All the flags. Set on open
-	U16 m_size = 0;
+	U32 m_size = 0;
 
 	/// Get the current machine's endianness
 	static OpenFlag getMachineEndianness();

+ 16 - 8
include/anki/util/List.h

@@ -352,7 +352,7 @@ public:
 	/// @see List::destroy
 	~List()
 	{
-		ANKI_ASSERT(!Base::isCreated() && "Requires manual destruction");
+		ANKI_ASSERT(Base::isEmpty() && "Requires manual destruction");
 	}
 
 	/// Move.
@@ -450,7 +450,7 @@ public:
 private:
 	void move(List& b)
 	{
-		ANKI_ASSERT(!Base::isCreated() && "Requires manual destruction");
+		ANKI_ASSERT(Base::isEmpty() && "Requires manual destruction");
 		Base::move(b);
 	}
 };
@@ -551,10 +551,10 @@ template<typename TClass>
 class ListAllocFreeEnabled
 {
 	template<typename, typename, typename, typename>
-	friend class ListIterator;
+	friend class detail::ListIterator;
 
 	template<typename, typename>
-	friend class ListBase;
+	friend class detail::ListBase;
 
 	template<typename>
 	friend class List;
@@ -562,13 +562,15 @@ class ListAllocFreeEnabled
 	template<typename>
 	friend class ListAllocFree;
 
+	friend TClass;
+
 private:
-	TClass* m_left;
-	TClass* m_right;
+	TClass* m_prev;
+	TClass* m_next;
 
 	ListAllocFreeEnabled()
-		: m_left(nullptr)
-		, m_right(nullptr)
+		: m_prev(nullptr)
+		, m_next(nullptr)
 	{}
 
 	TClass& getValue()
@@ -650,6 +652,12 @@ public:
 	{
 		Base::removeNode(pos.m_node);
 	}
+
+	/// Erase an element.
+	void erase(T* x)
+	{
+		Base::removeNode(x);
+	}
 };
 /// @}
 

+ 4 - 0
include/anki/util/List.inl.h

@@ -251,6 +251,10 @@ template<typename T, typename TNode>
 void ListBase<T, TNode>::removeNode(TNode* node)
 {
 	ANKI_ASSERT(node);
+	if(node != m_head)
+	{
+		ANKI_ASSERT(!(node->m_prev == nullptr && node->m_next == nullptr));
+	}
 
 	if(node == m_tail)
 	{

+ 10 - 21
src/scene/SceneGraph.cpp

@@ -158,7 +158,7 @@ Error SceneGraph::registerNode(SceneNode* node)
 {
 	ANKI_ASSERT(node);
 
-	// Add to dict if it has name
+	// Add to dict if it has a name
 	if(node->getName())
 	{
 		if(tryFindSceneNode(node->getName()))
@@ -171,7 +171,7 @@ Error SceneGraph::registerNode(SceneNode* node)
 	}
 
 	// Add to vector
-	m_nodes.pushBack(m_alloc, node);
+	m_nodes.pushBack(node);
 	++m_nodesCount;
 
 	return ErrorCode::NONE;
@@ -180,19 +180,8 @@ Error SceneGraph::registerNode(SceneNode* node)
 //==============================================================================
 void SceneGraph::unregisterNode(SceneNode* node)
 {
-	// Remove from vector
-	auto it = m_nodes.begin();
-	for(; it != m_nodes.end(); ++it)
-	{
-		if((*it) == node)
-		{
-			break;
-		}
-	}
-
-	ANKI_ASSERT(it != m_nodes.end());
-	m_nodes.erase(m_alloc, it);
-
+	// Remove from the graph
+	m_nodes.erase(node);
 	--m_nodesCount;
 
 	// Remove from dict
@@ -221,13 +210,13 @@ SceneNode* SceneGraph::tryFindSceneNode(const CString& name)
 	auto it = m_nodes.getBegin();
 	for(; it != m_nodes.getEnd(); ++it)
 	{
-		if((*it)->getName() == name)
+		if((*it).getName() == name)
 		{
 			break;
 		}
 	}
 
-	return (it == m_nodes.getEnd()) ? nullptr : (*it);
+	return (it == m_nodes.getEnd()) ? nullptr : &(*it);
 }
 
 //==============================================================================
@@ -242,13 +231,13 @@ void SceneGraph::deleteNodesMarkedForDeletion()
 		auto end = m_nodes.end();
 		for(; it != end; ++it)
 		{
-			SceneNode* node = *it;
+			SceneNode& node = *it;
 
-			if(node->getMarkedForDeletion())
+			if(node.getMarkedForDeletion())
 			{
 				// Delete node
-				unregisterNode(node);
-				m_alloc.deleteInstance(node);
+				unregisterNode(&node);
+				m_alloc.deleteInstance(&node);
 				m_objectsMarkedForDeletionCount.fetchSub(1);
 				found = true;
 				break;

+ 3 - 3
src/util/File.cpp

@@ -154,10 +154,10 @@ Error File::openCFile(const CString& filename, OpenFlag flags)
 	}
 
 	// Get file size
-	if(!err)
+	if(((flags & OpenFlag::READ) != OpenFlag::NONE) && !err)
 	{
 		fseek(ANKI_CFILE, 0, SEEK_END);
-		I size = ftell(ANKI_CFILE);
+		I64 size = ftell(ANKI_CFILE);
 		if(size < 1)
 		{
 			ANKI_LOGE("ftell() failed");
@@ -166,7 +166,7 @@ Error File::openCFile(const CString& filename, OpenFlag flags)
 		else
 		{
 			m_size = size;
-			fseek(ANKI_CFILE, 0, SEEK_SET);
+			rewind(ANKI_CFILE);
 		}
 	}