diff options
Diffstat (limited to 'src/ChunkSender.h')
-rw-r--r-- | src/ChunkSender.h | 103 |
1 files changed, 30 insertions, 73 deletions
diff --git a/src/ChunkSender.h b/src/ChunkSender.h index 8b187c5f9..b0c48b92b 100644 --- a/src/ChunkSender.h +++ b/src/ChunkSender.h @@ -29,6 +29,9 @@ Note that it may be called by world's BroadcastToChunk() if the client is still #include "ChunkDef.h" #include "ChunkDataCallback.h" +#include <unordered_set> +#include <unordered_map> + @@ -47,115 +50,70 @@ class cChunkSender; -/// Callback that can be used to notify chunk sender upon another chunkcoord notification -class cNotifyChunkSender : - public cChunkCoordCallback -{ - virtual void Call(int a_ChunkX, int a_ChunkZ) override; - - cChunkSender * m_ChunkSender; -public: - cNotifyChunkSender(cChunkSender * a_ChunkSender) : m_ChunkSender(a_ChunkSender) {} - - void SetChunkSender(cChunkSender * a_ChunkSender) - { - m_ChunkSender = a_ChunkSender; - } -} ; - - - - - class cChunkSender: public cIsThread, public cChunkDataSeparateCollector { typedef cIsThread super; public: - cChunkSender(void); + cChunkSender(cWorld & a_World); ~cChunkSender(); enum eChunkPriority { E_CHUNK_PRIORITY_HIGH = 0, - E_CHUNK_PRIORITY_MEDIUM = 1, - E_CHUNK_PRIORITY_LOW = 2, + PRIORITY_BROADCAST, + E_CHUNK_PRIORITY_MEDIUM, + E_CHUNK_PRIORITY_LOW, + }; - bool Start(cWorld * a_World); + bool Start(); void Stop(void); - /// Notifies that a chunk has become ready and it should be sent to all its clients - void ChunkReady(int a_ChunkX, int a_ChunkZ); - /// Queues a chunk to be sent to a specific client void QueueSendChunkTo(int a_ChunkX, int a_ChunkZ, eChunkPriority a_Priority, cClientHandle * a_Client); + void QueueSendChunkTo(int a_ChunkX, int a_ChunkZ, eChunkPriority a_Priority, std::list<cClientHandle *> a_Client); /// Removes the a_Client from all waiting chunk send operations void RemoveClient(cClientHandle * a_Client); protected: + + struct sChunkQueue + { + eChunkPriority m_Priority; + cChunkCoords m_Chunk; + + bool operator <(const sChunkQueue & a_Other) const { return this->m_Priority < a_Other.m_Priority; } + }; /// Used for sending chunks to specific clients struct sSendChunk { - int m_ChunkX; - int m_ChunkZ; - cClientHandle * m_Client; - - sSendChunk(int a_ChunkX, int a_ChunkZ, cClientHandle * a_Client) : - m_ChunkX(a_ChunkX), - m_ChunkZ(a_ChunkZ), - m_Client(a_Client) - { - } - - bool operator ==(const sSendChunk & a_Other) - { - return ( - (a_Other.m_ChunkX == m_ChunkX) && - (a_Other.m_ChunkZ == m_ChunkZ) && - (a_Other.m_Client == m_Client) - ); - } - } ; - typedef std::list<sSendChunk> sSendChunkList; - - struct sBlockCoord - { - int m_BlockX; - int m_BlockY; - int m_BlockZ; - - sBlockCoord(int a_BlockX, int a_BlockY, int a_BlockZ) : - m_BlockX(a_BlockX), - m_BlockY(a_BlockY), - m_BlockZ(a_BlockZ) + cChunkCoords m_Chunk; + std::unordered_set<cClientHandle *> m_Clients; + eChunkPriority m_Priority; + sSendChunk(cChunkCoords a_Chunk, eChunkPriority a_Priority) : + m_Chunk(a_Chunk), + m_Priority(a_Priority) { } - } ; - - typedef std::vector<sBlockCoord> sBlockCoords; + }; - cWorld * m_World; + cWorld & m_World; cCriticalSection m_CS; - cChunkCoordsList m_ChunksReady; - sSendChunkList m_SendChunksLowPriority; - sSendChunkList m_SendChunksMediumPriority; - sSendChunkList m_SendChunksHighPriority; + std::priority_queue<sChunkQueue> m_SendChunks; + std::unordered_map<cChunkCoords, sSendChunk, cChunkCoordsHash> m_ChunkInfo; cEvent m_evtQueue; // Set when anything is added to m_ChunksReady cEvent m_evtRemoved; // Set when removed clients are safe to be deleted int m_RemoveCount; // Number of threads waiting for a client removal (m_evtRemoved needs to be set this many times) - - cNotifyChunkSender m_Notify; // Used for chunks that don't have a valid lighting - they will be re-queued after lightcalc - // Data about the chunk that is being sent: // NOTE that m_BlockData[] is inherited from the cChunkDataCollector unsigned char m_BiomeMap[cChunkDef::Width * cChunkDef::Width]; - sBlockCoords m_BlockEntities; // Coords of the block entities to send + std::vector<Vector3i> m_BlockEntities; // Coords of the block entities to send // TODO: sEntityIDs m_Entities; // Entity-IDs of the entities to send // cIsThread override: @@ -168,9 +126,8 @@ protected: virtual void BlockEntity (cBlockEntity * a_Entity) override; /// Sends the specified chunk to a_Client, or to all chunk clients if a_Client == nullptr - void SendChunk(int a_ChunkX, int a_ChunkZ, cClientHandle * a_Client); + void SendChunk(int a_ChunkX, int a_ChunkZ, std::unordered_set<cClientHandle *> a_Clients); } ; - |