summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSid <36409334+heisid@users.noreply.github.com>2023-12-21 04:43:41 +0000
committerGitHub <noreply@github.com>2023-12-21 04:43:41 +0000
commitc9fdf69ddec787effe76d88e6a606eac054c1bfe (patch)
tree13ad84c491ac626686aa25eec921b1293504ea32
parentccdb9e90612bbaa0bb6357b56c0c95083f6104d6 (diff)
parent9d0453d24aefbaef33b448a91dceb34e4587fa67 (diff)
Merge pull request #1 from heisid/vector-field
Vector field
-rw-r--r--src/main.c213
1 files changed, 125 insertions, 88 deletions
diff --git a/src/main.c b/src/main.c
index 519dbfc..e536730 100644
--- a/src/main.c
+++ b/src/main.c
@@ -1,78 +1,100 @@
+#include <stdlib.h>
+#include <stdio.h>
+
#include "raylib.h"
#include "raymath.h"
-typedef struct InitConfig {
+typedef struct Config {
int SCREEN_WIDTH;
int SCREEN_HEIGHT;
- char TITLE[20];
+ int ORIGIN_X;
+ int ORIGIN_Y;
+ char TITLE[50];
int TARGET_FPS;
-} InitConfig;
+} Config;
+
+typedef struct Line {
+ Vector2 start;
+ Vector2 end;
+ Color color;
+} Line;
-typedef struct Ball {
- Vector2 pos;
+typedef struct Object {
+ float posX;
+ float posY;
float radius;
- float mass;
- Vector2 velocity;
- Vector2 force;
Color color;
-} Ball;
+ float charge;
+} Object;
-typedef struct Physics {
- float gravityConstant;
-} Physics;
+typedef struct VectorField {
+ int colSize;
+ int rowSize;
+ int spacing;
+ Line **lines;
+} VectorField;
-void doInitialization(InitConfig config);
-void doDrawing(Ball **balls, int totalBalls);
-void doUpdate(Ball **balls, int totalBalls, Physics physics);
+void Initialize(Config config);
+void InitializeVectorField(VectorField *vectorField, int colSize, int rowSize);
+void doDrawing(VectorField *vectorField, int colSize, int rowSize, Object *objects, int objectNum);
+void doUpdate(VectorField *vectorField, Object *objects, int objectNum);
int main(void)
{
- InitConfig config = {
+ Config config = {
1500,
900,
- "Just a fucking test",
+ 1500 / 2,
+ 900 / 2,
+ "Force Field Simulator",
60
};
- doInitialization(config);
-
- Physics physics = {
- .gravityConstant = 70.0f,
+ Initialize(config);
+
+ int spacing = 20;
+ int colSize = config.SCREEN_WIDTH / spacing - 1;
+ int rowSize = config.SCREEN_HEIGHT / spacing - 1;
+ Line **lines = NULL;
+ VectorField vectorField = {
+ .colSize = colSize,
+ .rowSize = rowSize,
+ .spacing = spacing,
+ .lines = lines
};
+ InitializeVectorField(&vectorField, colSize, rowSize);
- Ball luna = {
- .pos = {(float)config.SCREEN_WIDTH / 2, 0.0f + 100},
- .radius = 5,
- .mass = 200,
- .velocity = { 50.0f, 0.0f },
- .force = {0.0f, 0.0f},
- WHITE
- };
-
- Ball potato = {
- .pos = {(float)config.SCREEN_WIDTH / 2, (float)config.SCREEN_HEIGHT - 320},
- .radius = 5,
- .mass = 200,
- .velocity = { -80.0f, 0.0f },
- .force = {0.0f, 0.0f},
- YELLOW
+ Object object0 = {
+ .posX = (float)config.ORIGIN_X - 200,
+ .posY = (float)config.ORIGIN_Y,
+ .radius = 20,
+ .color = RED,
+ .charge = 100
};
- Ball earth = {
- .pos = {(float)config.SCREEN_WIDTH / 2, (float)config.SCREEN_HEIGHT / 2 },
+ Object object1 = {
+ .posX = (float)config.ORIGIN_X + 200,
+ .posY = (float)config.ORIGIN_Y,
.radius = 20,
- .mass = 15000,
- .velocity = { 0.0f, 0.0f },
- .force = {0.0f, 0.0f},
- BLUE
+ .color = BLUE,
+ .charge = -100
};
- Ball *balls[] = {&earth, &luna, &potato};
+// Object object2 = {
+// .posX = (float)config.ORIGIN_X + 200,
+// .posY = (float)config.ORIGIN_Y - 100,
+// .radius = 20,
+// .color = BLUE,
+// .charge = -100
+// };
+
+ Object objects[] = {object0, object1};
+ int objectNum = sizeof(objects) / sizeof(Object);
while (!WindowShouldClose())
{
- doUpdate(balls, 3, physics);
- doDrawing(balls, 3);
+ doUpdate(&vectorField, objects, objectNum);
+ doDrawing(&vectorField, colSize, rowSize, objects, objectNum);
}
CloseWindow();
@@ -80,66 +102,81 @@ int main(void)
return 0;
}
-void doInitialization(InitConfig config) {
+void Initialize(Config config) {
InitWindow(config.SCREEN_WIDTH, config.SCREEN_HEIGHT, config.TITLE);
SetTargetFPS(config.TARGET_FPS);
}
-//float pix2m(int pixels) {
-// // Pixel to meter conversion, 1 pixel = 1 cm
-// return 0.01f * (float)pixels;
-//}
-//
-//int m2pix(float metres) {
-// return (int)floorf(metres / 0.01f);
-//}
-
-Vector2 computeGravity(Ball *ball1, Ball *ball2, Physics physics) {
- // Gravity felt by ball2
- Vector2 displacement = Vector2Subtract(ball1->pos, ball2->pos);
- float gravityMag = (physics.gravityConstant * ball1->mass * ball2->mass) / Vector2LengthSqr(displacement);
- return Vector2Scale(Vector2Normalize(displacement), gravityMag);
+void MemAllocFailed(char *source) {
+ printf("Memory allocation for %s failed", source);
+ exit(42);
}
-Vector2 computeGravityNDimension(Ball *ball1, Ball *ball2, Physics physics, int dimension) {
- // Generalisasi. Nyoba kalo ada N-dimensi ruang
- Vector2 displacement = Vector2Subtract(ball1->pos, ball2->pos);
- float distance = Vector2Length(displacement);
- float distanceFactor = (float)pow(distance, dimension - 1);
- float gravityMag = (physics.gravityConstant * ball1->mass * ball2->mass) / distanceFactor;
- return Vector2Scale(Vector2Normalize(displacement), gravityMag);
+//float getRndAngle() {
+// float nMax = 360;
+// return (float)rand() / ((float)RAND_MAX / nMax); // NOLINT(cert-msc30-c, cert-msc50-cpp)
+//}
+
+void InitializeVectorField(VectorField *vectorField, int colSize, int rowSize) {
+ vectorField->lines = malloc(rowSize * sizeof(Line*));
+ for (int i = 0; i < rowSize; i++) {
+ vectorField->lines[i] = malloc(colSize * sizeof(Line));
+ for (int j = 0; j < colSize; j++) {
+ Vector2 start = {
+ (float)((j + 1) * vectorField->spacing),
+ (float)((i + 1) * vectorField->spacing)
+ };
+ Vector2 end = {start.x + 5, start.y - 5};
+ Line line = {
+ .start = start,
+ .end = end,
+ .color = WHITE
+ };
+ vectorField->lines[i][j] = line;
+ }
+ }
}
-void doUpdate(Ball **balls, int totalBalls, Physics physics) {
+void doUpdate(VectorField *vectorField, Object *objects, int objectNum) {
+ float forceConstant = 5000.0f;
float dt = GetFrameTime();
- for (int i = 0; i < totalBalls; i++) {
- Ball *ball = balls[i];
- // Sum over gravity felt from all other balls
- Vector2 gravityTotal = {0.0f, 0.0f};
- for (int j = 0; j < totalBalls; j++) {
- if (i != j) {
- Ball *otherBall = balls[j];
- Vector2 gravity = computeGravity(otherBall, ball, physics);
- gravityTotal = Vector2Add(gravityTotal, gravity);
+ for (int i = 0; i < vectorField->rowSize; i++) {
+ for (int j = 0; j < vectorField->colSize; j++) {
+ Vector2 resultant = Vector2Zero();
+ for (int k = 0; k < objectNum; k++) {
+ Object object = objects[k];
+ Vector2 distanceVector = Vector2Subtract(vectorField->lines[i][j].start, (Vector2){object.posX, object.posY});
+ float fieldStrength = forceConstant * object.charge / Vector2LengthSqr(distanceVector);
+ Vector2 force = Vector2Normalize(distanceVector);
+ force = Vector2Scale(force, fieldStrength);
+ resultant = Vector2Add(force, resultant);
+ }
+ float resultantMag = Clamp(Vector2Length(resultant), -20.0f, 20.0f);
+ if (fabsf(resultantMag) < 2.0f) {
+ resultantMag = resultantMag >= 0 ? 2.0f : -2.0f;
}
+ resultant = Vector2Normalize(resultant);
+ resultant = Vector2Scale(resultant, resultantMag);
+ vectorField->lines[i][j].end = Vector2Add(vectorField->lines[i][j].start, resultant);
}
- // Update position from last velocity
- ball->pos = Vector2Add(ball->pos, Vector2Scale(ball->velocity, dt));
- // a = F / m
- Vector2 acceleration = Vector2Scale(gravityTotal, 1.0f / ball->mass);
- // Update velocity for next frame
- ball->velocity = Vector2Add(ball->velocity, Vector2Scale(acceleration, dt));
}
+// objects[0].posX += 10 * dt;
+// objects[1].posX -= 10 * dt;
}
-void doDrawing(Ball **balls, int totalBalls) {
+void doDrawing(VectorField *vectorField, int colSize, int rowSize, Object *objects, int objectNum) {
BeginDrawing();
ClearBackground(BLACK);
- for (int i = 0; i < totalBalls; i++) {
- Ball *ball = balls[i];
- DrawCircleV(ball->pos, ball->radius, ball->color);
+ for (int i = 0; i < rowSize; i++) {
+ for (int j = 0; j < colSize; j++) {
+ DrawLineV(vectorField->lines[i][j].start, vectorField->lines[i][j].end, vectorField->lines[i][j].color);
+ }
+ }
+ for (int i = 0; i < objectNum; i++) {
+ Object object = objects[i];
+ DrawCircle((int)object.posX, (int)object.posY, object.radius, object.color);
}
EndDrawing();