precalculate warp values before beginning warp, and use them throughout the warp instead of recalculating in every function
standardize on always using the entire docked assembly for length and half-length calculation, instead of some places the assembly and some places just the dock leader
consolidate and simplify the compute_warpout* functions in light of the above
This maintains the type information which can be used for enforce
const-correctness and also for implementing more advanced ways of
handling the type information.
The warp-effect SEXP can now specify other animations from fireball.tbl that are not necessarily the standard or Knossos animations. Additionally, the SEXP can now specify the duration for the opening and closing of the warp effect.
This is similar to the other changes I already posted. Here the sound
instance handles are converted to their own handle type which will make
it easier to use the sound API.
The current scripting hook is pretty simple and straight forward but it
makes a couple of scripting applications harder to implement than
needed.
For example, a lot of scripts need to do some work every frame
for all or some objects. The script needs to manage an internal list of
all the objects that are affected by that list which includes removing
invalid objects to conserve resources. This effectively mirrors what the
engine already does and adds unnecessary overhead.
In these changes I added a generic event system which can be used by any
part of the code for providing callbacks when a specific event occurs.
As an example, I added hooks for the pre- and post-move events to the
object class which are called before and after physics are applied to an
object.
I integrated that feature into the scripting system so now a script can
simply register a function as a callback which will be called whenever
the target event is executed.
This can be used for mark parts of the code which should be unreachable
in normal execution. In debug mode, if such a statement is reached an
Error dialog is shown which aborts the execution. In release mode the
macro is replaced with a compiler specific expression that lets the
compiler know that this part is unreachable which allows it to optimize
the code better.
This adds a new class which allows to create type safe resource handle
types. At the moment, the engine uses ints pretty much everywhere for
providing handles to resources created by the specific subsystems. Since
all ints are the same to the C/C++ typesystem it is perfectly legal to
pass a sound handle to the graphics API as a buffer handle which will
obviously cause issues.
This adds a new type called "ID" which is a wrapper class for a generic
handle but with added type safety. An instance of this class cannot be
passed to a function expecting another type of handle which provided
compile-time type safety for these APIs.
As an initial test I converted the game sound handles to this new type.
I already found a bug in the mainhall system thanks to this new type.
The mainhall used the game sound handles as sound instance handles which
probably meant that that specific code never really worked right. I
removed the code since there was no better alternative for fixing it.
Applying the 'static' keyword to applicable routines both informs the
developer where the routine is likely to be used as well as allows the
compiler to perform additional optimizations.
Signed-off-by: Peter Mitsis <[email protected]>
This adds a step to the post-mission cleanup where we explicitly go through Objects and call obj_delete on everything not already deleted; this obviously needs testing.
Also a few cleanup steps in lab_init to make sure the lab isn't contaminated by leftover data from previously played missions.
Specifying the fog rendering options is now handled by the materials
system and the implementation of gr_set_fog was pretty much empty so I
removed it.
This allows to render screen space decals into the deferred lighting
buffers no matter how complex the underlying geometry is.
Currently there is only limited support for using this in the engine.
Only weapon impact decals are supported at the moment for testing
purposes.
This adds support for specifying multiple sounds for a single game sound
entry. The engine then selects which sound will be played based on the
strategy provided by the game data. This required a few changes to some
of the game code since previously every game sound had exactly one sound
file attached to it. The most notable change is that it is no longer
possible to determine the exact duration a sound can have so instead the
new code computes the maximum duration a sound can have and uses that
where appropriate.
This also adds support for randomizing the pitch and volume of the sound
to provide a more varied experience even if only a single sound is used.
One possible issue that exists is that the "sequential" strategy only
works globally at the moment so if two sources use the same game sound
concurrently then the two sources will share the sequence of sounds
since there is no sound instance data at the moment. That can be added
in a future change but should not present a huge issue for most
use-cases.
Visual Studio on Appveyor somehow causes deprecation error on _our_
definition of vsprintf. I have no idea why these changes introduced this
warning but I won't debug Visual Studio compiler bugs that I can't
reproduce with my Visual Studio version so I just disabled those
warnings.
There is nothing specific to OpenGL in that code anymore since it's all
handled in the shaders at this point. This will make the lighting
information available in the normal graphics code which allows to use
those values when filling the uniform buffer for the model rendering.
Adds a new "+Pulse Interval:" countermeasure field that enables the new behavior; all countermeasures that don't have this field defined still use the old behavior of the global frame counter.
This changes countermeasure logic quite a bit, but I attempted to mitigate performance implications by re-using an existing traversal of the object list in order to build the list of active countermeasures each frame. If any countermeasures are actively pulsing in a frame, the object list is traversed again, looking for homing weapons. Each homing weapon then goes through the active countermeasure list and checks to see if it got decoyed. Most of this central logic is unchanged from the old behavior, although no longer separated into two functions, and it should be more efficient since it's using a prepared list of active countermeasures instead of traversing the object list looking for countermeasures for every homing missile (which are themselves found by traversing the object list).