#include "wolfdef.h" /********************************** Returns True if a straight line between the player and actor is unobstructed **********************************/ Boolean CheckLine(actor_t *ActorPtr) { Word actorx,actory,actortx,actorty; /* Current actor's coords */ Word playerx,playery,playertx,playerty; /* Player's coords */ Word xl,xh,yl,yh; /* Min x,y Max x,y for test */ int delta; /* Pixel differance to calc Step and Frac */ int Step; /* Step value for each whole xy */ Word Frac; /* Fractional xy stepper */ Word deltafrac; /* True distance for whole numbers */ Word intercept; /* Temp for door code */ Word tile; /* Temp for tile check */ Byte partial; /* Fraction to force whole numbers */ actorx = ActorPtr->x; /* Get the actor's x,y */ actortx = actorx>>FRACBITS; /* Get the actor's tile x,y */ actory = ActorPtr->y; actorty = actory>>FRACBITS; playerx = actors[0].x; /* Get the player's x,y */ playertx = playerx>>FRACBITS; /* Get the player's tile x,y */ playery = actors[0].y; playerty = playery>>FRACBITS; /* The actor COULD be standing on a blocked tile (On a CLOSING door tile) */ #if 0 if (tilemap[actorty][actortx] & TI_BLOCKSIGHT) { /* Is the actor IN a wall? */ return FALSE; /* This could happen on a closing door */ } #endif /* check for solid tiles at x crossings */ if (playertx!=actortx) { /* Scan in the x direction? */ if (actortx= (16*FRACUNIT) || deltafrac >= (16*FRACUNIT)) { /* Farther than 16 tiles? */ return FALSE; } Step = FixedDiv(delta,deltafrac); /* How much to y step */ Frac = FixedByFrac(Step,partial)+yl; /* Init the Y coord */ do { ++xl; tile = tilemap[Frac>>FRACBITS][xl]; /* Get the current tile */ if (tile & TI_BLOCKSIGHT) { return FALSE; /* Can't see! */ } if (tile & TI_DOOR) { /* see if the door is open enough*/ intercept = ((Step/2)+Frac)&0xff; if (intercept > doors[tile&TI_NUMMASK].position) { return FALSE; /* Can't see! */ } } Frac += Step; } while (xl= 16*FRACUNIT || deltafrac >= 16*FRACUNIT) { return FALSE; } Step = FixedDiv(delta,deltafrac); Frac = FixedByFrac(Step,partial)+xl; do { ++yl; tile = tilemap[yl][Frac>>FRACBITS]; if (tile & TI_BLOCKSIGHT) { return FALSE; } if (tile & TI_DOOR) { /* see if the door is open enough*/ intercept = ((Step/2)+Frac)&0xff; if (intercept > doors[tile&TI_NUMMASK].position) { return FALSE; /* Can't see! */ } } Frac += Step; } while (ylclass]; /* Get pointer to info record */ sound = info->sightsound; /* Get the requested sound */ if (sound == SND_ESEE) { /* make random human sound*/ sound = NaziSound[w_rnd()&3]; /* Make a differant sound */ } PlaySound(sound|0x8000); /* Play the sight sound */ NewState(ActorPtr,info->sightstate); /* Set the next state */ ActorPtr->flags |= FL_ACTIVE; /* Make it active */ } /********************************** Called by actors that ARE NOT chasing the player. If the player is detected (by sight, noise, or proximity), the actor is put into it's combat frame. Incorporates a random reaction delay. **********************************/ void T_Stand(actor_t *ActorPtr) { if (ActorPtr->reacttime) { /* Waiting to react? */ if (ActorPtr->reacttime>TicCount) { /* Still waiting? */ ActorPtr->reacttime-=TicCount; /* Count down */ return; } if (ActorPtr->flags&FL_AMBUSH ) { /* Ambush actor? */ if (!CheckLine(ActorPtr)) { /* Can I see you? */ ActorPtr->reacttime=1; /* be very ready, but*/ return; /* don't attack yet*/ } ActorPtr->flags &= ~FL_AMBUSH; /* Clear the ambush flag */ } FirstSighting(ActorPtr); /* Attack the player! */ ActorPtr->reacttime=0; } /* Haven't seen player yet*/ if (madenoise || CheckLine(ActorPtr)) { /* Made a gun shot? Seen? */ ActorPtr->reacttime = (w_rnd() & classinfo[ActorPtr->class].reactionmask)*4+1; } }