0

I am trying to implement a very basic physics system, specifically gravity, in C. I have structured the individual components as follows:

typedef struct Gravity {
  float force[2];
} Gravity;

typedef struct Rigidbody {
  float velocity2];
  float acceleration[2];
} Rigidbody;

typedef struct Transform {
  float position[2];
  float rotation[2];
  float scale[2];
} Transform;

In my update function I iterate through all living entities that have those three components then directly update the array values for that specific entity:

void updatePhysics(ECS* ecs, float delta) {
  if (!ecs)
    return;

  for (Entity entity = 0; entity < (ecs -> entities -> count); entity++) {
    if (isLiving(ecs, entity)) {
      Gravity* gravity = getComponent(ecs, entity, GRAVITY);
      Rigidbody* rigidbody = getComponent(ecs, entity, RIGIDBODY);
      Transform* transform = getComponent(ecs, entity, RIGIDBODY);

      if ((gravity == NULL) || (rigidbody == NULL) || (transform == NULL))
        continue;

      printf("Update Method Check, Position: (%.1f, %.1f)\n", (transform -> position)[0], (transform -> position)[1]);
      for (int itr = 0; itr < 2; itr++) {
        (gravity -> force)[itr] *= delta;
        (rigidbody -> velocity)[itr] *= delta;

        (transform -> position)[itr] += (gravity -> force)[itr];
        (transform -> position)[itr] += (rigidbody -> velocity)[itr];
      }
    }
  }
}

I created a test entity with the required components and check it's current position in my main game loop:

static void frame(void) {
  if (keypress(KEY_ESCAPE))
    app.quit = true;

  Transform* transform = getComponent(app.ecs, player, TRANSFORM);
  printf("Main Game Loop, Position: (%.1f, %.1f)\n\n", (transform -> position)[0], (transform -> position)[1]);
}

Everything should work, but the position of the entity doesn't update globally, only locally in the physics update function. The output of the print statements:

Update Method Check, Position: (0.0, 0.0)
Main Game Loop, Position: (0.0, 0.0)

Update Method Check, Position: (0.0, -10.0)
Main Game Loop, Position: (0.0, 0.0)

Update Method Check, Position: (0.0, -30.0)
Main Game Loop, Position: (0.0, 0.0)

Update Method Check, Position: (0.0, -70.0)
Main Game Loop, Position: (0.0, 0.0)

Update Method Check, Position: (0.0, -150.0)
Main Game Loop, Position: (0.0, 0.0)

...

What am I missing that's preventing the entity's position from being updated globally?

Solution: There was an error in my getComponent() method where I was getting a Rigidbody component instead of a Transform component. Made the change to the proper component type and the bug is fixed.

Transform* transform = getComponent(ecs, entity, TRANSFORM);
2
  • 1
    Please post a minimal reproducible example. I suspect getComponent() doesn't return the same pointer either because of defect or because the arguments you pass to it are different. One easy way to check is to print out the address of the return value in both cases. Commented Jul 31, 2022 at 22:39
  • Yeah, you actually nailed it on the head. As I was creating an example, I noticed that I messed up on getComponent() and was improperly getting two Rigidbody components instead of the Transform component I needed. It works now, thank you @AllanWind Commented Jul 31, 2022 at 23:01

1 Answer 1

1

getComponent() doesn't return the same pointer in updatePhysics() and your test runner. Either because of defect in getComponent() (not shared with us), or it is being called with different arguments.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.