qzdoom/src/gamedata/p_blockmap.h

100 lines
2.2 KiB
C
Raw Normal View History

#ifndef __P_BLOCKMAP_H
#define __P_BLOCKMAP_H
#include "doomtype.h"
class AActor;
// [RH] Like msecnode_t, but for the blockmap
struct FBlockNode
{
AActor *Me; // actor this node references
int BlockIndex; // index into blocklinks for the block this node is in
int Group; // portal group this link belongs to (can be different than the actor's own group
FBlockNode **PrevActor; // previous actor in this block
FBlockNode *NextActor; // next actor in this block
FBlockNode **PrevBlock; // previous block this actor is in
FBlockNode *NextBlock; // next block this actor is in
static FBlockNode *Create (AActor *who, int x, int y, int group = -1);
void Release ();
static FBlockNode *FreeBlocks;
};
// BLOCKMAP
// Created from axis aligned bounding box
// of the map, a rectangular array of
// blocks of size 128x128.
// Used to speed up collision detection
// by spatial subdivision in 2D.
//
struct FBlockmap
{
int* blockmaplump; // offsets in blockmap are from here
int* blockmap;
int bmapwidth;
int bmapheight; // in mapblocks
double bmaporgx;
double bmaporgy; // origin of block map
FBlockNode** blocklinks; // for thing chains
// mapblocks are used to check movement
// against lines and things
enum
{
MAPBLOCKUNITS = 128
};
inline int GetBlockX(double xpos)
{
return int((xpos - bmaporgx) / MAPBLOCKUNITS);
}
inline int GetBlockY(double ypos)
{
return int((ypos - bmaporgy) / MAPBLOCKUNITS);
}
inline bool isValidBlock(int x, int y) const
{
return ((unsigned int)x < (unsigned int)bmapwidth &&
(unsigned int)y < (unsigned int)bmapheight);
}
inline int *GetLines(int x, int y) const
{
// There is an extra entry at the beginning of every block.
// Apparently, id had originally intended for it to be used
// to keep track of things, but the final code does not do that.
int offset = y*bmapwidth + x;
return blockmaplump + *(blockmap + offset) + 1;
}
bool VerifyBlockMap(int count, unsigned numlines);
void Clear()
{
if (blockmaplump != nullptr)
{
delete[] blockmaplump;
blockmaplump = nullptr;
}
if (blocklinks != nullptr)
{
delete[] blocklinks;
blocklinks = nullptr;
}
}
~FBlockmap()
{
Clear();
}
};
#endif