Skip to content

Commit fef9cc2

Browse files
committed
[renderer] Added mouse input handling.
Rotate octree when left mouse button is hold down and mouse is being moved. Added extensive camera class from Sascha Willems' example repository.
1 parent 7128b9a commit fef9cc2

File tree

7 files changed

+225
-393
lines changed

7 files changed

+225
-393
lines changed

include/inexor/vulkan-renderer/application.hpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,11 @@ class Application : public VulkanRenderer, public tools::CommandLineArgumentPars
8888

8989
VkResult update_keyboard_input();
9090

91+
VkResult update_mouse_input();
92+
93+
// TODO: Refactor!
94+
double cursor_x, cursor_y;
95+
9196
public:
9297
VkResult init();
9398

include/inexor/vulkan-renderer/camera.hpp

Lines changed: 168 additions & 189 deletions
Original file line numberDiff line numberDiff line change
@@ -3,207 +3,186 @@
33
#include <glm/glm.hpp>
44
#include <glm/gtc/matrix_transform.hpp>
55
#include <glm/gtc/quaternion.hpp>
6-
#include <spdlog/spdlog.h>
7-
8-
#include <mutex>
96

107
namespace inexor::vulkan_renderer {
118

12-
/// TODO: Add mutex!
13-
/// TODO: Because this camera class will be used by scripting as well, runtime errors should be expected.
9+
// TODO: Refactor method naming!
1410
class Camera {
1511
private:
16-
glm::vec3 position = glm::vec3(0.0f, 0.0f, 0.0f);
17-
18-
glm::vec3 direction = glm::vec3(0.0f, 0.0f, 0.0f);
19-
20-
float camera_speed = 1.0f;
21-
22-
// TODO: Change with respect to window resolution!
23-
float aspect_ratio = 800 / 600;
24-
25-
float yaw = 0.0f;
26-
27-
float pitch = 0.0f;
28-
29-
float roll = 0.0f;
30-
31-
float near_plane = 0.1f;
32-
33-
float far_plane = 10.0f;
34-
35-
float zoom = 45.0f;
36-
37-
bool camera_is_moving = false;
38-
39-
bool moving_backwards = false;
40-
41-
glm::vec3 world_up = glm::vec3(0.0f, 0.0f, 1.0f);
42-
43-
glm::vec3 world_front = glm::vec3(1.0f, 0.0f, 0.0f);
12+
float fov;
13+
float znear, zfar;
4414

45-
glm::vec3 world_right = glm::vec3(0.0f, 1.0f, 0.0f);
15+
void updateViewMatrix() {
16+
glm::mat4 rotM = glm::mat4(1.0f);
17+
glm::mat4 transM;
4618

47-
glm::mat4 view_matrix = glm::mat4();
19+
rotM = glm::rotate(rotM, glm::radians(rotation.x), glm::vec3(1.0f, 0.0f, 0.0f));
20+
rotM = glm::rotate(rotM, glm::radians(rotation.y), glm::vec3(0.0f, 1.0f, 0.0f));
21+
rotM = glm::rotate(rotM, glm::radians(rotation.z), glm::vec3(0.0f, 0.0f, 1.0f));
4822

49-
glm::mat4 projection_matrix = glm::mat4();
23+
transM = glm::translate(glm::mat4(1.0f), position * glm::vec3(1.0f, 1.0f, -1.0f));
5024

51-
/// Neccesary for taking into account the relative speed of the system's CPU.
52-
/// The timestep will be calculated in the main loop and will be passed on when update() is called.
53-
float timestep;
25+
if (type == CameraType::firstperson) {
26+
matrices.view = rotM * transM;
27+
} else {
28+
matrices.view = transM * rotM;
29+
}
5430

55-
private:
56-
/// @brief Updates the view matrix.
57-
void update_view_matrix();
58-
59-
/// @brief Updates the projection matrix.
60-
void update_projection_matrix();
31+
updated = true;
32+
};
6133

6234
public:
63-
Camera() = default;
64-
65-
~Camera() = default;
66-
67-
/// @brief Updates all matrices.
68-
void update_matrices();
69-
70-
/// @brief Start moving the camera every time update() is called.
71-
/// @param moving_backwards [in] True if the camera is moving backwards, false otherwise.
72-
void start_camera_movement(bool moving_backwards = false);
73-
74-
/// @brief Ends moving the camera every time update() is called.
75-
void end_camera_movement();
76-
77-
/// @brief Updates camera movement.
78-
/// @brief timestep [in] A float which scales with the amount of time which has passed since last rendering.
79-
void update(float timestep);
80-
81-
/// @brief Sets the camera position.
82-
/// @param position [in] The position of the camera.
83-
void set_position(const glm::vec3 &position);
84-
85-
/// @brief Returns he current camera position.
86-
glm::vec3 get_position() const;
87-
88-
/// @brief Sets the relative speed of the camera.
89-
/// @param speed [in] The velocity of the camera movement.
90-
void set_speed(float camera_speed);
91-
92-
/// @brief Returns the camera speed.
93-
float get_speed() const;
94-
95-
/// @brief
96-
/// @param direction [in] The direction in which we look.
97-
void set_direction(const glm::vec3 &direction);
98-
99-
/// @brief Returns the direction in which the camera is looking.
100-
glm::vec3 get_direction() const;
101-
102-
/// @brief Moves the camera forwards with respect to the relative camera speed.
103-
void move_forwards();
104-
105-
/// @brief Moves the camera backwards with respect to the relative camera speed.
106-
void move_backwards();
107-
108-
/// @brief Moves the camera along the x-axis.
109-
/// @param y [in] The distance on the x-axis.
110-
void move_camera_x(float x);
111-
112-
/// @brief Moves the camera along the y-axis.
113-
/// @param y [in] The distance on the y-axis.
114-
void move_camera_y(float y);
115-
116-
/// @brief Moves the camera along the z-axis.
117-
/// @param y [in] The distance on the z-axis.
118-
void move_camera_z(float z);
119-
120-
/// @brief Sets the yaw rotation angle.
121-
/// @param yaw [in] The yaw angle.
122-
void set_yaw(float yaw);
123-
124-
/// @brief Sets the pitch rotation angle.
125-
/// @param pitch [in] The pitch angle.
126-
void set_pitch(float pitch);
127-
128-
/// @brief Sets the roll rotation angle.
129-
/// @param roll [in] The roll angle.
130-
void set_roll(float roll);
131-
132-
/// @brief Returns the yaw rotation angle.
133-
float get_yaw() const;
134-
135-
/// @brief Returns the pitch rotation angle.
136-
float get_pitch() const;
137-
138-
/// @brief Returns the roll rotation angle.
139-
float get_roll() const;
140-
141-
/// @brief Sets the near plane for calculating the projection matrix.
142-
/// @param near_plane [in] The z-distance to the near plane.
143-
void set_near_plane(float near_plane);
144-
145-
/// @brief Returns the near plane.
146-
float get_near_plane() const;
147-
148-
/// @brief Sets the far plane for calculating the projection matrix.
149-
/// @param far_plane [in] The z-distance to the far plane.
150-
void set_far_plane(float far_plane);
151-
152-
/// @brief Returns the far plane.
153-
float get_far_plane() const;
154-
155-
/// @brief Sets the aspect ratio.
156-
/// @param aspect_ratio [in] The aspect ratio.
157-
void set_aspect_ratio(float aspect_ratio);
158-
159-
/// @brief Returns the aspect ratio.
160-
float get_aspect_ratio() const;
161-
162-
/// @brief Sets the rotation of the camera matrix.
163-
/// @param yaw [in] The yaw angle.
164-
/// @param pitch [in] The pitch angle.
165-
/// @param roll [in] The roll angle.
166-
void set_rotation(float yaw, float pitch, float roll);
167-
168-
/// @brief Rotates the Camera around a certain center.
169-
/// @brief rotation_center [in] The center of rotation.
170-
/// @brief angle_x [in] The angle around x-axis.
171-
/// @brief angle_y [in] The angle around y-axis.
172-
/// @todo
173-
void rotate(const glm::vec3 &rotation_center, float angle_x, float angle_y);
174-
175-
/// @brief Returns the rotation vector of the camera relative to the up vector.
176-
/// @todo
177-
glm::vec3 get_rotation() const;
178-
179-
/// @brief Returns the up vector.
180-
glm::vec3 get_up() const;
181-
182-
/// @brief Returns the front vector.
183-
glm::vec3 get_front() const;
184-
185-
/// @brief Returns the right vector.
186-
glm::vec3 get_right() const;
187-
188-
/// @brief Pan function (translate both camera eye and lookat point).
189-
/// @param x The angle on the x-axis.
190-
/// @param y The angle on the y-axis.
191-
/// @todo
192-
void pan(float x, float y);
193-
194-
/// @brief Sets the zoom of the camera.
195-
/// @param zoom [in] The camera zoom.
196-
void set_zoom(float zoom);
197-
198-
// TODO: min/max zoom!
199-
/// @brief Returns the camera zoom.
200-
float get_zoom() const;
201-
202-
/// @brief Returns the view matrix.
203-
glm::mat4 get_view_matrix();
204-
205-
/// @brief Returns the projection matrix.
206-
glm::mat4 get_projection_matrix();
35+
enum CameraType { lookat, firstperson };
36+
CameraType type = CameraType::lookat;
37+
38+
glm::vec3 rotation = glm::vec3();
39+
glm::vec3 position = glm::vec3();
40+
41+
float rotationSpeed = 1.0f;
42+
float movementSpeed = 1.0f;
43+
44+
bool updated = false;
45+
46+
struct {
47+
glm::mat4 perspective;
48+
glm::mat4 view;
49+
} matrices;
50+
51+
struct {
52+
bool left = false;
53+
bool right = false;
54+
bool up = false;
55+
bool down = false;
56+
} keys;
57+
58+
bool moving() {
59+
return keys.left || keys.right || keys.up || keys.down;
60+
}
61+
62+
float getNearClip() {
63+
return znear;
64+
}
65+
66+
float getFarClip() {
67+
return zfar;
68+
}
69+
70+
void setPerspective(float fov, float aspect, float znear, float zfar) {
71+
this->fov = fov;
72+
this->znear = znear;
73+
this->zfar = zfar;
74+
matrices.perspective = glm::perspective(glm::radians(fov), aspect, znear, zfar);
75+
};
76+
77+
void updateAspectRatio(float aspect) {
78+
matrices.perspective = glm::perspective(glm::radians(fov), aspect, znear, zfar);
79+
}
80+
81+
void setPosition(glm::vec3 position) {
82+
this->position = position;
83+
updateViewMatrix();
84+
}
85+
86+
void setRotation(glm::vec3 rotation) {
87+
this->rotation = rotation;
88+
updateViewMatrix();
89+
};
90+
91+
void rotate(glm::vec3 delta) {
92+
this->rotation += delta;
93+
updateViewMatrix();
94+
}
95+
96+
void setTranslation(glm::vec3 translation) {
97+
this->position = translation;
98+
updateViewMatrix();
99+
};
100+
101+
void translate(glm::vec3 delta) {
102+
this->position += delta;
103+
updateViewMatrix();
104+
}
105+
106+
void update(float deltaTime) {
107+
updated = false;
108+
if (type == CameraType::firstperson) {
109+
if (moving()) {
110+
glm::vec3 camFront;
111+
camFront.x = -cos(glm::radians(rotation.x)) * sin(glm::radians(rotation.y));
112+
camFront.y = sin(glm::radians(rotation.x));
113+
camFront.z = cos(glm::radians(rotation.x)) * cos(glm::radians(rotation.y));
114+
camFront = glm::normalize(camFront);
115+
116+
float moveSpeed = deltaTime * movementSpeed;
117+
118+
if (keys.up)
119+
position += camFront * moveSpeed;
120+
if (keys.down)
121+
position -= camFront * moveSpeed;
122+
if (keys.left)
123+
position -= glm::normalize(glm::cross(camFront, glm::vec3(0.0f, 1.0f, 0.0f))) * moveSpeed;
124+
if (keys.right)
125+
position += glm::normalize(glm::cross(camFront, glm::vec3(0.0f, 1.0f, 0.0f))) * moveSpeed;
126+
127+
updateViewMatrix();
128+
}
129+
}
130+
};
131+
132+
// Update camera passing separate axis data (gamepad)
133+
// Returns true if view or position has been changed
134+
bool updatePad(glm::vec2 axisLeft, glm::vec2 axisRight, float deltaTime) {
135+
bool retVal = false;
136+
137+
if (type == CameraType::firstperson) {
138+
// Use the common console thumbstick layout
139+
// Left = view, right = move
140+
141+
const float deadZone = 0.0015f;
142+
const float range = 1.0f - deadZone;
143+
144+
glm::vec3 camFront;
145+
camFront.x = -cos(glm::radians(rotation.x)) * sin(glm::radians(rotation.y));
146+
camFront.y = sin(glm::radians(rotation.x));
147+
camFront.z = cos(glm::radians(rotation.x)) * cos(glm::radians(rotation.y));
148+
camFront = glm::normalize(camFront);
149+
150+
float moveSpeed = deltaTime * movementSpeed * 2.0f;
151+
float rotSpeed = deltaTime * rotationSpeed * 50.0f;
152+
153+
// Move
154+
if (fabsf(axisLeft.y) > deadZone) {
155+
float pos = (fabsf(axisLeft.y) - deadZone) / range;
156+
position -= camFront * pos * ((axisLeft.y < 0.0f) ? -1.0f : 1.0f) * moveSpeed;
157+
retVal = true;
158+
}
159+
if (fabsf(axisLeft.x) > deadZone) {
160+
float pos = (fabsf(axisLeft.x) - deadZone) / range;
161+
position += glm::normalize(glm::cross(camFront, glm::vec3(0.0f, 1.0f, 0.0f))) * pos * ((axisLeft.x < 0.0f) ? -1.0f : 1.0f) * moveSpeed;
162+
retVal = true;
163+
}
164+
165+
// Rotate
166+
if (fabsf(axisRight.x) > deadZone) {
167+
float pos = (fabsf(axisRight.x) - deadZone) / range;
168+
rotation.y += pos * ((axisRight.x < 0.0f) ? -1.0f : 1.0f) * rotSpeed;
169+
retVal = true;
170+
}
171+
if (fabsf(axisRight.y) > deadZone) {
172+
float pos = (fabsf(axisRight.y) - deadZone) / range;
173+
rotation.x -= pos * ((axisRight.y < 0.0f) ? -1.0f : 1.0f) * rotSpeed;
174+
retVal = true;
175+
}
176+
} else {
177+
// todo: move code from example base class for look-at
178+
}
179+
180+
if (retVal) {
181+
updateViewMatrix();
182+
}
183+
184+
return retVal;
185+
}
207186
};
208187

209188
} // namespace inexor::vulkan_renderer

0 commit comments

Comments
 (0)