📄 wl_act1.c
字号:
// WL_ACT1.C
#include "WL_DEF.H"
#pragma hdrstop
/*
=============================================================================
STATICS
=============================================================================
*/
statobj_t statobjlist[MAXSTATS],*laststatobj;
struct
{
int picnum;
stat_t type;
} statinfo[] =
{
{SPR_STAT_0}, // puddle spr1v
{SPR_STAT_1,block}, // Green Barrel "
{SPR_STAT_2,block}, // Table/chairs "
{SPR_STAT_3,block}, // Floor lamp "
{SPR_STAT_4}, // Chandelier "
{SPR_STAT_5,block}, // Hanged man "
{SPR_STAT_6,bo_alpo}, // Bad food "
{SPR_STAT_7,block}, // Red pillar "
//
// NEW PAGE
//
{SPR_STAT_8,block}, // Tree spr2v
{SPR_STAT_9}, // Skeleton flat "
{SPR_STAT_10,block}, // Sink " (SOD:gibs)
{SPR_STAT_11,block}, // Potted plant "
{SPR_STAT_12,block}, // Urn "
{SPR_STAT_13,block}, // Bare table "
{SPR_STAT_14}, // Ceiling light "
#ifndef SPEAR
{SPR_STAT_15}, // Kitchen stuff "
#else
{SPR_STAT_15,block}, // Gibs!
#endif
//
// NEW PAGE
//
{SPR_STAT_16,block}, // suit of armor spr3v
{SPR_STAT_17,block}, // Hanging cage "
{SPR_STAT_18,block}, // SkeletoninCage "
{SPR_STAT_19}, // Skeleton relax "
{SPR_STAT_20,bo_key1}, // Key 1 "
{SPR_STAT_21,bo_key2}, // Key 2 "
{SPR_STAT_22,block}, // stuff (SOD:gibs)
{SPR_STAT_23}, // stuff
//
// NEW PAGE
//
{SPR_STAT_24,bo_food}, // Good food spr4v
{SPR_STAT_25,bo_firstaid}, // First aid "
{SPR_STAT_26,bo_clip}, // Clip "
{SPR_STAT_27,bo_machinegun}, // Machine gun "
{SPR_STAT_28,bo_chaingun}, // Gatling gun "
{SPR_STAT_29,bo_cross}, // Cross "
{SPR_STAT_30,bo_chalice}, // Chalice "
{SPR_STAT_31,bo_bible}, // Bible "
//
// NEW PAGE
//
{SPR_STAT_32,bo_crown}, // crown spr5v
{SPR_STAT_33,bo_fullheal}, // one up "
{SPR_STAT_34,bo_gibs}, // gibs "
{SPR_STAT_35,block}, // barrel "
{SPR_STAT_36,block}, // well "
{SPR_STAT_37,block}, // Empty well "
{SPR_STAT_38,bo_gibs}, // Gibs 2 "
{SPR_STAT_39,block}, // flag "
//
// NEW PAGE
//
#ifndef SPEAR
{SPR_STAT_40,block}, // Call Apogee spr7v
#else
{SPR_STAT_40}, // Red light
#endif
//
// NEW PAGE
//
{SPR_STAT_41}, // junk "
{SPR_STAT_42}, // junk "
{SPR_STAT_43}, // junk "
#ifndef SPEAR
{SPR_STAT_44}, // pots "
#else
{SPR_STAT_44,block}, // Gibs!
#endif
{SPR_STAT_45,block}, // stove " (SOD:gibs)
{SPR_STAT_46,block}, // spears " (SOD:gibs)
{SPR_STAT_47}, // vines "
//
// NEW PAGE
//
#ifdef SPEAR
{SPR_STAT_48,block}, // marble pillar
{SPR_STAT_49,bo_25clip}, // bonus 25 clip
{SPR_STAT_50,block}, // truck
{SPR_STAT_51,bo_spear}, // SPEAR OF DESTINY!
#endif
{SPR_STAT_26,bo_clip2}, // Clip "
{-1} // terminator
};
/*
===============
=
= InitStaticList
=
===============
*/
void InitStaticList (void)
{
laststatobj = &statobjlist[0];
}
/*
===============
=
= SpawnStatic
=
===============
*/
void SpawnStatic (int tilex, int tiley, int type)
{
laststatobj->shapenum = statinfo[type].picnum;
laststatobj->tilex = tilex;
laststatobj->tiley = tiley;
laststatobj->visspot = &spotvis[tilex][tiley];
switch (statinfo[type].type)
{
case block:
(unsigned)actorat[tilex][tiley] = 1; // consider it a blocking tile
case dressing:
laststatobj->flags = 0;
break;
case bo_cross:
case bo_chalice:
case bo_bible:
case bo_crown:
case bo_fullheal:
if (!loadedgame)
gamestate.treasuretotal++;
case bo_firstaid:
case bo_key1:
case bo_key2:
case bo_key3:
case bo_key4:
case bo_clip:
case bo_25clip:
case bo_machinegun:
case bo_chaingun:
case bo_food:
case bo_alpo:
case bo_gibs:
case bo_spear:
laststatobj->flags = FL_BONUS;
laststatobj->itemnumber = statinfo[type].type;
break;
}
laststatobj++;
if (laststatobj == &statobjlist[MAXSTATS])
Quit ("Too many static objects!\n");
}
/*
===============
=
= PlaceItemType
=
= Called during game play to drop actors' items. It finds the proper
= item number based on the item type (bo_???). If there are no free item
= spots, nothing is done.
=
===============
*/
void PlaceItemType (int itemtype, int tilex, int tiley)
{
int type;
statobj_t *spot;
//
// find the item number
//
for (type=0 ; ; type++)
{
if (statinfo[type].picnum == -1) // end of list
Quit ("PlaceItemType: couldn't find type!");
if (statinfo[type].type == itemtype)
break;
}
//
// find a spot in statobjlist to put it in
//
for (spot=&statobjlist[0] ; ; spot++)
{
if (spot==laststatobj)
{
if (spot == &statobjlist[MAXSTATS])
return; // no free spots
laststatobj++; // space at end
break;
}
if (spot->shapenum == -1) // -1 is a free spot
break;
}
//
// place it
//
spot->shapenum = statinfo[type].picnum;
spot->tilex = tilex;
spot->tiley = tiley;
spot->visspot = &spotvis[tilex][tiley];
spot->flags = FL_BONUS;
spot->itemnumber = statinfo[type].type;
}
/*
=============================================================================
DOORS
doorobjlist[] holds most of the information for the doors
doorposition[] holds the amount the door is open, ranging from 0 to 0xffff
this is directly accessed by AsmRefresh during rendering
The number of doors is limited to 64 because a spot in tilemap holds the
door number in the low 6 bits, with the high bit meaning a door center
and bit 6 meaning a door side tile
Open doors conect two areas, so sounds will travel between them and sight
will be checked when the player is in a connected area.
Areaconnect is incremented/decremented by each door. If >0 they connect
Every time a door opens or closes the areabyplayer matrix gets recalculated.
An area is true if it connects with the player's current spor.
=============================================================================
*/
#define DOORWIDTH 0x7800
#define OPENTICS 300
doorobj_t doorobjlist[MAXDOORS],*lastdoorobj;
int doornum;
unsigned doorposition[MAXDOORS]; // leading edge of door 0=closed
// 0xffff = fully open
byte far areaconnect[NUMAREAS][NUMAREAS];
boolean areabyplayer[NUMAREAS];
/*
==============
=
= ConnectAreas
=
= Scans outward from playerarea, marking all connected areas
=
==============
*/
void RecursiveConnect (int areanumber)
{
int i;
for (i=0;i<NUMAREAS;i++)
{
if (areaconnect[areanumber][i] && !areabyplayer[i])
{
areabyplayer[i] = true;
RecursiveConnect (i);
}
}
}
void ConnectAreas (void)
{
memset (areabyplayer,0,sizeof(areabyplayer));
areabyplayer[player->areanumber] = true;
RecursiveConnect (player->areanumber);
}
void InitAreas (void)
{
memset (areabyplayer,0,sizeof(areabyplayer));
areabyplayer[player->areanumber] = true;
}
/*
===============
=
= InitDoorList
=
===============
*/
void InitDoorList (void)
{
memset (areabyplayer,0,sizeof(areabyplayer));
_fmemset (areaconnect,0,sizeof(areaconnect));
lastdoorobj = &doorobjlist[0];
doornum = 0;
}
/*
===============
=
= SpawnDoor
=
===============
*/
void SpawnDoor (int tilex, int tiley, boolean vertical, int lock)
{
int areanumber;
unsigned far *map;
if (doornum==64)
Quit ("64+ doors on level!");
doorposition[doornum] = 0; // doors start out fully closed
lastdoorobj->tilex = tilex;
lastdoorobj->tiley = tiley;
lastdoorobj->vertical = vertical;
lastdoorobj->lock = lock;
lastdoorobj->action = dr_closed;
(unsigned)actorat[tilex][tiley] = doornum | 0x80; // consider it a solid wall
//
// make the door tile a special tile, and mark the adjacent tiles
// for door sides
//
tilemap[tilex][tiley] = doornum | 0x80;
map = mapsegs[0] + farmapylookup[tiley]+tilex;
if (vertical)
{
*map = *(map-1); // set area number
tilemap[tilex][tiley-1] |= 0x40;
tilemap[tilex][tiley+1] |= 0x40;
}
else
{
*map = *(map-mapwidth); // set area number
tilemap[tilex-1][tiley] |= 0x40;
tilemap[tilex+1][tiley] |= 0x40;
}
doornum++;
lastdoorobj++;
}
//===========================================================================
/*
=====================
=
= OpenDoor
=
=====================
*/
void OpenDoor (int door)
{
if (doorobjlist[door].action == dr_open)
doorobjlist[door].ticcount = 0; // reset open time
else
doorobjlist[door].action = dr_opening; // start it opening
}
/*
=====================
=
= CloseDoor
=
=====================
*/
void CloseDoor (int door)
{
int tilex,tiley,area;
objtype *check;
//
// don't close on anything solid
//
tilex = doorobjlist[door].tilex;
tiley = doorobjlist[door].tiley;
if (actorat[tilex][tiley])
return;
if (player->tilex == tilex && player->tiley == tiley)
return;
if (doorobjlist[door].vertical)
{
if ( player->tiley == tiley )
{
if ( ((player->x+MINDIST) >>TILESHIFT) == tilex )
return;
if ( ((player->x-MINDIST) >>TILESHIFT) == tilex )
return;
}
check = actorat[tilex-1][tiley];
if (check && ((check->x+MINDIST) >> TILESHIFT) == tilex )
return;
check = actorat[tilex+1][tiley];
if (check && ((check->x-MINDIST) >> TILESHIFT) == tilex )
return;
}
else if (!doorobjlist[door].vertical)
{
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -