text: // Emacs style mode select   -*- C++ -*-
  //-----------------------------------------------------------------------------
  //
  // $Id:$
  //
  // Copyright (C) 1993-1996 by id Software, Inc.
  //
  // This program is free software; you can redistribute it and/or
  // modify it under the terms of the GNU General Public License
  // as published by the Free Software Foundation; either version 2
  // 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 General Public License for more details.
  //
  // DESCRIPTION:
  //      Play functions, animation, global header.
  //
  //-----------------------------------------------------------------------------
  
  
  #ifndef __P_LOCAL__
  #define __P_LOCAL__
  
  #ifndef __R_LOCAL__
  #include "r_local.h"
  #endif
  
  #define FLOATSPEED              (FRACUNIT*4)
  
  
  #define MAXHEALTH               100
  #define VIEWHEIGHT              (41*FRACUNIT)
  
  // mapblocks are used to check movement
  // against lines and things
  #define MAPBLOCKUNITS   128
  #define MAPBLOCKSIZE    (MAPBLOCKUNITS*FRACUNIT)
  #define MAPBLOCKSHIFT   (FRACBITS+7)
  #define MAPBMASK                (MAPBLOCKSIZE-1)
  #define MAPBTOFRAC              (MAPBLOCKSHIFT-FRACBITS)
  
  
  // player radius for movement checking
  #define PLAYERRADIUS    16*FRACUNIT
  
  // MAXRADIUS is for precalculated sector block boxes
  // the spider demon is larger,
  // but we do not have any moving sectors nearby
  #define MAXRADIUS               32*FRACUNIT
  
  #define GRAVITY         FRACUNIT
  #define MAXMOVE         (30*FRACUNIT)
  
  #define USERANGE                (64*FRACUNIT)
  #define MELEERANGE              (64*FRACUNIT)
  #define MISSILERANGE    (32*64*FRACUNIT)
  
  // follow a player exlusively for 3 seconds
  #define BASETHRESHOLD           100
  
  
  
  //
  // P_TICK
  //
  
  // both the head and tail of the thinker list
  extern  thinker_t       thinkercap;
  
  
  void P_InitThinkers (void);
  void P_AddThinker (thinker_t* thinker);
  void P_RemoveThinker (thinker_t* thinker);
  
  
  //
  // P_PSPR
  //
  void P_SetupPsprites (player_t* curplayer);
  void P_MovePsprites (player_t* curplayer);
  void P_DropWeapon (player_t* player);
  
  
  //
  // P_USER
  //
  void    P_PlayerThink (player_t* player);
  
  
  //
  // P_MOBJ
  //
  #define ONFLOORZ                MININT
  #define ONCEILINGZ              MAXINT
  
  // Time interval for item respawning.
  #define ITEMQUESIZE             128
  
  extern mapthing_t       itemrespawnque[ITEMQUESIZE];
  extern int              itemrespawntime[ITEMQUESIZE];
  extern int              iquehead;
  extern int              iquetail;
  
  
  void P_RespawnSpecials (void);
  
  mobj_t*
  P_SpawnMobj
  ( fixed_t       x,
    fixed_t       y,
    fixed_t       z,
    mobjtype_t    type );
  
  void    P_RemoveMobj (mobj_t* th);
  boolean P_SetMobjState (mobj_t* mobj, statenum_t state);
  void    P_MobjThinker (mobj_t* mobj);
  
  void    P_SpawnPuff (fixed_t x, fixed_t y, fixed_t z);
  void    P_SpawnBlood (fixed_t x, fixed_t y, fixed_t z, int damage);
  mobj_t* P_SpawnMissile (mobj_t* source, mobj_t* dest, mobjtype_t type);
  void    P_SpawnPlayerMissile (mobj_t* source, mobjtype_t type);
  
  
  //
  // P_ENEMY
  //
  void P_NoiseAlert (mobj_t* target, mobj_t* emmiter);
  
  
  //
  // P_MAPUTL
  //
  typedef struct
  {
      fixed_t     x;
      fixed_t     y;
      fixed_t     dx;
      fixed_t     dy;
  
  } divline_t;
  
  typedef struct
  {
      fixed_t     frac;           // along trace line
      boolean     isaline;
      union {
          mobj_t* thing;
          line_t* line;
      }                   d;
  } intercept_t;
  
  #define MAXINTERCEPTS   128
  
  extern intercept_t      intercepts[MAXINTERCEPTS];
  extern intercept_t*     intercept_p;
  
  typedef boolean (*traverser_t) (intercept_t *in);
  
  fixed_t P_AproxDistance (fixed_t dx, fixed_t dy);
  int     P_PointOnLineSide (fixed_t x, fixed_t y, line_t* line);
  int     P_PointOnDivlineSide (fixed_t x, fixed_t y, divline_t* line);
  void    P_MakeDivline (line_t* li, divline_t* dl);
  fixed_t P_InterceptVector (divline_t* v2, divline_t* v1);
  int     P_BoxOnLineSide (fixed_t* tmbox, line_t* ld);
  
  extern fixed_t          opentop;
  extern fixed_t          openbottom;
  extern fixed_t          openrange;
  extern fixed_t          lowfloor;
  
  void    P_LineOpening (line_t* linedef);
  
  boolean P_BlockLinesIterator (int x, int y, boolean(*func)(line_t*) );
  boolean P_BlockThingsIterator (int x, int y, boolean(*func)(mobj_t*) );
  
  #define PT_ADDLINES             1
  #define PT_ADDTHINGS    2
  #define PT_EARLYOUT             4
  
  extern divline_t        trace;
  
  boolean
  P_PathTraverse
  ( fixed_t       x1,
    fixed_t       y1,
    fixed_t       x2,
    fixed_t       y2,
    int           flags,
    boolean       (*trav) (intercept_t *));
  
  void P_UnsetThingPosition (mobj_t* thing);
  void P_SetThingPosition (mobj_t* thing);
  
  
  //
  // P_MAP
  //
  
  // If "floatok" true, move would be ok
  // if within "tmfloorz - tmceilingz".
  extern boolean          floatok;
  extern fixed_t          tmfloorz;
  extern fixed_t          tmceilingz;
  
  
  extern  line_t*         ceilingline;
  
  boolean P_CheckPosition (mobj_t *thing, fixed_t x, fixed_t y);
  boolean P_TryMove (mobj_t* thing, fixed_t x, fixed_t y);
  boolean P_TeleportMove (mobj_t* thing, fixed_t x, fixed_t y);
  void    P_SlideMove (mobj_t* mo);
  boolean P_CheckSight (mobj_t* t1, mobj_t* t2);
  void    P_UseLines (player_t* player);
  
  boolean P_ChangeSector (sector_t* sector, boolean crunch);
  
  extern mobj_t*  linetarget;     // who got hit (or NULL)
  
  fixed_t
  P_AimLineAttack
  ( mobj_t*       t1,
    angle_t       angle,
    fixed_t       distance );
  
  void
  P_LineAttack
  ( mobj_t*       t1,
    angle_t       angle,
    fixed_t       distance,
    fixed_t       slope,
    int           damage );
  
  void
  P_RadiusAttack
  ( mobj_t*       spot,
    mobj_t*       source,
    int           damage );
  
  
  
  //
  // P_SETUP
  //
  extern byte*            rejectmatrix;   // for fast sight rejection
  extern short*           blockmaplump;   // offsets in blockmap are from here
  extern short*           blockmap;
  extern int              bmapwidth;
  extern int              bmapheight;     // in mapblocks
  extern fixed_t          bmaporgx;
  extern fixed_t          bmaporgy;       // origin of block map
  extern mobj_t**         blocklinks;     // for thing chains
  
  
  
  //
  // P_INTER
  //
  extern int              maxammo[NUMAMMO];
  extern int              clipammo[NUMAMMO];
  
  void
  P_TouchSpecialThing
  ( mobj_t*       special,
    mobj_t*       toucher );
  
  void
  P_DamageMobj
  ( mobj_t*       target,
    mobj_t*       inflictor,
    mobj_t*       source,
    int           damage );
  
  
  //
  // P_SPEC
  //
  #include "p_spec.h"
  
  
  #endif  // __P_LOCAL__
  //-----------------------------------------------------------------------------
  //
  // $Log:$
  //
  //-----------------------------------------------------------------------------
  
  
  