96 lines
2.7 KiB
C++
96 lines
2.7 KiB
C++
#include "components/GravityReceiverComponent.hpp"
|
|
|
|
#include "Entity.hpp"
|
|
#include "components/GravityWellComponent.hpp"
|
|
#include "components/NullZoneComponent.hpp"
|
|
#include "components/PhysicsComponent.hpp"
|
|
#include "components/StatsComponent.hpp"
|
|
#include "components/TransformComponent.hpp"
|
|
|
|
#include <algorithm>
|
|
#include <cmath>
|
|
|
|
void GravityReceiverComponent::Setup() {}
|
|
|
|
void GravityReceiverComponent::Update(float dt) {
|
|
if (!context || !context->probeEntity || entity != context->probeEntity) {
|
|
return;
|
|
}
|
|
|
|
if (!well && context->wellEntity) {
|
|
well = context->wellEntity;
|
|
}
|
|
if (!well) {
|
|
return;
|
|
}
|
|
|
|
auto myTransform = entity->GetComponent<TransformComponent>();
|
|
auto physics = entity->GetComponent<PhysicsComponent>();
|
|
auto wellTransform = well->GetComponent<TransformComponent>();
|
|
auto wellGravity = well->GetComponent<GravityWellComponent>();
|
|
if (!myTransform || !physics || !wellTransform || !wellGravity) {
|
|
return;
|
|
}
|
|
|
|
StatsComponent *statsPtr = nullptr;
|
|
if (context->statsEntity) {
|
|
auto stats = context->statsEntity->GetComponent<StatsComponent>();
|
|
if (stats) {
|
|
statsPtr = &stats->get();
|
|
}
|
|
}
|
|
|
|
if (!wellGravity->get().active) {
|
|
return;
|
|
}
|
|
if (statsPtr && statsPtr->value <= 0.0f) {
|
|
return;
|
|
}
|
|
|
|
inVoid = false;
|
|
if (context->entities) {
|
|
for (auto &other : *context->entities) {
|
|
if (!other || other.get() == entity) {
|
|
continue;
|
|
}
|
|
|
|
auto zone = other->GetComponent<NullZoneComponent>();
|
|
auto zoneTransform = other->GetComponent<TransformComponent>();
|
|
if (!zone || !zoneTransform) {
|
|
continue;
|
|
}
|
|
|
|
const float left = zoneTransform->get().x;
|
|
const float right = left + zone->get().width;
|
|
if (myTransform->get().x >= left && myTransform->get().x <= right) {
|
|
inVoid = true;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
if (inVoid) {
|
|
return;
|
|
}
|
|
|
|
const float dx = wellTransform->get().x - myTransform->get().x;
|
|
const float dy = wellTransform->get().y - myTransform->get().y;
|
|
const float dist = std::sqrt(dx * dx + dy * dy);
|
|
if (dist <= 0.0001f) {
|
|
return;
|
|
}
|
|
|
|
const float clampedDist = std::max(dist, wellGravity->get().minDist);
|
|
const float force = wellGravity->get().mass / (clampedDist * clampedDist);
|
|
const float nx = dx / dist;
|
|
const float ny = dy / dist;
|
|
|
|
physics->get().vx += nx * force * dt;
|
|
physics->get().vy += ny * force * dt;
|
|
|
|
if (statsPtr) {
|
|
statsPtr->Drain(statsPtr->drainRate * dt);
|
|
}
|
|
}
|
|
|
|
void GravityReceiverComponent::Cleanup() {}
|