// NeL - MMORPG Framework // Copyright (C) 2010 Winch Gate Property Limited // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU Affero General Public License as // published by the Free Software Foundation, either version 3 of the // License, or (at your option) any later version. // // This program 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 Affero General Public License for more details. // // You should have received a copy of the GNU Affero General Public License // along with this program. If not, see . #ifndef NL_FACE_GRID_H #define NL_FACE_GRID_H #include #include "nel/misc/types_nl.h" #include "nel/misc/vector.h" #include "nel/misc/file.h" #include "nel/misc/aabbox.h" #include "vector_2s.h" #include "surface_quad.h" #include "chain.h" #include "retrievable_surface.h" #include "chain_quad.h" #include "exterior_mesh.h" #include "quad_grid.h" #include "nel/pacs/u_global_position.h" namespace NLPACS { /** * A selection grid for the interior faces. It contains the indexes of the faces, as uint32. * \author Benjamin Legros * \author Nevrax France * \date 2001 */ class CFaceGrid { public: /** * A temporary grid, used to create a static CFaceGrid object. * \author Benjamin Legros * \author Nevrax France * \date 2001 */ class CFaceGridBuild { public: /// The grid. std::vector< std::vector > Grid; /// The width, in number of rows and lines of the grid. uint Width; /// The size of each element. float Size; public: /// Init an empty build object with width and size void init(uint width, float elsize); /// Insert a value in the grid void insert(const NLMISC::CVector &bmin, const NLMISC::CVector &bmax, uint32 value); }; protected: /// The width of the grid in rows and lines. uint16 _Width; /// The 2Log of the width of the grid. uint16 _Log2Width; /// The size (in meter) of each grid element. float _ElSize; /// The grid of indexes to the data buffer. std::vector _Grid; /// The grid data buffer (packed datas). std::vector _GridData; public: /// Constructor. CFaceGrid() : _Width(0), _Log2Width(0), _ElSize(0.0f) {} /// Clear the grid. void clear(); /// Create the face grid from a CFaceGridBuild. void create(const CFaceGridBuild &fgb); /// Select faces indexes close to a given point void select(const NLMISC::CVector &pos, std::vector &selected) const; /// Serial the face grid void serial(NLMISC::IStream &f); }; // CFaceGrid inline inline void CFaceGrid::clear() { _Width = 0; _Log2Width = 0; _ElSize = 0.0f; NLMISC::contReset(_Grid); NLMISC::contReset(_GridData); } inline void CFaceGrid::create(const CFaceGrid::CFaceGridBuild &fgb) { nlassert(fgb.Grid.size() == fgb.Width*fgb.Width); nlassert(fgb.Width < 32768); // clear first clear(); // setup grid size _Width = (uint16)fgb.Width; _ElSize = fgb.Size; _Log2Width = uint16(NLMISC::getPowerOf2(_Width)); // and store in packed format the data of the face grid build uint i; for (i=0; i &selected) const { selected.clear(); uint start, stop, idx; uint x, y; x = ((sint)(pos.x/_ElSize) & (_Width-1)); y = ((sint)(pos.y/_ElSize) & (_Width-1)); idx = x+(y<<_Log2Width); start = _Grid[idx++]; stop = (idx == _Grid.size()) ? (uint)_GridData.size() : _Grid[idx]; for (; start= (sint)Width) { x0 = 0; x1 = Width-1; } else { x0 &= (Width-1); x1 &= (Width-1); if (x1 < x0) x1 += Width; } if (y1-y0 >= (sint)Width) { y0 = 0; y1 = Width-1; } else { y0 &= (Width-1); y1 &= (Width-1); if (y1 < y0) y1 += Width; } sint x, y; for (y=y0; y<=y1; ++y) for (x=x0; x<=x1; ++x) Grid[(x&(Width-1))+(y&(Width-1))*Width].push_back(value); } }; // NLPACS #endif // NL_FACE_GRID_H /* End of face_grid.h */