117 lines
5.4 KiB
C++
117 lines
5.4 KiB
C++
/* +------------------------------------------------------+
|
|
____/ \____ /| - Open source game framework licensed to freely use, |
|
|
\ / / | copy, modify and sell without restriction |
|
|
+--\ ^__^ /--+ | |
|
|
| ~/ \~ | | - created for <https://foam.shampoo.ooo> |
|
|
| ~~~~~~~~~~~~ | +------------------------------------------------------+
|
|
| SPACE ~~~~~ | /
|
|
| ~~~~~~~ BOX |/
|
|
+--------------+
|
|
|
|
[math.hpp]
|
|
|
|
For math helper functions that require only GLM primitives, especially trigonometric functions.
|
|
Angle values are in radians. 0 is directly up on the screen in GL coordinates, and the angle increases
|
|
clockwise.
|
|
|
|
This test of points on a square and one point below the square should print the output below.
|
|
|
|
glm::vec2 a {5.0f, 5.0f}, b {1.0f, 1.0f}, c {1.0f, 5.0f}, d {5.0f, 1.0f}, e {5.0f, -1.0f};
|
|
std::cout << glm::degrees(sb::angle_between(a, b)) << " " << glm::degrees(sb::angle_between(b, a)) << " " <<
|
|
glm::degrees(sb::angle_between(a, c)) << " " << glm::degrees(sb::angle_between(c, a)) << " " <<
|
|
glm::degrees(sb::angle_between(b, e)) << " " << glm::degrees(sb::angle_between(e, b)) << std::endl <<
|
|
sb::velocity_to_delta(sb::angle_between(a, b), 4.0f * glm::sqrt(2.0f)) << " " <<
|
|
sb::velocity_to_delta(sb::angle_between(b, a), 4.0f * glm::sqrt(2.0f)) << " " <<
|
|
sb::velocity_to_delta(sb::angle_between(d, a), 4.0f) << " " <<
|
|
sb::velocity_to_delta(sb::angle_between(b, e), 1.0f) << std::endl;
|
|
|
|
Should print,
|
|
|
|
-135 45 -90 90 116.565 -63.435
|
|
{-4, -4} {4, 4} {0, 4} {0.894427, -0.447214}
|
|
|
|
This test of angle differences should print the output below.
|
|
|
|
float a = 0.0f, b = glm::pi<float>(), c = glm::half_pi<float>(), d = 0.5f, e = glm::pi<float>() * 4;
|
|
std::cout << sb::angle_difference(a, b) << " " << sb::angle_difference(a, c) << " " << sb::angle_difference(b, c) << " " <<
|
|
sb::angle_difference(a, d) << " " << sb::angle_difference(c, d) << " " << sb::angle_difference(a, e) << " " <<
|
|
sb::angle_difference(c, e) << " " << sb::angle_difference(d, e) << " " << sb::angle_difference(c, c) << std::endl <<
|
|
sb::angle_ratio(a, b) << " " << sb::angle_ratio(a, c) << " " << sb::angle_ratio(b, c) << " " << sb::angle_ratio(a, d) << " " <<
|
|
sb::angle_ratio(c, d) << " " << sb::angle_ratio(a, e) << " " << sb::angle_ratio(c, e) << " " << sb::angle_ratio(d, e) << " " <<
|
|
sb::angle_ratio(c, c) << std::endl;
|
|
|
|
Should print,
|
|
|
|
-3.14159 1.5708 -1.5708 0.5 -1.0708 3.49691e-07 -1.5708 -0.5 0
|
|
-1 0.5 -0.5 0.159155 -0.340845 1.1131e-07 -0.5 -0.159155 0
|
|
*/
|
|
|
|
#pragma once
|
|
|
|
#include <vector>
|
|
|
|
/* GLM */
|
|
#define GLM_ENABLE_EXPERIMENTAL
|
|
#include <glm/glm.hpp>
|
|
#include <glm/gtx/compatibility.hpp>
|
|
|
|
namespace sb
|
|
{
|
|
static inline const glm::vec3 ZAXIS {0.0f, 0.0f, 1.0f};
|
|
|
|
/*!
|
|
* Convert a vector described by the given angle and magnitude to an X and Y offset vector.
|
|
*
|
|
* @param angle a float representing the angle of velocity in radians, with 0 being up on the screen and increasing
|
|
* values going clockwise
|
|
* @param magnitude a float representing the speed, or the magnitude of the input vector in the X/Y plane
|
|
* @return a glm::vec2 of the change in X and Y for the given velocity vector
|
|
*/
|
|
glm::vec2 velocity_to_delta(float angle, float magnitude);
|
|
|
|
/*!
|
|
* @overload glm::vec2 velocity_to_delta(float angle, float magnitude)
|
|
*/
|
|
glm::vec2 velocity_to_delta(glm::vec2 velocity);
|
|
|
|
/*!
|
|
* Get the angle between two vectors, or the angle the first would rotate to to point toward the second.
|
|
*
|
|
* @param start X/Y coordinates
|
|
* @param end X/Y coordinates
|
|
* @return an angle in radians
|
|
*/
|
|
float angle_between(glm::vec2 start, glm::vec2 end);
|
|
|
|
/*!
|
|
* Get the signed shortest angle difference between two angles, or how much the first angle would have to rotate
|
|
* to be equivalent to the second angle. Negative is counter-clockwise, positive clockwise.
|
|
*
|
|
* @param start X/Y coordinates of the angle which the difference will be relative to
|
|
* @param end X/Y coordinates of the angle which the difference will be rotated to
|
|
* @return angle difference relative to the start parameter in radians
|
|
*/
|
|
float angle_difference(float start, float end);
|
|
|
|
/*!
|
|
* Get the angle difference between two angles as a signed ratio of how much of a 180 degree turn it is. Negative
|
|
* is counter-clockwise, positive clockwise.
|
|
*
|
|
* @param start X/Y coordinates of the angle which the difference will be relative to
|
|
* @param end X/Y coordinates of the angle which the difference will be rotated to
|
|
* @return angle difference relative to the start parameter as a signed ratio of how much of a 180 degree
|
|
* turn it is.
|
|
*/
|
|
float angle_ratio(float start, float end);
|
|
|
|
/*!
|
|
* Calculate a 2D bezier curve from four 2D control points.
|
|
*
|
|
* Adapted from public domain released code, 2007 Victor Blomqvist, originally at https://www.pygame.org/wiki/BezierCurve.
|
|
*
|
|
* @param vertices four 2D control points
|
|
* @param resolution number of points that will be in the computed curve
|
|
*/
|
|
std::vector<glm::vec2> bezier(const std::vector<glm::vec2>& vertices, int resolution = 30);
|
|
}
|