📄 directionmap.h
字号:
#ifndef DIRECTIONMAP_H
#define DIRECTIONMAP_H
#include "Map.h"
#include "SDLHelpers.h"
// ============================================================================
// DirectionCell Class
// ============================================================================
class DirectionCell
{
public:
// =======================================================
// Functions
// =======================================================
// -------------------------------------------------------
// Name: DirectionCell
// Description: constructs the cell
// -------------------------------------------------------
DirectionCell()
{
m_blocked = false;
m_item = 0;
m_person = 0;
m_exits[0] = -1;
m_exits[1] = -1;
m_exits[2] = -1;
m_exits[3] = -1;
m_tiles[0] = -1;
m_tiles[1] = -1;
m_x = -1;
m_y = -1;
}
// =======================================================
// Data
// =======================================================
// -------------------------------------------------------
// Name: m_blocked
// Description: determines if the cell is blocked by
// a feature of the geography, but not
// by items or people.
// -------------------------------------------------------
bool m_blocked;
// -------------------------------------------------------
// Name: m_item
// Description: The item in the cell
// -------------------------------------------------------
Item* m_item;
// -------------------------------------------------------
// Name: m_person
// Description: The person in the cell
// -------------------------------------------------------
Person* m_person;
// -------------------------------------------------------
// Name: m_exits
// Description: the exits from the cell
// -------------------------------------------------------
int m_exits[4];
// -------------------------------------------------------
// Name: m_tiles
// Description: the tiles of the cell
// -------------------------------------------------------
int m_tiles[2];
// -------------------------------------------------------
// Name: m_x
// Description: x coordinate of the cell
// -------------------------------------------------------
int m_x;
// -------------------------------------------------------
// Name: m_y
// Description: y coordinate of the cell
// -------------------------------------------------------
int m_y;
};
// this class is used to load data from the disk
class MapEntry
{
public:
int x;
int y;
int directions[4];
int layers[4];
};
// ============================================================================
// DirectionMap Class
// ============================================================================
class DirectionMap : public Map
{
protected:
// =======================================================
// Data
// =======================================================
// -------------------------------------------------------
// Name: m_rooms
// Description: The array of the rooms in the map
// -------------------------------------------------------
Array<DirectionCell> m_rooms;
// -------------------------------------------------------
// Name: m_tilebmps
// Description: an array of bitmaps that the tiles will
// be drawn from
// -------------------------------------------------------
SDL_Surface** m_tilebmps;
// =======================================================
// New Functions
// =======================================================
public:
// -------------------------------------------------------
// Name: DirectionMap
// Description: Constructor, constructs the map with the
// given tile set
// -------------------------------------------------------
DirectionMap( SDL_Surface** p_tilebmps )
: m_rooms( 0 )
{
m_tilebmps = p_tilebmps;
}
// -------------------------------------------------------
// Name: ~DirectionMap
// Description: destructor, deletes everything on the map
// -------------------------------------------------------
~DirectionMap()
{
int x;
// go through all of the rooms and delete the items
// and persons.
for( x = 0; x < m_rooms.Size(); x++ )
{
if( m_rooms[x].m_item != 0 )
delete m_rooms[x].m_item;
if( m_rooms[x].m_person != 0 )
delete m_rooms[x].m_person;
m_rooms[x].m_item = 0;
m_rooms[x].m_person = 0;
}
}
// -------------------------------------------------------
// Name: LoadFromFile
// Description: Loads the map from a file
// -------------------------------------------------------
void LoadFromFile( char* p_filename )
{
int x;
int maptype;
int cells;
MapEntry entry;
// open the file
FILE* f = fopen( p_filename, "rb" );
// file cant be opened, return
if( f == 0 )
return;
// read in the map type.
fread( &maptype, 1, sizeof(int), f );
// quit out if type isn't 1
if( maptype != 1 )
{
fclose( f );
return;
}
// read in the size of the map
fread( &cells, 1, sizeof(int), f );
// resize the map so that it fits
m_rooms.Resize( cells );
// read in the room data
for( x = 0; x < cells; x++ )
{
// read in each room
fread( &entry, 1, sizeof(MapEntry), f );
// load in the tile numbers for the 2 layers
m_rooms[x].m_tiles[0] = entry.layers[0];
m_rooms[x].m_tiles[1] = entry.layers[1];
// load in the coordinates
m_rooms[x].m_x = entry.x;
m_rooms[x].m_y = entry.y;
// read in the item and person
if( entry.layers[2] != -1 )
{
m_rooms[x].m_item = MakeItem( entry.layers[2],
entry.x,
entry.y,
x );
}
if( entry.layers[3] != -1 )
{
m_rooms[x].m_person = MakePerson( entry.layers[3],
entry.x,
entry.y,
x );
// check to see if the person is the player of the game
if( entry.layers[3] == 0 )
{
SetViewer( m_rooms[x].m_person );
}
}
// load up the exits of the room.
m_rooms[x].m_exits[0] = entry.directions[0];
m_rooms[x].m_exits[1] = entry.directions[1];
m_rooms[x].m_exits[2] = entry.directions[2];
m_rooms[x].m_exits[3] = entry.directions[3];
}
// read the exits in
fread( m_exits[0], 64, sizeof(char), f );
fread( m_exits[1], 64, sizeof(char), f );
fread( m_exits[2], 64, sizeof(char), f );
// close the file
fclose( f );
}
// =======================================================
// New Functions
// =======================================================
// -------------------------------------------------------
// Name: Draw
// Description: Draws the map onto the given surface,
// using the viewers coordinates as the
// midpoint of the screen.
// -------------------------------------------------------
void Draw( SDL_Surface* p_surface, int p_midx, int p_midy )
{
int i, z; // counting variables
int px, py; // pixel coordinates
int ox, oy; // offset coordinates
int current;
Item* item;
Person* person;
// calculate the offsetsfrom the viewer
ox = (-m_viewer->GetX() * 64) + p_midx - 32;
oy = (-m_viewer->GetY() * 64) + p_midy - 32;
for( i = 0; i < m_rooms.Size(); i++ )
{
// calculate the coordinates of the current tile
px = m_rooms[i].m_x * 64 + ox;
py = m_rooms[i].m_y * 64 + oy;
for( z = 0; z < 2; z++ )
{
current = m_rooms[i].m_tiles[z];
if( current != -1 )
{
// draw the tile
SDLBlit( m_tilebmps[current], p_surface, px, py );
}
}
item = m_rooms[i].m_item;
person = m_rooms[i].m_person;
if( item != 0 )
SDLBlit( item->GetGraphic(), p_surface, px, py );
if( person != 0 )
SDLBlit( person->GetGraphic(), p_surface, px, py );
}
}
// -------------------------------------------------------
// Name: CanMove
// Description: Determines if the given person can move
// in the given direction
// -------------------------------------------------------
bool CanMove( Person* p_person, int p_direction )
{
int cell = GetCellNumber( p_person->GetCell(), p_direction );
if( cell == -1 )
return false;
// check to see if the path is blocked or not.
if( m_rooms[cell].m_blocked == true )
return false;
// check to see if there is a person blocking the way
if( m_rooms[cell].m_person != 0 )
return false;
// check to see if there in an item blocking the way
if( m_rooms[cell].m_item != 0 )
{
// some items can block, others can't
if( m_rooms[cell].m_item->CanBlock() == true )
return false;
}
return true;
}
// -------------------------------------------------------
// Name: Move
// Description: Moves the given person in the given
// direction
// -------------------------------------------------------
void Move( Person* p_person, int p_direction )
{
int newcell;
// make sure the player can move
if( CanMove( p_person, p_direction ) == true )
{
// get the number of the new cell
newcell = GetCellNumber( p_person->GetCell(), p_direction );
// move the person to the new cell
m_rooms[newcell].m_person = p_person;
// clear the person pointer in the old cell
m_rooms[p_person->GetCell()].m_person = 0;
// set the new x, y, and cell variables
p_person->SetX( m_rooms[newcell].m_x );
p_person->SetY( m_rooms[newcell].m_y );
p_person->SetCell( newcell );
}
}
// -------------------------------------------------------
// Name: GetItem
// Description: Gets a pointer to the item in the given
// cell
// -------------------------------------------------------
Item* GetItem( int p_cell )
{
// check to see if the cell is in bounds first
if( p_cell >= GetNumberOfCells() || p_cell < 0 )
return 0;
return m_rooms[p_cell].m_item;
}
// -------------------------------------------------------
// Name: SetItem
// Description: Sets the item in the given cell.
// -------------------------------------------------------
void SetItem( int p_cell, Item* p_item )
{
// check to see if the cell is in bounds first
if( p_cell >= GetNumberOfCells() || p_cell < 0 )
return;
m_rooms[p_cell].m_item = p_item;
}
// -------------------------------------------------------
// Name: GetPerson
// Description: Gets a pointer to the person in the given
// cell
// -------------------------------------------------------
Person* GetPerson( int p_cell )
{
// check to see if the cell is in bounds first
if( p_cell >= GetNumberOfCells() || p_cell < 0 )
return 0;
return m_rooms[p_cell].m_person;
}
// -------------------------------------------------------
// Name: SetPerson
// Description: sets the person in the given cell.
// -------------------------------------------------------
void SetPerson( int p_cell, Person* p_person )
{
// check to see if the cell is in bounds first
if( p_cell >= GetNumberOfCells() || p_cell < 0 )
return;
m_rooms[p_cell].m_person = p_person;
}
// -------------------------------------------------------
// Name: GetCellNumber
// Description: Gets the number of the cell in the
// given direction
// -------------------------------------------------------
int GetCellNumber( int p_cell, int p_direction )
{
return m_rooms[p_cell].m_exits[p_direction];
}
// -------------------------------------------------------
// Name: GetNumberOfCells
// Description: Gets the number of cells in the map
// -------------------------------------------------------
int GetNumberOfCells()
{
return m_rooms.Size();
}
// -------------------------------------------------------
// Name: GetClosestDirection
// Description: Gets the direction that will move the
// first person closer to the second person.
// -------------------------------------------------------
int GetClosestDirection( Person* p_one, Person* p_two )
{
int direction = -1;
// if person 1 is above person 2, then go north
if( p_one->GetY() > p_two->GetY() )
direction = 0;
// if person 1 is left of person 2, then go east
else if( p_one->GetX() < p_two->GetX() )
direction = 1;
// if person 1 is below person 2, then go south
else if( p_one->GetY() < p_two->GetY() )
direction = 2;
// if person 1 is right of person 2, then go west
else if( p_one->GetX() > p_two->GetX() )
direction = 3;
return direction;
}
};
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -