Cogs.Core
FPSNavigationComponent.cpp
1#include "FPSNavigationComponent.h"
2
3#include "ViewContext.h"
4#include "Input/InputManager.h"
5#include "Services/Time.h"
6#include "Components/Core/TransformComponent.h"
7
8#include "Foundation/Reflection/Method.h"
9
10#include <glm/gtx/quaternion.hpp>
11
12#include <algorithm>
13#include <numbers>
14
15using namespace Cogs::Core;
16using namespace Cogs::Reflection;
17
18void Cogs::Core::FPSNavigationComponent::registerType()
19{
20 Field fields[] = {
21 Field(Name("enable"), &FPSNavigationComponent::enable),
22 Field(Name("enablePitch"), &FPSNavigationComponent::enablePitch),
23 Field(Name("maxLinearSpeed"), &FPSNavigationComponent::maxLinearSpeed),
24 Field(Name("maxAngularSpeed"), &FPSNavigationComponent::maxAngularSpeed),
25 Field(Name("axisForward"), &FPSNavigationComponent::axisForward),
26 Field(Name("axisRight"), &FPSNavigationComponent::axisRight),
27 Field(Name("axisUp"), &FPSNavigationComponent::axisUp),
28 Field(Name("axisDown"), &FPSNavigationComponent::axisDown),
29 Field(Name("axisRotateUp"), &FPSNavigationComponent::axisRotateUp),
30 Field(Name("axisRotateRight"), &FPSNavigationComponent::axisRotateRight),
31 Field(Name("actionRun"), &FPSNavigationComponent::actionRun),
32 Field(Name("actionEnableNavigation"), &FPSNavigationComponent::actionEnableNavigation),
33 Field(Name("pitch"), &FPSNavigationComponent::pitch),
34 Field(Name("yaw"), &FPSNavigationComponent::yaw),
35 };
36 Method methods[] = {
37 Method(Name("initialize"), &FPSNavigationComponent::initialize),
38 Method(Name("update"), &FPSNavigationComponent::update),
39 };
40
41 DynamicComponent::registerDerivedType<FPSNavigationComponent>().setMethods(methods).setFields(fields);
42}
43
44void Cogs::Core::FPSNavigationComponent::initialize(Cogs::Core::Context * context)
45{
46 this->context = context;
47}
48
49glm::vec3 Cogs::Core::FPSNavigationComponent::getOffset()
50{
51 auto & input = context->getDefaultView()->inputManager;
52 auto speed = glm::vec3(
53 input->getAxisValue(axisRight),
54 input->getAxisValue(axisForward),
55 input->getAxisValue(axisUp) - input->getAxisValue(axisDown)
56 );
57
58 speed *= maxLinearSpeed;
59 if (input->getActionState(actionRun)) speed *= 3;
60 return speed * (float)context->time->getAnimationTimeDelta();
61}
62
63glm::vec2 Cogs::Core::FPSNavigationComponent::getPitchYawOffset()
64{
65 auto & input = context->getDefaultView()->inputManager;
66
67 glm::vec2 pitchYaw(input->getAxisValue(axisRotateUp), -input->getAxisValue(axisRotateRight));
68
69 pitchYaw *= maxAngularSpeed * context->time->getAnimationTimeDelta();
70
71 return pitchYaw;
72}
73
74void Cogs::Core::FPSNavigationComponent::update()
75{
76 if (!enable) return;
77
78 auto & input = context->getDefaultView()->inputManager;
79 auto posOffset = getOffset();
80 auto rotOffset = getPitchYawOffset();
81 if (actionEnableNavigation != "") {
82 if (!input->getActionState(actionEnableNavigation)) return;
83 }
84
85
86 auto pitchOffset = rotOffset.x;
87 auto yawOffset = rotOffset.y;
88
89 pitch += pitchOffset;
90 yaw += yawOffset;
91
92 if (enablePitch) {
93 constexpr float maxPitch = std::numbers::pi_v<float> / 2.0f;
94 if (pitch < -maxPitch) pitch = -maxPitch;
95 if (pitch > maxPitch) pitch = maxPitch;
96 }
97 else {
98 pitch = 0;
99 }
100
101 auto yawRot = glm::quat(glm::vec3(0, 0, yaw));
102 auto pitchRot = glm::quat(glm::vec3(pitch, 0, 0));
103
104 // When pitch control is enabled, we add a 90 degree rotation to point the camera forward instead of down
105 if (enablePitch) pitchRot *= glm::quat(glm::vec3(glm::half_pi<float>(), 0, 0));
106
107 auto * navigationTransform = getComponent<TransformComponent>();
108 navigationTransform->transform.trs.rotation = yawRot * pitchRot;
109
110 //find move direction:
111 posOffset = glm::rotate(yawRot, posOffset);
112
113 //apply translation:
114 navigationTransform->transform.trs.position += posOffset;
115
116 navigationTransform->setChanged();
117}
A Context instance contains all the services, systems and runtime components needed to use Cogs.
Definition: Context.h:83
Field definition describing a single data member of a data structure.
Definition: Field.h:70
Simple method definition.
Definition: Method.h:72
Contains the Engine, Renderer, resource managers and other systems needed to run Cogs....
Contains reflection support.
Definition: Component.h:11
Represents an unique name.
Definition: Name.h:70