Reviewed physics module
A deeper revision required, not clear enough for the user Key: Create a PhysicObjects pool
This commit is contained in:
parent
94c92a58a1
commit
ed19064405
5 changed files with 64 additions and 98 deletions
|
@ -2,20 +2,10 @@
|
||||||
*
|
*
|
||||||
* raylib [physac] physics example - Basic rigidbody
|
* raylib [physac] physics example - Basic rigidbody
|
||||||
*
|
*
|
||||||
* Welcome to raylib!
|
* This example has been created using raylib 1.4 (www.raylib.com)
|
||||||
*
|
|
||||||
* To test examples, just press F6 and execute raylib_compile_execute script
|
|
||||||
* Note that compiled executable is placed in the same folder as .c file
|
|
||||||
*
|
|
||||||
* You can find all basic examples on C:\raylib\raylib\examples folder or
|
|
||||||
* raylib official webpage: www.raylib.com
|
|
||||||
*
|
|
||||||
* Enjoy using raylib. :)
|
|
||||||
*
|
|
||||||
* This example has been created using raylib 1.3 (www.raylib.com)
|
|
||||||
* raylib is licensed under an unmodified zlib/libpng license (View raylib.h for details)
|
* raylib is licensed under an unmodified zlib/libpng license (View raylib.h for details)
|
||||||
*
|
*
|
||||||
* Copyright (c) 2015 Ramon Santamaria (@raysan5)
|
* Copyright (c) 2016 Victor Fisac and Ramon Santamaria (@raysan5)
|
||||||
*
|
*
|
||||||
********************************************************************************************/
|
********************************************************************************************/
|
||||||
|
|
||||||
|
@ -33,13 +23,7 @@ int main()
|
||||||
|
|
||||||
InitWindow(screenWidth, screenHeight, "raylib [physics] example - basic rigidbody");
|
InitWindow(screenWidth, screenHeight, "raylib [physics] example - basic rigidbody");
|
||||||
|
|
||||||
InitPhysics(); // Initialize internal physics values (max rigidbodies/colliders available: 1024)
|
InitPhysics(3); // Initialize physics system with maximum physic objects
|
||||||
|
|
||||||
// Physics initialization
|
|
||||||
Physics worldPhysics = { true, false, (Vector2){ 0, -9.81f } };
|
|
||||||
|
|
||||||
// Set internal physics settings
|
|
||||||
SetPhysics(worldPhysics);
|
|
||||||
|
|
||||||
// Object initialization
|
// Object initialization
|
||||||
Transform player = (Transform){(Vector2){(screenWidth - OBJECT_SIZE) / 2, (screenHeight - OBJECT_SIZE) / 2}, 0.0f, (Vector2){OBJECT_SIZE, OBJECT_SIZE}};
|
Transform player = (Transform){(Vector2){(screenWidth - OBJECT_SIZE) / 2, (screenHeight - OBJECT_SIZE) / 2}, 0.0f, (Vector2){OBJECT_SIZE, OBJECT_SIZE}};
|
||||||
|
@ -55,6 +39,8 @@ int main()
|
||||||
float moveSpeed = 6.0f;
|
float moveSpeed = 6.0f;
|
||||||
float jumpForce = 5.0f;
|
float jumpForce = 5.0f;
|
||||||
|
|
||||||
|
bool physicsDebug = false;
|
||||||
|
|
||||||
SetTargetFPS(60);
|
SetTargetFPS(60);
|
||||||
//--------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
@ -91,14 +77,7 @@ int main()
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check debug mode toggle button input
|
// Check debug mode toggle button input
|
||||||
if(IsKeyPressed(KEY_P))
|
if (IsKeyPressed(KEY_P)) physicsDebug = !physicsDebug;
|
||||||
{
|
|
||||||
// Update program physics value
|
|
||||||
worldPhysics.debug = !worldPhysics.debug;
|
|
||||||
|
|
||||||
// Update internal physics value
|
|
||||||
SetPhysics(worldPhysics);
|
|
||||||
}
|
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
|
|
||||||
// Draw
|
// Draw
|
||||||
|
@ -112,7 +91,7 @@ int main()
|
||||||
DrawText("Use P to switch DEBUG MODE", (screenWidth - MeasureText("Use P to switch DEBUG MODE", 20)) / 2, screenHeight * 0.3f, 20, LIGHTGRAY);
|
DrawText("Use P to switch DEBUG MODE", (screenWidth - MeasureText("Use P to switch DEBUG MODE", 20)) / 2, screenHeight * 0.3f, 20, LIGHTGRAY);
|
||||||
|
|
||||||
// Check if debug mode is enabled
|
// Check if debug mode is enabled
|
||||||
if (worldPhysics.debug)
|
if (physicsDebug)
|
||||||
{
|
{
|
||||||
// Draw every internal physics stored collider if it is active
|
// Draw every internal physics stored collider if it is active
|
||||||
for (int i = 0; i < 2; i++)
|
for (int i = 0; i < 2; i++)
|
||||||
|
@ -122,14 +101,11 @@ int main()
|
||||||
DrawRectangleLines(GetCollider(i).bounds.x, GetCollider(i).bounds.y, GetCollider(i).bounds.width, GetCollider(i).bounds.height, GREEN);
|
DrawRectangleLines(GetCollider(i).bounds.x, GetCollider(i).bounds.y, GetCollider(i).bounds.width, GetCollider(i).bounds.height, GREEN);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Draw player
|
// Draw player and floor
|
||||||
DrawRectangleRec((Rectangle){player.position.x, player.position.y, player.scale.x, player.scale.y}, GRAY);
|
DrawRectangleRec((Rectangle){player.position.x, player.position.y, player.scale.x, player.scale.y}, GRAY);
|
||||||
|
|
||||||
// Draw floor
|
|
||||||
DrawRectangleRec((Rectangle){floor.position.x, floor.position.y, floor.scale.x, floor.scale.y}, BLACK);
|
DrawRectangleRec((Rectangle){floor.position.x, floor.position.y, floor.scale.x, floor.scale.y}, BLACK);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -139,6 +115,8 @@ int main()
|
||||||
|
|
||||||
// De-Initialization
|
// De-Initialization
|
||||||
//--------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------
|
||||||
|
UnloadPhysics(); // Unload physic objects
|
||||||
|
|
||||||
CloseWindow(); // Close window and OpenGL context
|
CloseWindow(); // Close window and OpenGL context
|
||||||
//--------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
|
@ -2,10 +2,10 @@
|
||||||
*
|
*
|
||||||
* raylib [physac] physics example - Rigidbody forces
|
* raylib [physac] physics example - Rigidbody forces
|
||||||
*
|
*
|
||||||
* This example has been created using raylib 1.3 (www.raylib.com)
|
* This example has been created using raylib 1.4 (www.raylib.com)
|
||||||
* raylib is licensed under an unmodified zlib/libpng license (View raylib.h for details)
|
* raylib is licensed under an unmodified zlib/libpng license (View raylib.h for details)
|
||||||
*
|
*
|
||||||
* Copyright (c) 2014 Ramon Santamaria (@raysan5)
|
* Copyright (c) 2016 Victor Fisac and Ramon Santamaria (@raysan5)
|
||||||
*
|
*
|
||||||
********************************************************************************************/
|
********************************************************************************************/
|
||||||
|
|
||||||
|
@ -26,15 +26,9 @@ int main()
|
||||||
|
|
||||||
InitWindow(screenWidth, screenHeight, "raylib [physics] example - rigidbodies forces");
|
InitWindow(screenWidth, screenHeight, "raylib [physics] example - rigidbodies forces");
|
||||||
|
|
||||||
InitPhysics(); // Initialize internal physics values (max rigidbodies/colliders available: 1024)
|
InitPhysics(MAX_OBJECTS + 1); // Initialize physics system with maximum physic objects
|
||||||
|
|
||||||
// Physics initialization
|
// Physic Objects initialization
|
||||||
Physics worldPhysics = {true, false, (Vector2){0, -9.81f}};
|
|
||||||
|
|
||||||
// Set internal physics settings
|
|
||||||
SetPhysics(worldPhysics);
|
|
||||||
|
|
||||||
// Objects initialization
|
|
||||||
Transform objects[MAX_OBJECTS];
|
Transform objects[MAX_OBJECTS];
|
||||||
|
|
||||||
for (int i = 0; i < MAX_OBJECTS; i++)
|
for (int i = 0; i < MAX_OBJECTS; i++)
|
||||||
|
@ -49,6 +43,8 @@ int main()
|
||||||
Transform floor = (Transform){(Vector2){0, screenHeight * 0.8f}, 0.0f, (Vector2){screenWidth, screenHeight * 0.2f}};
|
Transform floor = (Transform){(Vector2){0, screenHeight * 0.8f}, 0.0f, (Vector2){screenWidth, screenHeight * 0.2f}};
|
||||||
AddCollider(MAX_OBJECTS, (Collider){true, COLLIDER_RECTANGLE, (Rectangle){floor.position.x, floor.position.y, floor.scale.x, floor.scale.y}, 0});
|
AddCollider(MAX_OBJECTS, (Collider){true, COLLIDER_RECTANGLE, (Rectangle){floor.position.x, floor.position.y, floor.scale.x, floor.scale.y}, 0});
|
||||||
|
|
||||||
|
bool physicsDebug = false;
|
||||||
|
|
||||||
SetTargetFPS(60);
|
SetTargetFPS(60);
|
||||||
//--------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
@ -72,14 +68,7 @@ int main()
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check debug mode toggle button input
|
// Check debug mode toggle button input
|
||||||
if (IsKeyPressed(KEY_P))
|
if (IsKeyPressed(KEY_P)) physicsDebug = !physicsDebug;
|
||||||
{
|
|
||||||
// Update program physics value
|
|
||||||
worldPhysics.debug = !worldPhysics.debug;
|
|
||||||
|
|
||||||
// Update internal physics value
|
|
||||||
SetPhysics(worldPhysics);
|
|
||||||
}
|
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
|
|
||||||
// Draw
|
// Draw
|
||||||
|
@ -89,10 +78,10 @@ int main()
|
||||||
ClearBackground(RAYWHITE);
|
ClearBackground(RAYWHITE);
|
||||||
|
|
||||||
// Check if debug mode is enabled
|
// Check if debug mode is enabled
|
||||||
if (worldPhysics.debug)
|
if (physicsDebug)
|
||||||
{
|
{
|
||||||
// Draw every internal physics stored collider if it is active (floor included)
|
// Draw every internal physics stored collider if it is active (floor included)
|
||||||
for (int i = 0; i < MAX_OBJECTS + 1; i++)
|
for (int i = 0; i < MAX_OBJECTS; i++)
|
||||||
{
|
{
|
||||||
if (GetCollider(i).enabled)
|
if (GetCollider(i).enabled)
|
||||||
{
|
{
|
||||||
|
@ -137,6 +126,8 @@ int main()
|
||||||
|
|
||||||
// De-Initialization
|
// De-Initialization
|
||||||
//--------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------
|
||||||
|
UnloadPhysics(); // Unload physic objects
|
||||||
|
|
||||||
CloseWindow(); // Close window and OpenGL context
|
CloseWindow(); // Close window and OpenGL context
|
||||||
//--------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
59
src/physac.c
59
src/physac.c
|
@ -30,13 +30,12 @@
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include <math.h>
|
#include <math.h>
|
||||||
#include <stdio.h>
|
#include <stdlib.h> // Required for: malloc(), free()
|
||||||
|
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// Defines and Macros
|
// Defines and Macros
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
#define MAX_ELEMENTS 1024 // Stored rigidbodies and colliders array length
|
#define DECIMAL_FIX 0.26f // Decimal margin for collision checks (avoid rigidbodies shake)
|
||||||
#define DECIMAL_FIX 0.26f // Decimal margin for collision checks (avoid rigidbodies shake)
|
|
||||||
|
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// Types and Structures Definition
|
// Types and Structures Definition
|
||||||
|
@ -46,10 +45,13 @@
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// Global Variables Definition
|
// Global Variables Definition
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
static Physics physics;
|
static Collider *colliders; // Colliders array, dynamically allocated at runtime
|
||||||
static Collider colliders[MAX_ELEMENTS];
|
static Rigidbody *rigidbodies; // Rigitbody array, dynamically allocated at runtime
|
||||||
static Rigidbody rigidbodies[MAX_ELEMENTS];
|
static bool collisionChecker;
|
||||||
static bool collisionChecker = false;
|
|
||||||
|
static int maxElements; // Max physic elements to compute
|
||||||
|
static bool enabled; // Physics enabled? (true by default)
|
||||||
|
static Vector2 gravity; // Gravity value used for physic calculations
|
||||||
|
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// Module specific Functions Declarations
|
// Module specific Functions Declarations
|
||||||
|
@ -61,30 +63,39 @@ static void Vector2Normalize(Vector2 *vector);
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// Module Functions Definitions
|
// Module Functions Definitions
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
void InitPhysics(void)
|
void InitPhysics(int maxPhysicElements)
|
||||||
{
|
{
|
||||||
for (int i = 0; i < MAX_ELEMENTS; i++)
|
maxElements = maxPhysicElements;
|
||||||
|
|
||||||
|
colliders = (Collider *)malloc(maxElements*sizeof(Collider));
|
||||||
|
rigidbodies = (Rigidbody *)malloc(maxElements*sizeof(Rigidbody));
|
||||||
|
|
||||||
|
for (int i = 0; i < maxElements; i++)
|
||||||
{
|
{
|
||||||
|
colliders[i].enabled = false;
|
||||||
|
colliders[i].bounds = (Rectangle){ 0, 0, 0, 0 };
|
||||||
|
colliders[i].radius = 0;
|
||||||
|
|
||||||
rigidbodies[i].enabled = false;
|
rigidbodies[i].enabled = false;
|
||||||
rigidbodies[i].mass = 0.0f;
|
rigidbodies[i].mass = 0.0f;
|
||||||
rigidbodies[i].velocity = (Vector2){0, 0};
|
rigidbodies[i].velocity = (Vector2){ 0.0f, 0.0f };
|
||||||
rigidbodies[i].acceleration = (Vector2){0, 0};
|
rigidbodies[i].acceleration = (Vector2){ 0.0f, 0.0f };
|
||||||
rigidbodies[i].isGrounded = false;
|
rigidbodies[i].isGrounded = false;
|
||||||
rigidbodies[i].isContact = false;
|
rigidbodies[i].isContact = false;
|
||||||
rigidbodies[i].friction = 0.0f;
|
rigidbodies[i].friction = 0.0f;
|
||||||
|
|
||||||
colliders[i].enabled = false;
|
|
||||||
colliders[i].bounds = (Rectangle){0, 0, 0, 0};
|
|
||||||
colliders[i].radius = 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
collisionChecker = false;
|
||||||
|
enabled = true;
|
||||||
|
|
||||||
|
// NOTE: To get better results, gravity needs to be 1:10 from original parameter
|
||||||
|
gravity = (Vector2){ 0.0f, -9.81f/10.0f }; // By default, standard gravity
|
||||||
}
|
}
|
||||||
|
|
||||||
void SetPhysics(Physics settings)
|
void UnloadPhysics()
|
||||||
{
|
{
|
||||||
physics = settings;
|
free(colliders);
|
||||||
|
free(rigidbodies);
|
||||||
// To get good results, gravity needs to be 1:10 from original parameter
|
|
||||||
physics.gravity = (Vector2){physics.gravity.x / 10, physics.gravity.y / 10};
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void AddCollider(int index, Collider collider)
|
void AddCollider(int index, Collider collider)
|
||||||
|
@ -159,8 +170,8 @@ void ApplyPhysics(int index, Vector2 *position)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Apply gravity
|
// Apply gravity
|
||||||
rigidbodies[index].velocity.y += physics.gravity.y;
|
rigidbodies[index].velocity.y += gravity.y;
|
||||||
rigidbodies[index].velocity.x += physics.gravity.x;
|
rigidbodies[index].velocity.x += gravity.x;
|
||||||
|
|
||||||
// Apply acceleration
|
// Apply acceleration
|
||||||
rigidbodies[index].velocity.y += rigidbodies[index].acceleration.y;
|
rigidbodies[index].velocity.y += rigidbodies[index].acceleration.y;
|
||||||
|
@ -177,7 +188,7 @@ void ApplyPhysics(int index, Vector2 *position)
|
||||||
// Check collision with other colliders
|
// Check collision with other colliders
|
||||||
collisionChecker = false;
|
collisionChecker = false;
|
||||||
rigidbodies[index].isContact = false;
|
rigidbodies[index].isContact = false;
|
||||||
for (int j = 0; j < MAX_ELEMENTS; j++)
|
for (int j = 0; j < maxElements; j++)
|
||||||
{
|
{
|
||||||
if (index != j)
|
if (index != j)
|
||||||
{
|
{
|
||||||
|
@ -269,7 +280,7 @@ void AddRigidbodyForce(int index, Vector2 force)
|
||||||
|
|
||||||
void AddForceAtPosition(Vector2 position, float intensity, float radius)
|
void AddForceAtPosition(Vector2 position, float intensity, float radius)
|
||||||
{
|
{
|
||||||
for(int i = 0; i < MAX_ELEMENTS; i++)
|
for(int i = 0; i < maxElements; i++)
|
||||||
{
|
{
|
||||||
if(rigidbodies[i].enabled)
|
if(rigidbodies[i].enabled)
|
||||||
{
|
{
|
||||||
|
|
11
src/physac.h
11
src/physac.h
|
@ -35,13 +35,6 @@
|
||||||
// Collider types
|
// Collider types
|
||||||
typedef enum { COLLIDER_CIRCLE, COLLIDER_RECTANGLE, COLLIDER_CAPSULE } ColliderType;
|
typedef enum { COLLIDER_CIRCLE, COLLIDER_RECTANGLE, COLLIDER_CAPSULE } ColliderType;
|
||||||
|
|
||||||
// Physics struct
|
|
||||||
typedef struct Physics {
|
|
||||||
bool enabled;
|
|
||||||
bool debug; // Should be used by programmer for testing purposes
|
|
||||||
Vector2 gravity;
|
|
||||||
} Physics;
|
|
||||||
|
|
||||||
// Transform struct
|
// Transform struct
|
||||||
typedef struct Transform {
|
typedef struct Transform {
|
||||||
Vector2 position;
|
Vector2 position;
|
||||||
|
@ -77,8 +70,8 @@ extern "C" { // Prevents name mangling of functions
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// Module Functions Declarations
|
// Module Functions Declarations
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
void InitPhysics(void); // Initialize all internal physics values
|
void InitPhysics(int maxPhysicElements); // Initialize all internal physics values
|
||||||
void SetPhysics(Physics settings); // Set physics settings values using Physics data type to overwrite internal physics settings
|
void UnloadPhysics(); // Unload physic elements arrays
|
||||||
|
|
||||||
void AddRigidbody(int index, Rigidbody rigidbody); // Initialize a new rigidbody with parameters to internal index slot
|
void AddRigidbody(int index, Rigidbody rigidbody); // Initialize a new rigidbody with parameters to internal index slot
|
||||||
void AddCollider(int index, Collider collider); // Initialize a new Collider with parameters to internal index slot
|
void AddCollider(int index, Collider collider); // Initialize a new Collider with parameters to internal index slot
|
||||||
|
|
13
src/raylib.h
13
src/raylib.h
|
@ -466,13 +466,6 @@ typedef enum { CAMERA_CUSTOM = 0, CAMERA_FREE, CAMERA_ORBITAL, CAMERA_FIRST_PERS
|
||||||
// Collider types
|
// Collider types
|
||||||
typedef enum { COLLIDER_CIRCLE, COLLIDER_RECTANGLE, COLLIDER_CAPSULE } ColliderType;
|
typedef enum { COLLIDER_CIRCLE, COLLIDER_RECTANGLE, COLLIDER_CAPSULE } ColliderType;
|
||||||
|
|
||||||
// Physics struct
|
|
||||||
typedef struct Physics {
|
|
||||||
bool enabled;
|
|
||||||
bool debug; // Should be used by programmer for testing purposes
|
|
||||||
Vector2 gravity;
|
|
||||||
} Physics;
|
|
||||||
|
|
||||||
// Transform struct
|
// Transform struct
|
||||||
typedef struct Transform {
|
typedef struct Transform {
|
||||||
Vector2 position;
|
Vector2 position;
|
||||||
|
@ -808,10 +801,10 @@ void SetShaderMap(Shader *shader, int mapLocation, Texture2D texture, int textur
|
||||||
void SetBlendMode(int mode); // Set blending mode (alpha, additive, multiplied)
|
void SetBlendMode(int mode); // Set blending mode (alpha, additive, multiplied)
|
||||||
|
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
// Physics System Functions (engine-module: physics)
|
// Physics System Functions (engine-module: physac)
|
||||||
//----------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------
|
||||||
void InitPhysics(void); // Initialize all internal physics values
|
void InitPhysics(int maxPhysicElements); // Initialize all internal physics values
|
||||||
void SetPhysics(Physics settings); // Set physics settings values using Physics data type to overwrite internal physics settings
|
void UnloadPhysics(); // Unload physic elements arrays
|
||||||
|
|
||||||
void AddRigidbody(int index, Rigidbody rigidbody); // Initialize a new rigidbody with parameters to internal index slot
|
void AddRigidbody(int index, Rigidbody rigidbody); // Initialize a new rigidbody with parameters to internal index slot
|
||||||
void AddCollider(int index, Collider collider); // Initialize a new Collider with parameters to internal index slot
|
void AddCollider(int index, Collider collider); // Initialize a new Collider with parameters to internal index slot
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue