mirror of
https://github.com/TombEngine/TombEngine.git
synced 2025-04-28 15:57:59 +03:00
OIS input system (#556)
* Work
* Add ois.lib
* Add OIS headers/libs to project
* Fix small mistakes
* Update input.cpp
* Update input.cpp
* Update input.cpp
* Remove unnecessary event handlers as we are using direct polling
* Fix numpad controls not polling
* Enclose all input code under namespace, provide debug OIS lib variation
* Fix incorrect inventory call binding, add pause to control dialog
* Deselect by pushing inventory button as well, fix crossbow ammo string draw
* Demagic NUM_CONTROLS
* Verbose input init logging
* Calibrate and properly register movement analog axis input
* Fix crash when empty string is being displayed
* Initialize vibration interface, if it exists
* Register keyboard directional input as analog axis input as well
* Fix statistics exiting
* Fix weird UpdateInput call
* Copy current layout to configuration
* Fix issues with saving controls
* Register axis values for POVs too
* Register several POV directions at once
* Increase deadzone a bit
* Simplify enums
* Update input.cpp
* Move includes out of input.h
* Bump deadzone even further as it seems xbox controllers have massive axis errors
* Prevent event spamming in case OIS polling failed
* Destroy input system on exit, cosmetic changes
* Take deadzone into account when normalizing axis values
* Update TombEngine.vcxproj
* Resolve small precision loss in axis normalizing
* Clean up unused control constants and enums
* Update input.h
* Demagic InputActions enum
* Render pause menu header
* Introduce helper functions to modulate Lara turn rates and begin replacements
* Make turn directions explicit
* Conduct remaining replacements of turn rate modulations
* Update lara_helpers.cpp
* Add smoothstep function to math library
* Use scaled axis value for true analog input
* Update input.cpp
* Add Joey's camera rotation from old branch
* Fix camera not going back to previous position when stick is released
* Simplify ModulateLaraTurnRate()
* Widen look angle
* Avoid collisions with actions bound to non-directional axis
* Small tidying
* Remove unused header
* Remove copypasted code
* Mask flare animation
* Rename 5th and 6th axis to LT/RT
* Prototype force feedback support
* Add directional rumble support (probably XInput-only)
* Shake controller on startup if supports vibration
* Update OIS libs to support XInput FF
* Simplify ModulateLaraTurnRate()
* Update player modulation functions; simplify turning, leaning, and flexing in state functions; lara.h cleanup
* Update Win32ForceFeedback.h
* Fix crawl flex function
* Revert "Update Win32ForceFeedback.h"
This reverts commit aa7099ed5b
.
* Update OIS libs
* Add options for thumbstick camera and vibration
* Make use of autotarget option
* Display NON-SCREAMING names in controls, add hack to cancel axis value on both right+left input events
* Remove useless control hacks for simultaneous directional input
* Delete ten_itemdata_generated.h
* Add scroll lock to bindable controls
* Update input.cpp
* Update input.cpp
* Make input device namings consistent
* Bring back IN_SELECT override
* Fix crashing on startup and some other bugs
* Add rumble to some in-game events
* Add some more vibration events, stop them when going to menus
* Some changes to rumble power
* Add rumble for rocket/grenade launchers and explosive damage
* Add rumble for screen shake effect
* Fix 2 mistakes in inventory strings
* Rumble for camera more precisely
* Fix debounce in binocular mode
* Update camera.cpp
* Add HK lasersight rumble
* Simplify ModulateLaraLean()
* Update input.cpp
* Fix crawl flex modulation(?)
* Add slight rumble to harpoon and crossbow fire
* Remove the confusing counteracting turn rate reset in favour of something simpler
* Simplify turn rate reset input checks; leanup
* Clamp turn rate axis coeff when airborne
* Remove empty line
* Simplify a function
* Cleanup
* Fix rumble being constant
* Use shorter rumble time for shooting guns
* Fix single arm shooting
* Fix leaning left with joystick; clamp crawl flex max; tweak walk lean max; cleanup
* Don't do too long splat and jump smash vibrations
* Cancel turn rate when exiting water, grabbing ledge, or doing a splat
* Rename function
* Move ModulateLaraTurnRateY() callsin crawl and crouch turn states
* Reset turn rate when performing crawl vault
* Convert all health decrease events to DoDamage calls
* Remove SpasmEffectCount and unify touching with DoDamage
* Give specific time delay before sprint jump is possible
* Don't rumble on zero damage
* Reorder input pipeline to prevent left+right collisions
* Rename shady global
* Rumble when breaking neck in swandive
* Update lara_jump.cpp
* Don't vibrate on soft splat
* Fix combine item text alignment
* Vibrate in settings only if setting was changed
* Pulse gamepad on critical health condition
* Don't get out of water into objects
* Add critical air constant
Co-authored-by: Sezz
This commit is contained in:
parent
eb55180b05
commit
12663c7ce2
226 changed files with 5974 additions and 3333 deletions
59
Libs/ois/OIS.h
Normal file
59
Libs/ois/OIS.h
Normal file
|
@ -0,0 +1,59 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
/**\mainpage Object-oriented Input System
|
||||
*
|
||||
* Welcome to the documentation of OIS.
|
||||
*
|
||||
*
|
||||
* This website contains the documentation of the public API exposed by OIS.
|
||||
*
|
||||
* As the name of the library suggest, this is 100% Object-oriented.
|
||||
* Every C++ classes from the library is located inside the OIS namespace.
|
||||
*
|
||||
* This project is licensed under the terms of the <a href="https://opensource.org/licenses/Zlib">zlib/libpng licence</a>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef OIS_OISALL_H
|
||||
#define OIS_OISALL_H
|
||||
|
||||
#include "OISPrereqs.h"
|
||||
#include "OISObject.h"
|
||||
#include "OISMouse.h"
|
||||
#include "OISKeyboard.h"
|
||||
#include "OISJoyStick.h"
|
||||
#include "OISMultiTouch.h"
|
||||
#include "OISInputManager.h"
|
||||
#include "OISFactoryCreator.h"
|
||||
#include "OISException.h"
|
||||
#include "OISEvents.h"
|
||||
|
||||
#include "OISEffect.h"
|
||||
#include "OISInterface.h"
|
||||
#include "OISForceFeedback.h"
|
||||
|
||||
#endif
|
BIN
Libs/ois/OIS.lib
Normal file
BIN
Libs/ois/OIS.lib
Normal file
Binary file not shown.
78
Libs/ois/OISConfig.h
Normal file
78
Libs/ois/OISConfig.h
Normal file
|
@ -0,0 +1,78 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_CONFIG_HEADER
|
||||
#define OIS_CONFIG_HEADER
|
||||
|
||||
//----------------------------------------------------------------------------//
|
||||
//* This file contains defines for building certain parts of this Lib
|
||||
//* This file is not meant for External inclusion. However, you can edit this
|
||||
//* file before a build to effect what features are used internally
|
||||
//----------------------------------------------------------------------------//
|
||||
|
||||
/**
|
||||
@remarks
|
||||
These lines have no bearing on internal build of OIS. This is here for
|
||||
external build settings. Meaning, changing this does not require a
|
||||
rebuild of OIS. This just affects VC dll import settings, as the DLL
|
||||
build already defines this during its build for setting dll exports.
|
||||
The undefine here is here just incase you decide to only use
|
||||
DLL, and want to set it permently and recompile OIS too.. Avoid redefinition
|
||||
from DLL build of OIS.
|
||||
|
||||
So, if wanting to link against DLL version, just uncomment these lines.
|
||||
*/
|
||||
//#ifdef OIS_DYNAMIC_LIB
|
||||
//# undef OIS_DYNAMIC_LIB
|
||||
//#endif
|
||||
//#define OIS_DYNAMIC_LIB
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Build in support for LIRC / WinLIRC - remote control support.
|
||||
Requires Boost::asio
|
||||
@notes
|
||||
Experimental - Supports connecting and enumerating. Control does not
|
||||
yet return state or events
|
||||
*/
|
||||
//#define OIS_LIRC_SUPPORT
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Build in support for PC Nintendo WiiMote Win32 HID interface.
|
||||
Requires Boost::threads
|
||||
@notes
|
||||
Useable, but not quite finished - supports rumble, all buttons, & main orientation axis.
|
||||
Still needs Nunchuck, IR, and LED/Battery support.
|
||||
*/
|
||||
//#define OIS_WIN32_WIIMOTE_SUPPORT
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Build in support for Win32 XInput (Xbox 360 Controller)
|
||||
*/
|
||||
//#define OIS_WIN32_XINPUT_SUPPORT
|
||||
|
||||
#endif
|
286
Libs/ois/OISEffect.h
Normal file
286
Libs/ois/OISEffect.h
Normal file
|
@ -0,0 +1,286 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Effect_H
|
||||
#define OIS_Effect_H
|
||||
|
||||
#include "OISPrereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
//Predeclare some Effect Property structs
|
||||
class ForceEffect;
|
||||
class ConstantEffect;
|
||||
class RampEffect;
|
||||
class PeriodicEffect;
|
||||
class ConditionalEffect;
|
||||
|
||||
/**
|
||||
Force Feedback is a relatively complex set of properties to upload to a device.
|
||||
The best place for information on the different properties, effects, etc is in
|
||||
the DX Documentation and MSDN - there are even pretty graphs ther =)
|
||||
As this class is modeled on the the DX interface you can apply that same
|
||||
knowledge to creating effects via this class on any OS supported by OIS.
|
||||
|
||||
In anycase, this is the main class you will be using. There is *absolutely* no
|
||||
need to instance any of the supporting ForceEffect classes yourself.
|
||||
*/
|
||||
class _OISExport Effect
|
||||
{
|
||||
public:
|
||||
//! Type of force
|
||||
enum EForce {
|
||||
UnknownForce = 0,
|
||||
ConstantForce,
|
||||
RampForce,
|
||||
PeriodicForce,
|
||||
ConditionalForce,
|
||||
CustomForce,
|
||||
_ForcesNumber // Always keep in last position.
|
||||
};
|
||||
|
||||
static const char* getForceTypeName(EForce eValue);
|
||||
|
||||
//! Type of effect
|
||||
enum EType {
|
||||
//Type ----- Pairs with force:
|
||||
Unknown = 0, //UnknownForce
|
||||
Constant, //ConstantForce
|
||||
Ramp, //RampForce
|
||||
Square, //PeriodicForce
|
||||
Triangle, //PeriodicForce
|
||||
Sine, //PeriodicForce
|
||||
SawToothUp, //PeriodicForce
|
||||
SawToothDown, //PeriodicForce
|
||||
Friction, //ConditionalForce
|
||||
Damper, //ConditionalForce
|
||||
Inertia, //ConditionalForce
|
||||
Spring, //ConditionalForce
|
||||
Custom, //CustomForce
|
||||
_TypesNumber // Always keep in last position.
|
||||
};
|
||||
|
||||
static const char* getEffectTypeName(EType eValue);
|
||||
|
||||
//! Direction of the Force
|
||||
enum EDirection {
|
||||
NorthWest,
|
||||
North,
|
||||
NorthEast,
|
||||
East,
|
||||
SouthEast,
|
||||
South,
|
||||
SouthWest,
|
||||
West,
|
||||
_DirectionsNumber // Always keep in last position.
|
||||
};
|
||||
|
||||
static const char* getDirectionName(EDirection eValue);
|
||||
|
||||
/**
|
||||
This constructor allows you to set the force type and effect.
|
||||
*/
|
||||
Effect(EForce ef, EType et);
|
||||
virtual ~Effect();
|
||||
|
||||
const EForce force;
|
||||
const EType type;
|
||||
|
||||
//Infinite Time
|
||||
static const unsigned int OIS_INFINITE = 0xFFFFFFFF;
|
||||
|
||||
//-------------------------------------------------------------------//
|
||||
//--- Set these variables before uploading or modifying an effect ---//
|
||||
|
||||
//Direction to apply to the force - affects two axes+ effects
|
||||
EDirection direction;
|
||||
|
||||
//Number of button triggering an effect (-1 means no trigger)
|
||||
short trigger_button;
|
||||
|
||||
//Time to wait before an effect can be re-triggered (microseconds)
|
||||
unsigned int trigger_interval;
|
||||
|
||||
//Duration of an effect (microseconds)
|
||||
unsigned int replay_length;
|
||||
|
||||
//Time to wait before to start playing an effect (microseconds)
|
||||
unsigned int replay_delay;
|
||||
|
||||
//Get the specific Force Effect. This should be cast depending on the EForce
|
||||
ForceEffect* getForceEffect() const;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Set the number of Axes to use before the initial creation of the effect.
|
||||
Can only be done prior to creation! Use the FF interface to determine
|
||||
how many axes can be used (are availiable)
|
||||
*/
|
||||
void setNumAxes(short nAxes);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns the number of axes used in this effect
|
||||
*/
|
||||
short getNumAxes() const;
|
||||
|
||||
//------------- Library Internal -------------------------------------//
|
||||
/**
|
||||
set internally.. do not change or you will not be able to upload/stop
|
||||
this effect any more. It will become lost. It is mutable so even
|
||||
with const reference it can/will be changed by this lib
|
||||
*/
|
||||
mutable int _handle;
|
||||
|
||||
protected:
|
||||
// Prevent copying.
|
||||
Effect(const Effect&);
|
||||
Effect& operator=(Effect);
|
||||
|
||||
ForceEffect* effect; //Properties depend on EForce
|
||||
short axes; //Number of axes to use in effect
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------//
|
||||
/**
|
||||
Base class of all effect property classes
|
||||
*/
|
||||
class _OISExport ForceEffect
|
||||
{
|
||||
public:
|
||||
virtual ~ForceEffect() { }
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------//
|
||||
/**
|
||||
An optional envelope to be applied to the start/end of an effect. If any of
|
||||
these values are nonzero, then the envelope will be used in setting up the
|
||||
effect.
|
||||
*/
|
||||
class _OISExport Envelope : public ForceEffect
|
||||
{
|
||||
public:
|
||||
Envelope() :
|
||||
attackLength(0), attackLevel(0), fadeLength(0), fadeLevel(0) { }
|
||||
#if defined(OIS_MSVC_COMPILER)
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable : 4800)
|
||||
#endif
|
||||
bool isUsed() const
|
||||
{
|
||||
return attackLength | attackLevel | fadeLength | fadeLevel;
|
||||
}
|
||||
#if defined(OIS_MSVC_COMPILER)
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
// Duration of the attack (microseconds)
|
||||
unsigned int attackLength;
|
||||
|
||||
// Absolute level at the beginning of the attack (0 to 10K)
|
||||
// (automatically signed when necessary by FF core according to effect level sign)
|
||||
unsigned short attackLevel;
|
||||
|
||||
// Duration of fade (microseconds)
|
||||
unsigned int fadeLength;
|
||||
|
||||
// Absolute level at the end of fade (0 to 10K)
|
||||
// (automatically signed when necessary by FF core according to effect level sign)
|
||||
unsigned short fadeLevel;
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------//
|
||||
/**
|
||||
Use this class when dealing with Force type of Constant
|
||||
*/
|
||||
class _OISExport ConstantEffect : public ForceEffect
|
||||
{
|
||||
public:
|
||||
ConstantEffect() :
|
||||
level(5000) { }
|
||||
|
||||
Envelope envelope; //Optional envolope
|
||||
signed short level; //-10K to +10k
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------//
|
||||
/**
|
||||
Use this class when dealing with Force type of Ramp
|
||||
*/
|
||||
class _OISExport RampEffect : public ForceEffect
|
||||
{
|
||||
public:
|
||||
RampEffect() :
|
||||
startLevel(0), endLevel(0) { }
|
||||
|
||||
Envelope envelope; //Optional envelope
|
||||
signed short startLevel; //-10K to +10k
|
||||
signed short endLevel; //-10K to +10k
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------//
|
||||
/**
|
||||
Use this class when dealing with Force type of Periodic
|
||||
*/
|
||||
class _OISExport PeriodicEffect : public ForceEffect
|
||||
{
|
||||
public:
|
||||
PeriodicEffect() :
|
||||
magnitude(0), offset(0), phase(0), period(0) { }
|
||||
|
||||
Envelope envelope; //Optional Envelope
|
||||
|
||||
unsigned short magnitude; //0 to 10,0000
|
||||
signed short offset;
|
||||
unsigned short phase; //Position at which playback begins 0 to 35,999
|
||||
unsigned int period; //Period of effect (microseconds)
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------//
|
||||
/**
|
||||
Use this class when dealing with Force type of Condional
|
||||
*/
|
||||
class _OISExport ConditionalEffect : public ForceEffect
|
||||
{
|
||||
public:
|
||||
ConditionalEffect() :
|
||||
rightCoeff(0), leftCoeff(0), rightSaturation(0), leftSaturation(0),
|
||||
deadband(0), center(0) { }
|
||||
|
||||
signed short rightCoeff; //-10k to +10k (Positive Coeff)
|
||||
signed short leftCoeff; //-10k to +10k (Negative Coeff)
|
||||
|
||||
unsigned short rightSaturation; //0 to 10k (Pos Saturation)
|
||||
unsigned short leftSaturation; //0 to 10k (Neg Saturation)
|
||||
|
||||
//Region around center in which the condition is not active, in the range
|
||||
//from 0 through 10,000
|
||||
unsigned short deadband;
|
||||
|
||||
//(Offset in DX) -10k and 10k
|
||||
signed short center;
|
||||
};
|
||||
}
|
||||
#endif //OIS_Effect_H
|
47
Libs/ois/OISEvents.h
Normal file
47
Libs/ois/OISEvents.h
Normal file
|
@ -0,0 +1,47 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef _OIS_EVENTHEADERS_
|
||||
#define _OIS_EVENTHEADERS_
|
||||
#include "OISPrereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
/**
|
||||
Base class of all events
|
||||
*/
|
||||
class _OISExport EventArg
|
||||
{
|
||||
public:
|
||||
explicit EventArg(Object* obj) :
|
||||
device(obj) { }
|
||||
virtual ~EventArg() { }
|
||||
|
||||
//! Pointer to the Input Device
|
||||
const Object* device;
|
||||
};
|
||||
}
|
||||
|
||||
#endif //_OIS_EVENTHEADERS_
|
101
Libs/ois/OISException.h
Normal file
101
Libs/ois/OISException.h
Normal file
|
@ -0,0 +1,101 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef _OIS_EXCEPTION_HEADER_
|
||||
#define _OIS_EXCEPTION_HEADER_
|
||||
#include "OISPrereqs.h"
|
||||
#include <exception>
|
||||
|
||||
#ifdef OIS_WIN32_PLATFORM
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable : 4275) //Silence warning from MSVC when using std::exception as the base class of a dll-interface class (OIS::Exception)
|
||||
#endif
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
//! Simple enum's for dealing with exceptions
|
||||
enum OIS_ERROR {
|
||||
E_InputDisconnected,
|
||||
E_InputDeviceNonExistant,
|
||||
E_InputDeviceNotSupported,
|
||||
E_DeviceFull,
|
||||
E_NotSupported,
|
||||
E_NotImplemented,
|
||||
E_Duplicate,
|
||||
E_InvalidParam,
|
||||
E_General
|
||||
};
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Class for handling OIS exceptions. Much cleaner than checking every method for reurn value.
|
||||
Inherits from std::exception so you can simply log those messages if you want to be generic.
|
||||
Also note that this has a source file now since OSX was not finding the OIS::Exception symbol
|
||||
which would cause program abortion with now correponding exception type.
|
||||
*/
|
||||
class _OISExport Exception : public std::exception
|
||||
{
|
||||
public:
|
||||
//! Creates exception object
|
||||
Exception(OIS_ERROR err, const char* str, int line, const char* file) :
|
||||
eType(err), eLine(line), eFile(file), eText(str) { }
|
||||
|
||||
Exception(const Exception& other) :
|
||||
eType(other.eType), eLine(other.eLine), eFile(other.eFile), eText(other.eText) { }
|
||||
|
||||
~Exception() throw() { }
|
||||
|
||||
virtual const char* what() const throw();
|
||||
|
||||
//! The type of exception raised
|
||||
const OIS_ERROR eType;
|
||||
//! The line number it occurred on
|
||||
const int eLine;
|
||||
//! The source file
|
||||
const char* eFile;
|
||||
//! A message passed along when the exception was raised
|
||||
const char* eText;
|
||||
|
||||
private:
|
||||
// Unimplemented and unaccessible due to const members.
|
||||
Exception& operator=(Exception);
|
||||
};
|
||||
}
|
||||
|
||||
//! Use this macro to handle exceptions easily
|
||||
#define OIS_EXCEPT(err, str) throw(OIS::Exception(err, str, __LINE__, __FILE__))
|
||||
|
||||
//TODO choose what to do with this...
|
||||
//#define OIS_WARN( err, str ) throw( OIS::Exception(err, str, __LINE__, __FILE__) )
|
||||
#define OIS_WARN(err, str) \
|
||||
do \
|
||||
{ \
|
||||
} while(0)
|
||||
|
||||
#ifdef OIS_WIN32_PLATFORM
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
#endif //_OIS_EXCEPTION_HEADER_
|
84
Libs/ois/OISFactoryCreator.h
Normal file
84
Libs/ois/OISFactoryCreator.h
Normal file
|
@ -0,0 +1,84 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_FactoryCreator_H
|
||||
#define OIS_FactoryCreator_H
|
||||
|
||||
#include "OISPrereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
/**
|
||||
Interface for creating devices - all devices ultimately get enumerated/created via a factory.
|
||||
A factory can create multiple types of objects.
|
||||
*/
|
||||
class _OISExport FactoryCreator
|
||||
{
|
||||
public:
|
||||
/**
|
||||
@remarks Virtual Destructor
|
||||
*/
|
||||
virtual ~FactoryCreator() {};
|
||||
|
||||
/**
|
||||
@remarks Return a list of all unused devices the factory maintains
|
||||
*/
|
||||
virtual DeviceList freeDeviceList() = 0;
|
||||
|
||||
/**
|
||||
@remarks Number of total devices of requested type
|
||||
@param iType Type of devices to check
|
||||
*/
|
||||
virtual int totalDevices(Type iType) = 0;
|
||||
|
||||
/**
|
||||
@remarks Number of free devices of requested type
|
||||
@param iType Type of devices to check
|
||||
*/
|
||||
virtual int freeDevices(Type iType) = 0;
|
||||
|
||||
/**
|
||||
@remarks Does a Type exist with the given vendor name
|
||||
@param iType Type to check
|
||||
@param vendor Vendor name to test
|
||||
*/
|
||||
virtual bool vendorExist(Type iType, const std::string& vendor) = 0;
|
||||
|
||||
/**
|
||||
@remarks Creates the object
|
||||
@param iType Type to create
|
||||
@param bufferMode True to setup for buffered events
|
||||
@param vendor Create a device with the vendor name, "" means vendor name is unimportant
|
||||
*/
|
||||
virtual Object* createObject(InputManager* creator, Type iType, bool bufferMode, const std::string& vendor = "") = 0;
|
||||
|
||||
/**
|
||||
@remarks Destroys object
|
||||
@param obj Object to destroy
|
||||
*/
|
||||
virtual void destroyObject(Object* obj) = 0;
|
||||
};
|
||||
}
|
||||
#endif //OIS_FactoryCreator_H
|
123
Libs/ois/OISForceFeedback.h
Normal file
123
Libs/ois/OISForceFeedback.h
Normal file
|
@ -0,0 +1,123 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_ForceFeedBack_H
|
||||
#define OIS_ForceFeedBack_H
|
||||
|
||||
#include "OISPrereqs.h"
|
||||
#include "OISInterface.h"
|
||||
#include "OISEffect.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
/**
|
||||
Interface class for dealing with Force Feedback devices
|
||||
*/
|
||||
class _OISExport ForceFeedback : public Interface
|
||||
{
|
||||
public:
|
||||
ForceFeedback();
|
||||
virtual ~ForceFeedback() { }
|
||||
|
||||
/**
|
||||
@remarks
|
||||
This is like setting the master volume of an audio device.
|
||||
Individual effects have gain levels; however, this affects all
|
||||
effects at once.
|
||||
Note: If the device does not support master gain setting, nothing is done
|
||||
@param level
|
||||
A value between 0.0 and 1.0 represent the percentage of gain. 1.0
|
||||
being the highest possible force level (means no scaling).
|
||||
*/
|
||||
virtual void setMasterGain(float level) = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
If using Force Feedback effects, this should be turned off
|
||||
before uploading any effects. Auto centering is the motor moving
|
||||
the joystick back to center. DirectInput only has an on/off setting,
|
||||
whereas linux has levels.. Though, we go with DI's on/off mode only
|
||||
Note: If the device does not support auto-centering, nothing is done
|
||||
@param auto_on
|
||||
true to turn auto centering on, false to turn off.
|
||||
*/
|
||||
virtual void setAutoCenterMode(bool auto_on) = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Creates and Plays the effect immediately. If the device is full
|
||||
of effects, it will fail to be uploaded. You will know this by
|
||||
an invalid Effect Handle
|
||||
*/
|
||||
virtual void upload(const Effect* effect) = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Modifies an effect that is currently playing
|
||||
*/
|
||||
virtual void modify(const Effect* effect) = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Remove the effect from the device
|
||||
*/
|
||||
virtual void remove(const Effect* effect) = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Get the number of supported Axes for FF usage
|
||||
*/
|
||||
virtual short getFFAxesNumber() = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Get the current load (%, in [0, 100] of the FF device memory
|
||||
*/
|
||||
virtual unsigned short getFFMemoryLoad() = 0;
|
||||
|
||||
typedef std::multimap<Effect::EForce, Effect::EType> SupportedEffectList;
|
||||
/**
|
||||
@remarks
|
||||
Get a list of all supported effects
|
||||
*/
|
||||
const SupportedEffectList& getSupportedEffects() const;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Tell if a given force / effect type pair is supported
|
||||
*/
|
||||
bool supportsEffect(Effect::EForce force, Effect::EType type) const;
|
||||
|
||||
void _addEffectTypes(Effect::EForce force, Effect::EType type);
|
||||
void _setGainSupport(bool on);
|
||||
void _setAutoCenterSupport(bool on);
|
||||
|
||||
protected:
|
||||
SupportedEffectList mSupportedEffects;
|
||||
bool mSetGainSupport;
|
||||
bool mSetAutoCenterSupport;
|
||||
};
|
||||
}
|
||||
#endif //OIS_ForceFeedBack_H
|
213
Libs/ois/OISInputManager.h
Normal file
213
Libs/ois/OISInputManager.h
Normal file
|
@ -0,0 +1,213 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_InputManager_H
|
||||
#define OIS_InputManager_H
|
||||
|
||||
#include "OISPrereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
//Forward declare a couple of classes we might use later
|
||||
class LIRCFactoryCreator;
|
||||
class WiiMoteFactoryCreator;
|
||||
|
||||
/**
|
||||
Base Manager class. No longer a Singleton; so feel free to create as many InputManager's as you have
|
||||
windows.
|
||||
*/
|
||||
class _OISExport InputManager
|
||||
{
|
||||
public:
|
||||
/**
|
||||
@remarks
|
||||
Returns version number (useful in DLL/SO libs)
|
||||
@returns
|
||||
Bits: 1-8 Patch number, 9-16 Minor version, 17-32 Major version
|
||||
*/
|
||||
static unsigned int getVersionNumber();
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns version string (useful in DLL/SO libs)
|
||||
@returns
|
||||
Version name
|
||||
*/
|
||||
const std::string& getVersionName();
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Creates appropriate input system dependent on platform.
|
||||
@param winHandle
|
||||
Contains OS specific window handle (such as HWND or X11 Window)
|
||||
@returns
|
||||
A pointer to the created manager, or raises Exception
|
||||
*/
|
||||
static InputManager* createInputSystem(std::size_t winHandle);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Creates appropriate input system dependent on platform.
|
||||
@param paramList
|
||||
ParamList contains OS specific info (such as HWND and HINSTANCE for window apps),
|
||||
and access mode.
|
||||
@returns
|
||||
A pointer to the created manager, or raises Exception
|
||||
*/
|
||||
static InputManager* createInputSystem(ParamList& paramList);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Destroys the InputManager
|
||||
@param manager
|
||||
Manager to destroy
|
||||
*/
|
||||
static void destroyInputSystem(InputManager* manager);
|
||||
|
||||
/**
|
||||
@remarks Gets the name of the current platform input system
|
||||
*/
|
||||
const std::string& inputSystemName();
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns the number of the specified OIS::Type devices discovered by OIS
|
||||
@param iType
|
||||
Type that you are interested in
|
||||
*/
|
||||
int getNumberOfDevices(Type iType);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Lists all unused devices
|
||||
@returns
|
||||
DeviceList which contains Type and vendor of device
|
||||
*/
|
||||
DeviceList listFreeDevices();
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Tries to create an object with the specified vendor. If you have no
|
||||
preference of vendor, leave vender as default (""). Raises exception on failure
|
||||
*/
|
||||
Object* createInputObject(Type iType, bool bufferMode, const std::string& vendor = "");
|
||||
|
||||
/**
|
||||
@remarks Destroys Input Object
|
||||
*/
|
||||
void destroyInputObject(Object* obj);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Add a custom object factory to allow for user controls.
|
||||
@param factory
|
||||
Factory instance to add
|
||||
@notes
|
||||
Make sure you do not delete the factory before devices created from
|
||||
the factory are destroyed (either by calling RemoveFactoryCreator, or shutting down
|
||||
the input system). Order should be something like the following:
|
||||
* Create Input System
|
||||
* Create Factory Instance
|
||||
* AddFactoryCreator(factory)
|
||||
* Create a device from the InputManager (device created by factory)
|
||||
* One of the follwoing:
|
||||
* removeFactoryCreator(factory)
|
||||
* inputManager->destroyInputObject(obj)
|
||||
* destroyInputSystem(inputManager)
|
||||
* destroy Factory Instance
|
||||
You can safely delete the factory instance once you have removed it or shut down the
|
||||
input manager.
|
||||
*/
|
||||
void addFactoryCreator(FactoryCreator* factory);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Remove a previously added object factory
|
||||
@param factory
|
||||
Factory object to remove.
|
||||
@notes
|
||||
Removing a factory will automatically destroy any Objects created from the factory
|
||||
*/
|
||||
void removeFactoryCreator(FactoryCreator* factory);
|
||||
|
||||
//! All generic devices OIS supports internally (if they are compiled in)
|
||||
enum AddOnFactories {
|
||||
AddOn_All = 0, //All Devices
|
||||
AddOn_LIRC = 1, //PC Linux Infrared Remote Control
|
||||
AddOn_WiiMote = 2 //PC WiiMote Support
|
||||
};
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Enable an addon FactoryCreator extension. By default, none are activated.
|
||||
If the desired support was not compiled in, this has no effect. Calling
|
||||
multiple times has no effect. Once activated, there is no way to deactivate -
|
||||
simply destroy and recreate input manager.
|
||||
*/
|
||||
void enableAddOnFactory(AddOnFactories factory);
|
||||
|
||||
protected:
|
||||
/**
|
||||
@remarks
|
||||
Called from createInputSystem, gives derived input class a chance to setup after it is created
|
||||
*/
|
||||
virtual void _initialize(ParamList& paramList) = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Derived classes must provide input system name
|
||||
*/
|
||||
explicit InputManager(const std::string& name);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Virtual Destructor - this base class will clean up all devices still opened in mFactoryObjects list
|
||||
*/
|
||||
virtual ~InputManager();
|
||||
|
||||
//! OIS Version name
|
||||
const std::string m_VersionName;
|
||||
|
||||
//! FactoryCreator list
|
||||
FactoryList mFactories;
|
||||
|
||||
//! Factory created objects - useful so we can find creator to send destruction request to
|
||||
FactoryCreatedObject mFactoryObjects;
|
||||
|
||||
//! Name of the input system
|
||||
const std::string mInputSystemName;
|
||||
|
||||
//! Extra factory (not enabled by default)
|
||||
LIRCFactoryCreator* m_lircSupport;
|
||||
WiiMoteFactoryCreator* m_wiiMoteSupport;
|
||||
|
||||
private:
|
||||
// Prevent copying.
|
||||
InputManager(const InputManager&);
|
||||
InputManager& operator=(const InputManager&);
|
||||
};
|
||||
}
|
||||
#endif
|
49
Libs/ois/OISInterface.h
Normal file
49
Libs/ois/OISInterface.h
Normal file
|
@ -0,0 +1,49 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Interface_H
|
||||
#define OIS_Interface_H
|
||||
|
||||
#include "OISPrereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
/**
|
||||
An Object's interface is a way to gain write access to devices which support
|
||||
it. For example, force feedack.
|
||||
*/
|
||||
class _OISExport Interface
|
||||
{
|
||||
public:
|
||||
virtual ~Interface() {};
|
||||
|
||||
//! Type of Interface
|
||||
enum IType {
|
||||
ForceFeedback,
|
||||
Reserved
|
||||
};
|
||||
};
|
||||
}
|
||||
#endif //OIS_Interface_H
|
254
Libs/ois/OISJoyStick.h
Normal file
254
Libs/ois/OISJoyStick.h
Normal file
|
@ -0,0 +1,254 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Joystick_H
|
||||
#define OIS_Joystick_H
|
||||
#include "OISObject.h"
|
||||
#include "OISEvents.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
/** @remarks default sensitivity for vector3 component of joystick */
|
||||
#define OIS_JOYSTICK_VECTOR3_DEFAULT 2.28f
|
||||
|
||||
//! POV / HAT Joystick component
|
||||
class _OISExport Pov : public Component
|
||||
{
|
||||
public:
|
||||
Pov() :
|
||||
Component(OIS_POV), direction(0) { }
|
||||
|
||||
static const int Centered = 0x00000000;
|
||||
static const int North = 0x00000001;
|
||||
static const int South = 0x00000010;
|
||||
static const int East = 0x00000100;
|
||||
static const int West = 0x00001000;
|
||||
static const int NorthEast = 0x00000101;
|
||||
static const int SouthEast = 0x00000110;
|
||||
static const int NorthWest = 0x00001001;
|
||||
static const int SouthWest = 0x00001010;
|
||||
|
||||
int direction;
|
||||
};
|
||||
|
||||
//! A sliding axis - only used in Win32 Right Now
|
||||
class _OISExport Slider : public Component
|
||||
{
|
||||
public:
|
||||
Slider() :
|
||||
Component(OIS_Slider), abX(0), abY(0) {};
|
||||
//! true if pushed, false otherwise
|
||||
int abX, abY;
|
||||
};
|
||||
|
||||
/**
|
||||
Represents the state of the joystick
|
||||
All members are valid for both buffered and non buffered mode
|
||||
Sticks with zero values are not present on the device
|
||||
*/
|
||||
class _OISExport JoyStickState
|
||||
{
|
||||
public:
|
||||
//! Constructor
|
||||
JoyStickState() { clear(); }
|
||||
|
||||
//! Represents all the buttons (uses a bitset)
|
||||
std::vector<bool> mButtons;
|
||||
|
||||
//! Represents all the single axes on the device
|
||||
std::vector<Axis> mAxes;
|
||||
|
||||
//! Represents the value of a POV. Maximum of 4
|
||||
Pov mPOV[4];
|
||||
|
||||
//! Represent the max sliders
|
||||
Slider mSliders[4];
|
||||
|
||||
//! Represents all Vector type controls the device exports
|
||||
std::vector<Vector3> mVectors;
|
||||
|
||||
//! internal method to reset all variables to initial values
|
||||
void clear()
|
||||
{
|
||||
for(std::vector<bool>::iterator i = mButtons.begin(), e = mButtons.end(); i != e; ++i)
|
||||
{
|
||||
(*i) = false;
|
||||
}
|
||||
|
||||
for(std::vector<Axis>::iterator i = mAxes.begin(), e = mAxes.end(); i != e; ++i)
|
||||
{
|
||||
i->absOnly = true; //Currently, joysticks only report Absolute values
|
||||
i->clear();
|
||||
}
|
||||
|
||||
for(std::vector<Vector3>::iterator i = mVectors.begin(), e = mVectors.end(); i != e; ++i)
|
||||
{
|
||||
i->clear();
|
||||
}
|
||||
|
||||
for(int i = 0; i < 4; ++i)
|
||||
{
|
||||
mPOV[i].direction = Pov::Centered;
|
||||
mSliders[i].abX = mSliders[i].abY = 0;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/** Specialised for joystick events */
|
||||
class _OISExport JoyStickEvent : public EventArg
|
||||
{
|
||||
public:
|
||||
JoyStickEvent(Object* obj, const JoyStickState& st) :
|
||||
EventArg(obj), state(st) { }
|
||||
virtual ~JoyStickEvent() { }
|
||||
|
||||
const JoyStickState& state;
|
||||
|
||||
private:
|
||||
// Prevent copying.
|
||||
JoyStickEvent(const JoyStickEvent&);
|
||||
JoyStickEvent& operator=(JoyStickEvent);
|
||||
};
|
||||
|
||||
/**
|
||||
To recieve buffered joystick input, derive a class from this, and implement the
|
||||
methods here. Then set the call back to your JoyStick instance with JoyStick::setEventCallback
|
||||
Each JoyStick instance can use the same callback class, as a devID number will be provided
|
||||
to differentiate between connected joysticks. Of course, each can have a seperate
|
||||
callback instead.
|
||||
*/
|
||||
class _OISExport JoyStickListener
|
||||
{
|
||||
public:
|
||||
virtual ~JoyStickListener() { }
|
||||
/** @remarks Joystick button down event */
|
||||
virtual bool buttonPressed(const JoyStickEvent& arg, int button) = 0;
|
||||
|
||||
/** @remarks Joystick button up event */
|
||||
virtual bool buttonReleased(const JoyStickEvent& arg, int button) = 0;
|
||||
|
||||
/** @remarks Joystick axis moved event */
|
||||
virtual bool axisMoved(const JoyStickEvent& arg, int axis) = 0;
|
||||
|
||||
//-- Not so common control events, so are not required --//
|
||||
//! Joystick Event, and sliderID
|
||||
virtual bool sliderMoved(const JoyStickEvent& arg, int index)
|
||||
{
|
||||
OIS_UNUSED(arg);
|
||||
OIS_UNUSED(index);
|
||||
return true;
|
||||
}
|
||||
|
||||
//! Joystick Event, and povID
|
||||
virtual bool povMoved(const JoyStickEvent& arg, int index)
|
||||
{
|
||||
OIS_UNUSED(arg);
|
||||
OIS_UNUSED(index);
|
||||
return true;
|
||||
}
|
||||
|
||||
//! Joystick Event, and Vector3ID
|
||||
virtual bool vector3Moved(const JoyStickEvent& arg, int index)
|
||||
{
|
||||
OIS_UNUSED(arg);
|
||||
OIS_UNUSED(index);
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
Joystick base class. To be implemented by specific system (ie. DirectX joystick)
|
||||
This class is useful as you remain OS independent using this common interface.
|
||||
*/
|
||||
class _OISExport JoyStick : public Object
|
||||
{
|
||||
public:
|
||||
virtual ~JoyStick() { }
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns the number of requested components
|
||||
@param cType
|
||||
The ComponentType you are interested in knowing about
|
||||
*/
|
||||
int getNumberOfComponents(ComponentType cType) const;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Sets a cutoff limit for changes in the Vector3 component for movement to
|
||||
be ignored. Helps reduce much event traffic for frequent small/sensitive
|
||||
changes
|
||||
@param degrees
|
||||
The degree under which Vector3 events should be discarded
|
||||
*/
|
||||
void setVector3Sensitivity(float degrees = OIS_JOYSTICK_VECTOR3_DEFAULT);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns the sensitivity cutoff for Vector3 Component
|
||||
*/
|
||||
float getVector3Sensitivity() const;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Register/unregister a JoyStick Listener - Only one allowed for simplicity. If broadcasting
|
||||
is neccessary, just broadcast from the callback you registered.
|
||||
@param joyListener
|
||||
Send a pointer to a class derived from JoyStickListener or 0 to clear the callback
|
||||
*/
|
||||
virtual void setEventCallback(JoyStickListener* joyListener);
|
||||
|
||||
/** @remarks Returns currently set callback.. or null */
|
||||
JoyStickListener* getEventCallback() const;
|
||||
|
||||
/** @remarks Returns the state of the joystick - is valid for both buffered and non buffered mode */
|
||||
const JoyStickState& getJoyStickState() const { return mState; }
|
||||
|
||||
//! The minimal axis value
|
||||
static const int MIN_AXIS = -32768;
|
||||
|
||||
//! The maximum axis value
|
||||
static const int MAX_AXIS = 32767;
|
||||
|
||||
protected:
|
||||
JoyStick(const std::string& vendor, bool buffered, int devID, InputManager* creator);
|
||||
|
||||
//! Number of sliders
|
||||
int mSliders;
|
||||
|
||||
//! Number of POVs
|
||||
int mPOVs;
|
||||
|
||||
//! The JoyStickState structure (contains all component values)
|
||||
JoyStickState mState;
|
||||
|
||||
//! The callback listener
|
||||
JoyStickListener* mListener;
|
||||
|
||||
//! Adjustment factor for orientation vector accuracy
|
||||
float mVector3Sensitivity;
|
||||
};
|
||||
}
|
||||
#endif
|
343
Libs/ois/OISKeyboard.h
Normal file
343
Libs/ois/OISKeyboard.h
Normal file
|
@ -0,0 +1,343 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Keyboard_H
|
||||
#define OIS_Keyboard_H
|
||||
#include "OISObject.h"
|
||||
#include "OISEvents.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
//! Keyboard scan codes
|
||||
enum KeyCode {
|
||||
KC_UNASSIGNED = 0x00,
|
||||
KC_ESCAPE = 0x01,
|
||||
KC_1 = 0x02,
|
||||
KC_2 = 0x03,
|
||||
KC_3 = 0x04,
|
||||
KC_4 = 0x05,
|
||||
KC_5 = 0x06,
|
||||
KC_6 = 0x07,
|
||||
KC_7 = 0x08,
|
||||
KC_8 = 0x09,
|
||||
KC_9 = 0x0A,
|
||||
KC_0 = 0x0B,
|
||||
KC_MINUS = 0x0C, // - on main keyboard
|
||||
KC_EQUALS = 0x0D,
|
||||
KC_BACK = 0x0E, // backspace
|
||||
KC_TAB = 0x0F,
|
||||
KC_Q = 0x10,
|
||||
KC_W = 0x11,
|
||||
KC_E = 0x12,
|
||||
KC_R = 0x13,
|
||||
KC_T = 0x14,
|
||||
KC_Y = 0x15,
|
||||
KC_U = 0x16,
|
||||
KC_I = 0x17,
|
||||
KC_O = 0x18,
|
||||
KC_P = 0x19,
|
||||
KC_LBRACKET = 0x1A,
|
||||
KC_RBRACKET = 0x1B,
|
||||
KC_RETURN = 0x1C, // Enter on main keyboard
|
||||
KC_LCONTROL = 0x1D,
|
||||
KC_A = 0x1E,
|
||||
KC_S = 0x1F,
|
||||
KC_D = 0x20,
|
||||
KC_F = 0x21,
|
||||
KC_G = 0x22,
|
||||
KC_H = 0x23,
|
||||
KC_J = 0x24,
|
||||
KC_K = 0x25,
|
||||
KC_L = 0x26,
|
||||
KC_SEMICOLON = 0x27,
|
||||
KC_APOSTROPHE = 0x28,
|
||||
KC_GRAVE = 0x29, // accent
|
||||
KC_LSHIFT = 0x2A,
|
||||
KC_BACKSLASH = 0x2B,
|
||||
KC_Z = 0x2C,
|
||||
KC_X = 0x2D,
|
||||
KC_C = 0x2E,
|
||||
KC_V = 0x2F,
|
||||
KC_B = 0x30,
|
||||
KC_N = 0x31,
|
||||
KC_M = 0x32,
|
||||
KC_COMMA = 0x33,
|
||||
KC_PERIOD = 0x34, // . on main keyboard
|
||||
KC_SLASH = 0x35, // / on main keyboard
|
||||
KC_RSHIFT = 0x36,
|
||||
KC_MULTIPLY = 0x37, // * on numeric keypad
|
||||
KC_LMENU = 0x38, // left Alt
|
||||
KC_SPACE = 0x39,
|
||||
KC_CAPITAL = 0x3A,
|
||||
KC_F1 = 0x3B,
|
||||
KC_F2 = 0x3C,
|
||||
KC_F3 = 0x3D,
|
||||
KC_F4 = 0x3E,
|
||||
KC_F5 = 0x3F,
|
||||
KC_F6 = 0x40,
|
||||
KC_F7 = 0x41,
|
||||
KC_F8 = 0x42,
|
||||
KC_F9 = 0x43,
|
||||
KC_F10 = 0x44,
|
||||
KC_NUMLOCK = 0x45,
|
||||
KC_SCROLL = 0x46, // Scroll Lock
|
||||
KC_NUMPAD7 = 0x47,
|
||||
KC_NUMPAD8 = 0x48,
|
||||
KC_NUMPAD9 = 0x49,
|
||||
KC_SUBTRACT = 0x4A, // - on numeric keypad
|
||||
KC_NUMPAD4 = 0x4B,
|
||||
KC_NUMPAD5 = 0x4C,
|
||||
KC_NUMPAD6 = 0x4D,
|
||||
KC_ADD = 0x4E, // + on numeric keypad
|
||||
KC_NUMPAD1 = 0x4F,
|
||||
KC_NUMPAD2 = 0x50,
|
||||
KC_NUMPAD3 = 0x51,
|
||||
KC_NUMPAD0 = 0x52,
|
||||
KC_DECIMAL = 0x53, // . on numeric keypad
|
||||
KC_OEM_102 = 0x56, // < > | on UK/Germany keyboards
|
||||
KC_F11 = 0x57,
|
||||
KC_F12 = 0x58,
|
||||
KC_F13 = 0x64, // (NEC PC98)
|
||||
KC_F14 = 0x65, // (NEC PC98)
|
||||
KC_F15 = 0x66, // (NEC PC98)
|
||||
KC_KANA = 0x70, // (Japanese keyboard)
|
||||
KC_ABNT_C1 = 0x73, // / ? on Portugese (Brazilian) keyboards
|
||||
KC_CONVERT = 0x79, // (Japanese keyboard)
|
||||
KC_NOCONVERT = 0x7B, // (Japanese keyboard)
|
||||
KC_YEN = 0x7D, // (Japanese keyboard)
|
||||
KC_ABNT_C2 = 0x7E, // Numpad . on Portugese (Brazilian) keyboards
|
||||
KC_NUMPADEQUALS = 0x8D, // = on numeric keypad (NEC PC98)
|
||||
KC_PREVTRACK = 0x90, // Previous Track (KC_CIRCUMFLEX on Japanese keyboard)
|
||||
KC_AT = 0x91, // (NEC PC98)
|
||||
KC_COLON = 0x92, // (NEC PC98)
|
||||
KC_UNDERLINE = 0x93, // (NEC PC98)
|
||||
KC_KANJI = 0x94, // (Japanese keyboard)
|
||||
KC_STOP = 0x95, // (NEC PC98)
|
||||
KC_AX = 0x96, // (Japan AX)
|
||||
KC_UNLABELED = 0x97, // (J3100)
|
||||
KC_NEXTTRACK = 0x99, // Next Track
|
||||
KC_NUMPADENTER = 0x9C, // Enter on numeric keypad
|
||||
KC_RCONTROL = 0x9D,
|
||||
KC_MUTE = 0xA0, // Mute
|
||||
KC_CALCULATOR = 0xA1, // Calculator
|
||||
KC_PLAYPAUSE = 0xA2, // Play / Pause
|
||||
KC_MEDIASTOP = 0xA4, // Media Stop
|
||||
KC_TWOSUPERIOR = 0xAA, // ² on French AZERTY keyboard (same place as ~ ` on QWERTY)
|
||||
KC_VOLUMEDOWN = 0xAE, // Volume -
|
||||
KC_VOLUMEUP = 0xB0, // Volume +
|
||||
KC_WEBHOME = 0xB2, // Web home
|
||||
KC_NUMPADCOMMA = 0xB3, // , on numeric keypad (NEC PC98)
|
||||
KC_DIVIDE = 0xB5, // / on numeric keypad
|
||||
KC_SYSRQ = 0xB7,
|
||||
KC_RMENU = 0xB8, // right Alt
|
||||
KC_PAUSE = 0xC5, // Pause
|
||||
KC_HOME = 0xC7, // Home on arrow keypad
|
||||
KC_UP = 0xC8, // UpArrow on arrow keypad
|
||||
KC_PGUP = 0xC9, // PgUp on arrow keypad
|
||||
KC_LEFT = 0xCB, // LeftArrow on arrow keypad
|
||||
KC_RIGHT = 0xCD, // RightArrow on arrow keypad
|
||||
KC_END = 0xCF, // End on arrow keypad
|
||||
KC_DOWN = 0xD0, // DownArrow on arrow keypad
|
||||
KC_PGDOWN = 0xD1, // PgDn on arrow keypad
|
||||
KC_INSERT = 0xD2, // Insert on arrow keypad
|
||||
KC_DELETE = 0xD3, // Delete on arrow keypad
|
||||
KC_LWIN = 0xDB, // Left Windows key
|
||||
KC_RWIN = 0xDC, // Right Windows key
|
||||
KC_APPS = 0xDD, // AppMenu key
|
||||
KC_POWER = 0xDE, // System Power
|
||||
KC_SLEEP = 0xDF, // System Sleep
|
||||
KC_WAKE = 0xE3, // System Wake
|
||||
KC_WEBSEARCH = 0xE5, // Web Search
|
||||
KC_WEBFAVORITES = 0xE6, // Web Favorites
|
||||
KC_WEBREFRESH = 0xE7, // Web Refresh
|
||||
KC_WEBSTOP = 0xE8, // Web Stop
|
||||
KC_WEBFORWARD = 0xE9, // Web Forward
|
||||
KC_WEBBACK = 0xEA, // Web Back
|
||||
KC_MYCOMPUTER = 0xEB, // My Computer
|
||||
KC_MAIL = 0xEC, // Mail
|
||||
KC_MEDIASELECT = 0xED, // Media Select
|
||||
};
|
||||
|
||||
/**
|
||||
Specialised for key events
|
||||
*/
|
||||
class _OISExport KeyEvent : public EventArg
|
||||
{
|
||||
public:
|
||||
KeyEvent(Object* obj, KeyCode kc, unsigned int txt) :
|
||||
EventArg(obj), key(kc), text(txt) { }
|
||||
virtual ~KeyEvent() { }
|
||||
|
||||
//! KeyCode of event
|
||||
KeyCode key;
|
||||
//! Text character, depends on current TextTranslationMode
|
||||
unsigned int text;
|
||||
};
|
||||
|
||||
/**
|
||||
To recieve buffered keyboard input, derive a class from this, and implement the
|
||||
methods here. Then set the call back to your Keyboard instance with Keyboard::setEventCallback
|
||||
*/
|
||||
class _OISExport KeyListener
|
||||
{
|
||||
public:
|
||||
virtual ~KeyListener() { }
|
||||
virtual bool keyPressed(const KeyEvent& arg) = 0;
|
||||
virtual bool keyReleased(const KeyEvent& arg) = 0;
|
||||
};
|
||||
|
||||
/**
|
||||
Keyboard base class. To be implemented by specific system (ie. DirectX Keyboard)
|
||||
This class is useful as you remain OS independent using this common interface.
|
||||
*/
|
||||
class _OISExport Keyboard : public Object
|
||||
{
|
||||
public:
|
||||
virtual ~Keyboard() {};
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns true if key is donwn
|
||||
@param key
|
||||
A KeyCode to check
|
||||
*/
|
||||
virtual bool isKeyDown(KeyCode key) const = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Register/unregister a Keyboard Listener - Only one allowed for simplicity. If broadcasting
|
||||
is neccessary, just broadcast from the callback you registered.
|
||||
@param keyListener
|
||||
Send a pointer to a class derived from KeyListener or 0 to clear the callback
|
||||
*/
|
||||
virtual void setEventCallback(KeyListener* keyListener) { mListener = keyListener; }
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns currently set callback.. or 0
|
||||
*/
|
||||
KeyListener* getEventCallback() const { return mListener; }
|
||||
|
||||
//! TextTranslation Mode
|
||||
enum TextTranslationMode {
|
||||
Off,
|
||||
Unicode,
|
||||
Ascii
|
||||
};
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Enable extra processing to translate KC_*** to an
|
||||
actual text character based off of locale. Different
|
||||
managers may implement none or all. Check the
|
||||
translation mode after setting to be sure
|
||||
@param mode
|
||||
Off, Unicode, Ascii
|
||||
*/
|
||||
virtual void setTextTranslation(TextTranslationMode mode);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns current translation mode
|
||||
*/
|
||||
TextTranslationMode getTextTranslation() const { return mTextMode; }
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Translates KeyCode to string representation.
|
||||
For example, KC_ENTER will be "Enter" - Locale
|
||||
specific of course.
|
||||
@param kc
|
||||
KeyCode to convert
|
||||
@returns
|
||||
The string as determined from the current locale
|
||||
*/
|
||||
virtual const std::string& getAsString(KeyCode kc) = 0;
|
||||
|
||||
//! Enum of bit position of modifer
|
||||
enum Modifier {
|
||||
Shift = 0x0000001,
|
||||
LShift = 0x0000002,
|
||||
RShift = 0x0000004,
|
||||
Ctrl = 0x0000010,
|
||||
LCtrl = 0x0000020,
|
||||
RCtrl = 0x0000040,
|
||||
Alt = 0x0000100,
|
||||
LAlt = 0x0000200,
|
||||
RAlt = 0x0000400,
|
||||
CapsLock = 0x0001000,
|
||||
NumLock = 0x0010000,
|
||||
Win = 0x0100000,
|
||||
LWin = 0x0200000,
|
||||
RWin = 0x0400000
|
||||
};
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Translates string to KeyCode representation.
|
||||
For example, "Enter" will be KC_ENTER - Locale
|
||||
specific of course.
|
||||
@param str
|
||||
string to convert
|
||||
@returns
|
||||
The matching KeyCode
|
||||
*/
|
||||
virtual OIS::KeyCode getAsKeyCode(std::string str) = 0;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Check modifier status
|
||||
*/
|
||||
bool isModifierDown(Modifier mod) const;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Returns the full modifiers status bit field
|
||||
*/
|
||||
unsigned int getModifiers() const;
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Copies the state of the keys into the sent buffer
|
||||
(in the form of 1 is down and 0 is up)
|
||||
*/
|
||||
virtual void copyKeyStates(char keys[256]) const = 0;
|
||||
|
||||
protected:
|
||||
Keyboard(const std::string& vendor, bool buffered, int devID, InputManager* creator) :
|
||||
Object(vendor, OISKeyboard, buffered, devID, creator),
|
||||
mModifiers(0), mListener(0), mTextMode(Unicode) { }
|
||||
|
||||
//! Bit field that holds status of Alt, Ctrl, Shift, Win, CapsLock, and NumLock as well as Left and Right variants
|
||||
unsigned int mModifiers;
|
||||
|
||||
//! Used for buffered/actionmapping callback
|
||||
KeyListener* mListener;
|
||||
|
||||
//! The current translation mode
|
||||
TextTranslationMode mTextMode;
|
||||
};
|
||||
}
|
||||
#endif
|
153
Libs/ois/OISMouse.h
Normal file
153
Libs/ois/OISMouse.h
Normal file
|
@ -0,0 +1,153 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Mouse_H
|
||||
#define OIS_Mouse_H
|
||||
#include "OISObject.h"
|
||||
#include "OISEvents.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
//! Button ID for mouse devices
|
||||
enum MouseButtonID {
|
||||
MB_Left = 0,
|
||||
MB_Right,
|
||||
MB_Middle,
|
||||
MB_Button3,
|
||||
MB_Button4,
|
||||
MB_Button5,
|
||||
MB_Button6,
|
||||
MB_Button7
|
||||
};
|
||||
|
||||
/**
|
||||
Represents the state of the mouse
|
||||
All members are valid for both buffered and non buffered mode
|
||||
*/
|
||||
class _OISExport MouseState
|
||||
{
|
||||
public:
|
||||
MouseState() :
|
||||
width(50), height(50), buttons(0) {};
|
||||
|
||||
/** Represents the height/width of your display area.. used if mouse clipping
|
||||
or mouse grabbed in case of X11 - defaults to 50.. Make sure to set this
|
||||
and change when your size changes.. */
|
||||
mutable int width, height;
|
||||
|
||||
//! X Axis component
|
||||
Axis X;
|
||||
|
||||
//! Y Axis Component
|
||||
Axis Y;
|
||||
|
||||
//! Z Axis Component
|
||||
Axis Z;
|
||||
|
||||
//! represents all buttons - bit position indicates button down
|
||||
int buttons;
|
||||
|
||||
//! Button down test
|
||||
inline bool buttonDown(MouseButtonID button) const
|
||||
{
|
||||
return ((buttons & (1L << button)) == 0) ? false : true;
|
||||
}
|
||||
|
||||
//! Clear all the values
|
||||
void clear()
|
||||
{
|
||||
X.clear();
|
||||
Y.clear();
|
||||
Z.clear();
|
||||
buttons = 0;
|
||||
}
|
||||
};
|
||||
|
||||
/** Specialised for mouse events */
|
||||
class _OISExport MouseEvent : public EventArg
|
||||
{
|
||||
public:
|
||||
MouseEvent(Object* obj, const MouseState& ms) :
|
||||
EventArg(obj), state(ms) { }
|
||||
virtual ~MouseEvent() { }
|
||||
|
||||
//! The state of the mouse - including buttons and axes
|
||||
const MouseState& state;
|
||||
|
||||
private:
|
||||
// Prevent copying.
|
||||
MouseEvent(const MouseEvent&);
|
||||
MouseEvent& operator=(MouseEvent);
|
||||
};
|
||||
|
||||
/**
|
||||
To recieve buffered mouse input, derive a class from this, and implement the
|
||||
methods here. Then set the call back to your Mouse instance with Mouse::setEventCallback
|
||||
*/
|
||||
class _OISExport MouseListener
|
||||
{
|
||||
public:
|
||||
virtual ~MouseListener() { }
|
||||
virtual bool mouseMoved(const MouseEvent& arg) = 0;
|
||||
virtual bool mousePressed(const MouseEvent& arg, MouseButtonID id) = 0;
|
||||
virtual bool mouseReleased(const MouseEvent& arg, MouseButtonID id) = 0;
|
||||
};
|
||||
|
||||
/**
|
||||
Mouse base class. To be implemented by specific system (ie. DirectX Mouse)
|
||||
This class is useful as you remain OS independent using this common interface.
|
||||
*/
|
||||
class _OISExport Mouse : public Object
|
||||
{
|
||||
public:
|
||||
virtual ~Mouse() { }
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Register/unregister a Mouse Listener - Only one allowed for simplicity. If broadcasting
|
||||
is neccessary, just broadcast from the callback you registered.
|
||||
@param mouseListener
|
||||
Send a pointer to a class derived from MouseListener or 0 to clear the callback
|
||||
*/
|
||||
virtual void setEventCallback(MouseListener* mouseListener) { mListener = mouseListener; }
|
||||
|
||||
/** @remarks Returns currently set callback.. or 0 */
|
||||
MouseListener* getEventCallback() const { return mListener; }
|
||||
|
||||
/** @remarks Returns the state of the mouse - is valid for both buffered and non buffered mode */
|
||||
const MouseState& getMouseState() const { return mState; }
|
||||
|
||||
protected:
|
||||
Mouse(const std::string& vendor, bool buffered, int devID, InputManager* creator) :
|
||||
Object(vendor, OISMouse, buffered, devID, creator), mListener(0) { }
|
||||
|
||||
//! The state of the mouse
|
||||
MouseState mState;
|
||||
|
||||
//! Used for buffered/actionmapping callback
|
||||
MouseListener* mListener;
|
||||
};
|
||||
}
|
||||
#endif
|
183
Libs/ois/OISMultiTouch.h
Normal file
183
Libs/ois/OISMultiTouch.h
Normal file
|
@ -0,0 +1,183 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_MultiTouch_H
|
||||
#define OIS_MultiTouch_H
|
||||
#include "OISObject.h"
|
||||
#include "OISEvents.h"
|
||||
|
||||
#include <set>
|
||||
#include <vector>
|
||||
|
||||
#define OIS_MAX_NUM_TOUCHES 4 // 4 finger touches are probably the highest we'll ever get
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
/**
|
||||
Represents the state of the multi-touch device
|
||||
All members are valid for both buffered and non buffered mode
|
||||
*/
|
||||
|
||||
//! Touch Event type
|
||||
enum MultiTypeEventTypeID {
|
||||
MT_None = 0,
|
||||
MT_Pressed,
|
||||
MT_Released,
|
||||
MT_Moved,
|
||||
MT_Cancelled
|
||||
};
|
||||
|
||||
class _OISExport MultiTouchState
|
||||
{
|
||||
public:
|
||||
MultiTouchState() :
|
||||
width(50), height(50), touchType(MT_None) {};
|
||||
|
||||
/** Represents the height/width of your display area.. used if touch clipping
|
||||
or touch grabbed in case of X11 - defaults to 50.. Make sure to set this
|
||||
and change when your size changes.. */
|
||||
mutable int width, height;
|
||||
|
||||
//! X Axis component
|
||||
Axis X;
|
||||
|
||||
//! Y Axis Component
|
||||
Axis Y;
|
||||
|
||||
//! Z Axis Component
|
||||
Axis Z;
|
||||
|
||||
int touchType;
|
||||
|
||||
inline bool touchIsType(MultiTypeEventTypeID touch) const
|
||||
{
|
||||
return ((touchType & (1L << touch)) == 0) ? false : true;
|
||||
}
|
||||
|
||||
//! Clear all the values
|
||||
void clear()
|
||||
{
|
||||
X.clear();
|
||||
Y.clear();
|
||||
Z.clear();
|
||||
touchType = MT_None;
|
||||
}
|
||||
};
|
||||
|
||||
/** Specialised for multi-touch events */
|
||||
class _OISExport MultiTouchEvent : public EventArg
|
||||
{
|
||||
public:
|
||||
MultiTouchEvent(Object* obj, const MultiTouchState& ms) :
|
||||
EventArg(obj), state(ms) { }
|
||||
virtual ~MultiTouchEvent() { }
|
||||
|
||||
//! The state of the touch - including axes
|
||||
const MultiTouchState& state;
|
||||
};
|
||||
|
||||
/**
|
||||
To receive buffered touch input, derive a class from this, and implement the
|
||||
methods here. Then set the call back to your MultiTouch instance with MultiTouch::setEventCallback
|
||||
*/
|
||||
class _OISExport MultiTouchListener
|
||||
{
|
||||
public:
|
||||
virtual ~MultiTouchListener() { }
|
||||
virtual bool touchMoved(const MultiTouchEvent& arg) = 0;
|
||||
virtual bool touchPressed(const MultiTouchEvent& arg) = 0;
|
||||
virtual bool touchReleased(const MultiTouchEvent& arg) = 0;
|
||||
virtual bool touchCancelled(const MultiTouchEvent& arg) = 0;
|
||||
};
|
||||
|
||||
/**
|
||||
MultiTouch base class. To be implemented by specific system (ie. iPhone UITouch)
|
||||
This class is useful as you remain OS independent using this common interface.
|
||||
*/
|
||||
class _OISExport MultiTouch : public Object
|
||||
{
|
||||
public:
|
||||
virtual ~MultiTouch() { }
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Register/unregister a MultiTouch Listener - Only one allowed for simplicity. If broadcasting
|
||||
is necessary, just broadcast from the callback you registered.
|
||||
@param touchListener
|
||||
Send a pointer to a class derived from MultiTouchListener or 0 to clear the callback
|
||||
*/
|
||||
virtual void setEventCallback(MultiTouchListener* touchListener) { mListener = touchListener; }
|
||||
|
||||
/** @remarks Returns currently set callback.. or 0 */
|
||||
MultiTouchListener* getEventCallback() { return mListener; }
|
||||
|
||||
/** @remarks Clear out the set of input states. Should be called after input has been processed by the application */
|
||||
void clearStates(void) { mStates.clear(); }
|
||||
|
||||
/** @remarks Returns the state of the touch - is valid for both buffered and non buffered mode */
|
||||
std::vector<MultiTouchState> getMultiTouchStates() const { return mStates; }
|
||||
|
||||
/** @remarks Returns the first n touch states. Useful if you know your app only needs to
|
||||
process n touches. The return value is a vector to allow random access */
|
||||
const std::vector<MultiTouchState> getFirstNTouchStates(int n)
|
||||
{
|
||||
std::vector<MultiTouchState> states;
|
||||
for(unsigned int i = 0; i < mStates.size(); i++)
|
||||
{
|
||||
if(!(mStates[i].touchIsType(MT_None)))
|
||||
{
|
||||
states.push_back(mStates[i]);
|
||||
}
|
||||
}
|
||||
return states;
|
||||
}
|
||||
|
||||
/** @remarks Returns the first n touch states. Useful if you know your app only needs to
|
||||
process n touches. The return value is a vector to allow random access */
|
||||
const std::vector<MultiTouchState> getMultiTouchStatesOfType(MultiTypeEventTypeID type)
|
||||
{
|
||||
std::vector<MultiTouchState> states;
|
||||
for(unsigned int i = 0; i < mStates.size(); i++)
|
||||
{
|
||||
if(mStates[i].touchIsType(type))
|
||||
{
|
||||
states.push_back(mStates[i]);
|
||||
}
|
||||
}
|
||||
return states;
|
||||
}
|
||||
|
||||
protected:
|
||||
MultiTouch(const std::string& vendor, bool buffered, int devID, InputManager* creator) :
|
||||
Object(vendor, OISMultiTouch, buffered, devID, creator), mListener(0) { }
|
||||
|
||||
//! The state of the touch device, implemented in a vector to store the state from each finger touch
|
||||
std::vector<MultiTouchState> mStates;
|
||||
|
||||
//! Used for buffered/actionmapping callback
|
||||
MultiTouchListener* mListener;
|
||||
};
|
||||
}
|
||||
#endif
|
97
Libs/ois/OISObject.h
Normal file
97
Libs/ois/OISObject.h
Normal file
|
@ -0,0 +1,97 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Object_H
|
||||
#define OIS_Object_H
|
||||
|
||||
#include "OISPrereqs.h"
|
||||
#include "OISInterface.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
/** The base class of all input types. */
|
||||
class _OISExport Object
|
||||
{
|
||||
public:
|
||||
virtual ~Object() { }
|
||||
|
||||
/** @remarks Get the type of device */
|
||||
Type type() const { return mType; }
|
||||
|
||||
/** @remarks Get the vender string name */
|
||||
const std::string& vendor() const { return mVendor; }
|
||||
|
||||
/** @remarks Get buffered mode - true is buffered, false otherwise */
|
||||
virtual bool buffered() const { return mBuffered; }
|
||||
|
||||
/** @remarks Returns this input object's creator */
|
||||
InputManager* getCreator() const { return mCreator; }
|
||||
|
||||
/** @remarks Sets buffered mode */
|
||||
virtual void setBuffered(bool buffered) = 0;
|
||||
|
||||
/** @remarks Used for updating call once per frame before checking state or to update events */
|
||||
virtual void capture() = 0;
|
||||
|
||||
/** @remarks This may/may not) differentiate the different controllers based on (for instance) a port number (useful for console InputManagers) */
|
||||
virtual int getID() const { return mDevID; }
|
||||
|
||||
/**
|
||||
@remarks
|
||||
If available, get an interface to write to some devices.
|
||||
Examples include, turning on and off LEDs, ForceFeedback, etc
|
||||
@param type
|
||||
The type of interface you are looking for
|
||||
*/
|
||||
virtual Interface* queryInterface(Interface::IType type) = 0;
|
||||
|
||||
/** @remarks Internal... Do not call this directly. */
|
||||
virtual void _initialize() = 0;
|
||||
|
||||
protected:
|
||||
Object(const std::string& vendor, Type iType, bool buffered, int devID, InputManager* creator) :
|
||||
mVendor(vendor),
|
||||
mType(iType),
|
||||
mBuffered(buffered),
|
||||
mDevID(devID),
|
||||
mCreator(creator) { }
|
||||
|
||||
//! Vendor name if applicable/known
|
||||
std::string mVendor;
|
||||
|
||||
//! Type of controller object
|
||||
Type mType;
|
||||
|
||||
//! Buffered flag
|
||||
bool mBuffered;
|
||||
|
||||
//! Not fully implemented yet
|
||||
int mDevID;
|
||||
|
||||
//! The creator who created this object
|
||||
InputManager* mCreator;
|
||||
};
|
||||
}
|
||||
#endif
|
250
Libs/ois/OISPrereqs.h
Normal file
250
Libs/ois/OISPrereqs.h
Normal file
|
@ -0,0 +1,250 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Prereqs_H
|
||||
#define OIS_Prereqs_H
|
||||
//----------------------------------------------------------------------------//
|
||||
// This Header File contains: forward declared classes
|
||||
// * Forward Declarations of all public API classes
|
||||
// * Several typedef's used around the library
|
||||
// * Base class component types
|
||||
// * Preprocessor definitons
|
||||
//----------------------------------------------------------------------------//
|
||||
|
||||
//-------------- Common STL Containers ---------------------------------------//
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <map>
|
||||
#include "OISConfig.h"
|
||||
|
||||
// Default is blank for most OS's
|
||||
#define _OISExport
|
||||
|
||||
//-------------- Determine Compiler ---------------------------------
|
||||
#if defined( _MSC_VER )
|
||||
# define OIS_MSVC_COMPILER
|
||||
#elif defined( __GNUC__ )
|
||||
# if defined( __WIN32__ ) || defined( _WIN32 )
|
||||
# define OIS_MINGW_COMPILER
|
||||
# else
|
||||
# define OIS_GCC_COMPILER
|
||||
# endif
|
||||
#elif defined( __BORLANDC__ )
|
||||
# define OIS_BORLAND_COMPILER
|
||||
#else
|
||||
# error No Recognized Compiler!
|
||||
#endif
|
||||
|
||||
// --------------- Determine Operating System Platform ---------------
|
||||
#if defined( __WIN32__ ) || defined( _WIN32 ) // Windows 2000, XP, ETC
|
||||
# if defined ( _XBOX )
|
||||
# define OIS_XBOX_PLATFORM
|
||||
# else
|
||||
# define OIS_WIN32_PLATFORM
|
||||
# if defined( OIS_DYNAMIC_LIB )
|
||||
# undef _OISExport
|
||||
//Ignorable Dll interface warning...
|
||||
# if !defined(OIS_MINGW_COMPILER)
|
||||
# pragma warning (disable : 4251)
|
||||
# endif
|
||||
# if defined( OIS_NONCLIENT_BUILD )
|
||||
# define _OISExport __declspec( dllexport )
|
||||
# else
|
||||
# if defined(OIS_MINGW_COMPILER)
|
||||
# define _OISExport
|
||||
# else
|
||||
# define _OISExport __declspec( dllimport )
|
||||
# endif
|
||||
# endif
|
||||
# endif
|
||||
# endif
|
||||
#elif defined( __APPLE_CC__ ) // Apple OS X
|
||||
// Device Simulator
|
||||
# if __IPHONE_OS_VERSION_MIN_REQUIRED >= 20201 || __IPHONE_OS_VERSION_MIN_REQUIRED >= 20000
|
||||
//# if __IPHONE_OS_VERSION_MIN_REQUIRED >= 30000 || __IPHONE_OS_VERSION_MIN_REQUIRED >= 30000
|
||||
# define OIS_IPHONE_PLATFORM
|
||||
# else
|
||||
# define OIS_APPLE_PLATFORM
|
||||
# endif
|
||||
# undef _OISExport
|
||||
# define _OISExport __attribute__((visibility("default")))
|
||||
#else //Probably Linux
|
||||
# define OIS_LINUX_PLATFORM
|
||||
# include <unistd.h>
|
||||
#endif
|
||||
|
||||
//Is Processor 32 or 64 bits...
|
||||
#if defined(__x86_64__)
|
||||
# define OIS_ARCH_64
|
||||
#else
|
||||
# define OIS_ARCH_32
|
||||
#endif
|
||||
|
||||
//-------------- Various helper preprocessor definitions ---------------------//
|
||||
|
||||
#ifdef OIS_MSVC_COMPILER
|
||||
# define OIS_INLINE_PRAGMA(x) __pragma(x) // x is intentionally not wrapped; __pragma rejects expressions beginning with '('.
|
||||
#else
|
||||
# define OIS_INLINE_PRAGMA(x)
|
||||
#endif
|
||||
|
||||
#define OIS_MACRO_BEGIN do {
|
||||
|
||||
#define OIS_MACRO_END \
|
||||
} OIS_INLINE_PRAGMA(warning(push)) OIS_INLINE_PRAGMA(warning(disable:4127)) while (0) OIS_INLINE_PRAGMA(warning(pop))
|
||||
|
||||
// This creative trickery taken from this StackOverflow answer:
|
||||
// http://stackoverflow.com/questions/4030959/will-a-variablename-c-statement-be-a-no-op-at-all-times/4030983#4030983
|
||||
#define OIS_UNUSED(x)\
|
||||
OIS_MACRO_BEGIN\
|
||||
((void)(true ? 0 : ((x), void(), 0)));\
|
||||
OIS_MACRO_END
|
||||
|
||||
//-------------- Common Classes, Enums, and Typdef's -------------------------//
|
||||
#define OIS_VERSION_MAJOR 1
|
||||
#define OIS_VERSION_MINOR 5
|
||||
#define OIS_VERSION_PATCH 1
|
||||
#define OIS_VERSION_NAME "1.5.0"
|
||||
|
||||
#define OIS_VERSION ((OIS_VERSION_MAJOR << 16) | (OIS_VERSION_MINOR << 8) | OIS_VERSION_PATCH)
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
//Forward Declarations
|
||||
class InputManager;
|
||||
class FactoryCreator;
|
||||
class Object;
|
||||
class Keyboard;
|
||||
class Mouse;
|
||||
class JoyStick;
|
||||
class MultiTouch;
|
||||
class KeyListener;
|
||||
class MouseListener;
|
||||
class MultiTouchListener;
|
||||
class JoyStickListener;
|
||||
class Interface;
|
||||
class ForceFeedback;
|
||||
class Effect;
|
||||
class Exception;
|
||||
|
||||
//! Way to send OS nuetral parameters.. ie OS Window handles, modes, flags
|
||||
typedef std::multimap<std::string, std::string> ParamList;
|
||||
|
||||
//! List of FactoryCreator's
|
||||
typedef std::vector<FactoryCreator*> FactoryList;
|
||||
|
||||
//! Map of FactoryCreator created Objects
|
||||
typedef std::map<Object*, FactoryCreator*> FactoryCreatedObject;
|
||||
|
||||
//! Each Input class has a General Type variable, a form of RTTI
|
||||
enum Type
|
||||
{
|
||||
OISUnknown = 0,
|
||||
OISKeyboard = 1,
|
||||
OISMouse = 2,
|
||||
OISJoyStick = 3,
|
||||
OISTablet = 4,
|
||||
OISMultiTouch = 5
|
||||
};
|
||||
|
||||
//! Map of device objects connected and their respective vendors
|
||||
typedef std::multimap<Type, std::string> DeviceList;
|
||||
|
||||
//-------- Shared common components ------------------------//
|
||||
|
||||
//! Base type for all device components (button, axis, etc)
|
||||
enum ComponentType
|
||||
{
|
||||
OIS_Unknown = 0,
|
||||
OIS_Button = 1, //ie. Key, mouse button, joy button, etc
|
||||
OIS_Axis = 2, //ie. A joystick or mouse axis
|
||||
OIS_Slider = 3, //
|
||||
OIS_POV = 4, //ie. Arrow direction keys
|
||||
OIS_Vector3 = 5 //ie. WiiMote orientation
|
||||
};
|
||||
|
||||
//! Base of all device components (button, axis, etc)
|
||||
class _OISExport Component
|
||||
{
|
||||
public:
|
||||
Component() : cType(OIS_Unknown) {};
|
||||
explicit Component(ComponentType type) : cType(type) {};
|
||||
//! Indicates what type of coponent this is
|
||||
ComponentType cType;
|
||||
};
|
||||
|
||||
//! Button can be a keyboard key, mouse button, etc
|
||||
class _OISExport Button : public Component
|
||||
{
|
||||
public:
|
||||
Button() : Component(OIS_Button), pushed(false) {}
|
||||
explicit Button(bool bPushed) : Component(OIS_Button), pushed(bPushed) {}
|
||||
//! true if pushed, false otherwise
|
||||
bool pushed;
|
||||
};
|
||||
|
||||
//! Axis component
|
||||
class _OISExport Axis : public Component
|
||||
{
|
||||
public:
|
||||
Axis() : Component(OIS_Axis), abs(0), rel(0), absOnly(false) {};
|
||||
|
||||
//! Absoulte and Relative value components
|
||||
int abs, rel;
|
||||
|
||||
//! Indicates if this Axis only supports Absoulte (ie JoyStick)
|
||||
bool absOnly;
|
||||
|
||||
//! Used internally by OIS
|
||||
void clear()
|
||||
{
|
||||
abs = rel = 0;
|
||||
}
|
||||
};
|
||||
|
||||
//! A 3D Vector component (perhaps an orientation, as in the WiiMote)
|
||||
class _OISExport Vector3 : public Component
|
||||
{
|
||||
public:
|
||||
Vector3() {}
|
||||
Vector3(float _x, float _y, float _z) : Component(OIS_Vector3), x(_x), y(_y), z(_z) {};
|
||||
|
||||
//! X component of vector
|
||||
float x;
|
||||
|
||||
//! Y component of vector
|
||||
float y;
|
||||
|
||||
//! Z component of vector
|
||||
float z;
|
||||
|
||||
void clear()
|
||||
{
|
||||
x = y = z = 0.0f;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
#endif //end if prereq header defined
|
250
Libs/ois/OISPrereqs.h.in
Normal file
250
Libs/ois/OISPrereqs.h.in
Normal file
|
@ -0,0 +1,250 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Prereqs_H
|
||||
#define OIS_Prereqs_H
|
||||
//----------------------------------------------------------------------------//
|
||||
// This Header File contains: forward declared classes
|
||||
// * Forward Declarations of all public API classes
|
||||
// * Several typedef's used around the library
|
||||
// * Base class component types
|
||||
// * Preprocessor definitons
|
||||
//----------------------------------------------------------------------------//
|
||||
|
||||
//-------------- Common STL Containers ---------------------------------------//
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <map>
|
||||
#include "OISConfig.h"
|
||||
|
||||
// Default is blank for most OS's
|
||||
#define _OISExport
|
||||
|
||||
//-------------- Determine Compiler ---------------------------------
|
||||
#if defined( _MSC_VER )
|
||||
# define OIS_MSVC_COMPILER
|
||||
#elif defined( __GNUC__ )
|
||||
# if defined( __WIN32__ ) || defined( _WIN32 )
|
||||
# define OIS_MINGW_COMPILER
|
||||
# else
|
||||
# define OIS_GCC_COMPILER
|
||||
# endif
|
||||
#elif defined( __BORLANDC__ )
|
||||
# define OIS_BORLAND_COMPILER
|
||||
#else
|
||||
# error No Recognized Compiler!
|
||||
#endif
|
||||
|
||||
// --------------- Determine Operating System Platform ---------------
|
||||
#if defined( __WIN32__ ) || defined( _WIN32 ) // Windows 2000, XP, ETC
|
||||
# if defined ( _XBOX )
|
||||
# define OIS_XBOX_PLATFORM
|
||||
# else
|
||||
# define OIS_WIN32_PLATFORM
|
||||
# if defined( OIS_DYNAMIC_LIB )
|
||||
# undef _OISExport
|
||||
//Ignorable Dll interface warning...
|
||||
# if !defined(OIS_MINGW_COMPILER)
|
||||
# pragma warning (disable : 4251)
|
||||
# endif
|
||||
# if defined( OIS_NONCLIENT_BUILD )
|
||||
# define _OISExport __declspec( dllexport )
|
||||
# else
|
||||
# if defined(OIS_MINGW_COMPILER)
|
||||
# define _OISExport
|
||||
# else
|
||||
# define _OISExport __declspec( dllimport )
|
||||
# endif
|
||||
# endif
|
||||
# endif
|
||||
# endif
|
||||
#elif defined( __APPLE_CC__ ) // Apple OS X
|
||||
// Device Simulator
|
||||
# if __IPHONE_OS_VERSION_MIN_REQUIRED >= 20201 || __IPHONE_OS_VERSION_MIN_REQUIRED >= 20000
|
||||
//# if __IPHONE_OS_VERSION_MIN_REQUIRED >= 30000 || __IPHONE_OS_VERSION_MIN_REQUIRED >= 30000
|
||||
# define OIS_IPHONE_PLATFORM
|
||||
# else
|
||||
# define OIS_APPLE_PLATFORM
|
||||
# endif
|
||||
# undef _OISExport
|
||||
# define _OISExport __attribute__((visibility("default")))
|
||||
#else //Probably Linux
|
||||
# define OIS_LINUX_PLATFORM
|
||||
# include <unistd.h>
|
||||
#endif
|
||||
|
||||
//Is Processor 32 or 64 bits...
|
||||
#if defined(__x86_64__)
|
||||
# define OIS_ARCH_64
|
||||
#else
|
||||
# define OIS_ARCH_32
|
||||
#endif
|
||||
|
||||
//-------------- Various helper preprocessor definitions ---------------------//
|
||||
|
||||
#ifdef OIS_MSVC_COMPILER
|
||||
# define OIS_INLINE_PRAGMA(x) __pragma(x) // x is intentionally not wrapped; __pragma rejects expressions beginning with '('.
|
||||
#else
|
||||
# define OIS_INLINE_PRAGMA(x)
|
||||
#endif
|
||||
|
||||
#define OIS_MACRO_BEGIN do {
|
||||
|
||||
#define OIS_MACRO_END \
|
||||
} OIS_INLINE_PRAGMA(warning(push)) OIS_INLINE_PRAGMA(warning(disable:4127)) while (0) OIS_INLINE_PRAGMA(warning(pop))
|
||||
|
||||
// This creative trickery taken from this StackOverflow answer:
|
||||
// http://stackoverflow.com/questions/4030959/will-a-variablename-c-statement-be-a-no-op-at-all-times/4030983#4030983
|
||||
#define OIS_UNUSED(x)\
|
||||
OIS_MACRO_BEGIN\
|
||||
((void)(true ? 0 : ((x), void(), 0)));\
|
||||
OIS_MACRO_END
|
||||
|
||||
//-------------- Common Classes, Enums, and Typdef's -------------------------//
|
||||
#define OIS_VERSION_MAJOR @OIS_MAJOR_VERSION@
|
||||
#define OIS_VERSION_MINOR @OIS_MINOR_VERSION@
|
||||
#define OIS_VERSION_PATCH @OIS_PATCH_VERSION@
|
||||
#define OIS_VERSION_NAME "@OIS_SOVERSION@"
|
||||
|
||||
#define OIS_VERSION ((OIS_VERSION_MAJOR << 16) | (OIS_VERSION_MINOR << 8) | OIS_VERSION_PATCH)
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
//Forward Declarations
|
||||
class InputManager;
|
||||
class FactoryCreator;
|
||||
class Object;
|
||||
class Keyboard;
|
||||
class Mouse;
|
||||
class JoyStick;
|
||||
class MultiTouch;
|
||||
class KeyListener;
|
||||
class MouseListener;
|
||||
class MultiTouchListener;
|
||||
class JoyStickListener;
|
||||
class Interface;
|
||||
class ForceFeedback;
|
||||
class Effect;
|
||||
class Exception;
|
||||
|
||||
//! Way to send OS nuetral parameters.. ie OS Window handles, modes, flags
|
||||
typedef std::multimap<std::string, std::string> ParamList;
|
||||
|
||||
//! List of FactoryCreator's
|
||||
typedef std::vector<FactoryCreator*> FactoryList;
|
||||
|
||||
//! Map of FactoryCreator created Objects
|
||||
typedef std::map<Object*, FactoryCreator*> FactoryCreatedObject;
|
||||
|
||||
//! Each Input class has a General Type variable, a form of RTTI
|
||||
enum Type
|
||||
{
|
||||
OISUnknown = 0,
|
||||
OISKeyboard = 1,
|
||||
OISMouse = 2,
|
||||
OISJoyStick = 3,
|
||||
OISTablet = 4,
|
||||
OISMultiTouch = 5
|
||||
};
|
||||
|
||||
//! Map of device objects connected and their respective vendors
|
||||
typedef std::multimap<Type, std::string> DeviceList;
|
||||
|
||||
//-------- Shared common components ------------------------//
|
||||
|
||||
//! Base type for all device components (button, axis, etc)
|
||||
enum ComponentType
|
||||
{
|
||||
OIS_Unknown = 0,
|
||||
OIS_Button = 1, //ie. Key, mouse button, joy button, etc
|
||||
OIS_Axis = 2, //ie. A joystick or mouse axis
|
||||
OIS_Slider = 3, //
|
||||
OIS_POV = 4, //ie. Arrow direction keys
|
||||
OIS_Vector3 = 5 //ie. WiiMote orientation
|
||||
};
|
||||
|
||||
//! Base of all device components (button, axis, etc)
|
||||
class _OISExport Component
|
||||
{
|
||||
public:
|
||||
Component() : cType(OIS_Unknown) {};
|
||||
explicit Component(ComponentType type) : cType(type) {};
|
||||
//! Indicates what type of coponent this is
|
||||
ComponentType cType;
|
||||
};
|
||||
|
||||
//! Button can be a keyboard key, mouse button, etc
|
||||
class _OISExport Button : public Component
|
||||
{
|
||||
public:
|
||||
Button() : Component(OIS_Button), pushed(false) {}
|
||||
explicit Button(bool bPushed) : Component(OIS_Button), pushed(bPushed) {}
|
||||
//! true if pushed, false otherwise
|
||||
bool pushed;
|
||||
};
|
||||
|
||||
//! Axis component
|
||||
class _OISExport Axis : public Component
|
||||
{
|
||||
public:
|
||||
Axis() : Component(OIS_Axis), abs(0), rel(0), absOnly(false) {};
|
||||
|
||||
//! Absoulte and Relative value components
|
||||
int abs, rel;
|
||||
|
||||
//! Indicates if this Axis only supports Absoulte (ie JoyStick)
|
||||
bool absOnly;
|
||||
|
||||
//! Used internally by OIS
|
||||
void clear()
|
||||
{
|
||||
abs = rel = 0;
|
||||
}
|
||||
};
|
||||
|
||||
//! A 3D Vector component (perhaps an orientation, as in the WiiMote)
|
||||
class _OISExport Vector3 : public Component
|
||||
{
|
||||
public:
|
||||
Vector3() {}
|
||||
Vector3(float _x, float _y, float _z) : Component(OIS_Vector3), x(_x), y(_y), z(_z) {};
|
||||
|
||||
//! X component of vector
|
||||
float x;
|
||||
|
||||
//! Y component of vector
|
||||
float y;
|
||||
|
||||
//! Z component of vector
|
||||
float z;
|
||||
|
||||
void clear()
|
||||
{
|
||||
x = y = z = 0.0f;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
#endif //end if prereq header defined
|
BIN
Libs/ois/OIS_d.lib
Normal file
BIN
Libs/ois/OIS_d.lib
Normal file
Binary file not shown.
119
Libs/ois/win32/Win32ForceFeedback.h
Normal file
119
Libs/ois/win32/Win32ForceFeedback.h
Normal file
|
@ -0,0 +1,119 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Win32ForceFeedBack_H
|
||||
#define OIS_Win32ForceFeedBack_H
|
||||
|
||||
#include "OISPrereqs.h"
|
||||
#include "OISForceFeedback.h"
|
||||
#include "win32/Win32Prereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
class Win32ForceFeedback : public ForceFeedback
|
||||
{
|
||||
Win32ForceFeedback() { }
|
||||
|
||||
public:
|
||||
Win32ForceFeedback(IDirectInputDevice8* pDIJoy, const DIDEVCAPS* pDIJoyCaps);
|
||||
Win32ForceFeedback(unsigned int xInputIndex);
|
||||
~Win32ForceFeedback();
|
||||
|
||||
/** @copydoc ForceFeedback::upload */
|
||||
void upload(const Effect* effect);
|
||||
|
||||
/** @copydoc ForceFeedback::modify */
|
||||
void modify(const Effect* effect);
|
||||
|
||||
/** @copydoc ForceFeedback::remove */
|
||||
void remove(const Effect* effect);
|
||||
|
||||
/** @copydoc ForceFeedback::setMasterGain */
|
||||
void setMasterGain(float level);
|
||||
|
||||
/** @copydoc ForceFeedback::setAutoCenterMode */
|
||||
void setAutoCenterMode(bool auto_on);
|
||||
|
||||
/** @copydoc ForceFeedback::getFFAxesNumber */
|
||||
short getFFAxesNumber();
|
||||
|
||||
/** @copydoc ForceFeedback::getFFMemoryLoad */
|
||||
unsigned short getFFMemoryLoad();
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Internal use.. Used during enumeration to build a list of a devices
|
||||
support effects.
|
||||
*/
|
||||
void _addEffectSupport(LPCDIEFFECTINFO pdei);
|
||||
|
||||
/**
|
||||
@remarks
|
||||
Internal use.. Used during axis enumeration to get number of FF axes
|
||||
support effects.
|
||||
*/
|
||||
void _addFFAxis();
|
||||
|
||||
protected:
|
||||
//Specific Effect Settings
|
||||
void _updateConstantEffect(const Effect* effect);
|
||||
void _updateRampEffect(const Effect* effect);
|
||||
void _updatePeriodicEffect(const Effect* effect);
|
||||
void _updateConditionalEffect(const Effect* effect);
|
||||
void _updateCustomEffect(const Effect* effect);
|
||||
|
||||
//XInput-specific methods
|
||||
bool _isXInput();
|
||||
void _setXInputVibration(unsigned short leftPower, unsigned short rightPower);
|
||||
void _updateXInputConstantEffect(const Effect* effect);
|
||||
|
||||
//Sets the common properties to all effects
|
||||
void _setCommonProperties(DIEFFECT* diEffect, DWORD* rgdwAxes, LONG* rglDirection, DIENVELOPE* diEnvelope, DWORD struct_size, LPVOID struct_type, const Effect* effect, const Envelope* envelope);
|
||||
//Actually do the upload
|
||||
void _upload(GUID, DIEFFECT*, const Effect*);
|
||||
|
||||
// Map of currently uploaded effects (handle => effect)
|
||||
typedef std::map<int, LPDIRECTINPUTEFFECT> EffectList;
|
||||
EffectList mEffectList;
|
||||
|
||||
//Simple unique handle creation - allows for upto 2+ billion effects
|
||||
//during the lifetime of application. Hopefully, that is enough.
|
||||
int mHandles;
|
||||
|
||||
// Joystick device descriptor.
|
||||
IDirectInputDevice8* mJoyStick;
|
||||
|
||||
// Joystick capabilities.
|
||||
const DIDEVCAPS* mpDIJoyCaps;
|
||||
|
||||
// An index specifying XInput device index.
|
||||
// It will be -1 if device is DInput device.
|
||||
int mXInputIndex;
|
||||
|
||||
// Number of axis supporting FF.
|
||||
short mFFAxes;
|
||||
};
|
||||
}
|
||||
#endif //OIS_Win32ForceFeedBack_H
|
116
Libs/ois/win32/Win32InputManager.h
Normal file
116
Libs/ois/win32/Win32InputManager.h
Normal file
|
@ -0,0 +1,116 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef OIS_Win32InputManager_H
|
||||
#define OIS_Win32InputManager_H
|
||||
|
||||
#include "OISInputManager.h"
|
||||
#include "OISFactoryCreator.h"
|
||||
#include "win32/Win32Prereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
/** Win32InputManager specialization - Using DirectInput8 */
|
||||
class Win32InputManager : public InputManager, public FactoryCreator
|
||||
{
|
||||
public:
|
||||
Win32InputManager();
|
||||
virtual ~Win32InputManager();
|
||||
|
||||
//InputManager Overrides
|
||||
/** @copydoc InputManager::_initialize */
|
||||
void _initialize(ParamList& paramList);
|
||||
|
||||
//FactoryCreator Overrides
|
||||
/** @copydoc FactoryCreator::deviceList */
|
||||
DeviceList freeDeviceList();
|
||||
|
||||
/** @copydoc FactoryCreator::totalDevices */
|
||||
int totalDevices(Type iType);
|
||||
|
||||
/** @copydoc FactoryCreator::freeDevices */
|
||||
int freeDevices(Type iType);
|
||||
|
||||
/** @copydoc FactoryCreator::vendorExist */
|
||||
bool vendorExist(Type iType, const std::string& vendor);
|
||||
|
||||
/** @copydoc FactoryCreator::createObject */
|
||||
Object* createObject(InputManager* creator, Type iType, bool bufferMode, const std::string& vendor = "");
|
||||
|
||||
/** @copydoc FactoryCreator::destroyObject */
|
||||
void destroyObject(Object* obj);
|
||||
|
||||
//Internal Items
|
||||
//! Internal method, used for flaggin keyboard as available/unavailable for creation
|
||||
void _setKeyboardUsed(bool used) { keyboardUsed = used; }
|
||||
|
||||
//! Internal method, used for flaggin mouse as available/unavailable for creation
|
||||
void _setMouseUsed(bool used) { mouseUsed = used; }
|
||||
|
||||
//! Internal method, return unused joystick to queue
|
||||
void _returnJoyStick(const JoyStickInfo& joystick);
|
||||
|
||||
//! Returns HWND needed by DirectInput Device Object
|
||||
HWND getWindowHandle() { return hWnd; }
|
||||
|
||||
protected:
|
||||
//! internal class method for dealing with param list
|
||||
void _parseConfigSettings(ParamList& paramList);
|
||||
|
||||
//! internal class method for finding attached devices
|
||||
void _enumerateDevices();
|
||||
|
||||
//! Used during device enumeration
|
||||
static BOOL CALLBACK _DIEnumDevCallback(LPCDIDEVICEINSTANCE lpddi, LPVOID pvRef);
|
||||
|
||||
//! Keep a list of all joysticks enumerated, but not in use
|
||||
JoyStickInfoList unusedJoyStickList;
|
||||
|
||||
//! The window handle we are using
|
||||
HWND hWnd;
|
||||
|
||||
//! Direct Input Interface
|
||||
IDirectInput8* mDirectInput;
|
||||
|
||||
//! Used for keyboard device settings
|
||||
DWORD kbSettings;
|
||||
|
||||
//! Used for mouse device settings
|
||||
DWORD mouseSettings;
|
||||
|
||||
//! Used for joystick device settings
|
||||
DWORD joySettings;
|
||||
|
||||
//! Number of total joysticks (inuse or not)
|
||||
char joySticks;
|
||||
|
||||
//! Used to know if we used up keyboard
|
||||
bool keyboardUsed;
|
||||
|
||||
//! Used to know if we used up mouse
|
||||
bool mouseUsed;
|
||||
};
|
||||
}
|
||||
#endif
|
91
Libs/ois/win32/Win32JoyStick.h
Normal file
91
Libs/ois/win32/Win32JoyStick.h
Normal file
|
@ -0,0 +1,91 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef _WIN32_JOYSTICK_H_EADER_
|
||||
#define _WIN32_JOYSTICK_H_EADER_
|
||||
|
||||
#include "OISJoyStick.h"
|
||||
#include "win32/Win32Prereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
class Win32JoyStick : public JoyStick
|
||||
{
|
||||
public:
|
||||
Win32JoyStick(InputManager* creator, IDirectInput8* pDI, bool buffered, DWORD coopSettings, const JoyStickInfo& info);
|
||||
virtual ~Win32JoyStick();
|
||||
|
||||
/** @copydoc Object::setBuffered */
|
||||
virtual void setBuffered(bool buffered);
|
||||
|
||||
/** @copydoc Object::capture */
|
||||
virtual void capture();
|
||||
|
||||
//! hanlde xinput
|
||||
void captureXInput();
|
||||
|
||||
/** @copydoc Object::queryInterface */
|
||||
virtual Interface* queryInterface(Interface::IType type);
|
||||
|
||||
/** @copydoc Object::_initialize */
|
||||
virtual void _initialize();
|
||||
|
||||
#ifdef OIS_WIN32_XINPUT_SUPPORT
|
||||
/**
|
||||
@remarks
|
||||
Enum each PNP device using WMI and check each device ID to see if it contains
|
||||
"IG_" (ex. "VID_045E&PID_028E&IG_00"). If it does, then it's an XInput device
|
||||
Unfortunately this information can not be found by just using DirectInput
|
||||
*/
|
||||
static void CheckXInputDevices(JoyStickInfoList& joys);
|
||||
#endif
|
||||
|
||||
protected:
|
||||
//! Enumerates all things
|
||||
void _enumerate();
|
||||
//! Enumerate axis callback
|
||||
static BOOL CALLBACK DIEnumDeviceObjectsCallback(LPCDIDEVICEOBJECTINSTANCE lpddoi, LPVOID pvRef);
|
||||
//! Enumerate Force Feedback callback
|
||||
static BOOL CALLBACK DIEnumEffectsCallback(LPCDIEFFECTINFO pdei, LPVOID pvRef);
|
||||
|
||||
bool _doButtonClick(int button, DIDEVICEOBJECTDATA& di);
|
||||
bool _changePOV(int pov, DIDEVICEOBJECTDATA& di);
|
||||
|
||||
IDirectInput8* mDirectInput;
|
||||
IDirectInputDevice8* mJoyStick;
|
||||
DIDEVCAPS mDIJoyCaps;
|
||||
DWORD coopSetting;
|
||||
|
||||
JoyStickInfo mJoyInfo;
|
||||
|
||||
//! A force feedback device
|
||||
Win32ForceFeedback* mFfDevice;
|
||||
|
||||
//! Mapping
|
||||
int _AxisNumber;
|
||||
};
|
||||
}
|
||||
|
||||
#endif //_WIN32_JOYSTICK_H_EADER_
|
101
Libs/ois/win32/Win32KeyBoard.h
Normal file
101
Libs/ois/win32/Win32KeyBoard.h
Normal file
|
@ -0,0 +1,101 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef _WIN32_KEYBOARD_H_EADER_
|
||||
#define _WIN32_KEYBOARD_H_EADER_
|
||||
|
||||
#include "OISKeyboard.h"
|
||||
#include "win32/Win32Prereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
class Win32Keyboard : public Keyboard
|
||||
{
|
||||
public:
|
||||
/**
|
||||
@remarks
|
||||
Constructor
|
||||
@param pDI
|
||||
Valid DirectInput8 Interface
|
||||
@param buffered
|
||||
True for buffered input mode
|
||||
@param coopSettings
|
||||
A combination of DI Flags (see DX Help for info on input device settings)
|
||||
*/
|
||||
Win32Keyboard(InputManager* creator, IDirectInput8* pDI, bool buffered, DWORD coopSettings);
|
||||
virtual ~Win32Keyboard();
|
||||
|
||||
/** @copydoc Keyboard::isKeyDown */
|
||||
virtual bool isKeyDown(KeyCode key) const;
|
||||
|
||||
/** @copydoc Keyboard::getAsString */
|
||||
virtual const std::string& getAsString(KeyCode kc);
|
||||
|
||||
/** @copydoc Keyboard::getAsKeyCode */
|
||||
virtual KeyCode getAsKeyCode(std::string str)
|
||||
{ /*TODO: Implement OS version*/
|
||||
return KC_UNASSIGNED;
|
||||
}
|
||||
|
||||
/** @copydoc Keyboard::copyKeyStates */
|
||||
virtual void copyKeyStates(char keys[256]) const;
|
||||
|
||||
/** @copydoc Object::setBuffered */
|
||||
virtual void setBuffered(bool buffered);
|
||||
|
||||
/** @copydoc Object::capture */
|
||||
virtual void capture();
|
||||
|
||||
/** @copydoc Object::queryInterface */
|
||||
virtual Interface* queryInterface(Interface::IType type)
|
||||
{
|
||||
OIS_UNUSED(type);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/** @copydoc Object::_initialize */
|
||||
virtual void _initialize();
|
||||
|
||||
protected:
|
||||
void _readBuffered();
|
||||
void _read();
|
||||
|
||||
IDirectInput8* mDirectInput;
|
||||
IDirectInputDevice8* mKeyboard;
|
||||
DWORD coopSetting;
|
||||
|
||||
unsigned char KeyBuffer[256];
|
||||
|
||||
//! Internal method for translating KeyCodes to Text
|
||||
int _translateText(KeyCode kc);
|
||||
|
||||
//! Stored dead key from last translation
|
||||
WCHAR deadKey;
|
||||
|
||||
//! used for getAsString
|
||||
std::string mGetString;
|
||||
};
|
||||
}
|
||||
#endif //_WIN32_KEYBOARD_H_EADER_
|
66
Libs/ois/win32/Win32Mouse.h
Normal file
66
Libs/ois/win32/Win32Mouse.h
Normal file
|
@ -0,0 +1,66 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef _WIN32_MOUSE_H_EADER_
|
||||
#define _WIN32_MOUSE_H_EADER_
|
||||
|
||||
#include "OISMouse.h"
|
||||
#include "win32/Win32Prereqs.h"
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
class Win32Mouse : public Mouse
|
||||
{
|
||||
public:
|
||||
Win32Mouse(InputManager* creator, IDirectInput8* pDI, bool buffered, DWORD coopSettings);
|
||||
virtual ~Win32Mouse();
|
||||
|
||||
/** @copydoc Object::setBuffered */
|
||||
virtual void setBuffered(bool buffered);
|
||||
|
||||
/** @copydoc Object::capture */
|
||||
virtual void capture();
|
||||
|
||||
/** @copydoc Object::queryInterface */
|
||||
virtual Interface* queryInterface(Interface::IType type)
|
||||
{
|
||||
OIS_UNUSED(type);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/** @copydoc Object::_initialize */
|
||||
virtual void _initialize();
|
||||
|
||||
protected:
|
||||
bool _doMouseClick(int mouseButton, unsigned char di);
|
||||
|
||||
IDirectInput8* mDirectInput;
|
||||
IDirectInputDevice8* mMouse;
|
||||
DWORD coopSetting;
|
||||
HWND mHwnd;
|
||||
};
|
||||
}
|
||||
|
||||
#endif //_WIN32_MOUSE_H_EADER_
|
74
Libs/ois/win32/Win32Prereqs.h
Normal file
74
Libs/ois/win32/Win32Prereqs.h
Normal file
|
@ -0,0 +1,74 @@
|
|||
/*
|
||||
The zlib/libpng License
|
||||
|
||||
Copyright (c) 2018 Arthur Brainville
|
||||
Copyright (c) 2015 Andrew Fenn
|
||||
Copyright (c) 2005-2010 Phillip Castaneda (pjcast -- www.wreckedgames.com)
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty. In no
|
||||
event will the authors be held liable for any damages arising from the use of this
|
||||
software.
|
||||
|
||||
Permission is granted to anyone to use this software for any purpose, including
|
||||
commercial applications, and to alter it and redistribute it freely, subject to the
|
||||
following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that
|
||||
you wrote the original software. If you use this software in a product,
|
||||
an acknowledgment in the product documentation would be appreciated
|
||||
but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and must not be
|
||||
misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#ifndef _WIN32_INPUTSYSTEM_PREREQS_H
|
||||
#define _WIN32_INPUTSYSTEM_PREREQS_H
|
||||
|
||||
#include <cstddef>
|
||||
#define WIN32_LEAN_AND_MEAN
|
||||
#define DIRECTINPUT_VERSION 0x0800
|
||||
#include <windows.h>
|
||||
#include <dinput.h>
|
||||
|
||||
#ifdef OIS_WIN32_XINPUT_SUPPORT
|
||||
#include <xinput.h>
|
||||
#endif
|
||||
|
||||
//Max number of elements to collect from buffered DirectInput
|
||||
#define KEYBOARD_DX_BUFFERSIZE 17
|
||||
#define MOUSE_DX_BUFFERSIZE 128
|
||||
#define JOYSTICK_DX_BUFFERSIZE 129
|
||||
|
||||
//MinGW defines
|
||||
#if defined(OIS_MINGW_COMPILER)
|
||||
#undef FIELD_OFFSET
|
||||
#define FIELD_OFFSET offsetof
|
||||
#endif
|
||||
|
||||
namespace OIS
|
||||
{
|
||||
//Local Forward declarations
|
||||
class Win32InputManager;
|
||||
class Win32Keyboard;
|
||||
class Win32JoyStick;
|
||||
class Win32Mouse;
|
||||
class Win32ForceFeedback;
|
||||
|
||||
//Information needed to create DirectInput joysticks
|
||||
class JoyStickInfo
|
||||
{
|
||||
public:
|
||||
int devId;
|
||||
GUID deviceID;
|
||||
GUID productGuid;
|
||||
std::string vendor;
|
||||
bool isXInput;
|
||||
int xInputDev;
|
||||
};
|
||||
|
||||
typedef std::vector<JoyStickInfo> JoyStickInfoList;
|
||||
}
|
||||
|
||||
#endif //_WIN32_INPUTSYSTEM_PREREQS_H
|
|
@ -1,128 +0,0 @@
|
|||
-- Place in this LUA script all the strings of your game
|
||||
-- Please follow the rules for IDs in the comments before each section
|
||||
|
||||
local strings = {
|
||||
new_game = {"New Game", "Nouvelle partie", "Nuova partita", "Neues Spiel", "Nueva partida"},
|
||||
load_game = {"Load Game", "Chargement", "Carica partita", "Spiel laden", "Cargar partida"}
|
||||
}
|
||||
GameFlow:SetStrings(strings)
|
||||
local languages = {"English", "Français", "Italiano", "Deutsch", "Español"}
|
||||
GameFlow:SetLanguageNames(languages)
|
||||
|
||||
-- Global engine string, please don't change the IDs because internally TEN machine code refers to strings by fixed ID
|
||||
GameFlow.strings[1] = "Game";
|
||||
GameFlow.strings[2] = "Lara's home";
|
||||
GameFlow.strings[3] = "Controls";
|
||||
GameFlow.strings[4] = "Display";
|
||||
GameFlow.strings[5] = "Sound";
|
||||
GameFlow.strings[6] = "New game";
|
||||
GameFlow.strings[7] = "Load game";
|
||||
GameFlow.strings[8] = "Save game";
|
||||
GameFlow.strings[9] = "Exit game";
|
||||
GameFlow.strings[10] = "Exit to title";
|
||||
GameFlow.strings[11] = "Uzi";
|
||||
GameFlow.strings[12] = "Pistols";
|
||||
GameFlow.strings[13] = "Shotgun";
|
||||
GameFlow.strings[14] = "Revolver";
|
||||
GameFlow.strings[15] = "Revolver + LaserSight";
|
||||
GameFlow.strings[16] = "Desert Eagle";
|
||||
GameFlow.strings[17] = "Desert Eagle + LaserSight";
|
||||
GameFlow.strings[18] = "Desert Eagle Ammo";
|
||||
GameFlow.strings[19] = "HK Gun";
|
||||
GameFlow.strings[20] = "HK Gun (Silenced)";
|
||||
GameFlow.strings[21] = "Shotgun Normal Ammo";
|
||||
GameFlow.strings[22] = "Shotgun Wideshot Ammo";
|
||||
GameFlow.strings[23] = "HK Sniper Mode";
|
||||
GameFlow.strings[24] = "HK Burst Mode";
|
||||
GameFlow.strings[25] = "HK Rapid Mode";
|
||||
GameFlow.strings[26] = "HK Ammo";
|
||||
GameFlow.strings[27] = "Revolver Ammo";
|
||||
GameFlow.strings[28] = "Uzi Ammo";
|
||||
GameFlow.strings[29] = "Pistol Ammo";
|
||||
GameFlow.strings[30] = "LaserSight";
|
||||
GameFlow.strings[31] = "Silencer";
|
||||
GameFlow.strings[32] = "Large Medipack";
|
||||
GameFlow.strings[33] = "Small Medipack";
|
||||
GameFlow.strings[34] = "Binoculars";
|
||||
GameFlow.strings[35] = "Headset";
|
||||
GameFlow.strings[36] = "Flares";
|
||||
GameFlow.strings[37] = "Timex-TMX";
|
||||
GameFlow.strings[38] = "Crowbar";
|
||||
GameFlow.strings[39] = "Use";
|
||||
GameFlow.strings[40] = "Combine";
|
||||
GameFlow.strings[41] = "Separe";
|
||||
GameFlow.strings[42] = "Choose ammo";
|
||||
GameFlow.strings[43] = "Select level";
|
||||
GameFlow.strings[44] = "%02d days %02d:%02d:%02d";
|
||||
GameFlow.strings[45] = "Not saved";
|
||||
GameFlow.strings[46] = "Grenade launcher";
|
||||
GameFlow.strings[47] = "Grenade Normal Ammo";
|
||||
GameFlow.strings[48] = "Grenade Poisoned Ammo";
|
||||
GameFlow.strings[49] = "Grenade Explosive Ammo";
|
||||
GameFlow.strings[50] = "Harpoon gun";
|
||||
GameFlow.strings[51] = "Harpoon ammo";
|
||||
GameFlow.strings[52] = "Rocket launcher";
|
||||
GameFlow.strings[53] = "Rocket ammo";
|
||||
GameFlow.strings[54] = "Crossbow";
|
||||
GameFlow.strings[55] = "Crossbow + LaserSight";
|
||||
GameFlow.strings[56] = "Crossbow Normal Ammo";
|
||||
GameFlow.strings[57] = "Crossbow Poisoned Ammo";
|
||||
GameFlow.strings[58] = "Crossbow Explosive Ammo";
|
||||
GameFlow.strings[59] = "Diary";
|
||||
GameFlow.strings[60] = "Enabled";
|
||||
GameFlow.strings[61] = "Disabled";
|
||||
GameFlow.strings[62] = "Music volume";
|
||||
GameFlow.strings[63] = "SFX volume";
|
||||
GameFlow.strings[64] = "Screen resolution";
|
||||
GameFlow.strings[65] = "Dynamic shadows";
|
||||
GameFlow.strings[66] = "Underwater caustics";
|
||||
GameFlow.strings[67] = "Volumetric fog";
|
||||
GameFlow.strings[68] = "Apply";
|
||||
GameFlow.strings[69] = "Cancel";
|
||||
GameFlow.strings[70] = "Enable sound";
|
||||
GameFlow.strings[71] = "Special effects";
|
||||
GameFlow.strings[75] = "Small Waterskin (Empty)"
|
||||
GameFlow.strings[76] = "Large Waterskin (Empty)"
|
||||
GameFlow.strings[78] = "Move forward"
|
||||
GameFlow.strings[79] = "Move backward"
|
||||
GameFlow.strings[80] = "Move left"
|
||||
GameFlow.strings[81] = "Move right"
|
||||
GameFlow.strings[82] = "Duck"
|
||||
GameFlow.strings[83] = "Dash"
|
||||
GameFlow.strings[84] = "Walk"
|
||||
GameFlow.strings[85] = "Jump"
|
||||
GameFlow.strings[86] = "Action"
|
||||
GameFlow.strings[87] = "Draw weapon"
|
||||
GameFlow.strings[88] = "Use flare"
|
||||
GameFlow.strings[89] = "Look"
|
||||
GameFlow.strings[90] = "Roll"
|
||||
GameFlow.strings[91] = "Inventory"
|
||||
GameFlow.strings[92] = "Step left"
|
||||
GameFlow.strings[93] = "Step right"
|
||||
GameFlow.strings[94] = "Items"
|
||||
GameFlow.strings[95] = "Puzzles"
|
||||
|
||||
-- Level names (from 100 to 199)
|
||||
GameFlow.strings[100] = "Title level";
|
||||
GameFlow.strings[101] = "Strets of Rome";
|
||||
GameFlow.strings[102] = "Trajan Markets";
|
||||
GameFlow.strings[103] = "The Colosseum";
|
||||
GameFlow.strings[104] = "The base";
|
||||
GameFlow.strings[105] = "The submarine";
|
||||
GameFlow.strings[106] = "Deepsea Dive";
|
||||
GameFlow.strings[107] = "Sinking Submarine";
|
||||
GameFlow.strings[108] = "Gallows Tree";
|
||||
GameFlow.strings[109] = "Labyrinth";
|
||||
GameFlow.strings[110] = "Old Mill";
|
||||
GameFlow.strings[111] = "The 13th Floor";
|
||||
GameFlow.strings[112] = "Escape with the Iris";
|
||||
GameFlow.strings[113] = "Security breach";
|
||||
GameFlow.strings[114] = "Red alert!";
|
||||
GameFlow.strings[115] = "Test level";
|
||||
|
||||
-- Puzzle names (from 200 to 499)
|
||||
GameFlow.strings[200] = "Bronze key";
|
||||
GameFlow.strings[201] = "Golden key";
|
||||
|
||||
-- Examines strings (from 500 to 799, use \n sequence for new line)
|
||||
GameFlow.strings[500] = "Examine test \n This is a new line of text \n This is another new line of text";
|
|
@ -19,6 +19,16 @@ local strings = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
auto_target = {
|
||||
"Automatic targeting",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
back = {
|
||||
"Back",
|
||||
"",
|
||||
|
@ -259,6 +269,16 @@ local strings = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
controls_pause = {
|
||||
"Pause",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
controls_use_flare = {
|
||||
"Use Flare",
|
||||
"",
|
||||
|
@ -399,16 +419,6 @@ local strings = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
sounds = {
|
||||
"Audio settings",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
enable_sound = {
|
||||
"Enable Sounds",
|
||||
"",
|
||||
|
@ -669,6 +679,26 @@ local strings = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
options = {
|
||||
"Options",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
other_settings = {
|
||||
"Sound and Gameplay",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
output_settings = {
|
||||
"Output Settings",
|
||||
"",
|
||||
|
@ -719,6 +749,16 @@ local strings = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
reverb = {
|
||||
"Reverb",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
revolver = {
|
||||
"Revolver",
|
||||
"",
|
||||
|
@ -769,6 +809,16 @@ local strings = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
rumble = {
|
||||
"Vibration",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
save_game = {
|
||||
"Save game",
|
||||
"",
|
||||
|
@ -889,18 +939,8 @@ local strings = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
options = {
|
||||
"Options",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
sound = {
|
||||
"Sound settings",
|
||||
"Sound",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
|
@ -909,17 +949,7 @@ local strings = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
special_sound_fx = {
|
||||
"Special Sound FX",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
SILENCER_ITEM = {
|
||||
silencer = {
|
||||
"Silencer",
|
||||
"",
|
||||
"",
|
||||
|
@ -939,6 +969,16 @@ SILENCER_ITEM = {
|
|||
"",
|
||||
""
|
||||
},
|
||||
thumbstick_camera = {
|
||||
"Thumbstick camera",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
"",
|
||||
""
|
||||
},
|
||||
time_taken = {
|
||||
"Time Taken",
|
||||
"",
|
||||
|
|
|
@ -1,116 +0,0 @@
|
|||
local tracks = {
|
||||
AudioTrack.new("001", false),
|
||||
AudioTrack.new("002", false),
|
||||
AudioTrack.new("003", false),
|
||||
AudioTrack.new("004", false),
|
||||
AudioTrack.new("005", false),
|
||||
AudioTrack.new("006", false),
|
||||
AudioTrack.new("007", false),
|
||||
AudioTrack.new("008", false),
|
||||
AudioTrack.new("009", false),
|
||||
AudioTrack.new("010", false),
|
||||
AudioTrack.new("011", false),
|
||||
AudioTrack.new("012", false),
|
||||
AudioTrack.new("013", false),
|
||||
AudioTrack.new("014", false),
|
||||
AudioTrack.new("015", false),
|
||||
AudioTrack.new("016", false),
|
||||
AudioTrack.new("017", false),
|
||||
AudioTrack.new("018", false),
|
||||
AudioTrack.new("019", false),
|
||||
AudioTrack.new("020", false),
|
||||
AudioTrack.new("021", false),
|
||||
AudioTrack.new("022", false),
|
||||
AudioTrack.new("023", false),
|
||||
AudioTrack.new("024", false),
|
||||
AudioTrack.new("025", false),
|
||||
AudioTrack.new("026", false),
|
||||
AudioTrack.new("027", false),
|
||||
AudioTrack.new("028", false),
|
||||
AudioTrack.new("029", false),
|
||||
AudioTrack.new("030", false),
|
||||
AudioTrack.new("031", false),
|
||||
AudioTrack.new("032", false),
|
||||
AudioTrack.new("033", false),
|
||||
AudioTrack.new("034", false),
|
||||
AudioTrack.new("035", false),
|
||||
AudioTrack.new("036", false),
|
||||
AudioTrack.new("037", false),
|
||||
AudioTrack.new("038", false),
|
||||
AudioTrack.new("039", false),
|
||||
AudioTrack.new("040", false),
|
||||
AudioTrack.new("041", false),
|
||||
AudioTrack.new("042", false),
|
||||
AudioTrack.new("043", false),
|
||||
AudioTrack.new("044", false),
|
||||
AudioTrack.new("045", false),
|
||||
AudioTrack.new("046", false),
|
||||
AudioTrack.new("047", false),
|
||||
AudioTrack.new("048", false),
|
||||
AudioTrack.new("049", false),
|
||||
AudioTrack.new("050", false),
|
||||
AudioTrack.new("051", false),
|
||||
AudioTrack.new("052", false),
|
||||
AudioTrack.new("053", false),
|
||||
AudioTrack.new("054", false),
|
||||
AudioTrack.new("055", false),
|
||||
AudioTrack.new("056", false),
|
||||
AudioTrack.new("057", false),
|
||||
AudioTrack.new("058", false),
|
||||
AudioTrack.new("059", false),
|
||||
AudioTrack.new("060", false),
|
||||
AudioTrack.new("061", false),
|
||||
AudioTrack.new("062", false),
|
||||
AudioTrack.new("063", false),
|
||||
AudioTrack.new("064", false),
|
||||
AudioTrack.new("065", false),
|
||||
AudioTrack.new("066", false),
|
||||
AudioTrack.new("067", false),
|
||||
AudioTrack.new("068", false),
|
||||
AudioTrack.new("069", false),
|
||||
AudioTrack.new("070", false),
|
||||
AudioTrack.new("071", false),
|
||||
AudioTrack.new("072", false),
|
||||
AudioTrack.new("074", false),
|
||||
AudioTrack.new("075", false),
|
||||
AudioTrack.new("076", false),
|
||||
AudioTrack.new("077", false),
|
||||
AudioTrack.new("078", false),
|
||||
AudioTrack.new("079", false),
|
||||
AudioTrack.new("080", false),
|
||||
AudioTrack.new("081", false),
|
||||
AudioTrack.new("082", false),
|
||||
AudioTrack.new("083", false),
|
||||
AudioTrack.new("084", false),
|
||||
AudioTrack.new("085", false),
|
||||
AudioTrack.new("086", false),
|
||||
AudioTrack.new("087", false),
|
||||
AudioTrack.new("088", false),
|
||||
AudioTrack.new("089", false),
|
||||
AudioTrack.new("090", false),
|
||||
AudioTrack.new("091", false),
|
||||
AudioTrack.new("092", false),
|
||||
AudioTrack.new("093", false),
|
||||
AudioTrack.new("094", false),
|
||||
AudioTrack.new("095", false),
|
||||
AudioTrack.new("096", false),
|
||||
AudioTrack.new("097", false),
|
||||
AudioTrack.new("098", false),
|
||||
AudioTrack.new("099", false),
|
||||
AudioTrack.new("100", false),
|
||||
AudioTrack.new("101", true),
|
||||
AudioTrack.new("102", true),
|
||||
AudioTrack.new("103", true),
|
||||
AudioTrack.new("104", true),
|
||||
AudioTrack.new("105", true),
|
||||
AudioTrack.new("106", true),
|
||||
AudioTrack.new("107", true),
|
||||
AudioTrack.new("108", true),
|
||||
AudioTrack.new("109", false),
|
||||
AudioTrack.new("110", false),
|
||||
AudioTrack.new("111", false),
|
||||
AudioTrack.new("112", false),
|
||||
AudioTrack.new("073", false) -- secret must always be last one in the list
|
||||
};
|
||||
|
||||
SetAudioTracks(tracks);
|
Binary file not shown.
Before Width: | Height: | Size: 337 KiB |
|
@ -39,6 +39,8 @@
|
|||
|
||||
using namespace TEN::Effects::Lara;
|
||||
using namespace TEN::Control::Volumes;
|
||||
using namespace TEN::Input;
|
||||
|
||||
using std::function;
|
||||
using TEN::Renderer::g_Renderer;
|
||||
|
||||
|
@ -454,6 +456,8 @@ void LaraControl(ItemInfo* item, CollisionInfo* coll)
|
|||
if (lara->SprintEnergy < LARA_SPRINT_ENERGY_MAX && item->Animation.ActiveState != LS_SPRINT)
|
||||
lara->SprintEnergy++;
|
||||
|
||||
RumbleLaraHealthCondition(item);
|
||||
|
||||
lara->Control.IsLow = false;
|
||||
|
||||
bool isWater = TestEnvironment(ENV_FLAG_WATER, item);
|
||||
|
@ -844,28 +848,11 @@ void LaraWaterSurface(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
auto level = g_GameFlow->GetLevel(CurrentLevel);
|
||||
|
||||
if (level->GetLaraType() == LaraType::Divesuit)
|
||||
{
|
||||
if (lara->Control.TurnRate < -ANGLE(0.5f))
|
||||
lara->Control.TurnRate += ANGLE(0.5f);
|
||||
else if (lara->Control.TurnRate > ANGLE(0.5f))
|
||||
lara->Control.TurnRate -= ANGLE(0.5f);
|
||||
else
|
||||
lara->Control.TurnRate = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Reset turn rate.
|
||||
int sign = copysign(1, lara->Control.TurnRate);
|
||||
if (abs(lara->Control.TurnRate) > ANGLE(2.0f))
|
||||
lara->Control.TurnRate -= ANGLE(2.0f) * sign;
|
||||
else if (abs(lara->Control.TurnRate) > ANGLE(0.5f))
|
||||
lara->Control.TurnRate -= ANGLE(0.5f) * sign;
|
||||
else
|
||||
lara->Control.TurnRate = 0;
|
||||
}
|
||||
|
||||
// TODO: Subsuit gradually slows down at rate of 0.5 degrees. @Sezz 2022.06.23
|
||||
// Apply and reset turn rate.
|
||||
item->Pose.Orientation.y += lara->Control.TurnRate;
|
||||
if (!(TrInput & (IN_LEFT | IN_RIGHT)))
|
||||
lara->Control.TurnRate = 0;
|
||||
|
||||
if (level->GetLaraType() == LaraType::Divesuit)
|
||||
UpdateLaraSubsuitAngles(item);
|
||||
|
@ -931,22 +918,11 @@ void LaraUnderwater(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
auto* level = g_GameFlow->GetLevel(CurrentLevel);
|
||||
|
||||
if (level->GetLaraType() == LaraType::Divesuit)
|
||||
{
|
||||
if (lara->Control.TurnRate < -ANGLE(0.5f))
|
||||
lara->Control.TurnRate += ANGLE(0.5f);
|
||||
else if (lara->Control.TurnRate > ANGLE(0.5f))
|
||||
lara->Control.TurnRate -= ANGLE(0.5f);
|
||||
else
|
||||
lara->Control.TurnRate = 0;
|
||||
}
|
||||
else if (lara->Control.TurnRate < -ANGLE(2.0f))
|
||||
lara->Control.TurnRate += ANGLE(2.0f);
|
||||
else if (lara->Control.TurnRate > ANGLE(2.0f))
|
||||
lara->Control.TurnRate -= ANGLE(2.0f);
|
||||
else
|
||||
lara->Control.TurnRate = 0;
|
||||
// TODO: Subsuit gradually slowed down at rate of 0.5 degrees. @Sezz 2022.06.23
|
||||
// Apply and reset turn rate.
|
||||
item->Pose.Orientation.y += lara->Control.TurnRate;
|
||||
if (!(TrInput & (IN_LEFT | IN_RIGHT)))
|
||||
lara->Control.TurnRate = 0;
|
||||
|
||||
if (level->GetLaraType() == LaraType::Divesuit)
|
||||
UpdateLaraSubsuitAngles(item);
|
||||
|
|
|
@ -5,74 +5,77 @@
|
|||
struct ItemInfo;
|
||||
struct CollisionInfo;
|
||||
|
||||
#define LARA_GRAB_THRESHOLD ANGLE(40.0f)
|
||||
#define FRONT_ARC ANGLE(90.0f) // TODO: Check use.
|
||||
#define LARA_GRAB_THRESHOLD ANGLE(40.0f)
|
||||
#define FRONT_ARC ANGLE(90.0f) // TODO: Check use.
|
||||
|
||||
// Lean rates
|
||||
#define LARA_LEAN_RATE ANGLE(1.5f)
|
||||
#define LARA_LEAN_MAX ANGLE(11.0f)
|
||||
#define LARA_LEAN_MAX ANGLE(11.0f)
|
||||
|
||||
// Turn rates
|
||||
#define LARA_TURN_RATE ANGLE(2.25f)
|
||||
#define LARA_CRAWL_MOVE_TURN_RATE ANGLE(2.15f)
|
||||
#define LARA_POLE_TURN_RATE ANGLE(2.25f)
|
||||
#define LARA_SUBSUIT_TURN_RATE ANGLE(0.75f)
|
||||
// Turn rate acceleration rates
|
||||
#define LARA_TURN_RATE_ACCEL ANGLE(0.25f)
|
||||
#define LARA_CRAWL_MOVE_TURN_RATE_ACCEL ANGLE(0.15f)
|
||||
#define LARA_POLE_TURN_RATE_ACCEL ANGLE(0.25f)
|
||||
#define LARA_SUBSUIT_TURN_RATE_ACCEL ANGLE(0.25f)
|
||||
|
||||
// Turn rate maxes
|
||||
#define LARA_SLOW_TURN_MAX ANGLE(4.0f)
|
||||
#define LARA_SLOW_MED_TURN_MAX ANGLE(5.0f)
|
||||
#define LARA_MED_TURN_MAX ANGLE(6.0f)
|
||||
#define LARA_MED_FAST_TURN_MAX ANGLE(7.0f)
|
||||
#define LARA_FAST_TURN_MAX ANGLE(8.0f)
|
||||
#define LARA_WADE_TURN_MAX ANGLE(5.5f)
|
||||
#define LARA_SWAMP_TURN_MAX ANGLE(2.0f)
|
||||
#define LARA_JUMP_TURN_MAX ANGLE(3.0f)
|
||||
#define LARA_REACH_TURN_MAX ANGLE(1.3f)
|
||||
#define LARA_SLIDE_TURN_MAX ANGLE(5.70f)
|
||||
#define LARA_CRAWL_TURN_MAX ANGLE(2.0f)
|
||||
#define LARA_CRAWL_MOVE_TURN_MAX ANGLE(3.75f)
|
||||
#define LARA_CROUCH_ROLL_TURN_MAX ANGLE(2.75f)
|
||||
#define LARA_POLE_TURN_MAX ANGLE(4.5f)
|
||||
#define LARA_SLOW_TURN_RATE_MAX ANGLE(2.0f)
|
||||
#define LARA_SLOW_MED_TURN_RATE_MAX ANGLE(3.0f)
|
||||
#define LARA_MED_TURN_RATE_MAX ANGLE(4.0f)
|
||||
#define LARA_MED_FAST_TURN_RATE_MAX ANGLE(5.0f)
|
||||
#define LARA_FAST_TURN_RATE_MAX ANGLE(6.0f)
|
||||
#define LARA_WADE_TURN_RATE_MAX ANGLE(3.5f)
|
||||
#define LARA_SWAMP_TURN_RATE_MAX ANGLE(1.5f)
|
||||
#define LARA_JUMP_TURN_RATE_MAX ANGLE(1.0f)
|
||||
#define LARA_REACH_TURN_RATE_MAX ANGLE(0.8f)
|
||||
#define LARA_SLIDE_TURN_RATE_MAX ANGLE(3.70f)
|
||||
#define LARA_CRAWL_TURN_RATE_MAX ANGLE(1.5f)
|
||||
#define LARA_CRAWL_MOVE_TURN_RATE_MAX ANGLE(1.75f)
|
||||
#define LARA_CROUCH_ROLL_TURN_RATE_MAX ANGLE(0.75f)
|
||||
#define LARA_POLE_TURN_RATE_MAX ANGLE(2.5f)
|
||||
|
||||
// Flex rates
|
||||
#define LARA_CRAWL_FLEX_RATE ANGLE(2.25f)
|
||||
#define LARA_CRAWL_FLEX_MAX ANGLE(45.0f) / 2 // 2 = hardcoded number of bones to flex (head and torso).
|
||||
#define LARA_CRAWL_FLEX_MAX ANGLE(50.0f) / 2 // 2 = hardcoded number of bones to flex (head and torso).
|
||||
|
||||
constexpr auto LARA_HEIGHT = CLICK(3) - 1; // Lara height in basic states.
|
||||
constexpr auto LARA_HEIGHT_CRAWL = 350; // Lara height in crawl states.
|
||||
constexpr auto LARA_HEIGHT_MONKEY = 850; // Lara height in monkey swing states.
|
||||
constexpr auto LARA_HEIGHT_TREAD = 700; // Lara height in water treading states.
|
||||
constexpr auto LARA_HEIGHT_STRETCH = 870; // Lara height in jump-up and ledge hanging states.
|
||||
constexpr auto LARA_HEIGHT_REACH = 820; // Lara height in reach state.
|
||||
constexpr auto LARA_HEIGHT_SURFACE = 800; // Lara height when surfacing water.
|
||||
constexpr auto LARA_HEADROOM = 160; // Amount of reasonable space above Lara's head.
|
||||
constexpr auto LARA_RADIUS = 100;
|
||||
constexpr auto LARA_RADIUS_CRAWL = 200;
|
||||
constexpr auto LARA_RADIUS_UNDERWATER = 300;
|
||||
constexpr auto LARA_RADIUS_DEATH = 400;
|
||||
constexpr auto LARA_VELOCITY = 12;
|
||||
constexpr int LARA_HEIGHT = CLICK(3) - 1; // Lara height in basic states.
|
||||
constexpr int LARA_HEIGHT_CRAWL = 350; // Lara height in crawl states.
|
||||
constexpr int LARA_HEIGHT_MONKEY = 850; // Lara height in monkey swing states.
|
||||
constexpr int LARA_HEIGHT_TREAD = 700; // Lara height in water treading states.
|
||||
constexpr int LARA_HEIGHT_STRETCH = 870; // Lara height in jump up and ledge hanging states.
|
||||
constexpr int LARA_HEIGHT_REACH = 820; // Lara height in reach state.
|
||||
constexpr int LARA_HEIGHT_SURFACE = 800; // Lara height when resurfacing from water.
|
||||
constexpr int LARA_HEADROOM = 160; // Reasonable space above Lara's head.
|
||||
constexpr int LARA_RADIUS = 100;
|
||||
constexpr int LARA_RADIUS_CRAWL = 200;
|
||||
constexpr int LARA_RADIUS_UNDERWATER = 300;
|
||||
constexpr int LARA_RADIUS_DEATH = 400;
|
||||
constexpr int LARA_VELOCITY = 12;
|
||||
|
||||
// TODO: Convert velocities to floats and eliminate the division that goes on with these values. @Sezz
|
||||
constexpr auto LARA_SWIM_ACCELERATION = 8;
|
||||
constexpr auto LARA_SWIM_DECELERATION = 6;
|
||||
constexpr auto LARA_TREAD_VELOCITY_MAX = 70;
|
||||
constexpr auto LARA_SWIM_VELOCITY_MAX = 200;
|
||||
constexpr auto LARA_SWIM_INTERTIA_VELOCITY_MIN = 134;
|
||||
// TODO: Convert velocities to floats and eliminate the format conversion that goes on with these values. @Sezz
|
||||
constexpr int LARA_SWIM_VELOCITY_ACCEL = 2 * 4;
|
||||
constexpr int LARA_SWIM_VELOCITY_DECEL = 1.5f * 4;
|
||||
constexpr int LARA_TREAD_VELOCITY_MAX = 17.5f * 4;
|
||||
constexpr int LARA_SWIM_VELOCITY_MAX = 50 * 4;
|
||||
constexpr int LARA_SWIM_INTERTIA_VELOCITY_MIN = 33.5f * 4;
|
||||
|
||||
constexpr auto LARA_FREEFALL_VELOCITY = 131;
|
||||
constexpr auto LARA_DAMAGE_VELOCITY = 141;
|
||||
constexpr auto LARA_DEATH_VELOCITY = 155;
|
||||
constexpr auto LARA_DIVE_DEATH_VELOCITY = 134;
|
||||
constexpr auto LARA_TERMINAL_VELOCITY = CLICK(10);
|
||||
constexpr int LARA_FREEFALL_VELOCITY = 131;
|
||||
constexpr int LARA_DAMAGE_VELOCITY = 141;
|
||||
constexpr int LARA_DEATH_VELOCITY = 155;
|
||||
constexpr int LARA_DIVE_DEATH_VELOCITY = 134;
|
||||
constexpr int LARA_TERMINAL_VELOCITY = CLICK(10);
|
||||
|
||||
constexpr auto LARA_POSITION_ADJUST_MAX_TIME = FPS * 3; // 30 frames * 3 = 3 seconds allowed for position adjustment.
|
||||
constexpr auto LARA_POSE_TIME = FPS * 30; // 30 frames * 30 = 30 seconds to AFK pose.
|
||||
constexpr auto LARA_RUN_JUMP_TIME = 22; // Frames to count before a running jump is possible.
|
||||
constexpr auto LARA_POSITION_ADJUST_MAX_TIME = FPS * 3; // 30 frames * 3 = 3 seconds allowed for position adjustment.
|
||||
constexpr auto LARA_POSE_TIME = FPS * 30; // 30 frames * 30 = 30 seconds to AFK pose.
|
||||
constexpr auto LARA_RUN_JUMP_TIME = 22; // Frames to count before a running jump is possible.
|
||||
constexpr auto LARA_SPRINT_JUMP_TIME = 50; // Frames to count before a sprint jump is possible.
|
||||
|
||||
constexpr auto LARA_HEALTH_MAX = 1000.0f;
|
||||
constexpr auto LARA_AIR_MAX = 1800.0f;
|
||||
constexpr auto LARA_SPRINT_ENERGY_MAX = 120.0f;
|
||||
constexpr auto LARA_POISON_POTENCY_MAX = 64.0f;
|
||||
constexpr float LARA_HEALTH_MAX = 1000.0f;
|
||||
constexpr float LARA_HEALTH_CRITICAL = LARA_HEALTH_MAX / 4.0f;
|
||||
constexpr float LARA_AIR_MAX = 1800.0f;
|
||||
constexpr float LARA_AIR_CRITICAL = LARA_AIR_MAX / 4.0f;
|
||||
constexpr float LARA_SPRINT_ENERGY_MAX = 120.0f;
|
||||
constexpr float LARA_POISON_POTENCY_MAX = 64.0f;
|
||||
|
||||
extern LaraInfo Lara;
|
||||
extern ItemInfo* LaraItem;
|
||||
|
|
|
@ -19,6 +19,8 @@
|
|||
#include "Specific/setup.h"
|
||||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// ------------------------------
|
||||
// BASIC MOVEMENT & MISCELLANEOUS
|
||||
// Control & Collision Functions
|
||||
|
@ -127,9 +129,9 @@ void lara_as_walk_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
lara->Control.Count.RunJump++;
|
||||
if (lara->Control.Count.RunJump > (LARA_RUN_JUMP_TIME / 2 + 4))
|
||||
lara->Control.Count.RunJump = LARA_RUN_JUMP_TIME / 2 + 4;
|
||||
lara->Control.Count.Run++;
|
||||
if (lara->Control.Count.Run > (LARA_RUN_JUMP_TIME / 2 + 4))
|
||||
lara->Control.Count.Run = LARA_RUN_JUMP_TIME / 2 + 4;
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
{
|
||||
|
@ -141,21 +143,10 @@ void lara_as_walk_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
if (lara->Control.IsMoving)
|
||||
return;
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_MED_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX / 3, LARA_LEAN_RATE / 6);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_MED_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX / 3, LARA_LEAN_RATE / 6);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_MED_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE / 6, LARA_LEAN_MAX / 2);
|
||||
}
|
||||
|
||||
if (TrInput & IN_FORWARD)
|
||||
|
@ -245,9 +236,9 @@ void lara_as_run_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
lara->Control.Count.RunJump++;
|
||||
if (lara->Control.Count.RunJump > LARA_RUN_JUMP_TIME)
|
||||
lara->Control.Count.RunJump = LARA_RUN_JUMP_TIME;
|
||||
lara->Control.Count.Run++;
|
||||
if (lara->Control.Count.Run > LARA_RUN_JUMP_TIME)
|
||||
lara->Control.Count.Run = LARA_RUN_JUMP_TIME;
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
{
|
||||
|
@ -255,26 +246,15 @@ void lara_as_run_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_FAST_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_FAST_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX, LARA_LEAN_RATE);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_FAST_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_FAST_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX, LARA_LEAN_RATE);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_FAST_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE, LARA_LEAN_MAX);
|
||||
}
|
||||
|
||||
if (TrInput & IN_JUMP || lara->Control.RunJumpQueued)
|
||||
{
|
||||
if (lara->Control.Count.RunJump >= LARA_RUN_JUMP_TIME &&
|
||||
if (!(TrInput & IN_SPRINT) && lara->Control.Count.Run >= LARA_RUN_JUMP_TIME &&
|
||||
TestLaraRunJumpForward(item, coll))
|
||||
{
|
||||
item->Animation.TargetState = LS_JUMP_FORWARD;
|
||||
|
@ -285,7 +265,7 @@ void lara_as_run_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
}
|
||||
|
||||
if ((TrInput & IN_ROLL || (TrInput & IN_FORWARD && TrInput & IN_BACK)) &&
|
||||
!lara->Control.RunJumpQueued && // Jump queue blocks roll.
|
||||
!lara->Control.RunJumpQueued && // Jump queue blocks roll.
|
||||
lara->Control.WaterStatus != WaterStatus::Wade)
|
||||
{
|
||||
item->Animation.TargetState = LS_ROLL_FORWARD;
|
||||
|
@ -371,6 +351,7 @@ void lara_col_run_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
item->Animation.TargetState = LS_SPLAT;
|
||||
if (GetChange(item, &g_Level.Anims[item->Animation.AnimNumber]))
|
||||
{
|
||||
Rumble(0.4f, 0.15f);
|
||||
item->Animation.ActiveState = LS_SPLAT;
|
||||
return;
|
||||
}
|
||||
|
@ -421,21 +402,14 @@ void lara_as_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
if (BinocularOn)
|
||||
return;
|
||||
|
||||
if (!(TrInput & IN_JUMP) || isSwamp) // JUMP locks orientation outside swamps.
|
||||
if (!(TrInput & IN_JUMP) || isSwamp) // JUMP locks orientation outside swamps.
|
||||
{
|
||||
if (TrInput & IN_LEFT &&
|
||||
!(TrInput & IN_LSTEP || (TrInput & IN_WALK && TrInput & IN_LEFT))) // Sidestep locks orientation.
|
||||
if ((TrInput & IN_LEFT &&
|
||||
!(TrInput & IN_LSTEP || (TrInput & IN_WALK && TrInput & IN_LEFT))) || // Sidestep locks orientation.
|
||||
(TrInput & IN_RIGHT &&
|
||||
!(TrInput & IN_RSTEP || (TrInput & IN_WALK && TrInput & IN_RIGHT))))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT &&
|
||||
!(TrInput & IN_RSTEP || (TrInput & IN_WALK && TrInput & IN_RIGHT)))
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -538,7 +512,7 @@ void lara_as_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
if (TrInput & IN_SPRINT ||
|
||||
lara->Control.TurnRate <= -LARA_SLOW_TURN_MAX || TestLaraFastTurn(item))
|
||||
lara->Control.TurnRate <= -LARA_SLOW_TURN_RATE_MAX || TestLaraFastTurn(item))
|
||||
{
|
||||
item->Animation.TargetState = LS_TURN_LEFT_FAST;
|
||||
}
|
||||
|
@ -550,7 +524,7 @@ void lara_as_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
if (TrInput & IN_SPRINT ||
|
||||
lara->Control.TurnRate >= LARA_SLOW_TURN_MAX || TestLaraFastTurn(item))
|
||||
lara->Control.TurnRate >= LARA_SLOW_TURN_RATE_MAX || TestLaraFastTurn(item))
|
||||
{
|
||||
item->Animation.TargetState = LS_TURN_RIGHT_FAST;
|
||||
}
|
||||
|
@ -794,21 +768,10 @@ void lara_as_run_back(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_MED_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX / 3, LARA_LEAN_RATE / 4);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_MED_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX / 3, LARA_LEAN_RATE / 4);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_MED_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE / 4, LARA_LEAN_MAX / 3);
|
||||
}
|
||||
|
||||
if (TrInput & IN_ROLL)
|
||||
|
@ -880,12 +843,6 @@ void lara_as_turn_right_slow(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < 0)
|
||||
lara->Control.TurnRate = 0;
|
||||
else if (lara->Control.TurnRate > LARA_MED_FAST_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_MED_FAST_TURN_MAX;
|
||||
|
||||
if (lara->Control.WaterStatus == WaterStatus::Wade)
|
||||
{
|
||||
if (isSwamp)
|
||||
|
@ -896,6 +853,8 @@ void lara_as_turn_right_slow(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_MED_FAST_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_JUMP)
|
||||
{
|
||||
SetLaraJumpDirection(item, coll);
|
||||
|
@ -990,10 +949,10 @@ void lara_as_turn_right_slow(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
item->Animation.TargetState = LS_TURN_RIGHT_SLOW;
|
||||
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_RATE_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_RATE_MAX;
|
||||
}
|
||||
else */if (lara->Control.TurnRate > LARA_SLOW_MED_TURN_MAX)
|
||||
else */if (lara->Control.TurnRate > LARA_SLOW_MED_TURN_RATE_MAX)
|
||||
item->Animation.TargetState = LS_TURN_RIGHT_FAST;
|
||||
else USE_FEATURE_IF_CPP20([[likely]])
|
||||
item->Animation.TargetState = LS_TURN_RIGHT_SLOW;
|
||||
|
@ -1009,8 +968,7 @@ void PsuedoLaraAsWadeTurnRightSlow(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (lara->Control.TurnRate > LARA_WADE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_WADE_TURN_MAX;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_WADE_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_JUMP && TestLaraJumpUp(item, coll))
|
||||
{
|
||||
|
@ -1074,8 +1032,7 @@ void PsuedoLaraAsSwampTurnRightSlow(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (lara->Control.TurnRate > LARA_SWAMP_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SWAMP_TURN_MAX;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SWAMP_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_FORWARD)
|
||||
{
|
||||
|
@ -1150,12 +1107,6 @@ void lara_as_turn_left_slow(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > 0)
|
||||
lara->Control.TurnRate = 0;
|
||||
else if (lara->Control.TurnRate < -LARA_MED_FAST_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_MED_FAST_TURN_MAX;
|
||||
|
||||
if (lara->Control.WaterStatus == WaterStatus::Wade)
|
||||
{
|
||||
if (isSwamp)
|
||||
|
@ -1166,6 +1117,8 @@ void lara_as_turn_left_slow(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_MED_FAST_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_JUMP)
|
||||
{
|
||||
SetLaraJumpDirection(item, coll);
|
||||
|
@ -1260,10 +1213,10 @@ void lara_as_turn_left_slow(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
item->Animation.TargetState = LS_TURN_LEFT_SLOW;
|
||||
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_RATE_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_RATE_MAX;
|
||||
}
|
||||
else */if (lara->Control.TurnRate < -LARA_SLOW_MED_TURN_MAX)
|
||||
else */if (lara->Control.TurnRate < -LARA_SLOW_MED_TURN_RATE_MAX)
|
||||
item->Animation.TargetState = LS_TURN_LEFT_FAST;
|
||||
else USE_FEATURE_IF_CPP20([[likely]])
|
||||
item->Animation.TargetState = LS_TURN_LEFT_SLOW;
|
||||
|
@ -1279,8 +1232,7 @@ void PsuedoLaraAsWadeTurnLeftSlow(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (lara->Control.TurnRate < -LARA_WADE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_WADE_TURN_MAX;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_WADE_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_JUMP && TestLaraJumpUp(item, coll))
|
||||
{
|
||||
|
@ -1344,8 +1296,7 @@ void PsuedoLaraAsSwampTurnLeftSlow(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (lara->Control.TurnRate < -LARA_SWAMP_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SWAMP_TURN_MAX;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SWAMP_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_FORWARD)
|
||||
{
|
||||
|
@ -1504,29 +1455,16 @@ void lara_as_walk_back(ItemInfo* item, CollisionInfo* coll)
|
|||
if (lara->Control.IsMoving)
|
||||
return;
|
||||
|
||||
if (isSwamp &&
|
||||
lara->Control.WaterStatus == WaterStatus::Wade)
|
||||
if (isSwamp && lara->Control.WaterStatus == WaterStatus::Wade)
|
||||
{
|
||||
PseudoLaraAsSwampWalkBack(item, coll);
|
||||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX / 3, LARA_LEAN_RATE / 4);
|
||||
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX / 3, LARA_LEAN_RATE / 4);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE / 4, LARA_LEAN_MAX / 3);
|
||||
}
|
||||
|
||||
if (TrInput & IN_BACK &&
|
||||
|
@ -1544,22 +1482,10 @@ void PseudoLaraAsSwampWalkBack(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX / 3)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX / 3;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX / 3, LARA_LEAN_RATE / 3);
|
||||
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX / 3)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX / 3;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX / 3, LARA_LEAN_RATE / 3);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX / 3);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE / 3, LARA_LEAN_MAX / 3);
|
||||
}
|
||||
|
||||
if (TrInput & IN_BACK)
|
||||
|
@ -1631,11 +1557,7 @@ void lara_as_turn_right_fast(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_MED_TURN_MAX;
|
||||
else if (lara->Control.TurnRate > LARA_FAST_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_FAST_TURN_MAX;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, LARA_MED_TURN_RATE_MAX, LARA_FAST_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_JUMP)
|
||||
{
|
||||
|
@ -1762,11 +1684,7 @@ void lara_as_turn_left_fast(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > -LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_MED_TURN_MAX;
|
||||
else if (lara->Control.TurnRate < -LARA_FAST_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_FAST_TURN_MAX;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, LARA_MED_TURN_RATE_MAX, LARA_FAST_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_JUMP)
|
||||
{
|
||||
|
@ -1899,18 +1817,8 @@ void lara_as_step_right(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (!(TrInput & IN_WALK)) // WALK locks orientation.
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
}
|
||||
|
||||
// TODO: Funky?
|
||||
|
@ -1999,18 +1907,8 @@ void lara_as_step_left(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (!(TrInput & IN_WALK)) // WALK locks orientation.
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
}
|
||||
|
||||
if (TrInput & IN_LSTEP || (TrInput & IN_WALK && TrInput & IN_LEFT))
|
||||
|
@ -2231,21 +2129,10 @@ void lara_as_wade_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_FAST_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_FAST_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX, LARA_LEAN_RATE / 2);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_FAST_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_FAST_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX, LARA_LEAN_RATE / 2);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_MED_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE / 2, LARA_LEAN_MAX);
|
||||
}
|
||||
|
||||
if (TrInput & IN_FORWARD)
|
||||
|
@ -2274,21 +2161,10 @@ void PseudoLaraAsSwampWadeForward(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SWAMP_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SWAMP_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX / 5 * 3, LARA_LEAN_RATE / 3);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SWAMP_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SWAMP_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX / 5 * 3, LARA_LEAN_RATE / 3);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SWAMP_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE / 3, LARA_LEAN_MAX * 0.6f);
|
||||
}
|
||||
|
||||
if (TrInput & IN_FORWARD)
|
||||
|
@ -2364,9 +2240,9 @@ void lara_as_sprint(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
lara->SprintEnergy--;
|
||||
|
||||
lara->Control.Count.RunJump++;
|
||||
if (lara->Control.Count.RunJump > LARA_RUN_JUMP_TIME)
|
||||
lara->Control.Count.RunJump = LARA_RUN_JUMP_TIME;
|
||||
lara->Control.Count.Run++;
|
||||
if (lara->Control.Count.Run > LARA_SPRINT_JUMP_TIME)
|
||||
lara->Control.Count.Run = LARA_SPRINT_JUMP_TIME;
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
{
|
||||
|
@ -2374,21 +2250,10 @@ void lara_as_sprint(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX, LARA_LEAN_RATE);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX, LARA_LEAN_RATE);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE, LARA_LEAN_MAX);
|
||||
}
|
||||
|
||||
if (TrInput & IN_JUMP || lara->Control.RunJumpQueued)
|
||||
|
@ -2398,7 +2263,7 @@ void lara_as_sprint(ItemInfo* item, CollisionInfo* coll)
|
|||
item->Animation.TargetState = LS_SPRINT_DIVE;
|
||||
return;
|
||||
}
|
||||
else if (lara->Control.Count.RunJump >= LARA_RUN_JUMP_TIME &&
|
||||
else if (TrInput & IN_SPRINT && lara->Control.Count.Run >= LARA_SPRINT_JUMP_TIME &&
|
||||
TestLaraRunJumpForward(item, coll) && HasStateDispatch(item, LS_JUMP_FORWARD))
|
||||
{
|
||||
item->Animation.TargetState = LS_JUMP_FORWARD;
|
||||
|
@ -2481,6 +2346,8 @@ void lara_col_sprint(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TestLaraWall(item, OFFSET_RADIUS(coll->Setup.Radius), -CLICK(2.5f)) ||
|
||||
coll->HitTallObject)
|
||||
{
|
||||
Rumble(0.5f, 0.15f);
|
||||
|
||||
item->Animation.TargetState = LS_SPLAT;
|
||||
if (GetChange(item, &g_Level.Anims[item->Animation.AnimNumber]))
|
||||
{
|
||||
|
@ -2515,25 +2382,14 @@ void lara_as_sprint_dive(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
lara->Control.Count.RunJump++;
|
||||
if (lara->Control.Count.RunJump > LARA_RUN_JUMP_TIME)
|
||||
lara->Control.Count.RunJump = LARA_RUN_JUMP_TIME;
|
||||
lara->Control.Count.Run++;
|
||||
if (lara->Control.Count.Run > LARA_RUN_JUMP_TIME)
|
||||
lara->Control.Count.Run = LARA_RUN_JUMP_TIME;
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -(LARA_LEAN_MAX * 3) / 5, LARA_LEAN_RATE);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, (LARA_LEAN_MAX * 3) / 5, LARA_LEAN_RATE);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE, LARA_LEAN_MAX * 0.6f);
|
||||
}
|
||||
|
||||
item->Animation.TargetState = LS_RUN_FORWARD;
|
||||
|
|
|
@ -1,17 +1,20 @@
|
|||
#include "framework.h"
|
||||
#include "Game/Lara/lara_cheat.h"
|
||||
|
||||
#include <OISKeyboard.h>
|
||||
#include "Game/collision/collide_room.h"
|
||||
#include "Game/effects/effects.h"
|
||||
#include "Game/items.h"
|
||||
#include "Game/Lara/lara.h"
|
||||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
#include "Game/Lara/lara_helpers.h"
|
||||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
#include "Sound/sound.h"
|
||||
#include "Specific/input.h"
|
||||
#include "Specific/level.h"
|
||||
#include "Specific/setup.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
void lara_as_swimcheat(ItemInfo* item, CollisionInfo* coll)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
@ -22,17 +25,9 @@ void lara_as_swimcheat(ItemInfo* item, CollisionInfo* coll)
|
|||
item->Pose.Orientation.x += ANGLE(3.0f);
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= ANGLE(3.4f);
|
||||
if (lara->Control.TurnRate < -ANGLE(6.0f))
|
||||
lara->Control.TurnRate = -ANGLE(6.0f);
|
||||
}
|
||||
ModulateLaraTurnRateY(item, ANGLE(3.4f), 0, ANGLE(6.0f));
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += ANGLE(3.4f);
|
||||
if (lara->Control.TurnRate > ANGLE(6.0f))
|
||||
lara->Control.TurnRate = ANGLE(6.0f);
|
||||
}
|
||||
ModulateLaraTurnRateY(item, ANGLE(3.4f), 0, ANGLE(6.0f));
|
||||
|
||||
if (TrInput & IN_ACTION)
|
||||
TriggerDynamicLight(item->Pose.Position.x, item->Pose.Position.y, item->Pose.Position.z, 31, 150, 150, 150);
|
||||
|
@ -42,13 +37,13 @@ void lara_as_swimcheat(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TrInput & IN_JUMP)
|
||||
{
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_ACCELERATION * 2;
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_VELOCITY_ACCEL * 2;
|
||||
if (item->Animation.VerticalVelocity > LARA_SWIM_VELOCITY_MAX * 2)
|
||||
item->Animation.VerticalVelocity = LARA_SWIM_VELOCITY_MAX * 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (item->Animation.VerticalVelocity >= LARA_SWIM_ACCELERATION)
|
||||
if (item->Animation.VerticalVelocity >= LARA_SWIM_VELOCITY_ACCEL)
|
||||
item->Animation.VerticalVelocity -= item->Animation.VerticalVelocity / 8;
|
||||
else
|
||||
item->Animation.VerticalVelocity = 0;
|
||||
|
@ -61,7 +56,7 @@ void LaraCheatyBits(ItemInfo* item)
|
|||
|
||||
if (g_GameFlow->IsFlyCheatEnabled())
|
||||
{
|
||||
if (KeyMap[DIK_O])
|
||||
if (KeyMap[OIS::KeyCode::KC_O])
|
||||
{
|
||||
if (lara->Vehicle == NO_ITEM)
|
||||
{
|
||||
|
|
|
@ -13,6 +13,8 @@
|
|||
#include "Specific/input.h"
|
||||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// LADDER CLIMB
|
||||
// Control & Collision Functions
|
||||
|
|
|
@ -17,6 +17,8 @@
|
|||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
#include "ScriptInterfaceLevel.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// COLLISION TEST FUNCTIONS
|
||||
// For State Control & Collision
|
||||
|
@ -24,6 +26,8 @@
|
|||
|
||||
bool LaraDeflectEdge(ItemInfo* item, CollisionInfo* coll)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (coll->CollisionType == CT_FRONT || coll->CollisionType == CT_TOP_FRONT)
|
||||
{
|
||||
ShiftItem(item, coll);
|
||||
|
@ -31,6 +35,7 @@ bool LaraDeflectEdge(ItemInfo* item, CollisionInfo* coll)
|
|||
item->Animation.TargetState = LS_IDLE;
|
||||
item->Animation.Velocity = 0;
|
||||
item->Animation.Airborne = false;
|
||||
lara->Control.TurnRate = 0;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -64,8 +69,12 @@ bool LaraDeflectEdgeJump(ItemInfo* item, CollisionInfo* coll)
|
|||
SetAnimation(item, LA_LAND);
|
||||
LaraSnapToHeight(item, coll);
|
||||
}
|
||||
else if (abs(item->Animation.Velocity) > 47) // TODO: Demagic. This is Lara's running velocity. Jumps have a minimum of 50.
|
||||
else if (abs(item->Animation.Velocity) > 47)
|
||||
{
|
||||
// TODO: Demagic. This is Lara's running velocity. Jumps have a minimum of 50.
|
||||
SetAnimation(item, LA_JUMP_WALL_SMASH_START, 1);
|
||||
Rumble(0.5f, 0.15f);
|
||||
}
|
||||
|
||||
item->Animation.Velocity /= 4;
|
||||
lara->Control.MoveAngle += ANGLE(180.0f);
|
||||
|
|
|
@ -16,6 +16,8 @@
|
|||
#include "Specific/level.h"
|
||||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// CROUCH & CRAWL
|
||||
// Control & Collision Functions
|
||||
|
@ -57,10 +59,8 @@ void lara_as_crouch_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
if (BinocularOn)
|
||||
return;
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
lara->Control.TurnRate = -LARA_CRAWL_TURN_MAX;
|
||||
else if (TrInput & IN_RIGHT)
|
||||
lara->Control.TurnRate = LARA_CRAWL_TURN_MAX;
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_CRAWL_TURN_RATE_MAX);
|
||||
|
||||
if ((TrInput & IN_CROUCH || lara->Control.KeepLow) &&
|
||||
lara->Control.WaterStatus != WaterStatus::Wade)
|
||||
|
@ -156,21 +156,10 @@ void lara_as_crouch_roll(ItemInfo* item, CollisionInfo* coll)
|
|||
coll->Setup.EnableSpasm = false;
|
||||
Camera.targetDistance = SECTOR(1);
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_CROUCH_ROLL_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_CROUCH_ROLL_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX, LARA_LEAN_RATE);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_CROUCH_ROLL_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_CROUCH_ROLL_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX, LARA_LEAN_RATE);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_CROUCH_ROLL_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE, LARA_LEAN_MAX);
|
||||
}
|
||||
|
||||
item->Animation.TargetState = LS_CROUCH_IDLE;
|
||||
|
@ -247,8 +236,6 @@ void lara_as_crouch_turn_left(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_LOOK)
|
||||
LookUpDown(item);
|
||||
|
||||
lara->Control.TurnRate = -LARA_CRAWL_TURN_MAX;
|
||||
|
||||
if ((TrInput & IN_CROUCH || lara->Control.KeepLow) &&
|
||||
lara->Control.WaterStatus != WaterStatus::Wade)
|
||||
{
|
||||
|
@ -268,6 +255,7 @@ void lara_as_crouch_turn_left(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
item->Animation.TargetState = LS_CROUCH_TURN_LEFT;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_CRAWL_TURN_RATE_MAX);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -303,8 +291,6 @@ void lara_as_crouch_turn_right(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_LOOK)
|
||||
LookUpDown(item);
|
||||
|
||||
lara->Control.TurnRate = LARA_CRAWL_TURN_MAX;
|
||||
|
||||
if ((TrInput & IN_CROUCH || lara->Control.KeepLow) &&
|
||||
lara->Control.WaterStatus != WaterStatus::Wade)
|
||||
{
|
||||
|
@ -324,6 +310,7 @@ void lara_as_crouch_turn_right(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_RIGHT)
|
||||
{
|
||||
item->Animation.TargetState = LS_CROUCH_TURN_RIGHT;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_CRAWL_TURN_RATE_MAX);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -405,10 +392,8 @@ void lara_as_crawl_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
if (BinocularOn)
|
||||
return;
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
lara->Control.TurnRate = -LARA_CRAWL_TURN_MAX;
|
||||
else if (TrInput & IN_RIGHT)
|
||||
lara->Control.TurnRate = LARA_CRAWL_TURN_MAX;
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_CRAWL_TURN_RATE_MAX);
|
||||
|
||||
if ((TrInput & IN_CROUCH || lara->Control.KeepLow) &&
|
||||
lara->Control.WaterStatus != WaterStatus::Wade)
|
||||
|
@ -436,6 +421,7 @@ void lara_as_crawl_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
g_GameFlow->HasCrawlExtended())
|
||||
{
|
||||
item->Animation.TargetState = crawlVaultResult.TargetState;
|
||||
lara->Control.TurnRate = 0;
|
||||
ResetLaraFlex(item);
|
||||
return;
|
||||
}
|
||||
|
@ -540,21 +526,10 @@ void lara_as_crawl_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_CRAWL_MOVE_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_CRAWL_MOVE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_CRAWL_MOVE_TURN_MAX;
|
||||
|
||||
DoLaraCrawlFlex(item, coll, -LARA_CRAWL_FLEX_MAX, LARA_CRAWL_FLEX_RATE);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_CRAWL_MOVE_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_CRAWL_MOVE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_CRAWL_MOVE_TURN_MAX;
|
||||
|
||||
DoLaraCrawlFlex(item, coll, LARA_CRAWL_FLEX_MAX, LARA_CRAWL_FLEX_RATE);
|
||||
ModulateLaraTurnRateY(item, LARA_CRAWL_MOVE_TURN_RATE_ACCEL, 0, LARA_CRAWL_MOVE_TURN_RATE_MAX);
|
||||
ModulateLaraCrawlFlex(item, LARA_CRAWL_FLEX_RATE, LARA_CRAWL_FLEX_MAX);
|
||||
}
|
||||
|
||||
if ((TrInput & IN_CROUCH || lara->Control.KeepLow) &&
|
||||
|
@ -645,21 +620,10 @@ void lara_as_crawl_back(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_CRAWL_MOVE_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_CRAWL_MOVE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_CRAWL_MOVE_TURN_MAX;
|
||||
|
||||
DoLaraCrawlFlex(item, coll, LARA_CRAWL_FLEX_MAX, LARA_CRAWL_FLEX_RATE);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_CRAWL_MOVE_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_CRAWL_MOVE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_CRAWL_MOVE_TURN_MAX;
|
||||
|
||||
DoLaraCrawlFlex(item, coll, -LARA_CRAWL_FLEX_MAX, LARA_CRAWL_FLEX_RATE);
|
||||
ModulateLaraTurnRateY(item, LARA_CRAWL_MOVE_TURN_RATE_ACCEL, 0, LARA_CRAWL_MOVE_TURN_RATE_MAX);
|
||||
ModulateLaraCrawlFlex(item, LARA_CRAWL_FLEX_RATE, LARA_CRAWL_FLEX_MAX);
|
||||
}
|
||||
|
||||
if ((TrInput & IN_CROUCH || lara->Control.KeepLow) &&
|
||||
|
@ -741,8 +705,6 @@ void lara_as_crawl_turn_left(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
lara->Control.TurnRate = -LARA_CRAWL_TURN_MAX;
|
||||
|
||||
if ((TrInput & IN_CROUCH || lara->Control.KeepLow) &&
|
||||
lara->Control.WaterStatus != WaterStatus::Wade)
|
||||
{
|
||||
|
@ -767,6 +729,7 @@ void lara_as_crawl_turn_left(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
item->Animation.TargetState = LS_CRAWL_TURN_LEFT;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_CRAWL_MOVE_TURN_RATE_MAX);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -801,8 +764,6 @@ void lara_as_crawl_turn_right(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
lara->Control.TurnRate = LARA_CRAWL_TURN_MAX;
|
||||
|
||||
if ((TrInput & IN_CROUCH || lara->Control.KeepLow) &&
|
||||
lara->Control.WaterStatus != WaterStatus::Wade)
|
||||
{
|
||||
|
@ -827,6 +788,7 @@ void lara_as_crawl_turn_right(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_RIGHT)
|
||||
{
|
||||
item->Animation.TargetState = LS_CRAWL_TURN_RIGHT;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_CRAWL_MOVE_TURN_RATE_MAX);
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
@ -21,6 +21,7 @@
|
|||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
#include "ScriptInterfaceLevel.h"
|
||||
#include "Sound/sound.h"
|
||||
#include "Specific/configuration.h"
|
||||
#include "Specific/setup.h"
|
||||
#include "Specific/input.h"
|
||||
#include "Specific/level.h"
|
||||
|
@ -29,6 +30,7 @@
|
|||
#include "Objects/ScriptInterfaceObjectsHandler.h"
|
||||
|
||||
using namespace TEN::Entities::Generic;
|
||||
using namespace TEN::Input;
|
||||
|
||||
bool MonksAttackLara;
|
||||
ItemInfo* LastTargets[MAX_TARGETS];
|
||||
|
@ -1036,6 +1038,9 @@ void LaraTargetInfo(ItemInfo* laraItem, WeaponInfo* weaponInfo)
|
|||
|
||||
void LaraGetNewTarget(ItemInfo* laraItem, WeaponInfo* weaponInfo)
|
||||
{
|
||||
if (!g_Configuration.AutoTarget)
|
||||
return;
|
||||
|
||||
auto* lara = GetLaraInfo(laraItem);
|
||||
|
||||
if (BinocularRange)
|
||||
|
|
|
@ -12,6 +12,8 @@
|
|||
#include "Specific/input.h"
|
||||
#include "Specific/level.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// LEDGE HANG
|
||||
// Control & Collision Functions
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
#include "Objects/TR4/Vehicles/motorbike.h"
|
||||
|
||||
using namespace TEN::Renderer;
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// HELPER FUNCTIONS
|
||||
|
@ -47,7 +48,7 @@ void HandleLaraMovementParameters(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
// Reset running jump timer.
|
||||
if (!IsRunJumpCountableState((LaraState)item->Animation.ActiveState))
|
||||
lara->Control.Count.RunJump = 0;
|
||||
lara->Control.Count.Run = 0;
|
||||
|
||||
// Reset running jump action queue.
|
||||
if (!IsRunJumpQueueableState((LaraState)item->Animation.ActiveState))
|
||||
|
@ -64,16 +65,10 @@ void HandleLaraMovementParameters(ItemInfo* item, CollisionInfo* coll)
|
|||
ResetLaraFlex(item, 12.0f);
|
||||
}
|
||||
|
||||
// Reset turn rate.
|
||||
// TODO: Make it less stupid in the future. Do it according to a curve?
|
||||
int sign = copysign(1, lara->Control.TurnRate);
|
||||
if (abs(lara->Control.TurnRate) > ANGLE(2.0f))
|
||||
lara->Control.TurnRate -= ANGLE(2.0f) * sign;
|
||||
else if (abs(lara->Control.TurnRate) > ANGLE(0.5f))
|
||||
lara->Control.TurnRate -= ANGLE(0.5f) * sign;
|
||||
else
|
||||
lara->Control.TurnRate = 0;
|
||||
// Apply and reset turn rate.
|
||||
item->Pose.Orientation.y += lara->Control.TurnRate;
|
||||
if (!(TrInput & (IN_LEFT | IN_RIGHT)))
|
||||
lara->Control.TurnRate = 0;
|
||||
}
|
||||
|
||||
bool HandleLaraVehicle(ItemInfo* item, CollisionInfo* coll)
|
||||
|
@ -166,7 +161,7 @@ void EaseOutLaraHeight(ItemInfo* item, int height)
|
|||
static constexpr int rate = 50;
|
||||
int threshold = std::max(abs(item->Animation.Velocity) * 1.5f, CLICK(0.25f) / 4);
|
||||
int sign = std::copysign(1, height);
|
||||
|
||||
|
||||
if (TestEnvironment(ENV_FLAG_SWAMP, item) && height > 0)
|
||||
item->Pose.Position.y += SWAMP_GRAVITY;
|
||||
else if (abs(height) > (STEPUP_HEIGHT / 2)) // Outer range.
|
||||
|
@ -180,21 +175,6 @@ void EaseOutLaraHeight(ItemInfo* item, int height)
|
|||
item->Pose.Position.y += height;
|
||||
}
|
||||
|
||||
// TODO: Make lean rate proportional to the turn rate, allowing for nicer aesthetics with future analog stick input.
|
||||
void DoLaraLean(ItemInfo* item, CollisionInfo* coll, short maxAngle, short rate)
|
||||
{
|
||||
if (!item->Animation.Velocity)
|
||||
return;
|
||||
|
||||
rate = abs(rate);
|
||||
int sign = copysign(1, maxAngle);
|
||||
|
||||
if (coll->CollisionType == CT_LEFT || coll->CollisionType == CT_RIGHT)
|
||||
item->Pose.Orientation.z += std::min<short>(rate, abs((maxAngle * 3) / 5 - item->Pose.Orientation.z) / 3) * sign;
|
||||
else
|
||||
item->Pose.Orientation.z += std::min<short>(rate, abs(maxAngle - item->Pose.Orientation.z) / 3) * sign;
|
||||
}
|
||||
|
||||
// TODO: Some states can't make the most of this function due to missing step up/down animations.
|
||||
// Try implementing leg IK as a substitute to make step animations obsolete. @Sezz 2021.10.09
|
||||
void DoLaraStep(ItemInfo* item, CollisionInfo* coll)
|
||||
|
@ -245,26 +225,6 @@ void DoLaraCrawlToHangSnap(ItemInfo* item, CollisionInfo* coll)
|
|||
}
|
||||
}
|
||||
|
||||
void DoLaraCrawlFlex(ItemInfo* item, CollisionInfo* coll, short maxAngle, short rate)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (!item->Animation.Velocity)
|
||||
return;
|
||||
|
||||
int sign = copysign(1, maxAngle);
|
||||
rate = copysign(rate, maxAngle);
|
||||
|
||||
lara->ExtraTorsoRot.z += std::min(abs(rate), abs(maxAngle - lara->ExtraTorsoRot.z) / 6) * sign;
|
||||
|
||||
if (!(TrInput & IN_LOOK) &&
|
||||
item->Animation.ActiveState != LS_CRAWL_BACK)
|
||||
{
|
||||
lara->ExtraHeadRot.z = lara->ExtraTorsoRot.z / 2;
|
||||
lara->ExtraHeadRot.y = lara->ExtraHeadRot.z;
|
||||
}
|
||||
}
|
||||
|
||||
void DoLaraTightropeBalance(ItemInfo* item)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
@ -326,7 +286,7 @@ void DoLaraTightropeBalanceRegen(ItemInfo* item)
|
|||
}
|
||||
}
|
||||
|
||||
void DealLaraFallDamage(ItemInfo* item)
|
||||
void DoLaraFallDamage(ItemInfo* item)
|
||||
{
|
||||
if (item->Animation.VerticalVelocity >= LARA_DAMAGE_VELOCITY)
|
||||
{
|
||||
|
@ -334,9 +294,12 @@ void DealLaraFallDamage(ItemInfo* item)
|
|||
item->HitPoints = 0;
|
||||
else USE_FEATURE_IF_CPP20([[likely]])
|
||||
{
|
||||
int base = item->Animation.VerticalVelocity - (LARA_DAMAGE_VELOCITY - 1);
|
||||
float base = item->Animation.VerticalVelocity - (LARA_DAMAGE_VELOCITY - 1);
|
||||
item->HitPoints -= LARA_HEALTH_MAX * (pow(base, 2) / 196);
|
||||
}
|
||||
|
||||
float rumblePower = ((float)item->Animation.VerticalVelocity / (float)LARA_DEATH_VELOCITY) * 0.7f;
|
||||
Rumble(rumblePower, 0.3f);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -344,58 +307,113 @@ LaraInfo*& GetLaraInfo(ItemInfo* item)
|
|||
{
|
||||
if (item->ObjectNumber == ID_LARA)
|
||||
return (LaraInfo*&)item->Data;
|
||||
else
|
||||
{
|
||||
TENLog(std::string("Attempted to fetch LaraInfo data from entity with object ID ") + std::to_string(item->ObjectNumber), LogLevel::Warning);
|
||||
|
||||
TENLog(std::string("Attempted to fetch LaraInfo data from entity with object ID ") + std::to_string(item->ObjectNumber), LogLevel::Warning);
|
||||
|
||||
auto* firstLaraItem = FindItem(ID_LARA);
|
||||
return (LaraInfo*&)firstLaraItem->Data;
|
||||
auto* firstLaraItem = FindItem(ID_LARA);
|
||||
return (LaraInfo*&)firstLaraItem->Data;
|
||||
}
|
||||
}
|
||||
|
||||
short GetLaraSlideDirection(ItemInfo* item, CollisionInfo* coll)
|
||||
{
|
||||
short direction = coll->Setup.ForwardAngle;
|
||||
short headingAngle = coll->Setup.ForwardAngle;
|
||||
auto probe = GetCollision(item);
|
||||
|
||||
// Ground is flat.
|
||||
if (!probe.FloorTilt.x && !probe.FloorTilt.y)
|
||||
return direction;
|
||||
if (probe.FloorTilt == Vector2::Zero)
|
||||
return headingAngle;
|
||||
|
||||
direction = GetSurfaceAspectAngle(probe.FloorTilt.x, probe.FloorTilt.y);
|
||||
|
||||
// Determine nearest cardinal direction of surface aspect.
|
||||
if (!g_GameFlow->HasSlideExtended())
|
||||
direction = GetQuadrant(direction) * ANGLE(90.0f);
|
||||
|
||||
return direction;
|
||||
// Get either:
|
||||
// a) the surface aspect angle (extended slides), or
|
||||
// b) the derived nearest cardinal direction from it (original slides).
|
||||
headingAngle = GetSurfaceAspectAngle(probe.FloorTilt.x, probe.FloorTilt.y);
|
||||
if (g_GameFlow->HasSlideExtended())
|
||||
return headingAngle;
|
||||
else
|
||||
return (GetQuadrant(headingAngle) * ANGLE(90.0f));
|
||||
}
|
||||
|
||||
void ModulateLaraSlideVelocity(ItemInfo* item, CollisionInfo* coll)
|
||||
short ModulateLaraTurnRate(short turnRate, short accelRate, short minTurnRate, short maxTurnRate, float axisCoeff)
|
||||
{
|
||||
int sign = std::copysign(1, axisCoeff);
|
||||
short minTurnRateNormalized = minTurnRate * abs(axisCoeff);
|
||||
short maxTurnRateNormalized = maxTurnRate * abs(axisCoeff);
|
||||
|
||||
short newTurnRate = (turnRate + (accelRate * sign)) * sign;
|
||||
newTurnRate = std::clamp(newTurnRate, minTurnRateNormalized, maxTurnRateNormalized);
|
||||
return newTurnRate * sign;
|
||||
}
|
||||
|
||||
void ModulateLaraTurnRateX(ItemInfo* item, short accelRate, short minTurnRate, short maxTurnRate)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
constexpr int minVelocity = 50;
|
||||
constexpr int maxVelocity = LARA_TERMINAL_VELOCITY;
|
||||
|
||||
if (g_GameFlow->HasSlideExtended())
|
||||
{
|
||||
auto probe = GetCollision(item);
|
||||
short minSlideAngle = ANGLE(33.75f);
|
||||
short steepness = GetSurfaceSteepnessAngle(probe.FloorTilt.x, probe.FloorTilt.y);
|
||||
short direction = GetSurfaceAspectAngle(probe.FloorTilt.x, probe.FloorTilt.y);
|
||||
|
||||
float velocityMultiplier = 1 / (float)ANGLE(33.75f);
|
||||
int slideVelocity = std::min<int>(minVelocity + 10 * (steepness * velocityMultiplier), LARA_TERMINAL_VELOCITY);
|
||||
//short deltaAngle = abs((short)(direction - item->Pose.Orientation.y));
|
||||
|
||||
g_Renderer.PrintDebugMessage("%d", slideVelocity);
|
||||
|
||||
lara->ExtraVelocity.x += slideVelocity;
|
||||
lara->ExtraVelocity.y += slideVelocity * phd_sin(steepness);
|
||||
}
|
||||
else
|
||||
lara->ExtraVelocity.x += minVelocity;
|
||||
//lara->Control.TurnRate.x = ModulateLaraTurnRate(lara->Control.TurnRate.x, accelRate, minTurnRate, maxTurnRate, AxisMap[InputAxis::MoveVertical]);
|
||||
}
|
||||
|
||||
void ModulateLaraTurnRateY(ItemInfo* item, short accelRate, short minTurnRate, short maxTurnRate)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
float axisCoeff = AxisMap[InputAxis::MoveHorizontal];
|
||||
if (item->Animation.Airborne)
|
||||
{
|
||||
int sign = std::copysign(1, axisCoeff);
|
||||
axisCoeff = std::min(1.2f, abs(axisCoeff)) * sign;
|
||||
}
|
||||
|
||||
lara->Control.TurnRate/*.y*/ = ModulateLaraTurnRate(lara->Control.TurnRate/*.y*/, accelRate, minTurnRate, maxTurnRate, axisCoeff);
|
||||
}
|
||||
|
||||
void ModulateLaraSwimTurnRates(ItemInfo* item, CollisionInfo* coll)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
/*if (TrInput & (IN_FORWARD | IN_BACK))
|
||||
ModulateLaraTurnRateX(item, 0, 0, 0);*/
|
||||
|
||||
if (TrInput & IN_FORWARD)
|
||||
item->Pose.Orientation.x -= ANGLE(3.0f);
|
||||
else if (TrInput & IN_BACK)
|
||||
item->Pose.Orientation.x += ANGLE(3.0f);
|
||||
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_MED_TURN_RATE_MAX);
|
||||
|
||||
// TODO: ModulateLaraLean() doesn't really work here. @Sezz 2022.06.22
|
||||
if (TrInput & IN_LEFT)
|
||||
item->Pose.Orientation.z -= LARA_LEAN_RATE;
|
||||
else if (TrInput & IN_RIGHT)
|
||||
item->Pose.Orientation.z += LARA_LEAN_RATE;
|
||||
}
|
||||
}
|
||||
|
||||
void ModulateLaraSubsuitSwimTurnRates(ItemInfo* item)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (TrInput & IN_FORWARD && item->Pose.Orientation.x > -ANGLE(85.0f))
|
||||
lara->Control.Subsuit.DXRot = -ANGLE(45.0f);
|
||||
else if (TrInput & IN_BACK && item->Pose.Orientation.x < ANGLE(85.0f))
|
||||
lara->Control.Subsuit.DXRot = ANGLE(45.0f);
|
||||
else
|
||||
lara->Control.Subsuit.DXRot = 0;
|
||||
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
ModulateLaraTurnRateY(item, LARA_SUBSUIT_TURN_RATE_ACCEL, 0, LARA_MED_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
item->Pose.Orientation.z -= LARA_LEAN_RATE;
|
||||
else if (TrInput & IN_RIGHT)
|
||||
item->Pose.Orientation.z += LARA_LEAN_RATE;
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: Simplify this function. Some members of SubsuitControlData may be unnecessary. @Sezz 2022.06.22
|
||||
void UpdateLaraSubsuitAngles(ItemInfo* item)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
@ -465,60 +483,69 @@ void UpdateLaraSubsuitAngles(ItemInfo* item)
|
|||
}
|
||||
}
|
||||
|
||||
void ModulateLaraSubsuitSwimTurn(ItemInfo* item)
|
||||
void ModulateLaraLean(ItemInfo* item, CollisionInfo* coll, short baseRate, short maxAngle)
|
||||
{
|
||||
if (!item->Animation.Velocity)
|
||||
return;
|
||||
|
||||
float axisCoeff = AxisMap[InputAxis::MoveHorizontal];
|
||||
int sign = copysign(1, axisCoeff);
|
||||
short maxAngleNormalized = maxAngle * axisCoeff;
|
||||
|
||||
if (coll->CollisionType == CT_LEFT || coll->CollisionType == CT_RIGHT)
|
||||
maxAngleNormalized *= 0.6f;
|
||||
|
||||
item->Pose.Orientation.z += std::min<short>(baseRate, abs(maxAngleNormalized - item->Pose.Orientation.z) / 3) * sign;
|
||||
}
|
||||
|
||||
void ModulateLaraCrawlFlex(ItemInfo* item, short baseRate, short maxAngle)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (TrInput & IN_FORWARD && item->Pose.Orientation.x > -ANGLE(85.0f))
|
||||
lara->Control.Subsuit.DXRot = -ANGLE(45.0f);
|
||||
else if (TrInput & IN_BACK && item->Pose.Orientation.x < ANGLE(85.0f))
|
||||
lara->Control.Subsuit.DXRot = ANGLE(45.0f);
|
||||
else
|
||||
lara->Control.Subsuit.DXRot = 0;
|
||||
if (!item->Animation.Velocity)
|
||||
return;
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
float axisCoeff = AxisMap[InputAxis::MoveHorizontal];
|
||||
int sign = copysign(1, axisCoeff);
|
||||
short maxAngleNormalized = maxAngle * axisCoeff;
|
||||
|
||||
if (abs(lara->ExtraTorsoRot.z) < LARA_CRAWL_FLEX_MAX)
|
||||
lara->ExtraTorsoRot.z += std::min<short>(baseRate, abs(maxAngleNormalized - lara->ExtraTorsoRot.z) / 6) * sign;
|
||||
|
||||
if (!(TrInput & IN_LOOK) &&
|
||||
item->Animation.ActiveState != LS_CRAWL_BACK)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_SUBSUIT_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_MED_TURN_MAX;
|
||||
|
||||
item->Pose.Orientation.z -= LARA_LEAN_RATE;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_SUBSUIT_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_MED_TURN_MAX;
|
||||
|
||||
item->Pose.Orientation.z += LARA_LEAN_RATE;
|
||||
lara->ExtraHeadRot.z = lara->ExtraTorsoRot.z / 2;
|
||||
lara->ExtraHeadRot.y = lara->ExtraHeadRot.z;
|
||||
}
|
||||
}
|
||||
|
||||
void ModulateLaraSwimTurn(ItemInfo* item, CollisionInfo* coll)
|
||||
// TODO: Unused; I will pick this back up later. @Sezz 2022.06.22
|
||||
void ModulateLaraSlideVelocity(ItemInfo* item, CollisionInfo* coll)
|
||||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
if (TrInput & IN_FORWARD)
|
||||
item->Pose.Orientation.x -= ANGLE(2.0f);
|
||||
else if (TrInput & IN_BACK)
|
||||
item->Pose.Orientation.x += ANGLE(2.0f);
|
||||
constexpr int minVelocity = 50;
|
||||
constexpr int maxVelocity = LARA_TERMINAL_VELOCITY;
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (g_GameFlow->HasSlideExtended())
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_MED_TURN_MAX;
|
||||
auto probe = GetCollision(item);
|
||||
short minSlideAngle = ANGLE(33.75f);
|
||||
short steepness = GetSurfaceSteepnessAngle(probe.FloorTilt.x, probe.FloorTilt.y);
|
||||
short direction = GetSurfaceAspectAngle(probe.FloorTilt.x, probe.FloorTilt.y);
|
||||
|
||||
item->Pose.Orientation.z -= LARA_LEAN_RATE;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_MED_TURN_MAX;
|
||||
float velocityMultiplier = 1 / (float)ANGLE(33.75f);
|
||||
int slideVelocity = std::min<int>(minVelocity + 10 * (steepness * velocityMultiplier), LARA_TERMINAL_VELOCITY);
|
||||
//short deltaAngle = abs((short)(direction - item->Pose.Orientation.y));
|
||||
|
||||
item->Pose.Orientation.z += LARA_LEAN_RATE;
|
||||
g_Renderer.PrintDebugMessage("%d", slideVelocity);
|
||||
|
||||
lara->ExtraVelocity.x += slideVelocity;
|
||||
lara->ExtraVelocity.y += slideVelocity * phd_sin(steepness);
|
||||
}
|
||||
else
|
||||
lara->ExtraVelocity.x += minVelocity;
|
||||
}
|
||||
|
||||
void SetLaraJumpDirection(ItemInfo* item, CollisionInfo* coll)
|
||||
|
@ -562,8 +589,8 @@ void SetLaraRunJumpQueue(ItemInfo* item, CollisionInfo* coll)
|
|||
auto probe = GetCollision(item, item->Pose.Orientation.y, distance, -coll->Setup.Height);
|
||||
|
||||
if ((TestLaraRunJumpForward(item, coll) || // Area close ahead is permissive...
|
||||
(probe.Position.Ceiling - y) < -(coll->Setup.Height + (LARA_HEADROOM * 0.8f)) || // OR ceiling height far ahead is permissive
|
||||
(probe.Position.Floor - y) >= CLICK(0.5f)) && // OR there is a drop below far ahead.
|
||||
(probe.Position.Ceiling - y) < -(coll->Setup.Height + (LARA_HEADROOM * 0.8f)) || // OR ceiling height far ahead is permissive
|
||||
(probe.Position.Floor - y) >= CLICK(0.5f)) && // OR there is a drop below far ahead.
|
||||
probe.Position.Floor != NO_HEIGHT)
|
||||
{
|
||||
lara->Control.RunJumpQueued = IsRunJumpQueueableState((LaraState)item->Animation.TargetState);
|
||||
|
@ -695,11 +722,11 @@ void SetLaraSlideAnimation(ItemInfo* item, CollisionInfo* coll)
|
|||
// TODO: Do it later.
|
||||
void newSetLaraSlideAnimation(ItemInfo* item, CollisionInfo* coll)
|
||||
{
|
||||
short direction = GetLaraSlideDirection(item, coll);
|
||||
short deltaAngle = direction - item->Pose.Orientation.y;
|
||||
short headinAngle = GetLaraSlideDirection(item, coll);
|
||||
short deltaAngle = headinAngle - item->Pose.Orientation.y;
|
||||
|
||||
if (!g_GameFlow->HasSlideExtended())
|
||||
item->Pose.Orientation.y = direction;
|
||||
item->Pose.Orientation.y = headinAngle;
|
||||
|
||||
// Snap to height upon slide entrance.
|
||||
if (item->Animation.ActiveState != LS_SLIDE_FORWARD &&
|
||||
|
@ -837,3 +864,15 @@ void ResetLaraFlex(ItemInfo* item, float rate)
|
|||
else
|
||||
lara->ExtraTorsoRot.z = 0;
|
||||
}
|
||||
|
||||
void RumbleLaraHealthCondition(ItemInfo* lara)
|
||||
{
|
||||
auto* info = GetLaraInfo(lara);
|
||||
|
||||
if (lara->HitPoints > LARA_HEALTH_CRITICAL && !info->PoisonPotency)
|
||||
return;
|
||||
|
||||
bool pulse = (GlobalCounter & 0x0F) / 0x0F == 1;
|
||||
if (pulse)
|
||||
Rumble(0.2f, 0.1f);
|
||||
}
|
||||
|
|
|
@ -15,23 +15,26 @@ void HandleLaraMovementParameters(ItemInfo* item, CollisionInfo* coll);
|
|||
bool HandleLaraVehicle(ItemInfo* item, CollisionInfo* coll);
|
||||
void ApproachLaraTargetOrientation(ItemInfo* item, Vector3Shrt targetOrient, float rate = 1.0f);
|
||||
void EaseOutLaraHeight(ItemInfo* item, int height);
|
||||
void DoLaraLean(ItemInfo* item, CollisionInfo* coll, short maxAngle, short rate);
|
||||
void DoLaraStep(ItemInfo* item, CollisionInfo* coll);
|
||||
void DoLaraMonkeyStep(ItemInfo* item, CollisionInfo* coll);
|
||||
void DoLaraCrawlToHangSnap(ItemInfo* item, CollisionInfo* coll);
|
||||
void DoLaraCrawlFlex(ItemInfo* item, CollisionInfo* coll, short maxAngle, short rate);
|
||||
void DoLaraTightropeBalance(ItemInfo* item);
|
||||
void DoLaraTightropeLean(ItemInfo* item);
|
||||
void DoLaraTightropeBalanceRegen(ItemInfo* item);
|
||||
void DealLaraFallDamage(ItemInfo* item);
|
||||
void DoLaraFallDamage(ItemInfo* item);
|
||||
|
||||
LaraInfo*& GetLaraInfo(ItemInfo* item);
|
||||
short GetLaraSlideDirection(ItemInfo* item, CollisionInfo* coll);
|
||||
|
||||
void ModulateLaraSlideVelocity(ItemInfo* item, CollisionInfo* coll);
|
||||
short ModulateLaraTurnRate(short turnRate, short accelRate, short minTurnRate, short maxTurnRate, float axisCoeff);
|
||||
void ModulateLaraTurnRateX(ItemInfo* item, short accelRate, short minTurnRate, short maxTurnRate);
|
||||
void ModulateLaraTurnRateY(ItemInfo* item, short accelRate, short minTurnRate, short maxTurnRate);
|
||||
void ModulateLaraSwimTurnRates(ItemInfo* item, CollisionInfo* coll);
|
||||
void ModulateLaraSubsuitSwimTurnRates(ItemInfo* item);
|
||||
void UpdateLaraSubsuitAngles(ItemInfo* item);
|
||||
void ModulateLaraSubsuitSwimTurn(ItemInfo* item);
|
||||
void ModulateLaraSwimTurn(ItemInfo* item, CollisionInfo* coll);
|
||||
void ModulateLaraLean(ItemInfo* item, CollisionInfo* coll, short baseRate, short maxAngle);
|
||||
void ModulateLaraCrawlFlex(ItemInfo* item, short baseRate, short maxAngle);
|
||||
void ModulateLaraSlideVelocity(ItemInfo* item, CollisionInfo* coll);
|
||||
|
||||
void SetLaraJumpDirection(ItemInfo* item, CollisionInfo* coll);
|
||||
void SetLaraRunJumpQueue(ItemInfo* item, CollisionInfo* coll);
|
||||
|
@ -47,3 +50,5 @@ void SetLaraSwimDiveAnimation(ItemInfo* item);
|
|||
|
||||
void ResetLaraLean(ItemInfo* item, float rate = 1.0f, bool resetRoll = true, bool resetPitch = true);
|
||||
void ResetLaraFlex(ItemInfo* item, float rate = 1.0f);
|
||||
|
||||
void RumbleLaraHealthCondition(ItemInfo* lara);
|
||||
|
|
|
@ -16,6 +16,8 @@
|
|||
#include "Specific/level.h"
|
||||
#include "Specific/setup.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// JUMP
|
||||
// Control & Collision Functions
|
||||
|
@ -36,9 +38,9 @@ void lara_as_jump_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
// Update running jump counter in preparation for possible jump action soon after landing.
|
||||
lara->Control.Count.RunJump++;
|
||||
if (lara->Control.Count.RunJump > LARA_RUN_JUMP_TIME / 2)
|
||||
lara->Control.Count.RunJump = LARA_RUN_JUMP_TIME / 2;
|
||||
lara->Control.Count.Run++;
|
||||
if (lara->Control.Count.Run > LARA_RUN_JUMP_TIME / 2)
|
||||
lara->Control.Count.Run = LARA_RUN_JUMP_TIME / 2;
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
{
|
||||
|
@ -51,22 +53,12 @@ void lara_as_jump_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_JUMP_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_JUMP_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_JUMP_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_JUMP_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_JUMP_TURN_RATE_MAX);
|
||||
|
||||
if (TestLaraLand(item, coll))
|
||||
{
|
||||
DealLaraFallDamage(item);
|
||||
DoLaraFallDamage(item);
|
||||
|
||||
if (item->HitPoints <= 0) USE_FEATURE_IF_CPP20([[unlikely]])
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
|
@ -146,7 +138,7 @@ void lara_as_freefall(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TestLaraLand(item, coll))
|
||||
{
|
||||
DealLaraFallDamage(item);
|
||||
DoLaraFallDamage(item);
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
|
@ -198,22 +190,12 @@ void lara_as_reach(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_JUMP_TURN_MAX / 2)
|
||||
lara->Control.TurnRate = -LARA_JUMP_TURN_MAX / 2;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_JUMP_TURN_MAX / 2)
|
||||
lara->Control.TurnRate = LARA_JUMP_TURN_MAX / 2;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_JUMP_TURN_RATE_MAX / 2);
|
||||
|
||||
if (TestLaraLand(item, coll))
|
||||
{
|
||||
DealLaraFallDamage(item);
|
||||
DoLaraFallDamage(item);
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
|
@ -286,18 +268,8 @@ void lara_as_jump_prepare(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & (IN_FORWARD | IN_BACK) &&
|
||||
lara->Control.WaterStatus != WaterStatus::Wade)
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
}
|
||||
|
||||
// JUMP key repressed without directional key; cancel directional jump lock.
|
||||
|
@ -434,22 +406,12 @@ void lara_as_jump_back(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_JUMP_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_JUMP_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_JUMP_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_JUMP_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_JUMP_TURN_RATE_MAX);
|
||||
|
||||
if (TestLaraLand(item, coll))
|
||||
{
|
||||
DealLaraFallDamage(item);
|
||||
DoLaraFallDamage(item);
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
|
@ -505,7 +467,7 @@ void lara_as_jump_right(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TestLaraLand(item, coll))
|
||||
{
|
||||
DealLaraFallDamage(item);
|
||||
DoLaraFallDamage(item);
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
|
@ -562,7 +524,7 @@ void lara_as_jump_left(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TestLaraLand(item, coll))
|
||||
{
|
||||
DealLaraFallDamage(item);
|
||||
DoLaraFallDamage(item);
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
|
@ -707,22 +669,12 @@ void lara_as_fall_back(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_JUMP_TURN_MAX / 2)
|
||||
lara->Control.TurnRate = -LARA_JUMP_TURN_MAX / 2;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_JUMP_TURN_MAX / 2)
|
||||
lara->Control.TurnRate = LARA_JUMP_TURN_MAX / 2;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_JUMP_TURN_RATE_MAX / 2);
|
||||
|
||||
if (TestLaraLand(item, coll))
|
||||
{
|
||||
DealLaraFallDamage(item);
|
||||
DoLaraFallDamage(item);
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
|
@ -786,26 +738,15 @@ void lara_as_swan_dive(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_JUMP_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_JUMP_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX, LARA_LEAN_RATE / 2);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_JUMP_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_JUMP_TURN_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX, LARA_LEAN_RATE / 2);
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_JUMP_TURN_RATE_MAX);
|
||||
ModulateLaraLean(item, coll, LARA_LEAN_RATE / 2, LARA_LEAN_MAX);
|
||||
}
|
||||
|
||||
if (TestLaraLand(item, coll))
|
||||
{
|
||||
DealLaraFallDamage(item);
|
||||
DoLaraFallDamage(item);
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
|
@ -886,6 +827,7 @@ void lara_as_freefall_dive(ItemInfo* item, CollisionInfo* coll)
|
|||
item->HitPoints <= 0)
|
||||
{
|
||||
item->Animation.TargetState = LS_DEATH;
|
||||
Rumble(0.5f, 0.2f);
|
||||
}
|
||||
else if (TestLaraSlide(item, coll))
|
||||
SetLaraSlideAnimation(item, coll);
|
||||
|
|
|
@ -16,6 +16,8 @@
|
|||
#include "Specific/level.h"
|
||||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// MONKEY SWING
|
||||
// Control & Collision Functions
|
||||
|
@ -45,19 +47,12 @@ void lara_as_monkey_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
// Overhang hook.
|
||||
SlopeMonkeyExtra(item, coll);
|
||||
|
||||
if (TrInput & IN_LEFT &&
|
||||
!(TrInput & IN_LSTEP || (TrInput & IN_WALK && TrInput & IN_LEFT))) // Shimmy locks orientation.
|
||||
if ((TrInput & IN_LEFT &&
|
||||
!(TrInput & IN_LSTEP || (TrInput & IN_WALK && TrInput & IN_LEFT))) || // Shimmy locks orientation.
|
||||
(TrInput & IN_RIGHT &&
|
||||
!(TrInput & IN_RSTEP || (TrInput & IN_WALK && TrInput & IN_RIGHT))))
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX / 2)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX / 2;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT &&
|
||||
!(TrInput & IN_RSTEP || (TrInput & IN_WALK && TrInput & IN_RIGHT)))
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX / 2)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX / 2;
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX / 2);
|
||||
}
|
||||
|
||||
if (TrInput & IN_ACTION && lara->Control.CanMonkeySwing)
|
||||
|
@ -179,18 +174,8 @@ void lara_as_monkey_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_ACTION && lara->Control.CanMonkeySwing)
|
||||
{
|
||||
|
@ -266,18 +251,8 @@ void lara_as_monkey_back(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_ACTION && lara->Control.CanMonkeySwing)
|
||||
{
|
||||
|
@ -349,18 +324,8 @@ void lara_as_monkey_shimmy_left(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (!(TrInput & IN_WALK)) // WALK locks orientation.
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
}
|
||||
|
||||
if (TrInput & IN_ACTION && lara->Control.CanMonkeySwing)
|
||||
|
@ -433,18 +398,8 @@ void lara_as_monkey_shimmy_right(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (!(TrInput & IN_WALK)) // WALK locks orientation.
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
}
|
||||
|
||||
if (TrInput & IN_ACTION && lara->Control.CanMonkeySwing)
|
||||
|
@ -575,11 +530,7 @@ void lara_as_monkey_turn_left(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
item->Animation.TargetState = LS_MONKEY_TURN_LEFT;
|
||||
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_TURN_MAX;
|
||||
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -658,11 +609,7 @@ void lara_as_monkey_turn_right(ItemInfo* item, CollisionInfo* coll)
|
|||
if (TrInput & IN_RIGHT)
|
||||
{
|
||||
item->Animation.TargetState = LS_MONKEY_TURN_RIGHT;
|
||||
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_TURN_MAX;
|
||||
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL, 0, LARA_SLOW_TURN_RATE_MAX);
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
@ -14,6 +14,7 @@
|
|||
#include "Specific/input.h"
|
||||
#include "Specific/level.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Entities::Generic;
|
||||
|
||||
// -----------------------------------
|
||||
|
@ -737,20 +738,10 @@ void lara_as_pole_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TrInput & IN_ACTION)
|
||||
{
|
||||
if (item->Animation.ActiveState == LA_POLE_IDLE) // Hack.
|
||||
if (item->Animation.ActiveState == LA_POLE_IDLE) // HACK.
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_POLE_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_POLE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_POLE_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_POLE_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_POLE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_POLE_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_POLE_TURN_RATE_ACCEL, 0, LARA_POLE_TURN_RATE_MAX);
|
||||
}
|
||||
|
||||
// TODO: Add forward jump.
|
||||
|
@ -840,18 +831,8 @@ void lara_as_pole_up(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TrInput & IN_ACTION)
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_POLE_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_POLE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_POLE_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_POLE_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_POLE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_POLE_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_POLE_TURN_RATE_ACCEL, 0, LARA_POLE_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_JUMP)
|
||||
{
|
||||
|
@ -899,18 +880,8 @@ void lara_as_pole_down(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TrInput & IN_ACTION)
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_POLE_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_POLE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_POLE_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_POLE_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_POLE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_POLE_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_POLE_TURN_RATE_ACCEL, 0, LARA_POLE_TURN_RATE_MAX);
|
||||
|
||||
if (TrInput & IN_JUMP)
|
||||
{
|
||||
|
@ -999,11 +970,8 @@ void lara_as_pole_turn_clockwise(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_POLE_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_POLE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_POLE_TURN_MAX;
|
||||
|
||||
item->Animation.TargetState = LS_POLE_TURN_CLOCKWISE;
|
||||
ModulateLaraTurnRateY(item, LARA_POLE_TURN_RATE_ACCEL, 0, LARA_POLE_TURN_RATE_MAX);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1054,11 +1022,8 @@ void lara_as_pole_turn_counter_clockwise(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_POLE_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_POLE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_POLE_TURN_MAX;
|
||||
|
||||
item->Animation.TargetState = LS_POLE_TURN_COUNTER_CLOCKWISE;
|
||||
ModulateLaraTurnRateY(item, LARA_POLE_TURN_RATE_ACCEL, 0, LARA_POLE_TURN_RATE_MAX);
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
@ -26,6 +26,7 @@
|
|||
#include "Specific/input.h"
|
||||
#include "Sound/sound.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Effects::Lara;
|
||||
using namespace TEN::Entities::Switches;
|
||||
using namespace TEN::Effects::Environment;
|
||||
|
@ -341,6 +342,8 @@ void FireShotgun(ItemInfo* laraItem)
|
|||
SoundEffect(SFX_TR4_EXPLOSION1, &laraItem->Pose, TestEnvironment(ENV_FLAG_WATER, laraItem) ? SoundEnvironment::Water : SoundEnvironment::Land);
|
||||
SoundEffect(Weapons[(int)LaraWeaponType::Shotgun].SampleNum, &laraItem->Pose);
|
||||
|
||||
Rumble(0.5f, 0.2f);
|
||||
|
||||
Statistics.Game.AmmoUsed++;
|
||||
}
|
||||
}
|
||||
|
@ -451,7 +454,7 @@ void FireHarpoon(ItemInfo* laraItem)
|
|||
{
|
||||
auto* lara = GetLaraInfo(laraItem);
|
||||
|
||||
Ammo& ammos = GetAmmo(laraItem, LaraWeaponType::HarpoonGun);
|
||||
auto& ammos = GetAmmo(laraItem, LaraWeaponType::HarpoonGun);
|
||||
if (!ammos)
|
||||
return;
|
||||
|
||||
|
@ -499,6 +502,7 @@ void FireHarpoon(ItemInfo* laraItem)
|
|||
item->Animation.VerticalVelocity = -HARPOON_VELOCITY * phd_sin(item->Pose.Orientation.x);
|
||||
item->HitPoints = HARPOON_TIME;
|
||||
|
||||
Rumble(0.2f, 0.1f);
|
||||
AddActiveItem(itemNumber);
|
||||
|
||||
Statistics.Level.AmmoUsed++;
|
||||
|
@ -721,6 +725,8 @@ void FireGrenade(ItemInfo* laraItem)
|
|||
item->HitPoints = GRENADE_TIME;
|
||||
item->ItemFlags[0] = (int)WeaponAmmoType::Ammo2;
|
||||
|
||||
Rumble(0.4f, 0.25f);
|
||||
|
||||
AddActiveItem(itemNumber);
|
||||
|
||||
if (!ammo.hasInfinite())
|
||||
|
@ -1169,6 +1175,7 @@ void FireRocket(ItemInfo* laraItem)
|
|||
|
||||
AddActiveItem(itemNumber);
|
||||
|
||||
Rumble(0.4f, 0.3f);
|
||||
SoundEffect(SFX_TR4_EXPLOSION1, &laraItem->Pose);
|
||||
|
||||
Statistics.Level.AmmoUsed++;
|
||||
|
@ -1456,6 +1463,7 @@ void FireCrossbow(ItemInfo* laraItem, PHD_3DPOS* pos)
|
|||
|
||||
item->ItemFlags[0] = (int)lara->Weapons[(int)LaraWeaponType::Crossbow].SelectedAmmo;
|
||||
|
||||
Rumble(0.2f, 0.1f);
|
||||
SoundEffect(SFX_TR4_CROSSBOW_FIRE, &laraItem->Pose);
|
||||
|
||||
Statistics.Level.AmmoUsed++;
|
||||
|
@ -1723,6 +1731,8 @@ void FireHK(ItemInfo* laraItem, int mode)
|
|||
SmokeWeapon = LaraWeaponType::HK;
|
||||
TriggerGunShell(1, ID_GUNSHELL, LaraWeaponType::HK);
|
||||
lara->RightArm.FlashGun = Weapons[(int)LaraWeaponType::HK].FlashTime;
|
||||
|
||||
Rumble(0.2f, 0.1f);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1811,6 +1821,7 @@ void DoExplosiveDamageOnBaddy(ItemInfo* laraItem, ItemInfo* dest, ItemInfo* src,
|
|||
}
|
||||
else
|
||||
{
|
||||
Rumble(0.5f, 0.3f);
|
||||
laraItem->HitPoints -= (Weapons[(int)weaponType].Damage * 5);
|
||||
if (!TestEnvironment(ENV_FLAG_WATER, dest->RoomNumber) && laraItem->HitPoints <= Weapons[(int)weaponType].Damage)
|
||||
LaraBurn(laraItem);
|
||||
|
|
|
@ -15,6 +15,8 @@
|
|||
#include "Flow/ScriptInterfaceFlowHandler.h"
|
||||
#include "Specific/level.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
constexpr auto HORIZONTAL_ALIGN_NORTHEAST = 155;
|
||||
constexpr auto HORIZONTAL_ALIGN_SOUTHWEST = 101;
|
||||
constexpr auto FORWARD_ALIGNMENT = 868;
|
||||
|
|
|
@ -12,6 +12,8 @@
|
|||
#include "Specific/input.h"
|
||||
#include "Specific/level.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// SLIDE
|
||||
// Control & Collision Functions
|
||||
|
@ -46,17 +48,17 @@ void lara_as_slide_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
// TODO: Prepped for another time.
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLIDE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLIDE_TURN_MAX;
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE_ACCEL;
|
||||
if (lara->Control.TurnRate < -LARA_SLIDE_TURN_RATE_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLIDE_TURN_RATE_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX, LARA_LEAN_RATE / 3 * 2);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLIDE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLIDE_TURN_MAX;
|
||||
lara->Control.TurnRate += LARA_TURN_RATE_ACCEL;
|
||||
if (lara->Control.TurnRate > LARA_SLIDE_TURN_RATE_MAX)
|
||||
lara->Control.TurnRate = LARA_SLIDE_TURN_RATE_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX, LARA_LEAN_RATE / 3 * 2);
|
||||
}
|
||||
|
@ -155,17 +157,17 @@ void lara_as_slide_back(ItemInfo* item, CollisionInfo* coll)
|
|||
// TODO: Prepped for another time.
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate < -LARA_SLIDE_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLIDE_TURN_MAX;
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE_ACCEL;
|
||||
if (lara->Control.TurnRate < -LARA_SLIDE_TURN_RATE_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLIDE_TURN_RATE_MAX;
|
||||
|
||||
DoLaraLean(item, coll, LARA_LEAN_MAX, LARA_LEAN_RATE / 3 * 2);
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE;
|
||||
if (lara->Control.TurnRate > LARA_SLIDE_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLIDE_TURN_MAX;
|
||||
lara->Control.TurnRate += LARA_TURN_RATE_ACCEL;
|
||||
if (lara->Control.TurnRate > LARA_SLIDE_TURN_RATE_MAX)
|
||||
lara->Control.TurnRate = LARA_SLIDE_TURN_RATE_MAX;
|
||||
|
||||
DoLaraLean(item, coll, -LARA_LEAN_MAX, LARA_LEAN_RATE / 3 * 2);
|
||||
}
|
||||
|
|
|
@ -1154,7 +1154,7 @@ struct LaraCountData
|
|||
{
|
||||
unsigned int Pose;
|
||||
unsigned int PositionAdjust;
|
||||
unsigned int RunJump;
|
||||
unsigned int Run;
|
||||
unsigned int Death;
|
||||
unsigned int NoCheat;
|
||||
};
|
||||
|
@ -1276,7 +1276,6 @@ struct LaraInfo
|
|||
int HitFrame;
|
||||
int HitDirection;
|
||||
FX_INFO* SpasmEffect; // Not saved.
|
||||
unsigned int SpasmEffectCount;
|
||||
|
||||
short InteractedItem;
|
||||
int ProjectedFloorHeight;
|
||||
|
|
|
@ -13,6 +13,8 @@
|
|||
#include "Specific/level.h"
|
||||
#include "Specific/input.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// WATER SURFACE TREAD
|
||||
// Control & Collision Functions
|
||||
|
@ -39,7 +41,7 @@ void lara_as_surface_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
item->Animation.VerticalVelocity -= LARA_SWIM_DECELERATION;
|
||||
item->Animation.VerticalVelocity -= LARA_SWIM_VELOCITY_DECEL;
|
||||
if (item->Animation.VerticalVelocity < 0)
|
||||
item->Animation.VerticalVelocity = 0;
|
||||
|
||||
|
@ -55,18 +57,8 @@ void lara_as_surface_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate < -LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_MED_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate > LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_MED_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL * 1.25f, 0, LARA_MED_TURN_RATE_MAX);
|
||||
|
||||
if (DbInput & IN_JUMP)
|
||||
{
|
||||
|
@ -126,19 +118,9 @@ void lara_as_surface_swim_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
item->Animation.TargetState = LS_WATER_DEATH;
|
||||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate < -LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_MED_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate > LARA_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_MED_TURN_MAX;
|
||||
}
|
||||
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL * 1.25f, 0, LARA_MED_TURN_RATE_MAX);
|
||||
|
||||
if (!(TrInput & IN_FORWARD))
|
||||
item->Animation.TargetState = LS_ONWATER_IDLE;
|
||||
|
@ -146,7 +128,7 @@ void lara_as_surface_swim_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
if (DbInput & IN_JUMP)
|
||||
SetLaraSwimDiveAnimation(item);
|
||||
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_ACCELERATION;
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_VELOCITY_ACCEL;
|
||||
if (item->Animation.VerticalVelocity > LARA_TREAD_VELOCITY_MAX)
|
||||
item->Animation.VerticalVelocity = LARA_TREAD_VELOCITY_MAX;
|
||||
}
|
||||
|
@ -178,18 +160,8 @@ void lara_as_surface_swim_left(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (!(TrInput & IN_WALK)) // WALK locks orientation.
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_MED_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_MED_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL * 1.25f, 0, LARA_SLOW_MED_TURN_RATE_MAX);
|
||||
}
|
||||
|
||||
if (!(TrInput & IN_LSTEP || (TrInput & IN_WALK && TrInput & IN_LEFT)))
|
||||
|
@ -198,7 +170,7 @@ void lara_as_surface_swim_left(ItemInfo* item, CollisionInfo* coll)
|
|||
if (DbInput & IN_JUMP)
|
||||
SetLaraSwimDiveAnimation(item);
|
||||
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_ACCELERATION;
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_VELOCITY_ACCEL;
|
||||
if (item->Animation.VerticalVelocity > LARA_TREAD_VELOCITY_MAX)
|
||||
item->Animation.VerticalVelocity = LARA_TREAD_VELOCITY_MAX;
|
||||
}
|
||||
|
@ -227,18 +199,8 @@ void lara_as_surface_swim_right(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
if (!(TrInput & IN_WALK)) // WALK locks orientation.
|
||||
{
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_MED_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_MED_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL * 1.25f, 0, LARA_SLOW_MED_TURN_RATE_MAX);
|
||||
}
|
||||
|
||||
if (!(TrInput & IN_RSTEP || (TrInput & IN_WALK && TrInput & IN_RIGHT)))
|
||||
|
@ -247,7 +209,7 @@ void lara_as_surface_swim_right(ItemInfo* item, CollisionInfo* coll)
|
|||
if (DbInput & IN_JUMP)
|
||||
SetLaraSwimDiveAnimation(item);
|
||||
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_ACCELERATION;
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_VELOCITY_ACCEL;
|
||||
if (item->Animation.VerticalVelocity > LARA_TREAD_VELOCITY_MAX)
|
||||
item->Animation.VerticalVelocity = LARA_TREAD_VELOCITY_MAX;
|
||||
}
|
||||
|
@ -274,18 +236,8 @@ void lara_as_surface_swim_back(ItemInfo* item, CollisionInfo* coll)
|
|||
return;
|
||||
}
|
||||
|
||||
if (TrInput & IN_LEFT)
|
||||
{
|
||||
lara->Control.TurnRate -= LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate < -LARA_SLOW_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = -LARA_SLOW_MED_TURN_MAX;
|
||||
}
|
||||
else if (TrInput & IN_RIGHT)
|
||||
{
|
||||
lara->Control.TurnRate += LARA_TURN_RATE * 1.25f;
|
||||
if (lara->Control.TurnRate > LARA_SLOW_MED_TURN_MAX)
|
||||
lara->Control.TurnRate = LARA_SLOW_MED_TURN_MAX;
|
||||
}
|
||||
if (TrInput & (IN_LEFT | IN_RIGHT))
|
||||
ModulateLaraTurnRateY(item, LARA_TURN_RATE_ACCEL * 1.25f, 0, LARA_SLOW_MED_TURN_RATE_MAX);
|
||||
|
||||
if (DbInput & IN_JUMP)
|
||||
SetLaraSwimDiveAnimation(item);
|
||||
|
@ -293,7 +245,7 @@ void lara_as_surface_swim_back(ItemInfo* item, CollisionInfo* coll)
|
|||
if (!(TrInput & IN_BACK))
|
||||
item->Animation.TargetState = LS_ONWATER_IDLE;
|
||||
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_ACCELERATION;
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_VELOCITY_ACCEL;
|
||||
if (item->Animation.VerticalVelocity > LARA_TREAD_VELOCITY_MAX)
|
||||
item->Animation.VerticalVelocity = LARA_TREAD_VELOCITY_MAX;
|
||||
}
|
||||
|
|
|
@ -14,6 +14,8 @@
|
|||
#include "Specific/level.h"
|
||||
#include "Specific/input.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
// -----------------------------
|
||||
// UNDERWATER SWIM
|
||||
// Control & Collision Functions
|
||||
|
@ -45,14 +47,14 @@ void lara_as_underwater_idle(ItemInfo* item, CollisionInfo* coll)
|
|||
LookUpDown(item);
|
||||
|
||||
if (laraType == LaraType::Divesuit)
|
||||
ModulateLaraSubsuitSwimTurn(item);
|
||||
ModulateLaraSubsuitSwimTurnRates(item);
|
||||
else
|
||||
ModulateLaraSwimTurn(item, coll);
|
||||
ModulateLaraSwimTurnRates(item, coll);
|
||||
|
||||
if (TrInput & IN_JUMP)
|
||||
item->Animation.TargetState = LS_UNDERWATER_SWIM_FORWARD;
|
||||
|
||||
item->Animation.VerticalVelocity -= LARA_SWIM_DECELERATION;
|
||||
item->Animation.VerticalVelocity -= LARA_SWIM_VELOCITY_DECEL;
|
||||
if (item->Animation.VerticalVelocity < 0)
|
||||
item->Animation.VerticalVelocity = 0;
|
||||
|
||||
|
@ -86,11 +88,11 @@ void lara_as_underwater_swim_forward(ItemInfo* item, CollisionInfo* coll)
|
|||
}
|
||||
|
||||
if (laraType != LaraType::Divesuit)
|
||||
ModulateLaraSwimTurn(item, coll);
|
||||
ModulateLaraSwimTurnRates(item, coll);
|
||||
else
|
||||
ModulateLaraSubsuitSwimTurn(item);
|
||||
ModulateLaraSubsuitSwimTurnRates(item);
|
||||
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_ACCELERATION;
|
||||
item->Animation.VerticalVelocity += LARA_SWIM_VELOCITY_ACCEL;
|
||||
if (item->Animation.VerticalVelocity > LARA_SWIM_VELOCITY_MAX)
|
||||
item->Animation.VerticalVelocity = LARA_SWIM_VELOCITY_MAX;
|
||||
|
||||
|
@ -124,14 +126,14 @@ void lara_as_underwater_inertia(ItemInfo* item, CollisionInfo* coll)
|
|||
}
|
||||
|
||||
if (laraType != LaraType::Divesuit)
|
||||
ModulateLaraSwimTurn(item, coll);
|
||||
ModulateLaraSwimTurnRates(item, coll);
|
||||
else
|
||||
ModulateLaraSubsuitSwimTurn(item);
|
||||
ModulateLaraSubsuitSwimTurnRates(item);
|
||||
|
||||
if (TrInput & IN_JUMP)
|
||||
item->Animation.TargetState = LS_UNDERWATER_SWIM_FORWARD;
|
||||
|
||||
item->Animation.VerticalVelocity -= LARA_SWIM_DECELERATION;
|
||||
item->Animation.VerticalVelocity -= LARA_SWIM_VELOCITY_DECEL;
|
||||
if (item->Animation.VerticalVelocity < 0)
|
||||
item->Animation.VerticalVelocity = 0;
|
||||
|
||||
|
@ -154,7 +156,7 @@ void lara_as_underwater_death(ItemInfo* item, CollisionInfo* coll)
|
|||
|
||||
lara->Control.CanLook = false;
|
||||
|
||||
item->Animation.VerticalVelocity -= LARA_SWIM_DECELERATION;
|
||||
item->Animation.VerticalVelocity -= LARA_SWIM_VELOCITY_DECEL;
|
||||
if (item->Animation.VerticalVelocity < 0)
|
||||
item->Animation.VerticalVelocity = 0;
|
||||
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
#include "Specific/input.h"
|
||||
#include "Specific/level.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Renderer;
|
||||
using namespace TEN::Floordata;
|
||||
|
||||
|
@ -320,6 +321,7 @@ bool TestLaraHangJump(ItemInfo* item, CollisionInfo* coll)
|
|||
item->Animation.Velocity = 2;
|
||||
item->Animation.VerticalVelocity = 1;
|
||||
item->Animation.Airborne = true;
|
||||
lara->Control.TurnRate = 0;
|
||||
lara->Control.HandStatus = HandStatus::Busy;
|
||||
return true;
|
||||
}
|
||||
|
@ -938,6 +940,10 @@ bool TestLaraWaterClimbOut(ItemInfo* item, CollisionInfo* coll)
|
|||
if (!TestValidLedge(item, coll))
|
||||
return false;
|
||||
|
||||
TestForObjectOnLedge(item, coll);
|
||||
if (coll->HitStatic)
|
||||
return false;
|
||||
|
||||
auto probe = GetCollision(item, coll->Setup.ForwardAngle, CLICK(2), -CLICK(1));
|
||||
int headroom = probe.Position.Floor - probe.Position.Ceiling;
|
||||
|
||||
|
@ -987,6 +993,7 @@ bool TestLaraWaterClimbOut(ItemInfo* item, CollisionInfo* coll)
|
|||
item->Animation.Airborne = false;
|
||||
item->Animation.Velocity = 0;
|
||||
item->Animation.VerticalVelocity = 0;
|
||||
lara->Control.TurnRate = 0;
|
||||
lara->Control.HandStatus = HandStatus::Busy;
|
||||
lara->Control.WaterStatus = WaterStatus::Dry;
|
||||
return true;
|
||||
|
@ -1173,11 +1180,11 @@ bool IsRunJumpQueueableState(LaraState state)
|
|||
|
||||
bool IsRunJumpCountableState(LaraState state)
|
||||
{
|
||||
if (state == LS_RUN_FORWARD ||
|
||||
state == LS_WALK_FORWARD ||
|
||||
state == LS_JUMP_FORWARD ||
|
||||
if (state == LS_WALK_FORWARD ||
|
||||
state == LS_RUN_FORWARD ||
|
||||
state == LS_SPRINT ||
|
||||
state == LS_SPRINT_DIVE)
|
||||
state == LS_SPRINT_DIVE ||
|
||||
state == LS_JUMP_FORWARD)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
#include "Specific/setup.h"
|
||||
#include "Specific/input.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Math::Random;
|
||||
|
||||
struct PistolDef
|
||||
|
@ -41,7 +42,7 @@ void AnimatePistols(ItemInfo* laraItem, LaraWeaponType weaponType)
|
|||
auto* weapon = &Weapons[(int)weaponType];
|
||||
auto* p = &PistolsTable[(int)lara->Control.Weapon.GunType];
|
||||
|
||||
int soundPlayed = false;
|
||||
int fired = false;
|
||||
|
||||
if (laraItem->MeshBits)
|
||||
{
|
||||
|
@ -126,7 +127,7 @@ void AnimatePistols(ItemInfo* laraItem, LaraWeaponType weaponType)
|
|||
|
||||
SoundEffect(SFX_TR4_EXPLOSION1, &laraItem->Pose, SoundEnvironment::Land, 0.9f, 0.3f);
|
||||
SoundEffect(weapon->SampleNum, &laraItem->Pose);
|
||||
soundPlayed = true;
|
||||
fired = true;
|
||||
|
||||
if (weaponType == LaraWeaponType::Uzi)
|
||||
lara->Control.Weapon.UziRight = true;
|
||||
|
@ -215,10 +216,11 @@ void AnimatePistols(ItemInfo* laraItem, LaraWeaponType weaponType)
|
|||
lara->LeftArm.FlashGun = weapon->FlashTime;
|
||||
}
|
||||
|
||||
if (!soundPlayed)
|
||||
if (!fired)
|
||||
{
|
||||
SoundEffect(SFX_TR4_EXPLOSION1, &laraItem->Pose, SoundEnvironment::Land, 0.9f, 0.3f);
|
||||
SoundEffect(weapon->SampleNum, &laraItem->Pose);
|
||||
fired = true;
|
||||
}
|
||||
|
||||
if (weaponType == LaraWeaponType::Uzi)
|
||||
|
@ -265,6 +267,12 @@ void AnimatePistols(ItemInfo* laraItem, LaraWeaponType weaponType)
|
|||
}
|
||||
}
|
||||
|
||||
if (fired) // Rumble gamepad only once if any of the hands fired.
|
||||
{
|
||||
float power = weaponType == LaraWeaponType::Uzi ? GenerateFloat(0.1f, 0.3f) : 1.0f;
|
||||
Rumble(power, 0.1f);
|
||||
}
|
||||
|
||||
SetArmInfo(laraItem, &lara->LeftArm, frameLeft);
|
||||
}
|
||||
|
||||
|
|
|
@ -13,6 +13,7 @@
|
|||
#include "Game/Lara/lara_helpers.h"
|
||||
#include "Game/room.h"
|
||||
#include "Game/savegame.h"
|
||||
#include "Game/spotcam.h"
|
||||
#include "Objects/Generic/Object/burning_torch.h"
|
||||
#include "Sound/sound.h"
|
||||
#include "Specific/input.h"
|
||||
|
@ -20,6 +21,8 @@
|
|||
#include "Specific/setup.h"
|
||||
|
||||
using TEN::Renderer::g_Renderer;
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Entities::Generic;
|
||||
using namespace TEN::Effects::Environment;
|
||||
|
||||
|
@ -28,6 +31,9 @@ constexpr auto COLL_CANCEL_THRESHOLD = SECTOR(2);
|
|||
constexpr auto COLL_DISCARD_THRESHOLD = CLICK(0.5f);
|
||||
constexpr auto CAMERA_RADIUS = CLICK(1);
|
||||
|
||||
constexpr auto THUMBCAM_VERTICAL_CONSTRAINT_ANGLE = 120.0f;
|
||||
constexpr auto THUMBCAM_HORIZONTAL_CONSTRAINT_ANGLE = 80.0f;
|
||||
|
||||
struct OLD_CAMERA
|
||||
{
|
||||
short ActiveState;
|
||||
|
@ -102,6 +108,11 @@ void AlterFOV(int value)
|
|||
PhdPerspective = g_Renderer.ScreenWidth / 2 * phd_cos(CurrentFOV / 2) / phd_sin(CurrentFOV / 2);
|
||||
}
|
||||
|
||||
inline void RumbleFromBounce()
|
||||
{
|
||||
Rumble(std::clamp((float)abs(Camera.bounce) / 70.0f, 0.0f, 0.8f), 0.2f);
|
||||
}
|
||||
|
||||
|
||||
void InitialiseCamera()
|
||||
{
|
||||
|
@ -206,6 +217,7 @@ void MoveCamera(GameVector* ideal, int speed)
|
|||
Camera.target.y += GetRandomControl() % bounce - bounce2;
|
||||
Camera.target.z += GetRandomControl() % bounce - bounce2;
|
||||
Camera.bounce += 5;
|
||||
RumbleFromBounce();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -425,18 +437,34 @@ void ChaseCamera(ItemInfo* item)
|
|||
MoveCamera(&ideal, Camera.speed);
|
||||
}
|
||||
|
||||
void DoThumbstickCamera()
|
||||
{
|
||||
if (!g_Configuration.EnableThumbstickCameraControl)
|
||||
return;
|
||||
|
||||
if (Camera.laraNode == -1 && (Camera.target.x == OldCam.target.x &&
|
||||
Camera.target.y == OldCam.target.y &&
|
||||
Camera.target.z == OldCam.target.z))
|
||||
{
|
||||
Camera.targetAngle = ANGLE(THUMBCAM_VERTICAL_CONSTRAINT_ANGLE * AxisMap[InputAxis::CameraHorizontal]);
|
||||
Camera.targetElevation = ANGLE(-10.0f + (THUMBCAM_HORIZONTAL_CONSTRAINT_ANGLE * AxisMap[InputAxis::CameraVertical]));
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateCameraElevation()
|
||||
{
|
||||
DoThumbstickCamera();
|
||||
|
||||
if (Camera.laraNode != -1)
|
||||
{
|
||||
Vector3Int pos = { 0, 0, 0 };
|
||||
auto pos = Vector3Int();
|
||||
GetLaraJointPosition(&pos, Camera.laraNode);
|
||||
|
||||
Vector3Int pos1 = { 0, -CLICK(1), SECTOR(2) };
|
||||
auto pos1 = Vector3Int(0, -CLICK(1), SECTOR(2));
|
||||
GetLaraJointPosition(&pos1, Camera.laraNode);
|
||||
|
||||
pos.z = pos1.z - pos.z;
|
||||
pos.x = pos1.x - pos.x;
|
||||
pos.z = pos1.z - pos.z;
|
||||
Camera.actualAngle = Camera.targetAngle + phd_atan(pos.z, pos.x);
|
||||
}
|
||||
else
|
||||
|
@ -956,6 +984,7 @@ void LookCamera(ItemInfo* item)
|
|||
Camera.target.y += GetRandomControl() % (-Camera.bounce) - (-Camera.bounce >> 1);
|
||||
Camera.target.z += GetRandomControl() % (-Camera.bounce) - (-Camera.bounce >> 1);
|
||||
Camera.bounce += 5;
|
||||
RumbleFromBounce();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1075,7 +1104,7 @@ void BinocularCamera(ItemInfo* item)
|
|||
if (!LaserSight)
|
||||
{
|
||||
// TODO: Some of these inputs should ideally be blocked. @Sezz 2022.05.19
|
||||
if (InputBusy & (IN_DESELECT | IN_LOOK | IN_DRAW | IN_FLARE | IN_WALK | IN_JUMP))
|
||||
if (RawInput & (IN_DESELECT | IN_OPTION | IN_LOOK | IN_DRAW | IN_FLARE | IN_WALK | IN_JUMP))
|
||||
{
|
||||
item->MeshBits = ALL_JOINT_BITS;
|
||||
lara->Inventory.IsBusy = false;
|
||||
|
@ -1150,6 +1179,7 @@ void BinocularCamera(ItemInfo* item)
|
|||
Camera.target.y += (CLICK(0.25f) / 4) * (GetRandomControl() % (-Camera.bounce) - (-Camera.bounce >> 1));
|
||||
Camera.target.z += (CLICK(0.25f) / 4) * (GetRandomControl() % (-Camera.bounce) - (-Camera.bounce >> 1));
|
||||
Camera.bounce += 5;
|
||||
RumbleFromBounce();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1179,7 +1209,7 @@ void BinocularCamera(ItemInfo* item)
|
|||
int range = 0;
|
||||
int flags = 0;
|
||||
|
||||
if (!(InputBusy & IN_WALK))
|
||||
if (!(RawInput & IN_WALK))
|
||||
{
|
||||
range = 64;
|
||||
flags = 0x10000;
|
||||
|
@ -1190,7 +1220,7 @@ void BinocularCamera(ItemInfo* item)
|
|||
flags = 0x8000;
|
||||
}
|
||||
|
||||
if (InputBusy & IN_SPRINT)
|
||||
if (RawInput & IN_SPRINT)
|
||||
{
|
||||
BinocularRange -= range;
|
||||
if (BinocularRange < ANGLE(0.7f))
|
||||
|
@ -1198,7 +1228,7 @@ void BinocularCamera(ItemInfo* item)
|
|||
else
|
||||
SoundEffect(SFX_TR4_BINOCULARS_ZOOM, nullptr, SoundEnvironment::Land, 0.9f);
|
||||
}
|
||||
else if (InputBusy & IN_CROUCH)
|
||||
else if (RawInput & IN_CROUCH)
|
||||
{
|
||||
BinocularRange += range;
|
||||
if (BinocularRange > ANGLE(8.5f))
|
||||
|
@ -1215,10 +1245,10 @@ void BinocularCamera(ItemInfo* item)
|
|||
bool firing = false;
|
||||
auto& ammo = GetAmmo(item, lara->Control.Weapon.GunType);
|
||||
|
||||
if (!(InputBusy & IN_ACTION) ||
|
||||
if (!(RawInput & IN_ACTION) ||
|
||||
WeaponDelay || !ammo)
|
||||
{
|
||||
if (!(InputBusy & IN_ACTION))
|
||||
if (!(RawInput & IN_ACTION))
|
||||
{
|
||||
LSHKShotsFired = 0;
|
||||
Camera.bounce = 0;
|
||||
|
@ -1256,6 +1286,8 @@ void BinocularCamera(ItemInfo* item)
|
|||
SoundEffect(SFX_TR4_EXPLOSION1, nullptr, SoundEnvironment::Land, 1.0f, 0.4f);
|
||||
SoundEffect(SFX_TR4_HK_FIRE, nullptr);
|
||||
}
|
||||
|
||||
Camera.bounce = -16 - (GetRandomControl() & 0x1F);
|
||||
}
|
||||
else if (lara->Weapons[(int)LaraWeaponType::HK].SelectedAmmo == WeaponAmmoType::Ammo2)
|
||||
{
|
||||
|
@ -1277,6 +1309,8 @@ void BinocularCamera(ItemInfo* item)
|
|||
SoundEffect(SFX_TR4_EXPLOSION1, nullptr, SoundEnvironment::Land, 1.0f, 0.4f);
|
||||
SoundEffect(SFX_TR4_HK_FIRE, nullptr);
|
||||
}
|
||||
|
||||
Camera.bounce = -16 - (GetRandomControl() & 0x1F);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1289,6 +1323,8 @@ void BinocularCamera(ItemInfo* item)
|
|||
SoundEffect(SFX_TR4_EXPLOSION1, nullptr, SoundEnvironment::Land, 1.0f, 0.4f);
|
||||
SoundEffect(SFX_TR4_HK_FIRE, nullptr);
|
||||
}
|
||||
|
||||
Camera.bounce = -16 - (GetRandomControl() & 0x1F);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -1316,8 +1352,6 @@ void BinocularCamera(ItemInfo* item)
|
|||
SoundEffect(SFX_TR4_HK_FIRE, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
Camera.bounce = -16 - (GetRandomControl() & 0x1F);
|
||||
}
|
||||
|
||||
if (!ammo.hasInfinite())
|
||||
|
@ -1331,7 +1365,7 @@ void BinocularCamera(ItemInfo* item)
|
|||
{
|
||||
GetTargetOnLOS(&Camera.pos, &Camera.target, false, false);
|
||||
|
||||
if (!(InputBusy & IN_ACTION))
|
||||
if (!(RawInput & IN_ACTION))
|
||||
{
|
||||
// Reimplement this mode?
|
||||
}
|
||||
|
@ -2032,3 +2066,58 @@ void UpdateFadeScreenAndCinematicBars()
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
void HandleOptics()
|
||||
{
|
||||
if (!(TrInput & IN_LOOK) || UseSpotCam || TrackCameraInit ||
|
||||
((LaraItem->Animation.ActiveState != LS_IDLE || LaraItem->Animation.AnimNumber != LA_STAND_IDLE) &&
|
||||
(!Lara.Control.IsLow || TrInput & IN_CROUCH || LaraItem->Animation.TargetState != LS_CROUCH_IDLE || LaraItem->Animation.AnimNumber != LA_CROUCH_IDLE)))
|
||||
{
|
||||
if (BinocularRange == 0)
|
||||
{
|
||||
if (UseSpotCam || TrackCameraInit)
|
||||
TrInput &= ~IN_LOOK;
|
||||
}
|
||||
else
|
||||
{
|
||||
// If any input but optic controls (directions + action), immediately exit binoculars mode.
|
||||
if (TrInput != IN_NONE && ((TrInput & ~IN_OPTIC_CONTROLS) != IN_NONE))
|
||||
BinocularRange = 0;
|
||||
|
||||
if (LaserSight)
|
||||
{
|
||||
BinocularRange = 0;
|
||||
BinocularOn = false;
|
||||
LaserSight = false;
|
||||
Camera.type = BinocularOldCamera;
|
||||
Camera.bounce = 0;
|
||||
AlterFOV(ANGLE(80.0f));
|
||||
|
||||
LaraItem->MeshBits = ALL_JOINT_BITS;
|
||||
Lara.Inventory.IsBusy = false;
|
||||
ResetLaraFlex(LaraItem);
|
||||
|
||||
TrInput &= ~IN_LOOK;
|
||||
}
|
||||
else
|
||||
{
|
||||
TrInput |= IN_LOOK;
|
||||
DbInput = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (BinocularRange == 0)
|
||||
{
|
||||
if (Lara.Control.HandStatus == HandStatus::WeaponReady &&
|
||||
((Lara.Control.Weapon.GunType == LaraWeaponType::Revolver && Lara.Weapons[(int)LaraWeaponType::Revolver].HasLasersight) ||
|
||||
Lara.Control.Weapon.GunType == LaraWeaponType::HK ||
|
||||
(Lara.Control.Weapon.GunType == LaraWeaponType::Crossbow && Lara.Weapons[(int)LaraWeaponType::Crossbow].HasLasersight)))
|
||||
{
|
||||
BinocularRange = 128;
|
||||
BinocularOldCamera = Camera.oldType;
|
||||
BinocularOn = true;
|
||||
LaserSight = true;
|
||||
Lara.Inventory.IsBusy = true;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -48,9 +48,6 @@ enum CAMERA_FLAGS
|
|||
CF_CHASE_OBJECT = 3,
|
||||
};
|
||||
|
||||
constexpr auto MAX_CAMERA = 18;
|
||||
constexpr auto NO_MINY = 0xFFFFFF;
|
||||
|
||||
constexpr auto FADE_SCREEN_SPEED = 16.0f / 255.0f;
|
||||
|
||||
extern Vector3Int CurrentCameraPosition;
|
||||
|
@ -101,3 +98,4 @@ void SetScreenFadeOut(float speed);
|
|||
void SetScreenFadeIn(float speed);
|
||||
void SetCinematicBars(float height, float speed);
|
||||
void UpdateFadeScreenAndCinematicBars();
|
||||
void HandleOptics();
|
||||
|
|
|
@ -727,15 +727,7 @@ bool ItemPushItem(ItemInfo* item, ItemInfo* item2, CollisionInfo* coll, bool spa
|
|||
dz -= cosY * rz - sinY * rx;
|
||||
|
||||
lara->HitDirection = (item2->Pose.Orientation.y - phd_atan(dz, dz) - ANGLE(135.0f)) / ANGLE(90.0f);
|
||||
|
||||
if (!lara->HitFrame && !lara->SpasmEffectCount)
|
||||
{
|
||||
SoundEffect(SFX_TR4_LARA_INJURY, &item2->Pose);
|
||||
lara->SpasmEffectCount = GenerateInt(15, 35);
|
||||
}
|
||||
|
||||
if (lara->SpasmEffectCount)
|
||||
lara->SpasmEffectCount--;
|
||||
DoDamage(item2, 0); // Dummy hurt call. Only for ooh sound!
|
||||
|
||||
lara->HitFrame++;
|
||||
if (lara->HitFrame > 34)
|
||||
|
|
|
@ -67,6 +67,7 @@ using namespace TEN::Entities::TR4;
|
|||
using namespace TEN::Renderer;
|
||||
using namespace TEN::Math::Random;
|
||||
using namespace TEN::Floordata;
|
||||
using namespace TEN::Input;
|
||||
|
||||
int GameTimer = 0;
|
||||
int GlobalCounter = 0;
|
||||
|
@ -113,8 +114,6 @@ GameStatus ControlPhase(int numFrames, int demoMode)
|
|||
if (TrackCameraInit)
|
||||
UseSpotCam = false;
|
||||
|
||||
SetDebounce = true;
|
||||
|
||||
g_GameStringsHandler->ProcessDisplayStrings(DELTA_TIME);
|
||||
|
||||
static int framesCount = 0;
|
||||
|
@ -129,10 +128,7 @@ GameStatus ControlPhase(int numFrames, int demoMode)
|
|||
|
||||
// Poll the keyboard and update input variables
|
||||
if (CurrentLevel != 0)
|
||||
{
|
||||
if (S_UpdateInput() == -1)
|
||||
return GameStatus::None;
|
||||
}
|
||||
UpdateInput();
|
||||
|
||||
// Has Lara control been disabled?
|
||||
if (Lara.Control.Locked || CurrentLevel == 0)
|
||||
|
@ -142,14 +138,13 @@ GameStatus ControlPhase(int numFrames, int demoMode)
|
|||
TrInput &= IN_LOOK;
|
||||
}
|
||||
|
||||
// Does the player want to enter inventory?
|
||||
SetDebounce = false;
|
||||
|
||||
if (CurrentLevel != 0)
|
||||
{
|
||||
// Does the player want to enter inventory?
|
||||
if (TrInput & IN_SAVE && LaraItem->HitPoints > 0 && g_Gui.GetInventoryMode() != InventoryMode::Save)
|
||||
{
|
||||
StopAllSounds();
|
||||
StopRumble();
|
||||
|
||||
g_Gui.SetInventoryMode(InventoryMode::Save);
|
||||
|
||||
|
@ -159,6 +154,7 @@ GameStatus ControlPhase(int numFrames, int demoMode)
|
|||
else if (TrInput & IN_LOAD && g_Gui.GetInventoryMode() != InventoryMode::Load)
|
||||
{
|
||||
StopAllSounds();
|
||||
StopRumble();
|
||||
|
||||
g_Gui.SetInventoryMode(InventoryMode::Load);
|
||||
|
||||
|
@ -168,16 +164,18 @@ GameStatus ControlPhase(int numFrames, int demoMode)
|
|||
else if (TrInput & IN_PAUSE && g_Gui.GetInventoryMode() != InventoryMode::Pause && LaraItem->HitPoints > 0)
|
||||
{
|
||||
StopAllSounds();
|
||||
StopRumble();
|
||||
|
||||
g_Renderer.DumpGameScene();
|
||||
g_Gui.SetInventoryMode(InventoryMode::Pause);
|
||||
g_Gui.SetMenuToDisplay(Menu::Pause);
|
||||
g_Gui.SetSelectedOption(0);
|
||||
}
|
||||
else if ((DbInput & IN_DESELECT || g_Gui.GetEnterInventory() != NO_ITEM) &&
|
||||
else if ((DbInput & IN_OPTION || g_Gui.GetEnterInventory() != NO_ITEM) &&
|
||||
LaraItem->HitPoints > 0 && !BinocularOn)
|
||||
{
|
||||
// Stop all sounds
|
||||
StopAllSounds();
|
||||
StopRumble();
|
||||
|
||||
if (g_Gui.CallInventory(true))
|
||||
return GameStatus::LoadGame;
|
||||
|
@ -216,59 +214,7 @@ GameStatus ControlPhase(int numFrames, int demoMode)
|
|||
|
||||
// Handle lasersight and binocular
|
||||
if (CurrentLevel != 0)
|
||||
{
|
||||
if (!(TrInput & IN_LOOK) || UseSpotCam || TrackCameraInit ||
|
||||
((LaraItem->Animation.ActiveState != LS_IDLE || LaraItem->Animation.AnimNumber != LA_STAND_IDLE) &&
|
||||
(!Lara.Control.IsLow || TrInput & IN_CROUCH || LaraItem->Animation.TargetState != LS_CROUCH_IDLE || LaraItem->Animation.AnimNumber != LA_CROUCH_IDLE)))
|
||||
{
|
||||
if (BinocularRange == 0)
|
||||
{
|
||||
if (UseSpotCam || TrackCameraInit)
|
||||
TrInput &= ~IN_LOOK;
|
||||
}
|
||||
else
|
||||
{
|
||||
// If any input but optic controls (directions + action), immediately exit binoculars mode.
|
||||
if (TrInput != IN_NONE && ((TrInput & ~IN_OPTIC_CONTROLS) != IN_NONE))
|
||||
BinocularRange = 0;
|
||||
|
||||
if (LaserSight)
|
||||
{
|
||||
BinocularRange = 0;
|
||||
BinocularOn = false;
|
||||
LaserSight = false;
|
||||
Camera.type = BinocularOldCamera;
|
||||
Camera.bounce = 0;
|
||||
AlterFOV(ANGLE(80.0f));
|
||||
|
||||
LaraItem->MeshBits = ALL_JOINT_BITS;
|
||||
Lara.Inventory.IsBusy = false;
|
||||
ResetLaraFlex(LaraItem);
|
||||
|
||||
TrInput &= ~IN_LOOK;
|
||||
}
|
||||
else
|
||||
{
|
||||
TrInput |= IN_LOOK;
|
||||
DbInput = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (BinocularRange == 0)
|
||||
{
|
||||
if (Lara.Control.HandStatus == HandStatus::WeaponReady &&
|
||||
((Lara.Control.Weapon.GunType == LaraWeaponType::Revolver && Lara.Weapons[(int)LaraWeaponType::Revolver].HasLasersight) ||
|
||||
Lara.Control.Weapon.GunType == LaraWeaponType::HK ||
|
||||
(Lara.Control.Weapon.GunType == LaraWeaponType::Crossbow && Lara.Weapons[(int)LaraWeaponType::Crossbow].HasLasersight)))
|
||||
{
|
||||
BinocularRange = 128;
|
||||
BinocularOldCamera = Camera.oldType;
|
||||
BinocularOn = true;
|
||||
LaserSight = true;
|
||||
Lara.Inventory.IsBusy = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
HandleOptics();
|
||||
|
||||
// Update all items
|
||||
InItemControlLoop = true;
|
||||
|
@ -463,9 +409,6 @@ GameStatus DoTitle(int index, std::string const& ambient)
|
|||
{
|
||||
TENLog("DoTitle", LogLevel::Info);
|
||||
|
||||
// Reset all the globals for the game which needs this
|
||||
CleanUp();
|
||||
|
||||
// Load the level
|
||||
LoadLevelFile(index);
|
||||
|
||||
|
@ -477,7 +420,6 @@ GameStatus DoTitle(int index, std::string const& ambient)
|
|||
InitialiseFXArray(true);
|
||||
InitialisePickupDisplay();
|
||||
InitialiseCamera();
|
||||
StopAllSounds();
|
||||
|
||||
g_GameScript->ResetScripts(true);
|
||||
|
||||
|
@ -512,7 +454,7 @@ GameStatus DoTitle(int index, std::string const& ambient)
|
|||
// Play background music
|
||||
// MERGE: PlaySoundTrack(index);
|
||||
|
||||
// Initialize menu
|
||||
// Initialise menu
|
||||
g_Gui.SetMenuToDisplay(Menu::Title);
|
||||
g_Gui.SetSelectedOption(0);
|
||||
|
||||
|
@ -534,9 +476,7 @@ GameStatus DoTitle(int index, std::string const& ambient)
|
|||
{
|
||||
g_Renderer.RenderTitle();
|
||||
|
||||
SetDebounce = true;
|
||||
S_UpdateInput();
|
||||
SetDebounce = false;
|
||||
UpdateInput();
|
||||
|
||||
status = g_Gui.TitleOptions();
|
||||
|
||||
|
@ -576,9 +516,6 @@ GameStatus DoTitle(int index, std::string const& ambient)
|
|||
|
||||
GameStatus DoLevel(int index, std::string const& ambient, bool loadFromSavegame)
|
||||
{
|
||||
// Reset all the globals for the game which needs this
|
||||
CleanUp();
|
||||
|
||||
// Load the level
|
||||
LoadLevelFile(index);
|
||||
|
||||
|
@ -586,7 +523,6 @@ GameStatus DoLevel(int index, std::string const& ambient, bool loadFromSavegame)
|
|||
InitialiseFXArray(true);
|
||||
InitialisePickupDisplay();
|
||||
InitialiseCamera();
|
||||
StopAllSounds();
|
||||
|
||||
g_GameScript->ResetScripts(loadFromSavegame);
|
||||
|
||||
|
@ -681,6 +617,7 @@ GameStatus DoLevel(int index, std::string const& ambient, bool loadFromSavegame)
|
|||
// Here is the only way for exiting from the loop
|
||||
StopAllSounds();
|
||||
StopSoundTracks();
|
||||
StopRumble();
|
||||
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -398,8 +398,6 @@ bool DoRayBox(GameVector* start, GameVector* end, BOUNDING_BOX* box, PHD_3DPOS*
|
|||
int sp = -2;
|
||||
float minDistance = std::numeric_limits<float>::max();
|
||||
|
||||
int action = TrInput & IN_ACTION;
|
||||
|
||||
if (closesItemNumber < 0)
|
||||
{
|
||||
// Static meshes don't require further tests
|
||||
|
|
|
@ -25,7 +25,6 @@ struct BUBBLE_STRUCT
|
|||
int age;
|
||||
bool active;
|
||||
};
|
||||
|
||||
extern std::vector<BUBBLE_STRUCT> Bubbles;
|
||||
|
||||
void DisableBubbles();
|
||||
|
|
|
@ -89,9 +89,7 @@ void TriggerChaffEffects(ItemInfo* item, Vector3Int* pos, Vector3Int* vel, int s
|
|||
|
||||
TriggerChaffSparkles(pos, vel, &color, age, item);
|
||||
if (isUnderwater)
|
||||
{
|
||||
TriggerChaffBubbles(pos, item->RoomNumber);
|
||||
}
|
||||
else
|
||||
{
|
||||
Vector3 position = Vector3(pos->x,pos->y,pos->z);
|
||||
|
@ -105,7 +103,6 @@ void TriggerChaffEffects(ItemInfo* item, Vector3Int* pos, Vector3Int* vel, int s
|
|||
SoundEffect(cond ? SFX_TR4_FLARE_BURN_UNDERWATER : SFX_TR4_FLARE_BURN_DRY, & item->Pose, cond ? SoundEnvironment::Water : SoundEnvironment::Always, 1.0f, 0.5f);
|
||||
}
|
||||
|
||||
|
||||
void TriggerChaffSparkles(Vector3Int* pos, Vector3Int* vel, CVECTOR* color, int age, ItemInfo* item)
|
||||
{
|
||||
/*
|
||||
|
@ -145,7 +142,6 @@ void TriggerChaffSparkles(Vector3Int* pos, Vector3Int* vel, CVECTOR* color, int
|
|||
TEN::Effects::Spark::TriggerFlareSparkParticles(pos, vel,color,item->RoomNumber);
|
||||
}
|
||||
|
||||
|
||||
void TriggerChaffSmoke(Vector3Int* pos, Vector3Int* vel, int speed, bool moving, bool wind)
|
||||
{
|
||||
SMOKE_SPARKS* smoke;
|
||||
|
@ -201,9 +197,7 @@ void TriggerChaffSmoke(Vector3Int* pos, Vector3Int* vel, int speed, bool moving,
|
|||
smoke->rotAdd = (GetRandomControl() & 7) + 24;
|
||||
}
|
||||
else
|
||||
{
|
||||
smoke->flags = SP_EXPDEF | SP_DEF | SP_SCALE;
|
||||
}
|
||||
|
||||
if (wind)
|
||||
smoke->flags |= SP_WIND;
|
||||
|
@ -216,11 +210,10 @@ void TriggerChaffSmoke(Vector3Int* pos, Vector3Int* vel, int speed, bool moving,
|
|||
smoke->size = smoke->dSize = size;
|
||||
}
|
||||
|
||||
|
||||
void TriggerChaffBubbles(Vector3Int* pos, int FlareRoomNumber)
|
||||
{
|
||||
auto& bubble = Bubbles[GetFreeBubble()];
|
||||
|
||||
BUBBLE_STRUCT& bubble = Bubbles[GetFreeBubble()];
|
||||
bubble = {};
|
||||
bubble.active = true;
|
||||
bubble.size = 0;
|
||||
|
@ -240,4 +233,4 @@ void TriggerChaffBubbles(Vector3Int* pos, int FlareRoomNumber)
|
|||
bubble.wavePeriod = Vector3(GenerateFloat(-3.14, 3.14), GenerateFloat(-3.14, 3.14), GenerateFloat(-3.14, 3.14));
|
||||
bubble.waveSpeed = Vector3(1 / GenerateFloat(8, 16), 1 / GenerateFloat(8, 16), 1 / GenerateFloat(8, 16));
|
||||
bubble.roomNumber = FlareRoomNumber;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,4 +17,4 @@ void TriggerChaffBubbles(Vector3Int* pos, int FlareRoomNumber);
|
|||
/* void TriggerChaffEffects(ItemInfo* item, PHD_3DPOS pos, short angle, int speed, bool underwater);
|
||||
void TriggerChaffSparkles(PHD_3DPOS pos, short angle, int speed);
|
||||
void TriggerChaffSmoke(PHD_3DPOS pos, short angle, int speed, bool moving);
|
||||
void TriggerChaffBubbles(PHD_3DPOS pos, int FlareRoomNumber); */
|
||||
void TriggerChaffBubbles(PHD_3DPOS pos, int FlareRoomNumber); */
|
||||
|
|
|
@ -15,11 +15,7 @@
|
|||
using namespace TEN::Effects::Environment;
|
||||
using namespace TEN::Math::Random;
|
||||
|
||||
namespace TEN
|
||||
{
|
||||
namespace Effects
|
||||
{
|
||||
namespace Drip
|
||||
namespace TEN::Effects::Drip
|
||||
{
|
||||
using namespace DirectX::SimpleMath;
|
||||
|
||||
|
@ -36,11 +32,12 @@ namespace Drip
|
|||
{
|
||||
for (int i = 0; i < dripParticles.size(); i++)
|
||||
{
|
||||
DripParticle& d = dripParticles[i];
|
||||
if (!d.active) continue;
|
||||
auto& d = dripParticles[i];
|
||||
|
||||
if (!d.active)
|
||||
continue;
|
||||
|
||||
d.age++;
|
||||
|
||||
if (d.age > d.life)
|
||||
d.active = false;
|
||||
|
||||
|
@ -85,7 +82,7 @@ namespace Drip
|
|||
|
||||
void SpawnWetnessDrip(Vector3 const & pos, int room)
|
||||
{
|
||||
DripParticle& d = getFreeDrip();
|
||||
auto& d = getFreeDrip();
|
||||
d = {};
|
||||
d.active = true;
|
||||
d.pos = pos;
|
||||
|
@ -131,4 +128,4 @@ namespace Drip
|
|||
drip.active = true;
|
||||
}
|
||||
}
|
||||
}}}
|
||||
}
|
||||
|
|
|
@ -3,31 +3,31 @@
|
|||
#include <d3d11.h>
|
||||
#include <SimpleMath.h>
|
||||
|
||||
namespace TEN {
|
||||
namespace Effects {
|
||||
namespace Drip {
|
||||
constexpr float DRIP_LIFE = 25.0f;
|
||||
constexpr float DRIP_LIFE_LONG = 120.0f;
|
||||
constexpr float DRIP_WIDTH = 4;
|
||||
constexpr int NUM_DRIPS = 512;
|
||||
struct DripParticle {
|
||||
DirectX::SimpleMath::Vector3 pos;
|
||||
DirectX::SimpleMath::Vector3 velocity;
|
||||
DirectX::SimpleMath::Vector4 color;
|
||||
int room;
|
||||
float gravity;
|
||||
float life;
|
||||
float age;
|
||||
float height;
|
||||
bool active;
|
||||
};
|
||||
extern std::array<DripParticle, NUM_DRIPS> dripParticles;
|
||||
void UpdateDripParticles();
|
||||
void DisableDripParticles();
|
||||
DripParticle& getFreeDrip();
|
||||
void SpawnWetnessDrip(DirectX::SimpleMath::Vector3 pos, int room);
|
||||
void SpawnSplashDrips(Vector3 const & pos, int num, int room);
|
||||
void SpawnGunshellDrips(Vector3 const & pos, int room);
|
||||
}
|
||||
}
|
||||
}
|
||||
namespace TEN::Effects::Drip
|
||||
{
|
||||
constexpr float DRIP_LIFE = 25.0f;
|
||||
constexpr float DRIP_LIFE_LONG = 120.0f;
|
||||
constexpr float DRIP_WIDTH = 4;
|
||||
constexpr int NUM_DRIPS = 512;
|
||||
|
||||
struct DripParticle
|
||||
{
|
||||
Vector3 pos;
|
||||
Vector3 velocity;
|
||||
Vector4 color;
|
||||
int room;
|
||||
float gravity;
|
||||
float life;
|
||||
float age;
|
||||
float height;
|
||||
bool active;
|
||||
};
|
||||
extern std::array<DripParticle, NUM_DRIPS> dripParticles;
|
||||
|
||||
void UpdateDripParticles();
|
||||
void DisableDripParticles();
|
||||
DripParticle& getFreeDrip();
|
||||
void SpawnWetnessDrip(Vector3 pos, int room);
|
||||
void SpawnSplashDrips(Vector3 const& pos, int num, int room);
|
||||
void SpawnGunshellDrips(Vector3 const& pos, int room);
|
||||
}
|
||||
|
|
|
@ -9,80 +9,94 @@
|
|||
#include "Specific/trmath.h"
|
||||
|
||||
using namespace TEN::Math::Random;
|
||||
namespace TEN {
|
||||
namespace Effects {
|
||||
namespace Explosion {
|
||||
using namespace DirectX::SimpleMath;
|
||||
using namespace TEN::Effects::Spark;
|
||||
std::array<ExplosionParticle, 64> explosionParticles;
|
||||
constexpr float PARTICLE_DISTANCE = 512;
|
||||
void TriggerExplosion(Vector3 const& pos, float size, bool triggerSparks, bool triggerSmoke, bool triggerShockwave, int room)
|
||||
{
|
||||
SpawnExplosionParticle(pos);
|
||||
for (int i = 0; i < 3; i++) {
|
||||
Vector3 particlePos = pos + Vector3(GenerateFloat(-size / 2, size / 2), GenerateFloat(-size / 2, size / 2), GenerateFloat(-size / 2, size / 2));
|
||||
SpawnExplosionParticle(particlePos);
|
||||
}
|
||||
if (triggerSparks) {
|
||||
Vector3Int sparkPos;
|
||||
sparkPos.x = pos.x;
|
||||
sparkPos.y = pos.y;
|
||||
sparkPos.z = pos.z;
|
||||
//TriggerExplosionSparks(&sparkPos, room); @TODO
|
||||
}
|
||||
if (triggerShockwave) {
|
||||
PHD_3DPOS shockPos;
|
||||
shockPos.Position.x = pos.x;
|
||||
shockPos.Position.y = pos.y;
|
||||
shockPos.Position.z = pos.z;
|
||||
TriggerShockwave(&shockPos, 0, size, 64, 32, 32, 32, 30, rand() & 0xFFFF, 0);
|
||||
}
|
||||
}
|
||||
void UpdateExplosionParticles()
|
||||
{
|
||||
for (int i = 0; i < explosionParticles.size(); i++) {
|
||||
ExplosionParticle& e = explosionParticles[i];
|
||||
if (!e.active) continue;
|
||||
e.age++;
|
||||
if (e.age > e.life) {
|
||||
e.active = false;
|
||||
continue;
|
||||
};
|
||||
e.vel *= 0.98f;
|
||||
e.pos += e.vel;
|
||||
e.angularVel *= 0.98f;
|
||||
e.rotation += e.angularVel;
|
||||
int numSprites = -Objects[ID_EXPLOSION_SPRITES].nmeshes - 1;
|
||||
float normalizedAge = e.age / e.life;
|
||||
e.sprite = lerp(0, numSprites, normalizedAge);
|
||||
e.tint = Vector4::Lerp(Vector4(2, 2, 2, 1), Vector4(0, 0, 0, 0), normalizedAge);
|
||||
|
||||
}
|
||||
}
|
||||
ExplosionParticle& getFreeExplosionParticle()
|
||||
{
|
||||
for (int i = 0; i < explosionParticles.size(); i++)
|
||||
{
|
||||
if (!explosionParticles[i].active) {
|
||||
return explosionParticles[i];
|
||||
}
|
||||
}
|
||||
return explosionParticles[0];
|
||||
}
|
||||
void SpawnExplosionParticle(Vector3 const & pos)
|
||||
{
|
||||
ExplosionParticle& e = getFreeExplosionParticle();
|
||||
e = {};
|
||||
e.pos = pos;
|
||||
const float maxVel = 10;
|
||||
e.vel = Vector3(GenerateFloat(-maxVel / 2, maxVel / 2), GenerateFloat(-maxVel / 2, maxVel / 2), GenerateFloat(-maxVel / 2, maxVel / 2));
|
||||
e.active = true;
|
||||
e.tint = Vector4(1, 1, 1, 1);
|
||||
e.life = GenerateFloat(60, 90);
|
||||
e.size = GenerateFloat(512, 768);
|
||||
e.angularVel = GenerateFloat(-RADIAN, RADIAN);
|
||||
e.rotation = GenerateFloat(-0.05, 0.05);
|
||||
}
|
||||
namespace TEN::Effects::Explosion
|
||||
{
|
||||
using namespace DirectX::SimpleMath;
|
||||
using namespace TEN::Effects::Spark;
|
||||
|
||||
std::array<ExplosionParticle, 64> explosionParticles;
|
||||
|
||||
constexpr float PARTICLE_DISTANCE = 512;
|
||||
|
||||
void TriggerExplosion(Vector3 const& pos, float size, bool triggerSparks, bool triggerSmoke, bool triggerShockwave, int room)
|
||||
{
|
||||
SpawnExplosionParticle(pos);
|
||||
for (int i = 0; i < 3; i++)
|
||||
{
|
||||
Vector3 particlePos = pos + Vector3(GenerateFloat(-size / 2, size / 2), GenerateFloat(-size / 2, size / 2), GenerateFloat(-size / 2, size / 2));
|
||||
SpawnExplosionParticle(particlePos);
|
||||
}
|
||||
|
||||
if (triggerSparks)
|
||||
{
|
||||
Vector3Int sparkPos;
|
||||
sparkPos.x = pos.x;
|
||||
sparkPos.y = pos.y;
|
||||
sparkPos.z = pos.z;
|
||||
//TriggerExplosionSparks(&sparkPos, room); @TODO
|
||||
}
|
||||
|
||||
if (triggerShockwave)
|
||||
{
|
||||
PHD_3DPOS shockPos;
|
||||
shockPos.Position.x = pos.x;
|
||||
shockPos.Position.y = pos.y;
|
||||
shockPos.Position.z = pos.z;
|
||||
TriggerShockwave(&shockPos, 0, size, 64, 32, 32, 32, 30, rand() & 0xFFFF, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateExplosionParticles()
|
||||
{
|
||||
for (int i = 0; i < explosionParticles.size(); i++)
|
||||
{
|
||||
auto& e = explosionParticles[i];
|
||||
|
||||
if (!e.active)
|
||||
continue;
|
||||
|
||||
e.age++;
|
||||
if (e.age > e.life)
|
||||
{
|
||||
e.active = false;
|
||||
continue;
|
||||
};
|
||||
|
||||
e.vel *= 0.98f;
|
||||
e.pos += e.vel;
|
||||
e.angularVel *= 0.98f;
|
||||
e.rotation += e.angularVel;
|
||||
int numSprites = -Objects[ID_EXPLOSION_SPRITES].nmeshes - 1;
|
||||
float normalizedAge = e.age / e.life;
|
||||
e.sprite = lerp(0, numSprites, normalizedAge);
|
||||
e.tint = Vector4::Lerp(Vector4(2, 2, 2, 1), Vector4(0, 0, 0, 0), normalizedAge);
|
||||
}
|
||||
}
|
||||
|
||||
ExplosionParticle& getFreeExplosionParticle()
|
||||
{
|
||||
for (int i = 0; i < explosionParticles.size(); i++)
|
||||
{
|
||||
if (!explosionParticles[i].active)
|
||||
return explosionParticles[i];
|
||||
}
|
||||
|
||||
return explosionParticles[0];
|
||||
}
|
||||
|
||||
void SpawnExplosionParticle(Vector3 const & pos)
|
||||
{
|
||||
auto& e = getFreeExplosionParticle();
|
||||
e = {};
|
||||
e.pos = pos;
|
||||
const float maxVel = 10;
|
||||
e.vel = Vector3(GenerateFloat(-maxVel / 2, maxVel / 2), GenerateFloat(-maxVel / 2, maxVel / 2), GenerateFloat(-maxVel / 2, maxVel / 2));
|
||||
e.active = true;
|
||||
e.tint = Vector4(1, 1, 1, 1);
|
||||
e.life = GenerateFloat(60, 90);
|
||||
e.size = GenerateFloat(512, 768);
|
||||
e.angularVel = GenerateFloat(-RADIAN, RADIAN);
|
||||
e.rotation = GenerateFloat(-0.05, 0.05);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,27 +3,26 @@
|
|||
#include <d3d11.h>
|
||||
#include <SimpleMath.h>
|
||||
|
||||
namespace TEN {
|
||||
namespace Effects {
|
||||
namespace Explosion {
|
||||
struct ExplosionParticle {
|
||||
DirectX::SimpleMath::Vector3 pos;
|
||||
DirectX::SimpleMath::Vector3 vel;
|
||||
DirectX::SimpleMath::Vector4 tint;
|
||||
float size;
|
||||
float rotation;
|
||||
float angularVel;
|
||||
float age;
|
||||
float life;
|
||||
int room;
|
||||
int sprite;
|
||||
bool active;
|
||||
};
|
||||
extern std::array<ExplosionParticle, 64> explosionParticles;
|
||||
void TriggerExplosion(DirectX::SimpleMath::Vector3 const & pos, float size, bool triggerSparks, bool triggerSmoke, bool triggerShockwave, int room);
|
||||
void UpdateExplosionParticles();
|
||||
ExplosionParticle& getFreeExplosionParticle();
|
||||
void SpawnExplosionParticle(DirectX::SimpleMath::Vector3 const & pos);
|
||||
}
|
||||
}
|
||||
}
|
||||
namespace TEN::Effects::Explosion
|
||||
{
|
||||
struct ExplosionParticle
|
||||
{
|
||||
Vector3 pos;
|
||||
Vector3 vel;
|
||||
Vector4 tint;
|
||||
float size;
|
||||
float rotation;
|
||||
float angularVel;
|
||||
float age;
|
||||
float life;
|
||||
int room;
|
||||
int sprite;
|
||||
bool active;
|
||||
};
|
||||
extern std::array<ExplosionParticle, 64> explosionParticles;
|
||||
|
||||
void TriggerExplosion(Vector3 const& pos, float size, bool triggerSparks, bool triggerSmoke, bool triggerShockwave, int room);
|
||||
void UpdateExplosionParticles();
|
||||
ExplosionParticle& getFreeExplosionParticle();
|
||||
void SpawnExplosionParticle(Vector3 const& pos);
|
||||
}
|
||||
|
|
|
@ -9,10 +9,8 @@
|
|||
#include "Sound/sound.h"
|
||||
#include "Specific/level.h"
|
||||
|
||||
namespace TEN {
|
||||
namespace Effects {
|
||||
namespace Footprints {
|
||||
|
||||
namespace TEN::Effects::Footprints
|
||||
{
|
||||
std::deque<FOOTPRINT_STRUCT> footprints = std::deque<FOOTPRINT_STRUCT>();
|
||||
|
||||
bool CheckFootOnFloor(ItemInfo const & item, int mesh, Vector3& outFootprintPosition)
|
||||
|
@ -260,5 +258,3 @@ namespace Footprints {
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -4,12 +4,11 @@
|
|||
|
||||
struct ItemInfo;
|
||||
|
||||
namespace TEN{
|
||||
namespace Effects {
|
||||
namespace Footprints {
|
||||
|
||||
namespace TEN::Effects::Footprints
|
||||
{
|
||||
constexpr size_t MAX_FOOTPRINTS = 20;
|
||||
constexpr auto FOOTPRINT_SIZE = 64.0f;
|
||||
constexpr int FOOT_HEIGHT_OFFSET = 64;
|
||||
|
||||
struct FOOTPRINT_STRUCT
|
||||
{
|
||||
|
@ -21,12 +20,9 @@ namespace Footprints {
|
|||
float Opacity;
|
||||
bool Active;
|
||||
};
|
||||
|
||||
extern std::deque<FOOTPRINT_STRUCT> footprints;
|
||||
constexpr int FOOT_HEIGHT_OFFSET = 64;
|
||||
|
||||
bool CheckFootOnFloor(ItemInfo const & item, int mesh, Vector3& outFootprintPosition);
|
||||
void AddFootprint(ItemInfo* item, bool rightFoot);
|
||||
void UpdateFootprints();
|
||||
|
||||
}}}
|
||||
}
|
||||
|
|
|
@ -24,13 +24,13 @@ void InitialiseHair()
|
|||
{
|
||||
int* bone = &g_Level.Bones[Objects[ID_LARA_HAIR].boneIndex];
|
||||
|
||||
Hairs[h][0].initialized = true;
|
||||
Hairs[h][0].initialised = true;
|
||||
Hairs[h][0].pos.Orientation.y = 0;
|
||||
Hairs[h][0].pos.Orientation.x = -0x4000;
|
||||
|
||||
for (int i = 1; i < HAIR_SEGMENTS + 1; i++, bone += 4)
|
||||
{
|
||||
Hairs[h][i].initialized = true;
|
||||
Hairs[h][i].initialised = true;
|
||||
Hairs[h][i].pos.Position.x = *(bone + 1);
|
||||
Hairs[h][i].pos.Position.y = *(bone + 2);
|
||||
Hairs[h][i].pos.Position.z = *(bone + 3);
|
||||
|
@ -182,9 +182,9 @@ void HairControl(ItemInfo* item, int ponytail, ANIM_FRAME* framePtr)
|
|||
|
||||
int* bone = &g_Level.Bones[Objects[ID_LARA_HAIR].boneIndex];
|
||||
|
||||
if (Hairs[ponytail][0].initialized)
|
||||
if (Hairs[ponytail][0].initialised)
|
||||
{
|
||||
Hairs[ponytail][0].initialized = false;
|
||||
Hairs[ponytail][0].initialised = false;
|
||||
Hairs[ponytail][0].pos.Position.x = pos.x;
|
||||
Hairs[ponytail][0].pos.Position.y = pos.y;
|
||||
Hairs[ponytail][0].pos.Position.z = pos.z;
|
||||
|
@ -195,7 +195,7 @@ void HairControl(ItemInfo* item, int ponytail, ANIM_FRAME* framePtr)
|
|||
world = Matrix::CreateFromYawPitchRoll(TO_RAD(Hairs[ponytail][i].pos.Orientation.y), TO_RAD(Hairs[ponytail][i].pos.Orientation.x), 0) * world;
|
||||
world = Matrix::CreateTranslation(*(bone + 1), *(bone + 2), *(bone + 3)) * world;
|
||||
|
||||
Hairs[ponytail][i + 1].initialized = false;
|
||||
Hairs[ponytail][i + 1].initialised = false;
|
||||
Hairs[ponytail][i + 1].pos.Position.x = world.Translation().x;
|
||||
Hairs[ponytail][i + 1].pos.Position.y = world.Translation().y;
|
||||
Hairs[ponytail][i + 1].pos.Position.z = world.Translation().z;
|
||||
|
|
|
@ -14,7 +14,7 @@ struct HAIR_STRUCT
|
|||
Vector3Int hvel;
|
||||
Vector3Int unknown;
|
||||
|
||||
bool initialized = false;
|
||||
bool initialised = false;
|
||||
};
|
||||
extern HAIR_STRUCT Hairs[HAIR_MAX][HAIR_SEGMENTS + 1];
|
||||
|
||||
|
|
|
@ -7,4 +7,4 @@ namespace TEN::Effects::Lara
|
|||
void LaraBurn(ItemInfo* item);
|
||||
void LavaBurn(ItemInfo* item);
|
||||
void LaraBreath(ItemInfo* item);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -43,14 +43,13 @@ namespace TEN::Effects::Lightning
|
|||
int type;
|
||||
int sLife;
|
||||
};
|
||||
extern std::vector<LIGHTNING_INFO> Lightning;
|
||||
|
||||
extern int LightningRandomSeed;
|
||||
extern float FloatSinCosTable[8192];
|
||||
extern Vector3Int LightningPos[6];
|
||||
extern short LightningBuffer[1024];
|
||||
|
||||
extern std::vector<LIGHTNING_INFO> Lightning;
|
||||
|
||||
void InitialiseFloatSinCosTable();
|
||||
void UpdateLightning();
|
||||
void TriggerLightning(Vector3Int* src, Vector3Int* dest, char amplitude, byte r, byte g, byte b, byte life, char flags, char width, char segments);
|
||||
|
|
|
@ -6,8 +6,11 @@
|
|||
#include "Objects\objectslist.h"
|
||||
|
||||
struct ItemInfo;
|
||||
namespace TEN::Effects{
|
||||
struct SimpleParticle {
|
||||
|
||||
namespace TEN::Effects
|
||||
{
|
||||
struct SimpleParticle
|
||||
{
|
||||
DirectX::SimpleMath::Vector3 worldPosition;
|
||||
float size;
|
||||
float age;
|
||||
|
@ -24,4 +27,4 @@ namespace TEN::Effects{
|
|||
void TriggerSnowmobileSnow(ItemInfo* snowMobile);
|
||||
void TriggerSpeedboatFoam(ItemInfo* boat, Vector3 offset);
|
||||
void updateSimpleParticles();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,252 +16,246 @@
|
|||
using namespace TEN::Effects::Environment;
|
||||
using namespace TEN::Math::Random;
|
||||
|
||||
namespace TEN
|
||||
namespace TEN::Effects::Smoke
|
||||
{
|
||||
namespace Effects
|
||||
std::array<SmokeParticle, 128> SmokeParticles;
|
||||
|
||||
auto& GetFreeSmokeParticle()
|
||||
{
|
||||
namespace Smoke
|
||||
for (int i = 0; i < SmokeParticles.size(); i++)
|
||||
{
|
||||
std::array<SmokeParticle, 128> SmokeParticles;
|
||||
if (!SmokeParticles[i].active)
|
||||
return SmokeParticles[i];
|
||||
}
|
||||
|
||||
auto& GetFreeSmokeParticle()
|
||||
return SmokeParticles[0];
|
||||
}
|
||||
|
||||
void DisableSmokeParticles()
|
||||
{
|
||||
for (int i = 0; i < SmokeParticles.size(); i++)
|
||||
SmokeParticles[i].active = false;
|
||||
}
|
||||
|
||||
void UpdateSmokeParticles()
|
||||
{
|
||||
for (int i = 0; i < SmokeParticles.size(); i++)
|
||||
{
|
||||
auto& s = SmokeParticles[i];
|
||||
|
||||
if (!s.active)
|
||||
continue;
|
||||
|
||||
s.age += 1;
|
||||
if (s.age > s.life)
|
||||
{
|
||||
for (int i = 0; i < SmokeParticles.size(); i++)
|
||||
{
|
||||
if (!SmokeParticles[i].active)
|
||||
return SmokeParticles[i];
|
||||
}
|
||||
|
||||
return SmokeParticles[0];
|
||||
s.active = false;
|
||||
continue;
|
||||
}
|
||||
|
||||
void DisableSmokeParticles()
|
||||
s.velocity.y += s.gravity;
|
||||
|
||||
if (s.terminalVelocity != 0)
|
||||
{
|
||||
for (int i = 0; i < SmokeParticles.size(); i++)
|
||||
SmokeParticles[i].active = false;
|
||||
float velocityLength = s.velocity.Length();
|
||||
|
||||
if (velocityLength > s.terminalVelocity)
|
||||
s.velocity *= (s.terminalVelocity / velocityLength);
|
||||
}
|
||||
|
||||
void UpdateSmokeParticles()
|
||||
s.position += s.velocity;
|
||||
|
||||
if (s.affectedByWind)
|
||||
{
|
||||
for (int i = 0; i < SmokeParticles.size(); i++)
|
||||
if (TestEnvironment(ENV_FLAG_WIND, s.room))
|
||||
{
|
||||
auto& s = SmokeParticles[i];
|
||||
|
||||
if (!s.active)
|
||||
continue;
|
||||
|
||||
s.age += 1;
|
||||
if (s.age > s.life)
|
||||
{
|
||||
s.active = false;
|
||||
continue;
|
||||
}
|
||||
|
||||
s.velocity.y += s.gravity;
|
||||
|
||||
if (s.terminalVelocity != 0)
|
||||
{
|
||||
float velocityLength = s.velocity.Length();
|
||||
|
||||
if (velocityLength > s.terminalVelocity)
|
||||
s.velocity *= (s.terminalVelocity / velocityLength);
|
||||
}
|
||||
|
||||
s.position += s.velocity;
|
||||
|
||||
if (s.affectedByWind)
|
||||
{
|
||||
if (TestEnvironment(ENV_FLAG_WIND, s.room))
|
||||
{
|
||||
s.position.x += Weather.Wind().x;
|
||||
s.position.z += Weather.Wind().z;
|
||||
}
|
||||
}
|
||||
|
||||
float normalizedLife = std::clamp(s.age / s.life,0.0f,1.0f);
|
||||
s.size = lerp(s.sourceSize, s.destinationSize, normalizedLife);
|
||||
s.angularVelocity *= s.angularDrag;
|
||||
s.rotation += s.angularVelocity;
|
||||
s.color = DirectX::SimpleMath::Vector4::Lerp(s.sourceColor, s.destinationColor, normalizedLife);
|
||||
int numSprites = -Objects[ID_SMOKE_SPRITES].nmeshes;
|
||||
s.sprite = lerp(0, numSprites - 1, normalizedLife);
|
||||
s.position.x += Weather.Wind().x;
|
||||
s.position.z += Weather.Wind().z;
|
||||
}
|
||||
}
|
||||
|
||||
void TriggerFlareSmoke(const DirectX::SimpleMath::Vector3& pos, DirectX::SimpleMath::Vector3& direction, int life, int room)
|
||||
float normalizedLife = std::clamp(s.age / s.life,0.0f,1.0f);
|
||||
s.size = lerp(s.sourceSize, s.destinationSize, normalizedLife);
|
||||
s.angularVelocity *= s.angularDrag;
|
||||
s.rotation += s.angularVelocity;
|
||||
s.color = DirectX::SimpleMath::Vector4::Lerp(s.sourceColor, s.destinationColor, normalizedLife);
|
||||
int numSprites = -Objects[ID_SMOKE_SPRITES].nmeshes;
|
||||
s.sprite = lerp(0, numSprites - 1, normalizedLife);
|
||||
}
|
||||
}
|
||||
|
||||
void TriggerFlareSmoke(const DirectX::SimpleMath::Vector3& pos, DirectX::SimpleMath::Vector3& direction, int life, int room)
|
||||
{
|
||||
using namespace DirectX::SimpleMath;
|
||||
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.position = pos;
|
||||
s.age = 0;
|
||||
constexpr float d = 0.2f;
|
||||
|
||||
Vector3 randomDir = Vector3(GenerateFloat(-d, d), GenerateFloat(-d, d), GenerateFloat(-d, d));
|
||||
Vector3 direction2;
|
||||
(direction + randomDir).Normalize(direction2);
|
||||
|
||||
s.velocity = direction2 * GenerateFloat(7, 9);
|
||||
s.gravity = -0.2f;
|
||||
s.friction = GenerateFloat(0.7f, 0.85f);
|
||||
s.sourceColor = Vector4(1, 131 / 255.0f, 100 / 255.0f, 1);
|
||||
s.destinationColor = Vector4(1, 1, 1, 0);
|
||||
s.life = GenerateFloat(25, 35);
|
||||
s.angularVelocity = GenerateFloat(-0.3f, 0.3f);
|
||||
s.angularDrag = 0.97f;
|
||||
s.sourceSize = life > 4 ? GenerateFloat(16, 24) : GenerateFloat(100, 128);
|
||||
s.destinationSize = life > 4 ? GenerateFloat(160, 200) : GenerateFloat(256, 300);
|
||||
s.affectedByWind = true;
|
||||
s.active = true;
|
||||
s.room = room;
|
||||
}
|
||||
|
||||
//TODO: add additional "Weapon Special" param or something. Currently initial == 2 means Rocket Launcher backwards smoke.
|
||||
//TODO: Refactor different weapon types out of it
|
||||
void TriggerGunSmokeParticles(int x, int y, int z, int xv, int yv, int zv, byte initial, LaraWeaponType weaponType, byte count)
|
||||
{
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.active = true;
|
||||
s.position = Vector3(x, y, z);
|
||||
|
||||
Vector3 direction = Vector3(xv, yv, zv);
|
||||
direction.Normalize();
|
||||
|
||||
s.velocity = direction;
|
||||
s.gravity = -.1f;
|
||||
s.affectedByWind = TestEnvironment(ENV_FLAG_WIND, LaraItem);
|
||||
s.sourceColor = Vector4(.4, .4, .4, 1);
|
||||
s.destinationColor = Vector4(0, 0, 0, 0);
|
||||
|
||||
if (initial)
|
||||
{
|
||||
if (weaponType == LaraWeaponType::RocketLauncher)
|
||||
{
|
||||
using namespace DirectX::SimpleMath;
|
||||
float size = GenerateFloat(48, 80);
|
||||
s.sourceSize = size * 2;
|
||||
s.destinationSize = size * 8;
|
||||
s.sourceColor = {0.75,0.75,1,1};
|
||||
s.terminalVelocity = 0;
|
||||
s.friction = 0.82f;
|
||||
s.life = GenerateFloat(60, 90);
|
||||
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.position = pos;
|
||||
s.age = 0;
|
||||
constexpr float d = 0.2f;
|
||||
|
||||
Vector3 randomDir = Vector3(GenerateFloat(-d, d), GenerateFloat(-d, d), GenerateFloat(-d, d));
|
||||
Vector3 direction2;
|
||||
(direction + randomDir).Normalize(direction2);
|
||||
|
||||
s.velocity = direction2 * GenerateFloat(7, 9);
|
||||
s.gravity = -0.2f;
|
||||
s.friction = GenerateFloat(0.7f, 0.85f);
|
||||
s.sourceColor = Vector4(1, 131 / 255.0f, 100 / 255.0f, 1);
|
||||
s.destinationColor = Vector4(1, 1, 1, 0);
|
||||
s.life = GenerateFloat(25, 35);
|
||||
s.angularVelocity = GenerateFloat(-0.3f, 0.3f);
|
||||
s.angularDrag = 0.97f;
|
||||
s.sourceSize = life > 4 ? GenerateFloat(16, 24) : GenerateFloat(100, 128);
|
||||
s.destinationSize = life > 4 ? GenerateFloat(160, 200) : GenerateFloat(256, 300);
|
||||
s.affectedByWind = true;
|
||||
s.active = true;
|
||||
s.room = room;
|
||||
}
|
||||
|
||||
//TODO: add additional "Weapon Special" param or something. Currently initial == 2 means Rocket Launcher backwards smoke.
|
||||
//TODO: Refactor different weapon types out of it
|
||||
void TriggerGunSmokeParticles(int x, int y, int z, int xv, int yv, int zv, byte initial, LaraWeaponType weaponType, byte count)
|
||||
{
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.active = true;
|
||||
s.position = Vector3(x, y, z);
|
||||
|
||||
Vector3 direction = Vector3(xv, yv, zv);
|
||||
direction.Normalize();
|
||||
|
||||
s.velocity = direction;
|
||||
s.gravity = -.1f;
|
||||
s.affectedByWind = TestEnvironment(ENV_FLAG_WIND, LaraItem);
|
||||
s.sourceColor = Vector4(.4, .4, .4, 1);
|
||||
s.destinationColor = Vector4(0, 0, 0, 0);
|
||||
|
||||
if (initial)
|
||||
if (initial == 1)
|
||||
{
|
||||
if (weaponType == LaraWeaponType::RocketLauncher)
|
||||
{
|
||||
float size = GenerateFloat(48, 80);
|
||||
s.sourceSize = size * 2;
|
||||
s.destinationSize = size * 8;
|
||||
s.sourceColor = {0.75,0.75,1,1};
|
||||
s.terminalVelocity = 0;
|
||||
s.friction = 0.82f;
|
||||
s.life = GenerateFloat(60, 90);
|
||||
|
||||
if (initial == 1)
|
||||
{
|
||||
float size = GenerateFloat(48, 80);
|
||||
s.sourceSize = size * 2;
|
||||
s.destinationSize = size * 16;
|
||||
s.velocity = getRandomVectorInCone(direction,25);
|
||||
s.velocity *= GenerateFloat(0, 32);
|
||||
}
|
||||
else
|
||||
{
|
||||
float size = GenerateFloat(48, 80);
|
||||
s.sourceSize = size;
|
||||
s.destinationSize = size * 8;
|
||||
s.velocity = getRandomVectorInCone(direction,3);
|
||||
s.velocity *= GenerateFloat(0, 16);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
float size = GenerateFloat(48, 73);
|
||||
s.sourceSize = size * 2;
|
||||
s.destinationSize = size * 8;
|
||||
s.terminalVelocity = 0;
|
||||
s.friction = 0.88f;
|
||||
s.life = GenerateFloat(60, 90);
|
||||
s.velocity = getRandomVectorInCone(direction, 10);
|
||||
s.velocity *= GenerateFloat(16, 30);
|
||||
}
|
||||
float size = GenerateFloat(48, 80);
|
||||
s.sourceSize = size * 2;
|
||||
s.destinationSize = size * 16;
|
||||
s.velocity = getRandomVectorInCone(direction,25);
|
||||
s.velocity *= GenerateFloat(0, 32);
|
||||
}
|
||||
else
|
||||
{
|
||||
float size = (float)((GetRandomControl() & 0x0F) + 48); // -TriggerGunSmoke_SubFunction(weaponType);
|
||||
|
||||
if (weaponType == LaraWeaponType::RocketLauncher)
|
||||
s.sourceColor = {0.75,0.75,1,1};
|
||||
|
||||
s.sourceSize = size / 2;
|
||||
s.destinationSize = size * 4;
|
||||
s.terminalVelocity = 0;
|
||||
s.friction = 0.97f;
|
||||
s.life = GenerateFloat(42, 62);
|
||||
s.velocity *= GenerateFloat(16, 40);
|
||||
float size = GenerateFloat(48, 80);
|
||||
s.sourceSize = size;
|
||||
s.destinationSize = size * 8;
|
||||
s.velocity = getRandomVectorInCone(direction,3);
|
||||
s.velocity *= GenerateFloat(0, 16);
|
||||
}
|
||||
|
||||
s.position = Vector3(x, y, z);
|
||||
s.position += Vector3(GenerateFloat(-8, 8), GenerateFloat(-8, 8), GenerateFloat(-8, 8));
|
||||
s.angularVelocity = GenerateFloat(-PI / 4, PI / 4);
|
||||
s.angularDrag = 0.95f;
|
||||
s.room = LaraItem->RoomNumber;
|
||||
}
|
||||
|
||||
void TriggerQuadExhaustSmoke(int x, int y, int z, short angle, int velocity, int moving)
|
||||
else
|
||||
{
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.position = Vector3(x, y, z) + Vector3(GenerateFloat(8, 16), GenerateFloat(8, 16), GenerateFloat(8, 16));
|
||||
|
||||
float xVel = std::sin(TO_RAD(angle)) * velocity;
|
||||
float zVel = std::cos(TO_RAD(angle)) * velocity;
|
||||
|
||||
s.velocity = Vector3(xVel, GenerateFloat(-1, 4), zVel);
|
||||
s.sourceColor = Vector4(1, 1, 1, 1);
|
||||
s.destinationColor = Vector4(0, 0, 0, 0);
|
||||
s.sourceSize = GenerateFloat(8,24);
|
||||
s.active = true;
|
||||
s.affectedByWind = true;
|
||||
s.friction = 0.999f;
|
||||
s.gravity = -0.1f;
|
||||
s.life = GenerateFloat(16, 24);
|
||||
s.destinationSize = GenerateFloat(128, 160);
|
||||
s.angularVelocity = GenerateFloat(-1, 1);
|
||||
s.angularDrag = GenerateFloat(0.97, 0.999);
|
||||
}
|
||||
|
||||
void TriggerRocketSmoke(int x, int y, int z, int bodyPart)
|
||||
{
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.position = Vector3(x, y, z) + Vector3(GenerateFloat(8, 16), GenerateFloat(8, 16), GenerateFloat(8, 16));
|
||||
s.sourceColor = Vector4(0.8, 0.8, 1, 1);
|
||||
s.destinationColor = Vector4(0, 0, 0, 0);
|
||||
s.sourceSize = GenerateFloat(32, 64);
|
||||
s.active = true;
|
||||
s.velocity = getRandomVector() * GenerateFloat(1, 3);
|
||||
s.affectedByWind = true;
|
||||
s.friction = 0.979f;
|
||||
s.gravity = -0.1f;
|
||||
s.life = GenerateFloat(80, 120);
|
||||
s.destinationSize = GenerateFloat(1024, 1152);
|
||||
s.angularVelocity = GenerateFloat(-0.6, 0.6);
|
||||
s.angularDrag = GenerateFloat(0.87, 0.99);
|
||||
}
|
||||
|
||||
void TriggerBreathSmoke(long x, long y, long z, short angle)
|
||||
{
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.position = Vector3(x, y, z) + Vector3(GenerateFloat(8, 16), GenerateFloat(8, 16), GenerateFloat(8, 16));
|
||||
|
||||
float xVel = std::sin(TO_RAD(angle)) * GenerateFloat(8, 12);
|
||||
float zVel = std::cos(TO_RAD(angle)) * GenerateFloat(8, 12);
|
||||
|
||||
s.velocity = Vector3(xVel, 0, zVel);
|
||||
s.sourceColor = Vector4(1, 1, 1, 0.7f);
|
||||
s.destinationColor = Vector4(1, 1, 1, 0);
|
||||
s.sourceSize = GenerateFloat(8, 24);
|
||||
s.active = true;
|
||||
s.affectedByWind = true;
|
||||
s.friction = 0.999f;
|
||||
s.gravity = -0.1f;
|
||||
s.life = GenerateFloat(12, 20);
|
||||
s.destinationSize = GenerateFloat(128, 160);
|
||||
s.angularVelocity = GenerateFloat(-0.5f, 0.5f);
|
||||
s.angularDrag = GenerateFloat(0.95f, 0.95f);
|
||||
float size = GenerateFloat(48, 73);
|
||||
s.sourceSize = size * 2;
|
||||
s.destinationSize = size * 8;
|
||||
s.terminalVelocity = 0;
|
||||
s.friction = 0.88f;
|
||||
s.life = GenerateFloat(60, 90);
|
||||
s.velocity = getRandomVectorInCone(direction, 10);
|
||||
s.velocity *= GenerateFloat(16, 30);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
float size = (float)((GetRandomControl() & 0x0F) + 48); // -TriggerGunSmoke_SubFunction(weaponType);
|
||||
|
||||
if (weaponType == LaraWeaponType::RocketLauncher)
|
||||
s.sourceColor = {0.75,0.75,1,1};
|
||||
|
||||
s.sourceSize = size / 2;
|
||||
s.destinationSize = size * 4;
|
||||
s.terminalVelocity = 0;
|
||||
s.friction = 0.97f;
|
||||
s.life = GenerateFloat(42, 62);
|
||||
s.velocity *= GenerateFloat(16, 40);
|
||||
}
|
||||
|
||||
s.position = Vector3(x, y, z);
|
||||
s.position += Vector3(GenerateFloat(-8, 8), GenerateFloat(-8, 8), GenerateFloat(-8, 8));
|
||||
s.angularVelocity = GenerateFloat(-PI / 4, PI / 4);
|
||||
s.angularDrag = 0.95f;
|
||||
s.room = LaraItem->RoomNumber;
|
||||
}
|
||||
|
||||
void TriggerQuadExhaustSmoke(int x, int y, int z, short angle, int velocity, int moving)
|
||||
{
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.position = Vector3(x, y, z) + Vector3(GenerateFloat(8, 16), GenerateFloat(8, 16), GenerateFloat(8, 16));
|
||||
|
||||
float xVel = std::sin(TO_RAD(angle)) * velocity;
|
||||
float zVel = std::cos(TO_RAD(angle)) * velocity;
|
||||
|
||||
s.velocity = Vector3(xVel, GenerateFloat(-1, 4), zVel);
|
||||
s.sourceColor = Vector4(1, 1, 1, 1);
|
||||
s.destinationColor = Vector4(0, 0, 0, 0);
|
||||
s.sourceSize = GenerateFloat(8,24);
|
||||
s.active = true;
|
||||
s.affectedByWind = true;
|
||||
s.friction = 0.999f;
|
||||
s.gravity = -0.1f;
|
||||
s.life = GenerateFloat(16, 24);
|
||||
s.destinationSize = GenerateFloat(128, 160);
|
||||
s.angularVelocity = GenerateFloat(-1, 1);
|
||||
s.angularDrag = GenerateFloat(0.97, 0.999);
|
||||
}
|
||||
|
||||
void TriggerRocketSmoke(int x, int y, int z, int bodyPart)
|
||||
{
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.position = Vector3(x, y, z) + Vector3(GenerateFloat(8, 16), GenerateFloat(8, 16), GenerateFloat(8, 16));
|
||||
s.sourceColor = Vector4(0.8, 0.8, 1, 1);
|
||||
s.destinationColor = Vector4(0, 0, 0, 0);
|
||||
s.sourceSize = GenerateFloat(32, 64);
|
||||
s.active = true;
|
||||
s.velocity = getRandomVector() * GenerateFloat(1, 3);
|
||||
s.affectedByWind = true;
|
||||
s.friction = 0.979f;
|
||||
s.gravity = -0.1f;
|
||||
s.life = GenerateFloat(80, 120);
|
||||
s.destinationSize = GenerateFloat(1024, 1152);
|
||||
s.angularVelocity = GenerateFloat(-0.6, 0.6);
|
||||
s.angularDrag = GenerateFloat(0.87, 0.99);
|
||||
}
|
||||
|
||||
void TriggerBreathSmoke(long x, long y, long z, short angle)
|
||||
{
|
||||
auto& s = GetFreeSmokeParticle();
|
||||
s = {};
|
||||
s.position = Vector3(x, y, z) + Vector3(GenerateFloat(8, 16), GenerateFloat(8, 16), GenerateFloat(8, 16));
|
||||
|
||||
float xVel = std::sin(TO_RAD(angle)) * GenerateFloat(8, 12);
|
||||
float zVel = std::cos(TO_RAD(angle)) * GenerateFloat(8, 12);
|
||||
|
||||
s.velocity = Vector3(xVel, 0, zVel);
|
||||
s.sourceColor = Vector4(1, 1, 1, 0.7f);
|
||||
s.destinationColor = Vector4(1, 1, 1, 0);
|
||||
s.sourceSize = GenerateFloat(8, 24);
|
||||
s.active = true;
|
||||
s.affectedByWind = true;
|
||||
s.friction = 0.999f;
|
||||
s.gravity = -0.1f;
|
||||
s.life = GenerateFloat(12, 20);
|
||||
s.destinationSize = GenerateFloat(128, 160);
|
||||
s.angularVelocity = GenerateFloat(-0.5f, 0.5f);
|
||||
s.angularDrag = GenerateFloat(0.95f, 0.95f);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,45 +6,38 @@
|
|||
struct ItemInfo;
|
||||
enum class LaraWeaponType;
|
||||
|
||||
namespace TEN
|
||||
namespace TEN::Effects::Smoke
|
||||
{
|
||||
namespace Effects
|
||||
struct SmokeParticle
|
||||
{
|
||||
namespace Smoke
|
||||
{
|
||||
struct SmokeParticle
|
||||
{
|
||||
DirectX::SimpleMath::Vector4 sourceColor;
|
||||
DirectX::SimpleMath::Vector4 destinationColor;
|
||||
DirectX::SimpleMath::Vector4 color;
|
||||
DirectX::SimpleMath::Vector3 position;
|
||||
DirectX::SimpleMath::Vector3 velocity;
|
||||
int room;
|
||||
int sprite;
|
||||
float gravity;
|
||||
float friction;
|
||||
float sourceSize;
|
||||
float destinationSize;
|
||||
float size;
|
||||
float age;
|
||||
float life;
|
||||
float angularVelocity;
|
||||
float angularDrag;
|
||||
float rotation;
|
||||
float terminalVelocity;
|
||||
bool affectedByWind;
|
||||
bool active;
|
||||
};
|
||||
Vector4 sourceColor;
|
||||
Vector4 destinationColor;
|
||||
Vector4 color;
|
||||
Vector3 position;
|
||||
Vector3 velocity;
|
||||
int room;
|
||||
int sprite;
|
||||
float gravity;
|
||||
float friction;
|
||||
float sourceSize;
|
||||
float destinationSize;
|
||||
float size;
|
||||
float age;
|
||||
float life;
|
||||
float angularVelocity;
|
||||
float angularDrag;
|
||||
float rotation;
|
||||
float terminalVelocity;
|
||||
bool affectedByWind;
|
||||
bool active;
|
||||
};
|
||||
extern std::array<SmokeParticle, 128> SmokeParticles;
|
||||
|
||||
extern std::array<SmokeParticle, 128> SmokeParticles;
|
||||
|
||||
void UpdateSmokeParticles();
|
||||
void DisableSmokeParticles();
|
||||
void TriggerFlareSmoke(const DirectX::SimpleMath::Vector3& pos, DirectX::SimpleMath::Vector3& direction, int life, int room);
|
||||
void TriggerGunSmokeParticles(int x, int y, int z, int xv, int yv, int zv, byte initial, LaraWeaponType weaponType, byte count);
|
||||
void TriggerQuadExhaustSmoke(int x, int y, int z, short angle, int velocity, int moving);
|
||||
void TriggerRocketSmoke(int x, int y, int z, int bodyPart);
|
||||
void TriggerBreathSmoke(long x, long y, long z, short angle);
|
||||
}
|
||||
}
|
||||
void UpdateSmokeParticles();
|
||||
void DisableSmokeParticles();
|
||||
void TriggerFlareSmoke(const Vector3& pos, Vector3& direction, int life, int room);
|
||||
void TriggerGunSmokeParticles(int x, int y, int z, int xv, int yv, int zv, byte initial, LaraWeaponType weaponType, byte count);
|
||||
void TriggerQuadExhaustSmoke(int x, int y, int z, short angle, int velocity, int moving);
|
||||
void TriggerRocketSmoke(int x, int y, int z, int bodyPart);
|
||||
void TriggerBreathSmoke(long x, long y, long z, short angle);
|
||||
}
|
||||
|
|
|
@ -9,108 +9,110 @@
|
|||
using namespace DirectX::SimpleMath;
|
||||
using namespace TEN::Math::Random;
|
||||
|
||||
namespace TEN {
|
||||
namespace Effects {
|
||||
namespace Spark {
|
||||
std::array<SparkParticle, 128> SparkParticles;
|
||||
void UpdateSparkParticles()
|
||||
namespace TEN::Effects::Spark
|
||||
{
|
||||
std::array<SparkParticle, 128> SparkParticles;
|
||||
void UpdateSparkParticles()
|
||||
{
|
||||
for (int i = 0; i < SparkParticles.size(); i++)
|
||||
{
|
||||
auto& s = SparkParticles[i];
|
||||
|
||||
if (!s.active)
|
||||
continue;
|
||||
|
||||
s.age += 1;
|
||||
if (s.age > s.life)
|
||||
{
|
||||
for (int i = 0; i < SparkParticles.size(); i++) {
|
||||
SparkParticle& s = SparkParticles[i];
|
||||
if (!s.active)continue;
|
||||
s.age += 1;
|
||||
if (s.age > s.life) {
|
||||
s.active = false;
|
||||
continue;
|
||||
}
|
||||
s.velocity.y += s.gravity;
|
||||
s.velocity *= s.friction;
|
||||
s.pos += s.velocity;
|
||||
}
|
||||
s.active = false;
|
||||
continue;
|
||||
}
|
||||
|
||||
SparkParticle& GetFreeSparkParticle()
|
||||
{
|
||||
for (int i = 0; i < SparkParticles.size(); i++)
|
||||
{
|
||||
if (!SparkParticles[i].active) {
|
||||
return SparkParticles[i];
|
||||
}
|
||||
}
|
||||
return SparkParticles[0];
|
||||
}
|
||||
s.velocity.y += s.gravity;
|
||||
s.velocity *= s.friction;
|
||||
s.pos += s.velocity;
|
||||
}
|
||||
}
|
||||
|
||||
void TriggerFlareSparkParticles(Vector3Int* pos, Vector3Int* vel, CVECTOR* color, int room)
|
||||
{
|
||||
SparkParticle& s = GetFreeSparkParticle();
|
||||
s = {};
|
||||
s.age = 0;
|
||||
s.life = GenerateFloat(10, 20);
|
||||
s.friction = 0.98f;
|
||||
s.gravity = 1.2f;
|
||||
s.width = 8.0f;
|
||||
s.height = 48.0f;
|
||||
s.room = room;
|
||||
s.pos = Vector3(pos->x, pos->y, pos->z);
|
||||
Vector3 v = Vector3(vel->x, vel->y, vel->z);
|
||||
v += Vector3(GenerateFloat(-64, 64), GenerateFloat(-64, 64), GenerateFloat(-64, 64));
|
||||
v.Normalize(v);
|
||||
s.velocity = v *GenerateFloat(17,24);
|
||||
s.sourceColor = Vector4(1, 1, 1, 1);
|
||||
s.destinationColor = Vector4(color->r/255.0f,color->g/255.0f,color->b/255.0f,1);
|
||||
s.active = true;
|
||||
}
|
||||
SparkParticle& GetFreeSparkParticle()
|
||||
{
|
||||
for (int i = 0; i < SparkParticles.size(); i++)
|
||||
{
|
||||
if (!SparkParticles[i].active)
|
||||
return SparkParticles[i];
|
||||
}
|
||||
|
||||
void TriggerRicochetSpark(GameVector* pos, short angle, int num)
|
||||
{
|
||||
for (int i = 0; i < num; i++)
|
||||
{
|
||||
SparkParticle& s = GetFreeSparkParticle();
|
||||
s = {};
|
||||
s.age = 0;
|
||||
s.life = GenerateFloat(10, 20);
|
||||
s.friction = 0.98f;
|
||||
s.gravity = 1.2f;
|
||||
s.width = 8.0f;
|
||||
s.height = 64.0f;
|
||||
s.room = pos->roomNumber;
|
||||
s.pos = Vector3(pos->x, pos->y, pos->z);
|
||||
float ang = TO_RAD(angle);
|
||||
Vector3 v = Vector3(sin(ang + GenerateFloat(-PI / 2, PI / 2)), GenerateFloat(-1, 1), cos(ang + GenerateFloat(-PI / 2, PI / 2)));
|
||||
v += Vector3(GenerateFloat(-64, 64), GenerateFloat(-64, 64), GenerateFloat(-64, 64));
|
||||
v.Normalize(v);
|
||||
s.velocity = v * GenerateFloat(17, 24);
|
||||
s.sourceColor = Vector4(1, 0.8, 0.2f, 1) * 3;
|
||||
s.destinationColor = Vector4(0, 0, 0, 0);
|
||||
s.active = true;
|
||||
}
|
||||
}
|
||||
return SparkParticles[0];
|
||||
}
|
||||
|
||||
void TriggerFrictionSpark(GameVector* pos, Vector3Shrt angle, float length, int num)
|
||||
{
|
||||
for (int i = 0; i < num; i++)
|
||||
{
|
||||
SparkParticle& s = GetFreeSparkParticle();
|
||||
s = {};
|
||||
s.age = 0;
|
||||
s.life = GenerateFloat(8, 15);
|
||||
s.friction = 0.1f;
|
||||
s.gravity = 0.0f;
|
||||
s.height = length;
|
||||
s.width = GenerateFloat(16.0f, 32.0f);
|
||||
s.room = pos->roomNumber;
|
||||
s.pos = Vector3(pos->x + GenerateFloat(-16, 16), pos->y + GenerateFloat(-16, 16), pos->z + GenerateFloat(-16, 16));
|
||||
float ang = TO_RAD(angle.y);
|
||||
float vAng = -TO_RAD(angle.x);
|
||||
Vector3 v = Vector3(sin(ang), vAng + GenerateFloat(-PI / 16, PI / 16), cos(ang));
|
||||
v.Normalize(v);
|
||||
s.velocity = v * GenerateFloat(32, 64);
|
||||
s.sourceColor = Vector4(1, 0.7, 0.4f, 1) * 3;
|
||||
s.destinationColor = Vector4(0.4f, 0.1f, 0, 0.5f);
|
||||
s.active = true;
|
||||
}
|
||||
}
|
||||
void TriggerFlareSparkParticles(Vector3Int* pos, Vector3Int* vel, CVECTOR* color, int room)
|
||||
{
|
||||
auto& s = GetFreeSparkParticle();
|
||||
s = {};
|
||||
s.age = 0;
|
||||
s.life = GenerateFloat(10, 20);
|
||||
s.friction = 0.98f;
|
||||
s.gravity = 1.2f;
|
||||
s.width = 8.0f;
|
||||
s.height = 48.0f;
|
||||
s.room = room;
|
||||
s.pos = Vector3(pos->x, pos->y, pos->z);
|
||||
Vector3 v = Vector3(vel->x, vel->y, vel->z);
|
||||
v += Vector3(GenerateFloat(-64, 64), GenerateFloat(-64, 64), GenerateFloat(-64, 64));
|
||||
v.Normalize(v);
|
||||
s.velocity = v *GenerateFloat(17,24);
|
||||
s.sourceColor = Vector4(1, 1, 1, 1);
|
||||
s.destinationColor = Vector4(color->r/255.0f,color->g/255.0f,color->b/255.0f,1);
|
||||
s.active = true;
|
||||
}
|
||||
|
||||
void TriggerRicochetSpark(GameVector* pos, short angle, int num)
|
||||
{
|
||||
for (int i = 0; i < num; i++)
|
||||
{
|
||||
auto& s = GetFreeSparkParticle();
|
||||
s = {};
|
||||
s.age = 0;
|
||||
s.life = GenerateFloat(10, 20);
|
||||
s.friction = 0.98f;
|
||||
s.gravity = 1.2f;
|
||||
s.width = 8.0f;
|
||||
s.height = 64.0f;
|
||||
s.room = pos->roomNumber;
|
||||
s.pos = Vector3(pos->x, pos->y, pos->z);
|
||||
float ang = TO_RAD(angle);
|
||||
Vector3 v = Vector3(sin(ang + GenerateFloat(-PI / 2, PI / 2)), GenerateFloat(-1, 1), cos(ang + GenerateFloat(-PI / 2, PI / 2)));
|
||||
v += Vector3(GenerateFloat(-64, 64), GenerateFloat(-64, 64), GenerateFloat(-64, 64));
|
||||
v.Normalize(v);
|
||||
s.velocity = v * GenerateFloat(17, 24);
|
||||
s.sourceColor = Vector4(1, 0.8, 0.2f, 1) * 3;
|
||||
s.destinationColor = Vector4(0, 0, 0, 0);
|
||||
s.active = true;
|
||||
}
|
||||
}
|
||||
|
||||
void TriggerFrictionSpark(GameVector* pos, Vector3Shrt angle, float length, int num)
|
||||
{
|
||||
for (int i = 0; i < num; i++)
|
||||
{
|
||||
auto& s = GetFreeSparkParticle();
|
||||
s = {};
|
||||
s.age = 0;
|
||||
s.life = GenerateFloat(8, 15);
|
||||
s.friction = 0.1f;
|
||||
s.gravity = 0.0f;
|
||||
s.height = length;
|
||||
s.width = GenerateFloat(16.0f, 32.0f);
|
||||
s.room = pos->roomNumber;
|
||||
s.pos = Vector3(pos->x + GenerateFloat(-16, 16), pos->y + GenerateFloat(-16, 16), pos->z + GenerateFloat(-16, 16));
|
||||
float ang = TO_RAD(angle.y);
|
||||
float vAng = -TO_RAD(angle.x);
|
||||
Vector3 v = Vector3(sin(ang), vAng + GenerateFloat(-PI / 16, PI / 16), cos(ang));
|
||||
v.Normalize(v);
|
||||
s.velocity = v * GenerateFloat(32, 64);
|
||||
s.sourceColor = Vector4(1, 0.7, 0.4f, 1) * 3;
|
||||
s.destinationColor = Vector4(0.4f, 0.1f, 0, 0.5f);
|
||||
s.active = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -3,32 +3,29 @@
|
|||
#include <SimpleMath.h>
|
||||
#include "Specific/phd_global.h"
|
||||
|
||||
namespace TEN {
|
||||
namespace Effects {
|
||||
namespace Spark {
|
||||
struct SparkParticle {
|
||||
DirectX::SimpleMath::Vector3 pos;
|
||||
DirectX::SimpleMath::Vector3 velocity;
|
||||
DirectX::SimpleMath::Vector4 sourceColor;
|
||||
DirectX::SimpleMath::Vector4 destinationColor;
|
||||
DirectX::SimpleMath::Vector4 color;
|
||||
int room;
|
||||
float gravity;
|
||||
float friction;
|
||||
float age;
|
||||
float life;
|
||||
float width;
|
||||
float height;
|
||||
bool active;
|
||||
};
|
||||
|
||||
extern std::array<SparkParticle, 128> SparkParticles;
|
||||
namespace TEN::Effects::Spark
|
||||
{
|
||||
struct SparkParticle
|
||||
{
|
||||
Vector3 pos;
|
||||
Vector3 velocity;
|
||||
Vector4 sourceColor;
|
||||
Vector4 destinationColor;
|
||||
Vector4 color;
|
||||
int room;
|
||||
float gravity;
|
||||
float friction;
|
||||
float age;
|
||||
float life;
|
||||
float width;
|
||||
float height;
|
||||
bool active;
|
||||
};
|
||||
extern std::array<SparkParticle, 128> SparkParticles;
|
||||
|
||||
void UpdateSparkParticles();
|
||||
SparkParticle& GetFreeSparkParticle();
|
||||
void TriggerFlareSparkParticles(Vector3Int* pos, Vector3Int* vel, CVECTOR* color,int room);
|
||||
void TriggerRicochetSpark(GameVector* pos, short angle, int num);
|
||||
void TriggerFrictionSpark(GameVector* pos, Vector3Shrt angle, float length, int num);
|
||||
}
|
||||
}
|
||||
}
|
||||
void UpdateSparkParticles();
|
||||
SparkParticle& GetFreeSparkParticle();
|
||||
void TriggerFlareSparkParticles(Vector3Int* pos, Vector3Int* vel, CVECTOR* color, int room);
|
||||
void TriggerRicochetSpark(GameVector* pos, short angle, int num);
|
||||
void TriggerFrictionSpark(GameVector* pos, Vector3Shrt angle, float length, int num);
|
||||
}
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
#include "framework.h"
|
||||
#include "Game/gui.h"
|
||||
|
||||
#include <OISKeyboard.h>
|
||||
#include "Game/animation.h"
|
||||
#include "Game/camera.h"
|
||||
#include "Game/control/control.h"
|
||||
|
@ -23,6 +24,8 @@
|
|||
#include "Scripting/Include/ScriptInterfaceGame.h"
|
||||
|
||||
using namespace TEN::Renderer;
|
||||
using namespace TEN::Input;
|
||||
|
||||
GuiController g_Gui;
|
||||
|
||||
const char* optmessages[] =
|
||||
|
@ -58,6 +61,7 @@ const char* controlmsgs[] =
|
|||
STRING_CONTROLS_LOOK,
|
||||
STRING_CONTROLS_ROLL,
|
||||
STRING_CONTROLS_INVENTORY,
|
||||
STRING_CONTROLS_PAUSE,
|
||||
STRING_CONTROLS_STEP_LEFT,
|
||||
STRING_CONTROLS_STEP_RIGHT
|
||||
};
|
||||
|
@ -160,8 +164,8 @@ InventoryObject inventry_objects_list[INVENTORY_TABLE_SIZE] =
|
|||
{ID_CROSSBOW_ITEM, 0, 0.5f, ANGLE(-90), ANGLE(33), 0, OPT_EQUIP | OPT_COMBINABLE | OPT_CHOOSEAMMO_CROSSBOW, STRING_CROSSBOW, 1, INV_ROT_Y},
|
||||
{ID_CROSSBOW_ITEM, 0, 0.5f, ANGLE(-90), ANGLE(33), 0, OPT_EQUIP | OPT_SEPERATABLE | OPT_CHOOSEAMMO_CROSSBOW, STRING_CROSSBOW_LASER, 3, INV_ROT_Y},
|
||||
{ID_CROSSBOW_AMMO1_ITEM, 0, 0.5f, ANGLE(90), 0, 0, OPT_USE, STRING_CROSSBOW_AMMO1, NO_JOINT_BITS, INV_ROT_Y},
|
||||
{ID_CROSSBOW_AMMO2_ITEM, 0, 0.5f, ANGLE(90), 0, 0, OPT_USE, STRING_CROSSBOW_AMMO1, NO_JOINT_BITS, INV_ROT_Y},
|
||||
{ID_CROSSBOW_AMMO3_ITEM, 0, 0.5f, ANGLE(90), 0, 0, OPT_USE, STRING_CROSSBOW_AMMO1, NO_JOINT_BITS, INV_ROT_Y},
|
||||
{ID_CROSSBOW_AMMO2_ITEM, 0, 0.5f, ANGLE(90), 0, 0, OPT_USE, STRING_CROSSBOW_AMMO2, NO_JOINT_BITS, INV_ROT_Y},
|
||||
{ID_CROSSBOW_AMMO3_ITEM, 0, 0.5f, ANGLE(90), 0, 0, OPT_USE, STRING_CROSSBOW_AMMO3, NO_JOINT_BITS, INV_ROT_Y},
|
||||
{ID_HK_ITEM, 0, 0.5f, ANGLE(0), ANGLE(280), 0, OPT_EQUIP | OPT_COMBINABLE | OPT_CHOOSEAMMO_HK, STRING_HK, 1, INV_ROT_Y},
|
||||
{ID_HK_ITEM, 0, 0.5f, ANGLE(-45), ANGLE(280), 0, OPT_EQUIP | OPT_SEPERATABLE | OPT_CHOOSEAMMO_HK, STRING_HK_SILENCED, NO_JOINT_BITS, INV_ROT_Y},
|
||||
{ID_HK_AMMO_ITEM, 3, 0.5f, ANGLE(90), 0, 0, OPT_USE, STRING_HK_AMMO, 2},
|
||||
|
@ -568,7 +572,7 @@ void GuiController::DoDebouncedInput()
|
|||
else
|
||||
dbSelect = 0;
|
||||
|
||||
if ((TrInput & IN_DESELECT))
|
||||
if (TrInput & IN_OPTION || TrInput & IN_DESELECT)
|
||||
{
|
||||
if (!dbDeselect)
|
||||
goDeselect = 1;
|
||||
|
@ -608,18 +612,15 @@ InventoryResult GuiController::TitleOptions()
|
|||
break;
|
||||
|
||||
case Menu::Display:
|
||||
option_count = 6;
|
||||
HandleDisplaySettingsInput(false);
|
||||
break;
|
||||
|
||||
case Menu::Controls:
|
||||
option_count = 17;
|
||||
HandleControlSettingsInput(false);
|
||||
break;
|
||||
|
||||
case Menu::Sound:
|
||||
option_count = 4;
|
||||
HandleSoundSettingsInput(false);
|
||||
case Menu::OtherSettings:
|
||||
HandleOtherSettingsInput(false);
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -717,24 +718,7 @@ InventoryResult GuiController::TitleOptions()
|
|||
}
|
||||
else if (menu_to_display == Menu::Options)
|
||||
{
|
||||
switch (selected_option)
|
||||
{
|
||||
case 0:
|
||||
FillDisplayOptions();
|
||||
menu_to_display = Menu::Display;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
menu_to_display = Menu::Controls;
|
||||
selected_option = 0;
|
||||
break;
|
||||
|
||||
case 2:
|
||||
FillSound();
|
||||
menu_to_display = Menu::Sound;
|
||||
selected_option = 0;
|
||||
break;
|
||||
}
|
||||
HandleOptionsInput();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -745,7 +729,7 @@ InventoryResult GuiController::TitleOptions()
|
|||
void GuiController::FillDisplayOptions()
|
||||
{
|
||||
// Copy configuration to a temporary object
|
||||
memcpy(&CurrentSettings.conf, &g_Configuration, sizeof(GameConfiguration));
|
||||
BackupOptions();
|
||||
|
||||
// Get current display mode
|
||||
CurrentSettings.selectedScreenResolution = 0;
|
||||
|
@ -763,10 +747,9 @@ void GuiController::FillDisplayOptions()
|
|||
|
||||
void GuiController::HandleDisplaySettingsInput(bool pause)
|
||||
{
|
||||
SetDebounce = true;
|
||||
S_UpdateInput();
|
||||
SetDebounce = false;
|
||||
option_count = 6;
|
||||
|
||||
UpdateInput();
|
||||
DoDebouncedInput();
|
||||
|
||||
if (goDeselect)
|
||||
|
@ -892,8 +875,9 @@ void GuiController::HandleDisplaySettingsInput(bool pause)
|
|||
|
||||
void GuiController::HandleControlSettingsInput(bool pause)
|
||||
{
|
||||
option_count = KEY_COUNT + 1;
|
||||
|
||||
CurrentSettings.waitingForkey = false;
|
||||
memcpy(&CurrentSettings.conf.KeyboardLayout, &KeyboardLayout[1], NUM_CONTROLS);
|
||||
|
||||
if (CurrentSettings.ignoreInput)
|
||||
{
|
||||
|
@ -902,12 +886,10 @@ void GuiController::HandleControlSettingsInput(bool pause)
|
|||
return;
|
||||
}
|
||||
|
||||
SetDebounce = true;
|
||||
S_UpdateInput();
|
||||
SetDebounce = false;
|
||||
UpdateInput();
|
||||
DoDebouncedInput();
|
||||
|
||||
if (goSelect && selected_option != 16 && selected_option != 17)
|
||||
if (goSelect && (selected_option <= 16))
|
||||
{
|
||||
SoundEffect(SFX_TR4_MENU_SELECT, nullptr, SoundEnvironment::Always);
|
||||
CurrentSettings.waitingForkey = true;
|
||||
|
@ -918,13 +900,10 @@ void GuiController::HandleControlSettingsInput(bool pause)
|
|||
{
|
||||
TrInput = 0;
|
||||
DbInput = 0;
|
||||
ZeroMemory(KeyMap, 256);
|
||||
|
||||
while (true)
|
||||
{
|
||||
SetDebounce = true;
|
||||
S_UpdateInput();
|
||||
SetDebounce = false;
|
||||
UpdateInput();
|
||||
|
||||
if (CurrentSettings.ignoreInput)
|
||||
{
|
||||
|
@ -934,22 +913,19 @@ void GuiController::HandleControlSettingsInput(bool pause)
|
|||
else
|
||||
{
|
||||
int selectedKey = 0;
|
||||
for (selectedKey = 0; selectedKey < 256; selectedKey++)
|
||||
for (selectedKey = 0; selectedKey < MAX_INPUT_SLOTS; selectedKey++)
|
||||
{
|
||||
if (KeyMap[selectedKey] & 0x80)
|
||||
if (KeyMap[selectedKey])
|
||||
break;
|
||||
}
|
||||
|
||||
if (selectedKey == 256)
|
||||
if (selectedKey == MAX_INPUT_SLOTS)
|
||||
selectedKey = 0;
|
||||
|
||||
if (selectedKey && g_KeyNames[selectedKey])
|
||||
{
|
||||
if (selectedKey != DIK_ESCAPE)
|
||||
{
|
||||
KeyboardLayout[1][selected_option] = selectedKey;
|
||||
DefaultConflict();
|
||||
}
|
||||
KeyboardLayout[1][selected_option] = selectedKey;
|
||||
DefaultConflict();
|
||||
|
||||
CurrentSettings.waitingForkey = false;
|
||||
CurrentSettings.ignoreInput = true;
|
||||
|
@ -995,21 +971,23 @@ void GuiController::HandleControlSettingsInput(bool pause)
|
|||
|
||||
if (goSelect)
|
||||
{
|
||||
if (selected_option == 16) // Apply
|
||||
if (selected_option == option_count - 1) // Apply
|
||||
{
|
||||
SoundEffect(SFX_TR4_MENU_SELECT, nullptr, SoundEnvironment::Always);
|
||||
memcpy(KeyboardLayout[1], CurrentSettings.conf.KeyboardLayout, NUM_CONTROLS);
|
||||
memcpy(CurrentSettings.conf.KeyboardLayout, KeyboardLayout[1], KEY_COUNT * sizeof(short));
|
||||
memcpy(g_Configuration.KeyboardLayout, KeyboardLayout[1], KEY_COUNT * sizeof(short));
|
||||
SaveConfiguration();
|
||||
menu_to_display = pause ? Menu::Pause : Menu::Options;
|
||||
selected_option = 1;
|
||||
selected_option = 2;
|
||||
return;
|
||||
}
|
||||
|
||||
if (selected_option == 17) // Cancel
|
||||
if (selected_option == option_count) // Cancel
|
||||
{
|
||||
SoundEffect(SFX_TR4_MENU_SELECT, nullptr, SoundEnvironment::Always);
|
||||
memcpy(KeyboardLayout[1], CurrentSettings.conf.KeyboardLayout, KEY_COUNT * sizeof(short));
|
||||
menu_to_display = pause ? Menu::Pause : Menu::Options;
|
||||
selected_option = 1;
|
||||
selected_option = 2;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -1019,21 +997,45 @@ void GuiController::HandleControlSettingsInput(bool pause)
|
|||
SoundEffect(SFX_TR4_MENU_SELECT, nullptr, SoundEnvironment::Always);
|
||||
|
||||
menu_to_display = Menu::Options;
|
||||
selected_option = 1;
|
||||
selected_option = 2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void GuiController::FillSound()
|
||||
void GuiController::BackupOptions()
|
||||
{
|
||||
memcpy(&CurrentSettings.conf, &g_Configuration, sizeof(GameConfiguration));
|
||||
}
|
||||
|
||||
void GuiController::HandleSoundSettingsInput(bool pause)
|
||||
void GuiController::HandleOptionsInput()
|
||||
{
|
||||
SetDebounce = true;
|
||||
S_UpdateInput();
|
||||
SetDebounce = false;
|
||||
switch (selected_option)
|
||||
{
|
||||
case 0:
|
||||
FillDisplayOptions();
|
||||
menu_to_display = Menu::Display;
|
||||
selected_option = 0;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
BackupOptions();
|
||||
menu_to_display = Menu::OtherSettings;
|
||||
selected_option = 0;
|
||||
break;
|
||||
|
||||
case 2:
|
||||
BackupOptions();
|
||||
menu_to_display = Menu::Controls;
|
||||
selected_option = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void GuiController::HandleOtherSettingsInput(bool pause)
|
||||
{
|
||||
option_count = 7;
|
||||
|
||||
UpdateInput();
|
||||
DoDebouncedInput();
|
||||
|
||||
if (goDeselect)
|
||||
|
@ -1041,22 +1043,44 @@ void GuiController::HandleSoundSettingsInput(bool pause)
|
|||
SoundEffect(SFX_TR4_MENU_SELECT, nullptr, SoundEnvironment::Always);
|
||||
|
||||
menu_to_display = Menu::Options;
|
||||
selected_option = 2;
|
||||
selected_option = 1;
|
||||
|
||||
SetVolumeMusic(g_Configuration.MusicVolume);
|
||||
SetVolumeFX(g_Configuration.SfxVolume);
|
||||
return;
|
||||
}
|
||||
|
||||
if (goLeft || goRight)
|
||||
{
|
||||
switch (selected_option)
|
||||
{
|
||||
|
||||
case 0:
|
||||
SoundEffect(SFX_TR4_MENU_CHOOSE, nullptr, SoundEnvironment::Always);
|
||||
CurrentSettings.conf.EnableReverb = !CurrentSettings.conf.EnableReverb;
|
||||
break;
|
||||
|
||||
case 3:
|
||||
SoundEffect(SFX_TR4_MENU_CHOOSE, nullptr, SoundEnvironment::Always);
|
||||
CurrentSettings.conf.AutoTarget = !CurrentSettings.conf.AutoTarget;
|
||||
break;
|
||||
|
||||
case 4:
|
||||
SoundEffect(SFX_TR4_MENU_CHOOSE, nullptr, SoundEnvironment::Always);
|
||||
CurrentSettings.conf.EnableRumble = !CurrentSettings.conf.EnableRumble;
|
||||
break;
|
||||
|
||||
case 5:
|
||||
SoundEffect(SFX_TR4_MENU_CHOOSE, nullptr, SoundEnvironment::Always);
|
||||
CurrentSettings.conf.EnableThumbstickCameraControl = !CurrentSettings.conf.EnableThumbstickCameraControl;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (goLeft)
|
||||
{
|
||||
switch (selected_option)
|
||||
{
|
||||
case 0:
|
||||
SoundEffect(SFX_TR4_MENU_CHOOSE, nullptr, SoundEnvironment::Always);
|
||||
CurrentSettings.conf.EnableAudioSpecialEffects = !CurrentSettings.conf.EnableAudioSpecialEffects;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
if (CurrentSettings.conf.MusicVolume > 0)
|
||||
{
|
||||
|
@ -1071,7 +1095,6 @@ void GuiController::HandleSoundSettingsInput(bool pause)
|
|||
else
|
||||
db -= 2;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case 2:
|
||||
|
@ -1088,7 +1111,6 @@ void GuiController::HandleSoundSettingsInput(bool pause)
|
|||
else
|
||||
db -= 2;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -1097,11 +1119,6 @@ void GuiController::HandleSoundSettingsInput(bool pause)
|
|||
{
|
||||
switch (selected_option)
|
||||
{
|
||||
case 0:
|
||||
SoundEffect(SFX_TR4_MENU_CHOOSE, nullptr, SoundEnvironment::Always);
|
||||
CurrentSettings.conf.EnableAudioSpecialEffects = !CurrentSettings.conf.EnableAudioSpecialEffects;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
if (CurrentSettings.conf.MusicVolume < 100)
|
||||
{
|
||||
|
@ -1116,7 +1133,6 @@ void GuiController::HandleSoundSettingsInput(bool pause)
|
|||
else
|
||||
db -= 2;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case 2:
|
||||
|
@ -1133,7 +1149,6 @@ void GuiController::HandleSoundSettingsInput(bool pause)
|
|||
else
|
||||
db -= 2;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -1162,22 +1177,29 @@ void GuiController::HandleSoundSettingsInput(bool pause)
|
|||
{
|
||||
SoundEffect(SFX_TR4_MENU_SELECT, nullptr, SoundEnvironment::Always);
|
||||
|
||||
if (selected_option == 3)
|
||||
if (selected_option == option_count - 1)
|
||||
{
|
||||
// Was rumble setting changed?
|
||||
bool indicateRumble = CurrentSettings.conf.EnableRumble && !g_Configuration.EnableRumble;
|
||||
|
||||
// Save the configuration
|
||||
memcpy(&g_Configuration, &CurrentSettings.conf, sizeof(GameConfiguration));
|
||||
SaveConfiguration();
|
||||
|
||||
// Rumble if setting was changed
|
||||
if (indicateRumble)
|
||||
Rumble(0.5f);
|
||||
|
||||
menu_to_display = pause ? Menu::Pause : Menu::Options;
|
||||
selected_option = pause ? 1 : 2;
|
||||
selected_option = 1;
|
||||
}
|
||||
else if (selected_option == 4)
|
||||
else if (selected_option == option_count)
|
||||
{
|
||||
SoundEffect(SFX_TR4_MENU_SELECT, nullptr, SoundEnvironment::Always);
|
||||
SetVolumeMusic(g_Configuration.MusicVolume);
|
||||
SetVolumeFX(g_Configuration.SfxVolume);
|
||||
menu_to_display = pause ? Menu::Pause : Menu::Options;
|
||||
selected_option = pause ? 1 : 2;
|
||||
selected_option = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1201,25 +1223,20 @@ InventoryResult GuiController::DoPauseMenu()
|
|||
break;
|
||||
|
||||
case Menu::Display:
|
||||
option_count = 6;
|
||||
HandleDisplaySettingsInput(true);
|
||||
break;
|
||||
|
||||
case Menu::Controls:
|
||||
option_count = 17;
|
||||
HandleControlSettingsInput(true);
|
||||
break;
|
||||
|
||||
case Menu::Sound:
|
||||
option_count = 4;
|
||||
HandleSoundSettingsInput(true);
|
||||
case Menu::OtherSettings:
|
||||
HandleOtherSettingsInput(true);
|
||||
break;
|
||||
}
|
||||
|
||||
ClearInputVariables(1);
|
||||
SetDebounce = true;
|
||||
S_UpdateInput();
|
||||
SetDebounce = false;
|
||||
UpdateInput();
|
||||
DoDebouncedInput();
|
||||
|
||||
if (menu_to_display == Menu::Pause || menu_to_display == Menu::Options)
|
||||
|
@ -1287,25 +1304,7 @@ InventoryResult GuiController::DoPauseMenu()
|
|||
break;
|
||||
|
||||
case Menu::Options:
|
||||
|
||||
switch (selected_option)
|
||||
{
|
||||
case 0:
|
||||
FillDisplayOptions();
|
||||
menu_to_display = Menu::Display;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
selected_option = 0;
|
||||
menu_to_display = Menu::Controls;
|
||||
break;
|
||||
|
||||
case 2:
|
||||
FillSound();
|
||||
selected_option = 0;
|
||||
menu_to_display = Menu::Sound;
|
||||
break;
|
||||
}
|
||||
HandleOptionsInput();
|
||||
break;
|
||||
|
||||
case Menu::Statistics:
|
||||
|
@ -1866,7 +1865,7 @@ void GuiController::ConstructCombineObjectList()
|
|||
rings[(int)RingTypes::Ammo]->ringactive = 0;
|
||||
}
|
||||
|
||||
void GuiController::InitializeInventory()
|
||||
void GuiController::InitialiseInventory()
|
||||
{
|
||||
compassNeedleAngle = 4096;
|
||||
AlterFOV(ANGLE(80.0f));
|
||||
|
@ -3049,9 +3048,9 @@ void GuiController::DrawCurrentObjectList(int ringnum)
|
|||
if (ringnum == (int)RingTypes::Inventory)
|
||||
objmeup = (int)(phd_centery - (phd_winymax + 1) * 0.0625 * 3.0);
|
||||
else
|
||||
objmeup = (int)((phd_winymax + 1) * 0.0625 * 3.0 + phd_centery);
|
||||
objmeup = (int)(phd_centery + (phd_winymax + 1) * 0.0625 * 2.0);
|
||||
|
||||
g_Renderer.DrawString(phd_centerx, ringnum == (int)RingTypes::Inventory ? 230 : 300, textbufme, PRINTSTRING_COLOR_YELLOW, PRINTSTRING_CENTER | PRINTSTRING_OUTLINE);
|
||||
g_Renderer.DrawString(phd_centerx, objmeup, textbufme, PRINTSTRING_COLOR_YELLOW, PRINTSTRING_CENTER | PRINTSTRING_OUTLINE);
|
||||
}
|
||||
|
||||
if (!i && !rings[ringnum]->objlistmovement)
|
||||
|
@ -3195,7 +3194,7 @@ bool GuiController::CallInventory(bool reset_mode)
|
|||
if (reset_mode)
|
||||
invMode = InventoryMode::InGame;
|
||||
|
||||
InitializeInventory();
|
||||
InitialiseInventory();
|
||||
Camera.numberFrames = 2;
|
||||
|
||||
bool exitLoop = false;
|
||||
|
@ -3206,9 +3205,8 @@ bool GuiController::CallInventory(bool reset_mode)
|
|||
if (compassNeedleAngle != 1024)
|
||||
compassNeedleAngle -= 32;
|
||||
|
||||
SetDebounce = true;
|
||||
S_UpdateInput();
|
||||
TrInput = InputBusy;
|
||||
UpdateInput();
|
||||
TrInput = RawInput;
|
||||
GameTimer++;
|
||||
|
||||
if (DbInput & IN_OPTION)
|
||||
|
@ -3298,7 +3296,7 @@ void GuiController::DoStatisticsMode()
|
|||
{
|
||||
SoundEffect(SFX_TR4_MENU_SELECT, nullptr, SoundEnvironment::Always);
|
||||
goDeselect = 0;
|
||||
invMode = InventoryMode::None;
|
||||
invMode = InventoryMode::InGame;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -97,7 +97,7 @@ enum class Menu
|
|||
Options,
|
||||
Display,
|
||||
Controls,
|
||||
Sound
|
||||
OtherSettings
|
||||
};
|
||||
|
||||
enum InventoryObjectTypes
|
||||
|
@ -442,10 +442,11 @@ private:
|
|||
void ClearInputVariables(bool flag);
|
||||
void HandleDisplaySettingsInput(bool pause);
|
||||
void HandleControlSettingsInput(bool pause);
|
||||
void HandleSoundSettingsInput(bool pause);
|
||||
void FillSound();
|
||||
void HandleOtherSettingsInput(bool pause);
|
||||
void HandleOptionsInput();
|
||||
void BackupOptions();
|
||||
bool DoObjectsCombine(int obj1, int obj2);
|
||||
void InitializeInventory();
|
||||
void InitialiseInventory();
|
||||
void FillDisplayOptions();
|
||||
bool IsItemCurrentlyCombinable(short obj);
|
||||
bool IsItemInInventory(short obj);
|
||||
|
|
|
@ -72,20 +72,20 @@ void UpdateHealthBar(ItemInfo* item, int flash)
|
|||
{
|
||||
auto* lara = GetLaraInfo(item);
|
||||
|
||||
auto HitPoints = item->HitPoints;
|
||||
auto hitPoints = item->HitPoints;
|
||||
|
||||
if (HitPoints < 0)
|
||||
HitPoints = 0;
|
||||
else if (HitPoints > LARA_HEALTH_MAX)
|
||||
HitPoints = LARA_HEALTH_MAX;
|
||||
if (hitPoints < 0)
|
||||
hitPoints = 0;
|
||||
else if (hitPoints > LARA_HEALTH_MAX)
|
||||
hitPoints = LARA_HEALTH_MAX;
|
||||
|
||||
// OPT: smoothly transition health bar display.
|
||||
// Smoothly transition health bar display.
|
||||
if (EnableSmoothHealthBar)
|
||||
{
|
||||
if (OldHitPoints != HitPoints)
|
||||
if (OldHitPoints != hitPoints)
|
||||
{
|
||||
MutateAmount += OldHitPoints - HitPoints;
|
||||
OldHitPoints = HitPoints;
|
||||
MutateAmount += OldHitPoints - hitPoints;
|
||||
OldHitPoints = hitPoints;
|
||||
HealthBarTimer = 40;
|
||||
}
|
||||
|
||||
|
@ -100,17 +100,16 @@ void UpdateHealthBar(ItemInfo* item, int flash)
|
|||
if (MutateAmount > -0.5f && MutateAmount < 0.5f)
|
||||
{
|
||||
MutateAmount = 0;
|
||||
HealthBar = HitPoints;
|
||||
HealthBar = hitPoints;
|
||||
}
|
||||
}
|
||||
|
||||
// OG: discretely transition health bar display.
|
||||
// Discretely transition health bar display.
|
||||
else
|
||||
{
|
||||
if (OldHitPoints != HitPoints)
|
||||
if (OldHitPoints != hitPoints)
|
||||
{
|
||||
OldHitPoints = HitPoints;
|
||||
HealthBar = HitPoints;
|
||||
OldHitPoints = hitPoints;
|
||||
HealthBar = hitPoints;
|
||||
HealthBarTimer = 40;
|
||||
}
|
||||
}
|
||||
|
@ -118,8 +117,8 @@ void UpdateHealthBar(ItemInfo* item, int flash)
|
|||
if (HealthBarTimer < 0)
|
||||
HealthBarTimer = 0;
|
||||
|
||||
// Flash when at 1/4 capacity AND HP bar is not transitioning.
|
||||
if (HealthBar <= LARA_HEALTH_MAX / 4)
|
||||
// Flash when at critical capacity and bar is not transitioning.
|
||||
if (HealthBar <= LARA_HEALTH_CRITICAL)
|
||||
{
|
||||
if (!BinocularRange)
|
||||
{
|
||||
|
@ -179,7 +178,7 @@ void UpdateAirBar(ItemInfo* item, int flash)
|
|||
else if (air > LARA_AIR_MAX)
|
||||
air = LARA_AIR_MAX;
|
||||
|
||||
if (air <= (LARA_AIR_MAX / 4))
|
||||
if (air <= LARA_AIR_CRITICAL)
|
||||
{
|
||||
if (flash)
|
||||
DrawAirBar(air / LARA_AIR_MAX);
|
||||
|
|
|
@ -8,9 +8,14 @@
|
|||
#include "ScriptInterfaceGame.h"
|
||||
#include "Specific/setup.h"
|
||||
#include "Specific/level.h"
|
||||
#include "Specific/input.h"
|
||||
#include "Objects/ScriptInterfaceObjectsHandler.h"
|
||||
#include "Sound/sound.h"
|
||||
#include "Specific/prng.h"
|
||||
|
||||
using namespace TEN::Floordata;
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Math::Random;
|
||||
|
||||
void ItemInfo::SetBits(JointBitType type, std::vector<int> jointIndices)
|
||||
{
|
||||
|
@ -646,3 +651,32 @@ int FindItem(ItemInfo* item)
|
|||
|
||||
return -1;
|
||||
}
|
||||
|
||||
void DoDamage(ItemInfo* item, int damage)
|
||||
{
|
||||
static int lastHurtTime = 0;
|
||||
|
||||
if (item->HitPoints <= 0)
|
||||
return;
|
||||
|
||||
item->HitStatus = true;
|
||||
|
||||
item->HitPoints -= damage;
|
||||
if (item->HitPoints < 0)
|
||||
item->HitPoints = 0;
|
||||
|
||||
if (item->IsLara())
|
||||
{
|
||||
if (damage > 0)
|
||||
{
|
||||
float power = item->HitPoints ? GenerateFloat(0.1f, 0.4f) : 0.5f;
|
||||
Rumble(power, 0.15f);
|
||||
}
|
||||
|
||||
if ((GlobalCounter - lastHurtTime) > (FPS * 2 + GenerateInt(0, FPS)))
|
||||
{
|
||||
SoundEffect(SFX_TR4_LARA_INJURY, &LaraItem->Pose);
|
||||
lastHurtTime = GlobalCounter;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -149,3 +149,4 @@ void UpdateItemRoom(ItemInfo* item, int height, int xOffset = 0, int zOffset = 0
|
|||
std::vector<int> FindAllItems(short objectNumber);
|
||||
ItemInfo* FindItem(int objectNumber);
|
||||
int FindItem(ItemInfo* item);
|
||||
void DoDamage(ItemInfo* item, int damage);
|
||||
|
|
|
@ -85,8 +85,7 @@ void ControlMissile(short fxNumber)
|
|||
{
|
||||
if (ItemNearLara(&fx->pos, 350))
|
||||
{
|
||||
LaraItem->HitPoints -= 3;
|
||||
LaraItem->hitStatus = 1;
|
||||
DoDamage(LaraItem, 3);
|
||||
LaraBurn(LaraItem);
|
||||
return;
|
||||
}
|
||||
|
@ -95,14 +94,12 @@ void ControlMissile(short fxNumber)
|
|||
{
|
||||
/*if (fx->objectNumber == KNIFE)
|
||||
{
|
||||
LaraItem->HitPoints -= KNIFE_DAMAGE;
|
||||
SoundEffect(317, &fx->pos);
|
||||
DoDamage(LaraItem, KNIFE_DAMAGE);
|
||||
KillEffect(fx_number);
|
||||
}
|
||||
else*/ if (fx->objectNumber == ID_SCUBA_HARPOON)
|
||||
{
|
||||
LaraItem->HitPoints -= DIVER_HARPOON_DAMAGE;
|
||||
SoundEffect(317, &fx->pos);
|
||||
DoDamage(LaraItem, DIVER_HARPOON_DAMAGE);
|
||||
KillEffect(fxNumber);
|
||||
}
|
||||
|
||||
|
|
|
@ -47,8 +47,7 @@ bool ShotLara(ItemInfo* item, AI_INFO* AI, BITE_INFO* gun, short extraRotation,
|
|||
if (hit)
|
||||
{
|
||||
CreatureEffect(item, gun, &GunHit);
|
||||
LaraItem->HitPoints -= damage;
|
||||
LaraItem->HitStatus = true;
|
||||
DoDamage(LaraItem, damage);
|
||||
}
|
||||
else if (targetable)
|
||||
CreatureEffect(item, gun, &GunMiss);
|
||||
|
@ -94,10 +93,7 @@ short GunHit(int x, int y, int z, short velocity, short yRot, short roomNumber)
|
|||
{
|
||||
Vector3Int pos = { 0, 0, 0 };
|
||||
GetLaraJointPosition(&pos, (25 * GetRandomControl()) >> 15);
|
||||
|
||||
DoBloodSplat(pos.x, pos.y, pos.z, (GetRandomControl() & 3) + 3, LaraItem->Pose.Orientation.y, LaraItem->RoomNumber);
|
||||
SoundEffect(SFX_TR4_LARA_INJURY, &LaraItem->Pose);
|
||||
|
||||
return GunShot(x, y, z, velocity, yRot, roomNumber);
|
||||
}
|
||||
|
||||
|
|
|
@ -28,6 +28,7 @@
|
|||
#include "Specific/phd_global.h"
|
||||
#include "Specific/setup.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Entities::Generic;
|
||||
|
||||
// TODO: Adjust these bounds when crawl surface alignment is implemented. @Sezz 2021.11.04
|
||||
|
|
|
@ -260,7 +260,7 @@ bool SaveGame::Save(int slot)
|
|||
count.add_no_cheat(Lara.Control.Count.NoCheat);
|
||||
count.add_pose(Lara.Control.Count.Pose);
|
||||
count.add_position_adjust(Lara.Control.Count.PositionAdjust);
|
||||
count.add_run_jump(Lara.Control.Count.RunJump);
|
||||
count.add_run_jump(Lara.Control.Count.Run);
|
||||
auto countOffset = count.Finish();
|
||||
|
||||
Save::WeaponControlDataBuilder weaponControl{ fbb };
|
||||
|
@ -390,7 +390,6 @@ bool SaveGame::Save(int slot)
|
|||
lara.add_poison_potency(Lara.PoisonPotency);
|
||||
lara.add_projected_floor_height(Lara.ProjectedFloorHeight);
|
||||
lara.add_right_arm(rightArmOffset);
|
||||
lara.add_spasm_effect_count(Lara.SpasmEffectCount);
|
||||
lara.add_sprint_energy(Lara.SprintEnergy);
|
||||
lara.add_target_facing_angle(Lara.TargetOrientation.y);
|
||||
lara.add_target_arm_angles(laraTargetAnglesOffset);
|
||||
|
@ -1620,7 +1619,7 @@ bool SaveGame::Load(int slot)
|
|||
Lara.Control.Count.NoCheat = s->lara()->control()->count()->no_cheat();
|
||||
Lara.Control.Count.Pose = s->lara()->control()->count()->pose();
|
||||
Lara.Control.Count.PositionAdjust = s->lara()->control()->count()->position_adjust();
|
||||
Lara.Control.Count.RunJump = s->lara()->control()->count()->run_jump();
|
||||
Lara.Control.Count.Run = s->lara()->control()->count()->run_jump();
|
||||
Lara.Control.Count.Death = s->lara()->control()->count()->death();
|
||||
Lara.Control.IsClimbingLadder = s->lara()->control()->is_climbing_ladder();
|
||||
Lara.Control.IsLow = s->lara()->control()->is_low();
|
||||
|
@ -1738,7 +1737,6 @@ bool SaveGame::Load(int slot)
|
|||
Lara.Control.Tightrope.TightropeItem = s->lara()->control()->tightrope()->tightrope_item();
|
||||
Lara.Control.Tightrope.TimeOnTightrope = s->lara()->control()->tightrope()->time_on_tightrope();
|
||||
Lara.Control.WaterStatus = (WaterStatus)s->lara()->control()->water_status();
|
||||
Lara.SpasmEffectCount = s->lara()->spasm_effect_count();
|
||||
Lara.SprintEnergy = s->lara()->sprint_energy();
|
||||
Lara.TargetEntity = (s->lara()->target_entity_number() >= 0 ? &g_Level.Items[s->lara()->target_entity_number()] : nullptr);
|
||||
Lara.TargetArmOrient.y = s->lara()->target_arm_angles()->Get(0);
|
||||
|
|
|
@ -11,9 +11,12 @@
|
|||
#include "Game/Lara/lara_helpers.h"
|
||||
#include "Specific/input.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Renderer;
|
||||
using namespace TEN::Control::Volumes;
|
||||
|
||||
constexpr auto MAX_CAMERA = 18;
|
||||
|
||||
int TrackCameraInit;
|
||||
int SpotcamTimer;
|
||||
int SpotcamPaused;
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
#include "Specific/trmath.h"
|
||||
#include "input.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Effects::Lara;
|
||||
using namespace TEN::Effects::Lightning;
|
||||
using namespace TEN::Effects::Environment;
|
||||
|
|
|
@ -19,6 +19,8 @@
|
|||
#include "Objects/Generic/Doors/double_doors.h"
|
||||
#include "Game/collision/collide_item.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Doors
|
||||
{
|
||||
Vector3Int DoubleDoorPos(0, 0, 220);
|
||||
|
|
|
@ -23,6 +23,8 @@
|
|||
#include "Game/collision/collide_item.h"
|
||||
#include "Game/itemdata/itemdata.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Doors
|
||||
{
|
||||
Vector3Int CrowbarDoorPos(-412, 0, 256);
|
||||
|
|
|
@ -20,6 +20,8 @@
|
|||
#include "Game/collision/collide_item.h"
|
||||
#include "Game/itemdata/door_data.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Doors
|
||||
{
|
||||
enum STATES_PUSHPULL_KICK_DOOR
|
||||
|
|
|
@ -19,6 +19,8 @@
|
|||
#include "Objects/Generic/Doors/underwater_door.h"
|
||||
#include "Game/collision/collide_item.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Doors
|
||||
{
|
||||
Vector3Int UnderwaterDoorPos(-251, -540, -46);
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
#include "Game/control/los.h"
|
||||
#include "Renderer/Renderer11Enums.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Entities::Effects;
|
||||
|
||||
namespace TEN::Entities::Generic
|
||||
|
|
|
@ -12,8 +12,8 @@
|
|||
#include "Renderer/Renderer11.h"
|
||||
#include "Game/collision/collide_item.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Renderer;
|
||||
|
||||
using namespace TEN::Floordata;
|
||||
|
||||
OBJECT_COLLISION_BOUNDS CeilingTrapDoorBounds =
|
||||
|
|
|
@ -14,6 +14,8 @@
|
|||
#include "Game/collision/collide_item.h"
|
||||
#include "Renderer/Renderer11Enums.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
OBJECT_TEXTURE* WaterfallTextures[6];
|
||||
float WaterfallY[6];
|
||||
int lastWaterfallY = 0;
|
||||
|
|
|
@ -13,6 +13,8 @@
|
|||
#include "Game/collision/collide_item.h"
|
||||
#include "Game/collision/sphere.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Generic
|
||||
{
|
||||
Vector3Int PolePos = { 0, 0, -208 };
|
||||
|
|
|
@ -15,6 +15,8 @@
|
|||
#include "Sound/sound.h"
|
||||
#include "Game/camera.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Generic
|
||||
{
|
||||
PENDULUM CurrentPendulum;
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
#include "Game/animation.h"
|
||||
#include "Game/items.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
using namespace TEN::Entities::Doors;
|
||||
|
||||
namespace TEN::Entities::Switches
|
||||
|
|
|
@ -12,6 +12,8 @@
|
|||
#include "Game/animation.h"
|
||||
#include "Game/items.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Switches
|
||||
{
|
||||
Vector3Int CrowbarPos = { -89, 0, -328 };
|
||||
|
|
|
@ -10,6 +10,8 @@
|
|||
#include "Game/animation.h"
|
||||
#include "Game/items.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Switches
|
||||
{
|
||||
OBJECT_COLLISION_BOUNDS FullBlockSwitchBounds =
|
||||
|
|
|
@ -9,6 +9,8 @@
|
|||
#include "Game/collision/collide_item.h"
|
||||
#include "Game/items.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Switches
|
||||
{
|
||||
OBJECT_COLLISION_BOUNDS SwitchBounds =
|
||||
|
|
|
@ -9,6 +9,8 @@
|
|||
#include "Game/collision/collide_item.h"
|
||||
#include "Game/items.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Switches
|
||||
{
|
||||
OBJECT_COLLISION_BOUNDS JumpSwitchBounds =
|
||||
|
|
|
@ -11,6 +11,8 @@
|
|||
#include "Game/collision/collide_item.h"
|
||||
#include "Game/items.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Switches
|
||||
{
|
||||
OBJECT_COLLISION_BOUNDS PulleyBounds =
|
||||
|
|
|
@ -9,6 +9,8 @@
|
|||
#include "Game/animation.h"
|
||||
#include "Game/items.h"
|
||||
|
||||
using namespace TEN::Input;
|
||||
|
||||
namespace TEN::Entities::Switches
|
||||
{
|
||||
Vector3Int RailSwitchPos = { 0, 0, -550 };
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue