2019-10-03 18:04:14 -04:00
|
|
|
/**
|
|
|
|
@file constants.h
|
|
|
|
|
|
|
|
This file contains definitions of game constants that are not considered
|
|
|
|
part of game settings and whose change can ffect the game balance and
|
|
|
|
playability, e.g. physics constants.
|
|
|
|
|
|
|
|
by Miloslav Ciz (drummyfish), 2019
|
|
|
|
|
|
|
|
Released under CC0 1.0 (https://creativecommons.org/publicdomain/zero/1.0/)
|
|
|
|
plus a waiver of all other intellectual property. The goal of this work is
|
|
|
|
be and remain completely in the public domain forever, available for any use
|
|
|
|
whatsoever.
|
|
|
|
*/
|
|
|
|
|
2019-09-25 09:51:19 -04:00
|
|
|
#ifndef _SFG_CONSTANTS_H
|
|
|
|
#define _SFG_CONSTANTS_H
|
|
|
|
|
|
|
|
/**
|
|
|
|
How quickly player turns left/right, in degrees per second.
|
|
|
|
*/
|
2019-10-01 14:25:21 -04:00
|
|
|
#define SFG_PLAYER_TURN_SPEED 210
|
2019-09-25 09:51:19 -04:00
|
|
|
|
|
|
|
/**
|
|
|
|
How quickly player moves, in squares per second.
|
|
|
|
*/
|
2019-10-01 14:25:21 -04:00
|
|
|
#define SFG_PLAYER_MOVE_SPEED 10
|
|
|
|
|
|
|
|
/**
|
|
|
|
Gravity acceleration in squares / (second^2).
|
|
|
|
*/
|
|
|
|
|
|
|
|
#define SFG_GRAVITY_ACCELERATION 30
|
2019-09-25 09:51:19 -04:00
|
|
|
|
2019-10-03 14:09:00 -04:00
|
|
|
/**
|
|
|
|
Initial upwards speed of player's jump, in squares per second.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#define SFG_PLAYER_JUMP_SPEED 80
|
|
|
|
|
2019-09-26 21:34:49 -04:00
|
|
|
/**
|
|
|
|
How quickly elevators and squeezers move, in RCL_Unit per second.
|
|
|
|
*/
|
|
|
|
#define SFG_MOVING_WALL_SPEED 1024
|
|
|
|
|
2019-10-04 15:09:10 -04:00
|
|
|
/**
|
|
|
|
How quickly doors open and close, in RCL_Unit per second.
|
|
|
|
*/
|
|
|
|
#define SFG_DOOR_OPEN_SPEED 2048
|
|
|
|
|
2019-10-06 10:47:47 -04:00
|
|
|
/**
|
|
|
|
Says the (Chebyshev) distance in game squares at which level elements
|
|
|
|
(items, monsters etc.) become active.
|
|
|
|
*/
|
2019-12-28 14:16:44 -05:00
|
|
|
#define SFG_LEVEL_ELEMENT_ACTIVE_DISTANCE 10
|
2019-10-06 10:47:47 -04:00
|
|
|
|
2019-10-17 17:58:19 -04:00
|
|
|
/**
|
2019-10-18 10:34:51 -04:00
|
|
|
Rate at which AI will be updated, which also affects how fast enemies will
|
|
|
|
appear.
|
2019-10-17 17:58:19 -04:00
|
|
|
*/
|
2019-10-22 10:48:27 -04:00
|
|
|
#define SFG_AI_FPS 4
|
2019-10-18 11:26:13 -04:00
|
|
|
|
|
|
|
/**
|
|
|
|
Says a probability (0 - 255) of the AI changing its state during one update
|
|
|
|
step.
|
|
|
|
*/
|
2019-10-22 10:48:27 -04:00
|
|
|
#define SFG_AI_RANDOM_CHANGE_PROBABILITY 40
|
2019-10-17 17:58:19 -04:00
|
|
|
|
2019-10-21 09:21:22 -04:00
|
|
|
/**
|
|
|
|
Speed of rocket projectile, in squares per second.
|
|
|
|
*/
|
2019-11-09 15:45:32 -05:00
|
|
|
#define SFG_FIREBALL_SPEED 15
|
2019-10-21 09:21:22 -04:00
|
|
|
|
2019-10-21 17:50:19 -04:00
|
|
|
/**
|
|
|
|
Distance at which level elements (sprites) collide, in RCL_Unit (1024 per
|
|
|
|
square).
|
|
|
|
*/
|
2019-10-21 19:34:40 -04:00
|
|
|
#define SFG_ELEMENT_COLLISION_DISTANCE 800
|
|
|
|
|
2019-10-22 08:27:56 -04:00
|
|
|
/**
|
|
|
|
Height, in RCL_Units, at which collisions happen with level elements
|
|
|
|
(sprites).
|
|
|
|
*/
|
|
|
|
#define SFG_ELEMENT_COLLISION_HEIGHT 1024
|
|
|
|
|
2019-10-21 19:34:40 -04:00
|
|
|
/**
|
|
|
|
Distance at which explosion does damage and throws away the player and
|
|
|
|
monsters, in RCL_Units.
|
|
|
|
*/
|
|
|
|
#define SFG_EXPLOSION_DISTANCE 2048
|
2019-10-21 17:50:19 -04:00
|
|
|
|
2019-10-24 17:20:35 -04:00
|
|
|
/**
|
|
|
|
How much damage explosion causes in its range.
|
|
|
|
*/
|
|
|
|
#define SFG_EXPLOSION_DAMAGE 18
|
|
|
|
|
2019-10-23 18:09:46 -04:00
|
|
|
/**
|
|
|
|
Maximum player health.
|
|
|
|
*/
|
|
|
|
#define SFG_PLAYER_MAX_HEALTH 100
|
|
|
|
|
2019-10-24 17:20:35 -04:00
|
|
|
/**
|
|
|
|
At which value health indicator shows a warning (red color).
|
|
|
|
*/
|
|
|
|
#define SFG_PLAYER_HEALTH_WARNING_LEVEL 20
|
|
|
|
|
2019-10-25 18:50:22 -04:00
|
|
|
/**
|
|
|
|
Amount of health that is increased by taking a health kit.
|
|
|
|
*/
|
|
|
|
#define SFG_HEALTH_KIT_VALUE 20
|
|
|
|
|
2019-12-30 14:44:14 -05:00
|
|
|
#define SFG_MAX_MONSTERS 64
|
|
|
|
|
|
|
|
#define SFG_MAX_PROJECTILES 12
|
|
|
|
|
|
|
|
#define SFG_MAX_DOORS 32
|
|
|
|
|
|
|
|
#define SFG_PROJECTILE_EXPLOSION 0
|
|
|
|
#define SFG_PROJECTILE_FIREBALL 1
|
|
|
|
#define SFG_PROJECTILE_PLASMA 2
|
|
|
|
#define SFG_PROJECTILE_DUST 3
|
|
|
|
#define SFG_PROJECTILE_BULLET 4
|
|
|
|
#define SFG_PROJECTILE_NONE 255
|
|
|
|
|
|
|
|
// ----------------------------
|
|
|
|
// derived constants
|
|
|
|
|
|
|
|
#define SFG_GAME_RESOLUTION_X \
|
|
|
|
(SFG_SCREEN_RESOLUTION_X / SFG_RESOLUTION_SCALEDOWN)
|
|
|
|
|
|
|
|
#define SFG_GAME_RESOLUTION_Y \
|
|
|
|
(SFG_SCREEN_RESOLUTION_Y / SFG_RESOLUTION_SCALEDOWN)
|
|
|
|
|
|
|
|
#define SFG_MS_PER_FRAME (1000 / SFG_FPS) // ms per frame with target FPS
|
|
|
|
|
|
|
|
#if SFG_MS_PER_FRAME == 0
|
|
|
|
#define SFG_MS_PER_FRAME 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_WEAPON_IMAGE_SCALE \
|
|
|
|
(SFG_GAME_RESOLUTION_X / (SFG_TEXTURE_SIZE * 5))
|
|
|
|
|
|
|
|
#if SFG_WEAPON_IMAGE_SCALE == 0
|
|
|
|
#define SFG_WEAPON_IMAGE_SCALE 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_WEAPONBOB_OFFSET_PIXELS \
|
|
|
|
(SFG_WEAPONBOB_OFFSET * SFG_WEAPON_IMAGE_SCALE)
|
|
|
|
|
|
|
|
#define SFG_WEAPON_IMAGE_POSITION_X \
|
|
|
|
(SFG_GAME_RESOLUTION_X / 2 - (SFG_WEAPON_IMAGE_SCALE * SFG_TEXTURE_SIZE) / 2)
|
|
|
|
|
|
|
|
#define SFG_WEAPON_IMAGE_POSITION_Y \
|
|
|
|
(SFG_GAME_RESOLUTION_Y - (SFG_WEAPON_IMAGE_SCALE * SFG_TEXTURE_SIZE))
|
|
|
|
|
|
|
|
#define SFG_PLAYER_TURN_UNITS_PER_FRAME \
|
|
|
|
((SFG_PLAYER_TURN_SPEED * RCL_UNITS_PER_SQUARE) / (360 * SFG_FPS))
|
|
|
|
|
|
|
|
#if SFG_PLAYER_TURN_UNITS_PER_FRAME == 0
|
|
|
|
#define SFG_PLAYER_TURN_UNITS_PER_FRAME 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_PLAYER_MOVE_UNITS_PER_FRAME \
|
|
|
|
((SFG_PLAYER_MOVE_SPEED * RCL_UNITS_PER_SQUARE) / SFG_FPS)
|
|
|
|
|
|
|
|
#if SFG_PLAYER_MOVE_UNITS_PER_FRAME == 0
|
|
|
|
#define SFG_PLAYER_MOVE_UNITS_PER_FRAME 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_FIREBALL_MOVE_UNITS_PER_FRAME \
|
|
|
|
((SFG_FIREBALL_SPEED * RCL_UNITS_PER_SQUARE) / SFG_FPS)
|
|
|
|
|
|
|
|
#if SFG_FIREBALL_MOVE_UNITS_PER_FRAME == 0
|
|
|
|
#define SFG_FIREBALL_MOVE_UNITS_PER_FRAME 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_GRAVITY_SPEED_INCREASE_PER_FRAME \
|
|
|
|
((SFG_GRAVITY_ACCELERATION * RCL_UNITS_PER_SQUARE) / (SFG_FPS * SFG_FPS))
|
|
|
|
|
|
|
|
#if SFG_GRAVITY_SPEED_INCREASE_PER_FRAME == 0
|
|
|
|
#define SFG_GRAVITY_SPEED_INCREASE_PER_FRAME 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_HEADBOB_FRAME_INCREASE_PER_FRAME \
|
|
|
|
(SFG_HEADBOB_SPEED / SFG_FPS)
|
|
|
|
|
|
|
|
#if SFG_HEADBOB_FRAME_INCREASE_PER_FRAME == 0
|
|
|
|
#define SFG_HEADBOB_FRAME_INCREASE_PER_FRAME 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_HEADBOB_ENABLED (SFG_HEADBOB_SPEED > 0 && SFG_HEADBOB_OFFSET > 0)
|
|
|
|
|
|
|
|
#define SFG_CAMERA_SHEAR_STEP_PER_FRAME \
|
|
|
|
((SFG_GAME_RESOLUTION_Y * SFG_CAMERA_SHEAR_SPEED) / SFG_FPS)
|
|
|
|
|
|
|
|
#if SFG_CAMERA_SHEAR_STEP_PER_FRAME == 0
|
|
|
|
#define SFG_CAMERA_SHEAR_STEP_PER_FRAME 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_CAMERA_MAX_SHEAR_PIXELS \
|
|
|
|
(SFG_CAMERA_MAX_SHEAR * SFG_GAME_RESOLUTION_Y / 1024)
|
|
|
|
|
|
|
|
#define SFG_FONT_SIZE_SMALL \
|
|
|
|
(SFG_GAME_RESOLUTION_X / (SFG_FONT_CHARACTER_SIZE * 50))
|
|
|
|
|
|
|
|
#if SFG_FONT_SIZE_SMALL == 0
|
|
|
|
#define SFG_FONT_SIZE_SMALL 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_FONT_SIZE_MEDIUM \
|
|
|
|
(SFG_GAME_RESOLUTION_X / (SFG_FONT_CHARACTER_SIZE * 30))
|
|
|
|
|
|
|
|
#if SFG_FONT_SIZE_MEDIUM == 0
|
|
|
|
#define SFG_FONT_SIZE_MEDIUM 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_FONT_SIZE_BIG \
|
|
|
|
(SFG_GAME_RESOLUTION_X / (SFG_FONT_CHARACTER_SIZE * 18))
|
|
|
|
|
|
|
|
#if SFG_FONT_SIZE_BIG == 0
|
|
|
|
#define SFG_FONT_SIZE_BIG 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_Z_BUFFER_SIZE SFG_GAME_RESOLUTION_X
|
|
|
|
|
|
|
|
/**
|
|
|
|
Step in which walls get higher, in raycastlib units.
|
|
|
|
*/
|
|
|
|
#define SFG_WALL_HEIGHT_STEP (RCL_UNITS_PER_SQUARE / 4)
|
|
|
|
|
|
|
|
#define SFG_CEILING_MAX_HEIGHT\
|
|
|
|
(16 * RCL_UNITS_PER_SQUARE - RCL_UNITS_PER_SQUARE / 2 )
|
|
|
|
|
|
|
|
#define SFG_DOOR_DEFAULT_STATE 0x1f
|
|
|
|
#define SFG_DOOR_UP_DOWN_MASK 0x20
|
|
|
|
#define SFG_DOOR_VERTICAL_POSITION_MASK 0x1f
|
|
|
|
#define SFG_DOOR_HEIGHT_STEP (RCL_UNITS_PER_SQUARE / 0x1f)
|
|
|
|
|
|
|
|
#define SFG_DOOR_INCREMENT_PER_FRAME \
|
|
|
|
(SFG_DOOR_OPEN_SPEED / (SFG_DOOR_HEIGHT_STEP * SFG_FPS))
|
|
|
|
|
|
|
|
#if SFG_DOOR_INCREMENT_PER_FRAME == 0
|
|
|
|
#define SFG_DOOR_INCREMENT_PER_FRAME 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_MAX_ITEMS SFG_MAX_LEVEL_ELEMENTS
|
|
|
|
|
|
|
|
#define SFG_MAX_SPRITE_SIZE SFG_GAME_RESOLUTION_X
|
|
|
|
|
|
|
|
#define SFG_MAP_PIXEL_SIZE (SFG_GAME_RESOLUTION_Y / SFG_MAP_SIZE)
|
|
|
|
|
|
|
|
#if SFG_MAP_PIXEL_SIZE == 0
|
|
|
|
#define SFG_MAP_SIZE 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_AI_UPDATE_FRAME_INTERVAL \
|
|
|
|
(SFG_FPS / SFG_AI_FPS)
|
|
|
|
|
|
|
|
#if SFG_AI_UPDATE_FRAME_INTERVAL == 0
|
|
|
|
#define SFG_AI_UPDATE_FRAME_INTERVAL 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_EXPLOSION_DURATION_DOUBLE_FRAMES \
|
|
|
|
(SFG_EXPLOSION_DURATION / SFG_MS_PER_FRAME)
|
|
|
|
|
|
|
|
#if SFG_EXPLOSION_DURATION_DOUBLE_FRAMES == 0
|
|
|
|
#define SFG_EXPLOSION_DURATION_FRAMES 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_SPRITE_ANIMATION_FRAME_DURATION \
|
|
|
|
(SFG_FPS / SFG_SPRITE_ANIMATION_SPEED)
|
|
|
|
|
|
|
|
#if SFG_SPRITE_ANIMATION_FRAME_DURATION == 0
|
|
|
|
#define SFG_SPRITE_ANIMATION_FRAME_DURATION 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_HUD_MARGIN (SFG_GAME_RESOLUTION_X / 40)
|
|
|
|
|
|
|
|
#define SFG_HUD_HEALTH_INDICATOR_WIDTH_PIXELS \
|
|
|
|
(SFG_GAME_RESOLUTION_Y / SFG_HUD_HEALTH_INDICATOR_WIDTH)
|
|
|
|
|
|
|
|
#define SFG_HUD_HEALTH_INDICATOR_DURATION_FRAMES \
|
|
|
|
(SFG_HUD_HEALTH_INDICATOR_DURATION / SFG_MS_PER_FRAME)
|
|
|
|
|
|
|
|
#if SFG_HUD_HEALTH_INDICATOR_DURATION_FRAMES == 0
|
|
|
|
#define SFG_HUD_HEALTH_INDICATOR_DURATION_FRAMES 1
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#define SFG_HUD_BAR_HEIGHT \
|
|
|
|
(SFG_FONT_CHARACTER_SIZE * SFG_FONT_SIZE_MEDIUM + SFG_HUD_MARGIN * 2 + 1)
|
|
|
|
|
|
|
|
// ----------------------------
|
|
|
|
// weapons
|
|
|
|
|
|
|
|
#define SFG_WEAPON_KNIFE 0
|
|
|
|
#define SFG_WEAPON_SHOTGUN 1
|
|
|
|
#define SFG_WEAPON_MACHINE_GUN 2
|
|
|
|
#define SFG_WEAPON_ROCKET_LAUNCHER 3
|
|
|
|
#define SFG_WEAPON_PLASMAGUN 4
|
|
|
|
|
|
|
|
#define SFG_WEAPONS_TOTAL 5
|
|
|
|
|
|
|
|
#define SFG_WEAPON_ATTRIBUTE(fireType,fireCooldownMs) \
|
|
|
|
((uint8_t) (fireType | ((fireCooldownMs / (SFG_MS_PER_FRAME * 4)) << 3)))
|
|
|
|
|
|
|
|
#define SFG_GET_WEAPON_FIRE_TYPE(weaponNumber) \
|
|
|
|
(SFG_weaponAttributeTable[weaponNumber] & 0x7)
|
|
|
|
|
|
|
|
#define SFG_GET_WEAPON_FIRE_COOLDOWN_FRAMES(weaponNumber) \
|
|
|
|
((SFG_weaponAttributeTable[weaponNumber] >> 3) * 4)
|
|
|
|
|
|
|
|
#define SFG_WEAPON_FIRE_TYPE_MELEE 0
|
|
|
|
#define SFG_WEAPON_FIRE_TYPE_BULLET 1
|
|
|
|
#define SFG_WEAPON_FIRE_TYPE_SPREAD_BULLETS 2
|
|
|
|
#define SFG_WEAPON_FIRE_TYPE_FIREBALL 3
|
|
|
|
#define SFG_WEAPON_FIRE_TYPE_PLASMA 4
|
|
|
|
|
|
|
|
/**
|
|
|
|
Table of Weapon attributes, each as a byte in format :
|
|
|
|
|
|
|
|
cccccfff
|
|
|
|
|
|
|
|
fff: fire type
|
|
|
|
ccccc: fire cooldown in frames, i.e. time after which the next shot can be
|
|
|
|
shot again, ccccc has to be multiplied by 32 to ge the real value
|
|
|
|
*/
|
|
|
|
SFG_PROGRAM_MEMORY uint8_t SFG_weaponAttributeTable[SFG_WEAPONS_TOTAL] =
|
|
|
|
{
|
|
|
|
/* knife */ SFG_WEAPON_ATTRIBUTE(SFG_WEAPON_FIRE_TYPE_MELEE,400),
|
|
|
|
/* shotgun */ SFG_WEAPON_ATTRIBUTE(SFG_WEAPON_FIRE_TYPE_SPREAD_BULLETS,800),
|
|
|
|
/* m. gun */ SFG_WEAPON_ATTRIBUTE(SFG_WEAPON_FIRE_TYPE_BULLET,300),
|
|
|
|
/* r. laun. */ SFG_WEAPON_ATTRIBUTE(SFG_WEAPON_FIRE_TYPE_FIREBALL,900),
|
|
|
|
/* plasma */ SFG_WEAPON_ATTRIBUTE(SFG_WEAPON_FIRE_TYPE_PLASMA,350)
|
|
|
|
};
|
|
|
|
|
2019-09-25 09:51:19 -04:00
|
|
|
#endif // guard
|