Types
Variables
Functions
eul->matrix(arg0: matrix, arg1: euler-angles) => matrixsource
Convert from euler angles to 4x4 matrix.
eul->quat(arg0: quaternion, arg1: euler-angles) => quaternionsource
Convert euler angles to quaternion, not very efficient.
matrix->eul(arg0: euler-angles, arg1: matrix, arg2: int) => euler-anglessource
Convert matrix to euler angles with given order flag.
Not clear how this works if the matrix has more than just a rotation.
quat->eul(arg0: euler-angles, arg1: quaternion, arg2: int) => euler-anglessource
Conver quaternion to euler angles with given order, not very efficient.
set-eul!(arg0: euler-angles, arg1: float, arg2: float, arg3: float, arg4: int) => euler-anglessource
Set euler angles and the flag bits.
Types
float-type: uint32source
rgba: uint32source
xyzw: uint128source
xyzwh: uint128source
Functions
fractional-part(arg0: float) => floatsource
Get the fractional part of a float.
lerp(arg0: float, arg1: float, arg2: float) => floatsource
Linearly interpolate between arg0 and arg1.
lerp-clamp(arg0: float, arg1: float, arg2: float) => floatsource
Linearly interpolate between arg0 and arg1. arg2 is clamped to [0, 1]
lerp-scale(arg0: float, arg1: float, arg2: float, arg3: float, arg4: float) => floatsource
Linearly remap arg2 in [arg3, arg4] to [arg0, arg1].
More efficient than the -old version.
lerp-scale-old(arg0: float, arg1: float, arg2: float, arg3: float, arg4: float) => floatsource
log-x-plus-1-order9(arg0: float) => floatsource
Fast approximation of ln(x + 1). Probably only accurate for x in [0, 1].
print-time(arg0: object, arg1: time-frame) => nonesource
Print a time-frame as minutes:seconds:milliseconds
rand-uint31-gen(gen: random-generator) => uintsource
Generate a supposedly random integer.
Note, this might not quite be right.
But the highest bit is always zero, like it says
and it looks kinda random to me.
rand-vu-float-range(arg0: float, arg1: float) => floatsource
Get a random float in between arg0 and arg1
rand-vu-init(seed: float) => floatsource
Initialize the VU0 random generator
rand-vu-int-count(arg0: int) => intsource
Get an integer in the range [0, max).
rand-vu-int-count-excluding(arg0: int, arg1: int) => intsource
Get an integer in the range [0, arg0).
If bit n is set in arg1, exclude this value from being returned.
rand-vu-int-range(arg0: int, arg1: int) => intsource
Get an integer in the given range (inclusive)
rand-vu-int-range-exclude(arg0: int, arg1: int, arg2: int) => intsource
Get an integer in the range [0, arg0), excluding arg2.
Note that this doesn't use bits like rand-vu-int-count-excluding.
rand-vu-nostep() => floatsource
Get the number currently in the random generator.
This will be equal to the last call of (rand-vu)
This will not update the random generator
rand-vu-percent?(arg0: float) => symbolsource
Get a boolean that's true with the given probability (in 0, 1)
sawtooth-wave(arg0: float) => floatsource
Sample a sawtooth with period 1. In range (0, 1)
seek-ease(arg0: float, arg1: float, arg2: float, arg3: float, arg4: float) => floatsource
Move arg0 toward arg1, and slow down before reaching the end.
When farther than arg3 away, move by at most arg2.
When closer than arg3, linearly ramp down the movement amount from arg2 to 0.
When closer than arg4, just go all the way there.
seek-ease-in-out(arg0: float, arg1: float, arg2: float, arg3: float, arg4: float, arg5: float, arg6: float) => floatsource
Move arg0 toward arg2, and slow down at the start and end.
When within arg4 of arg1 (at the beginning of movement), ramp up speed, with a minimum speed of arg6
When within arg5 of arg2 (at the end of movement), ramp down speed, with a minimum speed of arg5
Normally, move at most arg3
smooth-interp(arg0: float, arg1: float, arg2: float, arg3: float, arg4: float) => floatsource
Remap arg2 from (arg3, arg4) to (arg0, arg1), using cubic interpolation.
Satisfies:
- f(arg3) = arg0
- f(arg4) = arg1
- f'(arg3) = f'(arg4) = 0
smooth-step(arg0: float) => floatsource
Interpolate between 0, 1 with a cubic polynomial.
These are picked so f(0) = 0, f(1) = 1, f'(0) = f'(1) = 0.
triangle-wave(arg0: float) => floatsource
Sample a triangle wave. Period is 4, in range (-1, 1) (so slope is 1 or -1).
Variables
*_vu-reg-R_*: intsource
const exp-strail: pointersource
Types
matrix: structuresource
Functions
matrix-copy!(arg0: matrix, arg1: matrix) => matrixsource
Copy arg1 to arg0
Expand description
This file implements the GOAL matrix library.
In general, a vector is always treated as a row vector.
Chaining transformation is done like v_row * T1_goal * T2_goal, which means do T1 before T2.
This is the opposite of the usual convention:
T2_normal * T1_normal * v_col
However, there is good news:
T1_normal = T1_goal ^ T
T2_normal = T2_goal ^ T
This is due to the property
(A * B)^T = B^T * A^T
So a homogeneous transformation is:
R_xx R_xy R_xz 0
R_yx R_yy R_yz 0
R_zx R_zy R_zz 0
T_x T_y T_z 1
which is probably the transpose of what you're used to.
note that they also used row-major storage, so the 3rd qword of a matrix is the translation
part of the affine transform.
In general, be careful with using these functions as they often have strange
requirements for the form of the input matrix or if the input/output matrix are
allowed to be the same memory.
Functions
column-scale-matrix!(arg0: matrix, arg1: vector, arg2: matrix) => matrixsource
Scale an existing matrix. Okay for dst = src. The scaling is applied column-wise.
Meaning the x component of scale will scale the first column of src.
matrix*!(arg0: matrix, arg1: matrix, arg2: matrix) => matrixsource
Set dst = src1 * src2. It is okay for any arguments to be the same data.
This is a moderately efficient implementation.
matrix+!(arg0: matrix, arg1: matrix, arg2: matrix) => matrixsource
Set dst = src1 + src2. It is okay for any arguments to be the same data.
This is not an efficient implementation.
matrix-!(arg0: matrix, arg1: matrix, arg2: matrix) => matrixsource
Set dst = src1 - src1. It is okay for any arugments to be the same data.
This is not an efficient implementation.
matrix-3x3-determinant(arg0: matrix) => floatsource
Compute the determinant of a 3x3 matrix
matrix-3x3-inverse!(arg0: matrix, arg1: matrix) => matrixsource
Compute the inverse of a 3x3 matrix. Not very efficient.
Requires src != dst.
matrix-3x3-inverse-transpose!(arg0: matrix, arg1: matrix) => matrixsource
Invert and transpose.
Requires dst != src.
matrix-3x3-normalize!(arg0: matrix, arg1: matrix) => matrixsource
Unused.
matrix-4x4-determinant(arg0: matrix) => floatsource
Take the determinant of a 4x4 matrix, but this is wrong.
matrix-4x4-inverse!(arg0: matrix, arg1: matrix) => matrixsource
Invert a 4x4 matrix. This assumes that the input is a homogeneous transform.
Src and dst can be the same.
matrix-4x4-inverse-transpose!(arg0: matrix, arg1: matrix) => matrixsource
Invert and transpose an entire 4x4. I think has no restrictions, other than dst != src. Unused.
The answer is wrong. The determinant function is wrong.
matrix->quat(arg0: matrix, arg1: quaternion) => quaternionsource
Convert matrix to quaternion, works for matrix with scale.
unlike matrix->quaternion.
matrix->scale(arg0: matrix, arg1: vector) => vectorsource
Get the scale of a matrix.
matrix->trans(arg0: matrix, arg1: vector) => vectorsource
Multiply xyz by 1/w.
matrix->transformq(arg0: transformq, arg1: matrix) => transformqsource
Create a transformq from a matrix. Allowing scale, etc.
matrix-axis-angle!(arg0: matrix, arg1: vector, arg2: float) => matrixsource
Create an axis-angle rotation matrix.
matrix-axis-sin-cos!(dst: matrix, axis: vector, s: float, c: float) => matrixsource
Create an axis-angle rotation matrix. But given the sin/cos of the angle.
matrix-axis-sin-cos-vu!(arg0: matrix, arg1: vector, arg2: float, arg3: float) => nonesource
Create an axis-angle rotation matrix. But given the sin/cos of the angle.
matrix-identity!(arg0: matrix) => matrixsource
Set dst to the identity matrix.
matrix-inv-scale!(arg0: matrix, arg1: vector) => matrixsource
Set dst to a homogeneous transform with only a scale.
The x,y,z components of scale are inverted and used as the x,y,z scaling factors
matrix-inverse-of-rot-trans!(arg0: matrix, arg1: matrix) => matrixsource
Set dst = src^-1, assuming src is a homogeneous tranform with only rotation/translation.
NOTE: THIS FUNCTION REQUIRES dst != src
matrix-lerp!(arg0: matrix, arg1: matrix, arg2: matrix, arg3: float) => matrixsource
Lerp an entire matrix, coefficient-wise.
matrix-mirror!(arg0: matrix, arg1: vector, arg2: vector) => matrixsource
Make a matrix that mirrors. Arguments are unclear.
matrix-rotate-x!(arg0: matrix, arg1: float) => matrixsource
Set dst to a homogeneous transform matrix for a rotation around the x-axis (degrees)
matrix-rotate-xyz!(arg0: matrix, arg1: vector) => matrixsource
Rotate in x,y,z order
matrix-rotate-xyz-2!(arg0: matrix, arg1: vector) => matrixsource
matrix-rotate-y!(arg0: matrix, arg1: float) => matrixsource
Set dst to a homoegeneous transform matrix for a rotation around the y axis (degrees)
matrix-rotate-yx!(arg0: matrix, arg1: float, arg2: float) => matrixsource
Rotate by y then x.
matrix-rotate-yxy!(arg0: matrix, arg1: vector) => matrixsource
Rotate. I believe in yxy order? Compared to the other rotations, this one
is quite a bit more optimized and avoid repeated trig operations.
matrix-rotate-yxz!(arg0: matrix, arg1: vector) => matrixsource
Rotate in y,x,z order.
matrix-rotate-yzx!(arg0: matrix, arg1: vector) => matrixsource
Rotate in y,z,x order
matrix-rotate-z!(arg0: matrix, arg1: float) => matrixsource
Set dst to a homogeneous transform matrix for a rotation around the z-axis (degrees)
matrix-rotate-zxy!(arg0: matrix, arg1: vector) => matrixsource
Rotate in z,x,y order
matrix-rotate-zyx!(arg0: matrix, arg1: vector) => matrixsource
Rotate in z,y,x order.
matrix-scale!(arg0: matrix, arg1: vector) => matrixsource
Set dst to a homogenous transform with only a scale. The x,y,z components
of scale become the x,y,z scaling factors
matrix-translate!(arg0: matrix, arg1: vector) => matrixsource
Set dst to a homogeneous transform with only a translation of trans
matrix-translate+!(arg0: matrix, arg1: matrix, arg2: vector) => matrixsource
Add the given translation to the translation of homogenous transform mat src
and store in dst. It is okay for dst = src.
matrix-transpose!(dst: matrix, src: matrix) => matrixsource
Set dst = src^T. src and dst can be the same.
matrix-y-angle(arg0: matrix) => floatsource
If mat has its upper 3x3 as a rotation, gets the y axis rotation.
matrix3-determinant(arg0: matrix) => floatsource
Unused. Not sure if this has limitations compared to the above version.
matrix3-inverse-transpose!(arg0: matrix, arg1: matrix) => matrixsource
Unused. Not sure if this has limitations compared to other version.
matrix<-quat(arg0: matrix, arg1: quaternion) => matrixsource
Modify the rotation part of a transform.
matrix<-scale(arg0: matrix, arg1: vector) => matrixsource
Set the scale of a matrix by rescaling.
matrix<-trans(arg0: matrix, arg1: vector) => matrixsource
Set the translation.
matrixp*!(arg0: matrix, arg1: matrix, arg2: matrix) => matrixsource
Set dst = src1 * src2. NOTE: this function is a wrapper around matrix*!
that adds no additional functionality. It seems to be a leftover from
a time when matrix*! wasn't safe to use in place. This is unused.
scale-matrix!(arg0: matrix, arg1: vector, arg2: matrix) => matrixsource
Scale an existing matrix. Okay for dst = src. The scaling is applied per row.
This means the x component of scale is used to scale the first row of src.
The w component of scale is used.
vector-matrix*!(arg0: vector, arg1: vector, arg2: matrix) => vectorsource
Set dst = vec * mat. dst may be equal to src.
vector-rotate*!(arg0: vector, arg1: vector, arg2: matrix) => vectorsource
Set dst to be the input vector rotated by the rotation part of mat.
The input matrix should be a homogeneous transform with a rotation matrix as its upper-left 3x3.
dst may be equal to src.
vector3s-matrix*!(arg0: vector3s, arg1: vector3s, arg2: matrix) => vector3ssource
Set dst to be ([src 1.0] * mat).xyz. Doesn't touch the w of dst.
dst and vec can be the same memory
vector3s-rotate*!(arg0: vector3s, arg1: vector3s, arg2: matrix) => vector3ssource
Set dst to vec rotated by the rotation in the homogeneous transform mat.
mat should not have a scale/shear (the upper 3x3 should be a pure rotation).
Variables
Types
quaternion: structuresource
Variables
Functions
matrix->quaternion(arg0: quaternion, arg1: matrix) => quaternionsource
Convert a rotation matrix to a quaternion.
matrix-with-scale->quaternion(arg0: quaternion, arg1: matrix) => quaternionsource
Convert a matrix with a rotation and scale into a quaternion (just the rotation)
quaternion*!(arg0: quaternion, arg1: quaternion, arg2: quaternion) => quaternionsource
Real quaternion multiplication
quaternion+!(arg0: quaternion, arg1: quaternion, arg2: quaternion) => quaternionsource
Add quaternions as vectors.
quaternion-!(arg0: quaternion, arg1: quaternion, arg2: quaternion) => quaternionsource
Subtract quaternions as vectors.
quaternion->matrix(arg0: matrix, arg1: quaternion) => matrixsource
Convert quaternion to matrix.
quaternion->matrix-2(arg0: matrix, arg1: quaternion) => matrixsource
Unused alternate quaternion->matrix function.
quaternion-axis-angle!(arg0: quaternion, arg1: float, arg2: float, arg3: float, arg4: float) => quaternionsource
Construct a quaternion from an axis and angle. The axis should be normalized.
quaternion-conjugate!(arg0: quaternion, arg1: quaternion) => quaternionsource
Set arg0 to the conjugate of arg1 (negate only ijk).
If arg1 is normalized, this is equivalent to the inverse
NOTE: this gives you the inverse rotation.
quaternion-copy!(arg0: quaternion, arg1: quaternion) => quaternionsource
Set arg0 = arg1
quaternion-delta-y(arg0: quaternion, arg1: quaternion) => floatsource
Difference in yaw between two quaternions
quaternion-dot(arg0: quaternion, arg1: quaternion) => floatsource
Treat quaternions as vectors and take the dot product.
quaternion-exp!(arg0: quaternion, arg1: quaternion) => quaternionsource
Quaternion exponentiation. Unused
quaternion-float*!(arg0: quaternion, arg1: quaternion, arg2: float) => quaternionsource
Multiply each element
quaternion-float/!(arg0: quaternion, arg1: quaternion, arg2: float) => quaternionsource
Divide each element
quaternion-i!(arg0: quaternion) => quaternionsource
Create unit i quaternion
quaternion-identity!(arg0: quaternion) => quaternionsource
Set quaternion to 0,0,0,1 (identity)
quaternion-inverse!(arg0: quaternion, arg1: quaternion) => quaternionsource
Invert a quaternion. The inverse will satisfy q * q^-1 = identity, even if q is not normalized.
If your quaternion is normalized, it is faster/more accurate to do quaternion-conjugate!
quaternion-j!(arg0: quaternion) => quaternionsource
Create unit j quaternion.
quaternion-k!(arg0: quaternion) => quaternionsource
Create unit k quaternion
quaternion-left-mult-matrix!(arg0: matrix, arg1: quaternion) => matrixsource
Place quaternion coefficients into a matrix. Unused.
quaternion-log!(arg0: quaternion, arg1: quaternion) => quaternionsource
Take the log of a quaternion. Unused.
quaternion-look-at!(arg0: quaternion, arg1: vector, arg2: vector) => quaternionsource
Look along arg1, with arg2 as up.
quaternion-negate!(arg0: quaternion, arg1: quaternion) => quaternionsource
Set arg0 = -arg1.
quaternion-norm(arg0: quaternion) => floatsource
Get the norm of a quaternion.
quaternion-norm2(arg0: quaternion) => floatsource
Get the squared norm of a quaternion
quaternion-normalize!(arg0: quaternion) => quaternionsource
Normalize a quaternion
quaternion-pseudo-seek(arg0: quaternion, arg1: quaternion, arg2: quaternion, arg3: float) => quaternionsource
Seek one quaternion toward another. Not using real slerp, so this is only good if the quaternions
are pretty similar.
quaternion-pseudo-slerp!(arg0: quaternion, arg1: quaternion, arg2: quaternion, arg3: float) => quaternionsource
This is a bad interpolation between quaternions. It lerps then normalizes.
It will behave extremely poorly for 180 rotations.
It is unused.
quaternion-right-mult-matrix!(arg0: matrix, arg1: quaternion) => matrixsource
Place quaternion coefficients into a matrix.
You can convert a quaternion to a matrix by taking the product of this
right-mult and left-mult matrix, but this method is not used.
Instead, quaternion->matrix is a more efficient implementation.
quaternion-rotate-local-x!(arg0: quaternion, arg1: quaternion, arg2: float) => quaternionsource
Rotate existing quaternion along x axis.
quaternion-rotate-local-y!(arg0: quaternion, arg1: quaternion, arg2: float) => quaternionsource
Rotate existing quaternion along y axis.
quaternion-rotate-local-z!(arg0: quaternion, arg1: quaternion, arg2: float) => quaternionsource
Rotate existing quaternion along z axis.
quaternion-rotate-x!(arg0: quaternion, arg1: quaternion, arg2: float) => quaternionsource
Rotate existing quaternion along x axis (right multiply)
quaternion-rotate-y!(arg0: quaternion, arg1: quaternion, arg2: float) => quaternionsource
Rotate existing quaternion along y axis (right multiply)
quaternion-rotate-y-to-vector!(arg0: quaternion, arg1: quaternion, arg2: quaternion, arg3: float) => quaternionsource
Rotate along y so z-axis points to match another. Use arg3 as the max rotation amount.
quaternion-rotate-z!(arg0: quaternion, arg1: quaternion, arg2: float) => quaternionsource
Rotate existing quaternion along z axis (right multiply)
quaternion-set!(arg0: quaternion, arg1: float, arg2: float, arg3: float, arg4: float) => quaternionsource
Set arg0 = [arg1, arg2, arg3, arg4]
quaternion-slerp!(arg0: quaternion, arg1: quaternion, arg2: quaternion, arg3: float) => quaternionsource
Real quaternion slerp. Spherical-linear interpolation is a nice way to interpolate
between quaternions.
quaternion-smooth-seek!(arg0: quaternion, arg1: quaternion, arg2: quaternion, arg3: float) => quaternionsource
Another hacky rotation interpolation.
quaternion-validate(arg0: quaternion) => nonesource
quaternion-vector-angle!(arg0: quaternion, arg1: vector, arg2: float) => quaternionsource
Construct a quaternion from an axis and angle. The axis should be normalized.
quaternion-vector-len(arg0: quaternion) => floatsource
Assuming quaternion is normalized, get the length of the xyz part.
quaternion-vector-y-angle(arg0: quaternion, arg1: vector) => floatsource
Not sure. Angle between quaternion and axis, projected in xz plane?
quaternion-x-angle(arg0: quaternion) => floatsource
Get the x rotation angle. Not very efficient
quaternion-xz-angle(arg0: quaternion) => floatsource
yet another function to compute the yaw of a quaternion. This is a particularly inefficient version.
quaternion-y-angle(arg0: quaternion) => floatsource
Get the y rotation angle. Not very efficient
quaternion-z-angle(arg0: quaternion) => floatsource
Get the z rotation angle. Not very efficient
quaternion-zero!(arg0: quaternion) => quaternionsource
Set quaternion to all 0's
quaternion-zxy!(arg0: quaternion, arg1: vector) => quaternionsource
Make a quaternion from a sequence of z, x, y axis rotations.
quaternion<-rotate-y-vector(arg0: quaternion, arg1: vector) => quaternionsource
Create a quaternion representing only the yaw of the given vector
vector-angle<-quaternion!(arg0: vector, arg1: quaternion) => vectorsource
Convert the quaternion arg1 to axis-angle form and store in arg0 (angle goes in w)
vector-rotate-x!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Rotate vector along x axis.
vector-rotate-y!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Rotate vector along y axis.
vector-rotate-z!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Rotate vector along z axis.
vector-x-angle(arg0: vector) => floatsource
Get the pitch angle of a vector.
vector-x-quaternion!(arg0: vector, arg1: quaternion) => vectorsource
Get the first row of the rotation matrix for this quaternion
vector-y-angle(arg0: vector) => floatsource
Get the yaw angle of a vector.
vector-y-quaternion!(arg0: vector, arg1: quaternion) => vectorsource
Get the second row of the rotation matrix for this quaternion
vector-z-quaternion!(arg0: vector, arg1: quaternion) => vectorsource
Get the third row of the rotation matrix for this quaternion
Types
Functions
transform-matrix-calc!(arg0: transform, arg1: matrix) => matrixsource
Convert a transform to matrix. Not efficient, and the output is the second arg.
transform-matrix-parent-calc!(arg0: transform, arg1: matrix, arg2: vector) => matrixsource
Convert a transform to a matrix, applying an inverse scaling.
trs-matrix-calc!(arg0: trs, arg1: matrix) => matrixsource
Convert a trs to a matrix
Types
trsqv: trsqsource
Fields
type: type
trans: vector
rot: vector
scale: vector
quat: quaternion
pause-adjust-distance: meters
nav-radius: meters
transv: vector
rotv: vector
scalev: vector
dir-targ: quaternion
angle-change-time: time-frame
old-y-angle-diff: float
Methods
seek-toward-heading-vec!(obj: trsqv, arg0: vector, arg1: float, arg2: time-frame) => quaternionsource
Adjust the orientation to point along dir, only changing our yaw.
The vel is a maximum velocity limit.
The frame count is the time constant (first order).
There's some logic to avoid rapidly changing directions
set-heading-vec!(obj: trsqv, arg0: vector) => quaternionsource
Makes us look in the arg0 direction immediately. Pitch will be unchanged.
seek-to-point-toward-point!(obj: trsqv, arg0: vector, arg1: float, arg2: time-frame) => quaternionsource
Seek toward pointing toward arg0 from our current location.
point-toward-point!(obj: trsqv, arg0: vector) => quaternionsource
Immediately point toward arg0
seek-toward-yaw-angle!(obj: trsqv, arg0: float, arg1: float, arg2: time-frame) => quaternionsource
Seek toward the given yaw angle.
set-yaw-angle-clear-roll-pitch!(obj: trsqv, arg0: float) => quaternionsource
Immediately clear our roll and pitch and set yaw to the given angle
set-roll-to-grav!(obj: trsqv, arg0: float) => quaternionsource
Set our roll so that our local down aligns with standard gravity
set-roll-to-grav-2!(obj: trsqv, arg0: float) => quaternionsource
Set our roll so that our local down aligns with standard gravity
rotate-toward-orientation!(obj: trsqv, arg0: quaternion, arg1: float, arg2: float, arg3: int, arg4: int, arg5: float) => quaternionsource
Adjust our orientation toward target, subject to some rate limits.
For jak 1, I said:
I don't think this is a very robust function and probably doesn't work right in cases
where an axis flips by 180 degrees.
But now they use matrix-from-two-vectors-the-long-way-smooth to fix it! Good job.
This additionally uses the fancy logic of matrix-from-two-vectors-smooth.
set-quaternion!(obj: trsqv, arg0: quaternion) => quaternionsource
Set the rotation as a quaternion
set-heading-vec-clear-roll-pitch!(obj: trsqv, arg0: vector) => quaternionsource
Set our rotation to point along the given heading, with no roll or pitch.
point-toward-point-clear-roll-pitch!(obj: trsqv, arg0: vector) => quaternionsource
Set our orientation to point toward arg0, clearing roll and pitch
rot->dir-targ!(obj: trsqv) => quaternionsource
Set the dir-targ to our current orientation
global-y-angle-to-point(obj: trsqv, arg0: vector) => floatsource
Get the angle in the xz plane from the position of this trsqv to the point arg0.
(ignores our current yaw)
relative-y-angle-to-point(obj: trsqv, arg0: vector) => floatsource
Get the y angle between the current orientation and arg0. (how much we'd have to yaw to point at arg0)
roll-relative-to-gravity(obj: trsqv) => floatsource
Get our roll, relative to 'down' from gravity
set-and-limit-velocity(obj: trsqv, unkBitfield: int, limit: vector, arg2: float) => trsqvsource
TODO - arg1 is an bitfield of some sort
get-quaternion(obj: trsqv) => quaternionsource
Get the rotation as a quaternion.
Functions
matrix<-no-trans-transformq!(arg0: matrix, arg1: transformq) => matrixsource
Create 4x4 affine transform with no translation.
matrix<-parented-transformq!(arg0: matrix, arg1: transformq, arg2: vector) => matrixsource
Unused. Seems like the parented thing means there's an inverse scale in arg2.
matrix<-transformq!(arg0: matrix, arg1: transformq) => matrixsource
Convert to 4x4 affine transform.
matrix<-transformq+rot-offset!(arg0: matrix, arg1: transformq, arg2: vector) => matrixsource
Affine transform for a point offset in the destination frame of the transformq (rather than just
adding an offset at the end)
matrix<-transformq+trans!(arg0: matrix, arg1: transformq, arg2: vector) => matrixsource
Convert to affine transform with an additional translation (in the local frame).
matrix<-transformq+world-trans!(arg0: matrix, arg1: transformq, arg2: vector) => matrixsource
Convert to affine transform with an additional translation in the world frame (not rotated)
transformq-copy!(arg0: transformq, arg1: transformq) => transformqsource
Set arg0 = arg1
Expand description
The "rotation" unit stores an angle in a float, where 1.0 = 1/65,536 (1/2^16) of a rotation.
Use the ~r format specifier to print rotations as degrees.
In general, functions which use these units will only be accurate to within 1/65,536th of a rotation,
as they often internally convert the float to an integer. These function also handle wrapping
correctly, and will output angles in the range -32768 to 32768 (+/- one half of a rotation)
Functions with these units have deg or nothing special in the name.
Some functions use radians. These typically have rad in the name, and they don't handle wrapping.
The input must be in the range -pi to pi
General note on floating point constants: to avoid ambiguity/rounding issues related to printing/parsing, weird
constants are stored as hex. Commonly used constants that are exactly represented (1, 0.5, etc) will appear
normally.
Functions
atan-series-rad(arg0: float) => floatsource
A helper function for atan
atan0(arg0: float, arg1: float) => floatsource
inverse tangent, to rotation units. y,x order. Does not handle signs correctly.
Do not use this function directly, instead use atan2
cos-rad(arg0: float) => floatsource
Cosine with taylor series. Input is in radians, in -pi, pi.
- TODO constants
coserp(arg0: float, arg1: float, arg2: float) => floatsource
Weird lerp with cosine (over 90 degrees?)
coserp-clamp(arg0: float, arg1: float, arg2: float) => floatsource
Weird 90 degree lerp with cosine, clamped to min,max
coserp180-clamp(arg0: float, arg1: float, arg2: float) => floatsource
Classic coserp with saturation
deg-(arg0: float, arg1: float) => floatsource
Compute arg0-arg1, unwrapped, using rotation units.
Result should be in the range (-180, 180)
deg-diff(arg0: float, arg1: float) => floatsource
Very similar to the function above, but computes arg1 - arg0 instead.
deg-lerp-clamp(arg0: float, arg1: float, arg2: float) => floatsource
Map [0, 1] to min-val, max-val, handling wrapping and saturating, using rotation units.
deg-seek(arg0: float, arg1: float, arg2: float) => floatsource
Move in toward target by at most max-diff, using rotation units
deg-seek-smooth(arg0: float, arg1: float, arg2: float, arg3: float) => floatsource
Step amount of the way from in to target, by at most max-diff, using rotation units
ease-in-out(arg0: int, arg1: int) => floatsource
Weird coserp like mapping from 0 to 1 as progress goes from 0 to total
sign(arg0: float) => floatsource
Similar to above, but returns 0 if input is 0.
But is more complicated.
sign-float(arg0: float) => floatsource
Return 1 if arg0 is positive or zero, -1 otherwise.
Fast (no branching)
sin-rad(arg0: float) => floatsource
Compute the sine of an angle in radians.
No unwrap is done, should be in -pi, pi
sincos!(out: vector, x: float) => intsource
Compute the sine and cosine of x, store it in the output array.
The input is in rotation units, and is unwrapped properly.
Also has the cosine bug
sincos-rad!(out: vector, x: float) => intsource
Compute the sine and cosine of x, store it in the output array.
Has the cosine bug.
sinerp(arg0: float, arg1: float, arg2: float) => floatsource
map amount to min,max using sine. Kinda weird, usually people use cosine.
sinerp-clamp(arg0: float, arg1: float, arg2: float) => floatsource
Like sinerp, but clamp to min,max
tan-rad(arg0: float) => floatsource
This function appears to be named wrong and actually operates on rotation units.
vector-cos-rad!(arg0: vector, arg1: vector) => vectorsource
Compute the cosine of all 4 vector elements.
Radians, with no wrapping. Uses taylor series with 4 coefficients.
vector-rad<-vector-deg!(out: vector, in: vector) => nonesource
Convert a vector in rotation units to radians, and unwrap.
Input can be anything, output will be -2pi to pi.
vector-rad<-vector-deg/2!(out: vector, in: vector) => intsource
Divide the input by two, and then convert from rotation units to radians, unwrapping.
Not sure why this really needs to be separate the from previous function...
vector-sin-rad!(arg0: vector, arg1: vector) => vectorsource
Taylor series approximation of sine on all 4 elements in a vector.
Inputs should be in radians, in -pi to pi.
Somehow their coefficients are a little bit off.
Like the first coefficient, which should obviously be 1, is not quite 1.
vector-sincos!(arg0: vector, arg1: vector, arg2: vector) => intsource
Compute sine and cosine of each element in a vector, in rotation units
vector-sincos-rad!(arg0: vector, arg1: vector, arg2: vector) => intsource
Compute the sine and cosine of each element of src, storing it in dst-sin and dst-cos.
This is more efficient than separate calls to sin and cos.
Inputs should be radians in -pi to pi.
Variables
const binary-table: arraysource
FIX_COSINE_BUG: unknownsource
ROT_TO_RAD: unknownsource
sincos-table: arraysource
Expand description
Changes:
- vector+!, vector-!, vector-dot, vector4-dot replaced with actual implementations.
Types
bit-array: basicsource
Fields
type: type
length: int32
allocated-length: int32
_pad: uint8
bytes: uint8
Methods
clear-all!(obj: bit-array) => _type_source
Set all bits to 0.
box8s-array: inline-array-classsource
cylinder: structuresource
cylinder-flat: structuresource
Fields
origin: vector
axis: vector
radius: float
length: float
Methods
debug-draw(obj: cylinder-flat, arg0: vector4w) => nonesource
ray-flat-cyl-intersect(obj: cylinder-flat, arg0: vector, arg1: vector) => floatsource
isphere: vec4ssource
plane: vectorsource
qword: structuresource
rgbaf: vectorsource
vector-array: inline-array-classsource
vector4: structuresource
vector4w: structuresource
vertical-planes-array: basicsource
Functions
vector+!(dst: vector, a: vector, b: vector) => vectorsource
Set dst = a + b. The w component of dst is set to 0.
vector-!(dst: vector, a: vector, b: vector) => vectorsource
Set dst = a - b. The w componenent of dst is set to 0.
vector-copy!(arg0: vector, arg1: vector) => vectorsource
Copy arg1 to arg0.
vector-dot(a: vector, b: vector) => floatsource
Take the dot product of two vectors.
Only does the x, y, z compoments.
Originally handwritten assembly to space out loads and use FPU accumulator
vector-dot-vu(arg0: vector, arg1: vector) => floatsource
Take the dot product (xyz only). Using VU0.
vector-length<(arg0: vector, arg1: float) => symbolsource
vector-length>(arg0: vector, arg1: float) => symbolsource
vector-reset!(dst: vector) => vectorsource
Set vector to 0,0,0,1.
vector-zero!(dest: vector) => vectorsource
Set xyzw to 0.
vector4-dot(a: vector, b: vector) => floatsource
Take the dot product of two vectors.
Does the x, y, z, and w compoments
vector4-dot-vu(arg0: vector, arg1: vector) => floatsource
Take the dot product (xyzw). Using VU0.
Variables
Functions
rand-vu-sphere-point!(arg0: vector, arg1: float) => vectorsource
Get a random point on the sphere at the origin with radius arg1.
The point is on the surface of the sphere.
rot-zxy-from-vector!(arg0: vector, arg1: vector) => vectorsource
I think this gives you a vector of euler angles to rotate some unit vector
to arg1.
rot-zyx-from-vector!(arg0: vector, arg1: vector) => vectorsource
I think this gives you a vector of euler angles to rotate some unit vector
to arg1.
rotate-x<-vector+vector(arg0: vector, arg1: vector) => floatsource
Get the x rotation between vectors. These should have the same length.
rotate-y<-vector+vector(arg0: vector, arg1: vector) => floatsource
Get the y rotation between vectors. These should have the same length.
rotate-z<-vector+vector(arg0: vector, arg1: vector) => floatsource
Get the z rotation between vectors. These should have the same length.
seek-with-smooth(arg0: float, arg1: float, arg2: float, arg3: float, arg4: float) => floatsource
Move value closer to target.
If we are within deadband, just go straight to target.
If not, try to go alpha*err. If that is a larger step than max-step, limit to max-step
sphere<-vector!(arg0: sphere, arg1: vector) => spheresource
Set the position of the sphere to arg1. Does not change the radius
sphere<-vector+r!(arg0: sphere, arg1: vector, arg2: float) => spheresource
Set the position of the sphere from arg1 and the radius from arg2
spheres-overlap?(arg0: sphere, arg1: sphere) => symbolsource
Do the spheres overlap?
vector+*!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
set arg0 = arg1 + (arg3 * arg2). The w component will be set to 1
vector+float!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Add float to each component of vector. The w component is set to 1
vector+float*!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
arg0 = arg1 + arg2 * arg3.
vector-*!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
Set arg0 = arg1 - (arg3 * arg2). The w component will be set to 1.
vector--float*!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
Set arg0 = arg1 - (arg2 * arg3). The w component will be set to 1
Is this different from vector-*!
vector-average!(arg0: vector, arg1: vector, arg2: vector) => vectorsource
Set arg0 to the average of arg1 and arg2. Set w to 1.
vector-cross!(arg0: vector, arg1: vector, arg2: vector) => vectorsource
Compute the cross product. The w component is set to junk.
vector-cvt.s.w!(arg0: vector, arg1: vector) => vectorsource
Convert float to int32.
vector-cvt.w.s!(arg0: vector, arg1: vector) => vectorsource
Convert float to int32. Truncate.
vector-deg-diff(arg0: vector, arg1: vector, arg2: vector) => nonesource
Wrapped difference, degrees units. Will have the usual 16-bit accuracy issue
vector-deg-lerp-clamp!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
Apply deg-lerp-clamp to the xyz components of a vector. Sets w = 1.
vector-degf(arg0: vector, arg1: vector) => vectorsource
Convert a vector (in integer degree units) to floating point rotations.
Truncates to the nearest rotation.
Like the previous function, this is stupid and unused
vector-degi(arg0: vector, arg1: vector) => vectorsource
Convert a vector (in rotations) to degrees units, stored in an int.
Truncates to the nearest rotation.
Neither the input or output is a commonly used form.
Unsurprisingly, this strange function is never used.
vector-degmod(arg0: vector, arg1: vector) => vectorsource
This one is actually right. Wraps degrees units (in floats, like they should be)
to +/- half a rotation.
vector-delta(arg0: vector, arg1: vector) => floatsource
Sum of the elementwise absolute value of differences
vector-float*!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Multiply all values in a vector by arg2. Set w to 1.
vector-float/!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Divide all components by arg2. The w component will be set to 1.
vector-from-ups!(arg0: vector, arg1: vector) => vectorsource
Go from units per second to units per frame?
vector-identity!(arg0: vector) => vectorsource
Set arg0 to 1, 1, 1, 1
vector-length(arg0: vector) => floatsource
Get the length of the xyz part.
vector-length-max!(arg0: vector, arg1: float) => vectorsource
Make vector at most arg1 length (xyz only).
If it is larger, project onto sphere.
Doesn't touch w
vector-length-squared(arg0: vector) => floatsource
Get the squared length of the xyz part.
vector-lerp!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
Linearly interpolate between two vectors. Alpha isn't clamped.
w will be set to 1.
vector-lerp-clamp!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
Linearly interpolate between two vectors, clamping alpha to 0, 1
w will be set to 1.
vector-negate!(arg0: vector, arg1: vector) => vectorsource
Negate xyz, set w to 1
vector-negate-in-place!(arg0: vector) => vectorsource
Negate xyz. Doesn't touch w.
vector-normalize!(arg0: vector, arg1: float) => vectorsource
Modify arg0 in place to have length arg1 for its xyz components. The w part is not changed.
vector-normalize-copy!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Normalize, but not in place.
This implementation is very good compared to the vector-normalize! one.
The w component is set to 1.
vector-normalize-ret-len!(arg0: vector, arg1: float) => floatsource
Modify arg0 in place to have length arg1 for its xyz components.
The w part isn't changed and the original length is returned.
vector-rotate-around-x!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Rotate a vector around the x axis
vector-rotate-around-y!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Rotate a vector around the y axis
vector-rotate-around-z!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Rotate a vector around the z axis
vector-rotate90-around-y!(arg0: vector, arg1: vector) => vectorsource
Rotate a vector 90 degrees around y.
vector-seconds(arg0: vector, arg1: vector) => vectorsource
Convert from actual seconds to the seconds unit.
vector-seconds!(arg0: vector) => vectorsource
Convert from actual seconds to seconds, in place
vector-seek!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Seek arg0 toward arg1. The arg0 is both read and written.
arg2 is saturated to (0, 1)
vector-seek-2d-xz-smooth!(arg0: vector, arg1: vector, arg2: float, arg3: float) => vectorsource
Smoothly seek vec's x and z components toward target.
The step always points toward the target and has length (dist * alpha)
If the step is longer than max-step, the step is projected onto a circle of radius max-step.
Doesn't touch y or w.
vector-seek-2d-yz-smooth!(arg0: vector, arg1: vector, arg2: float, arg3: float) => vectorsource
Smoothly seek vec's y and z components toward target.
The step always points toward the target and has length (dist * alpha)
If the step is longer than max-step, the step is projected onto a circle of radius max-step.
Doesn't touch x or w.
vector-seek-3d-smooth!(arg0: vector, arg1: vector, arg2: float, arg3: float) => vectorsource
Smoothly seek vec's x, y, and z components toward target.
The step always points toward the target and has length (dist * alpha)
If the step is longer than max-step, the step is projected onto a circle of radius max-step.
Doesn't touch w.
vector-smooth-seek!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Smoothly seek vec toward target.
The step always points toward the target and has length (dist * alpha)
If the step is longer than max-step, the step is projected onto a square with side length arg2.
Note that this doesn't project to a circle like the function below...
vector-to-ups!(arg0: vector, arg1: vector) => vectorsource
Go from units per frame to units per second?
vector-v!(arg0: vector) => vectorsource
Convert a velocity to a displacement per frame. The velocity should be in X/actual_second.
Uses the current process clock.
vector-v*float!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Go from velocity to delta-p per frame, scaling by scale
vector-v*float+!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
Euler forward step, scaling velocity by velocity-scale
vector-v*float++!(arg0: vector, arg1: vector, arg2: float) => vectorsource
update position with given velocity, scaled by scale.
vector-v+!(arg0: vector, arg1: vector, arg2: vector) => vectorsource
Euler forward step, using the current display time settings
vector-v++!(arg0: vector, arg1: vector) => vectorsource
Update position in place, using display's current timing
vector-vector-angle-safe(arg0: vector, arg1: vector) => floatsource
Get the angle between two vectors, with some 'safety' applied...
vector-vector-distance(arg0: vector, arg1: vector) => floatsource
Subtract the xyz parts and get the norm
vector-vector-distance-squared(arg0: vector, arg1: vector) => floatsource
Squared norm of the difference of the xyz parts
vector-vector-xy-distance(arg0: vector, arg1: vector) => floatsource
distance on the xy plane
vector-vector-xz-distance(arg0: vector, arg1: vector) => floatsource
Distance on the xz plane
vector-vector-xz-distance-squared(arg0: vector, arg1: vector) => floatsource
Distance on the xz plane squared
vector-xz-cross!(arg0: vector, arg1: vector, arg2: vector) => vectorsource
Compute the cross product of the xz components of inputs.
vector-xz-length(arg0: vector) => floatsource
Get the length of the xz part
vector-xz-length-max!(arg0: vector, arg1: float) => vectorsource
Make vector at most arg1 length (xz only).
It it is larger, project onto circle.
Doesn't touch w or y
vector-xz-length-squared(arg0: vector) => floatsource
Get the length of the xz part, squared.
vector-xz-normalize!(arg0: vector, arg1: float) => vectorsource
Normalize, xz components only
vector-xz-normalize-copy!(arg0: vector, arg1: vector, arg2: float) => vectorsource
Normalize, xz components only
vector/!(arg0: vector, arg1: vector, arg2: vector) => vectorsource
Set arg0 = arg1 / arg2. The w component will be set to 1.
The implementation is kind of crazy.
vector3s*float!(arg0: vector, arg1: vector, arg2: float) => vectorsource
mult vectors3 by float
vector3s-!(arg0: vector, arg1: vector, arg2: vector) => vectorsource
Subtract 2 vectors3: c = (a - b).
vector3s-copy!(arg0: vector, arg1: vector) => vectorsource
Copy a vector3s
vector4-add!(arg0: vector4, arg1: vector4, arg2: vector4) => nonesource
Add 2 vector4s
vector4-array-add!(arg0: inline-array, arg1: inline-array, arg2: inline-array, arg3: int) => nonesource
Apply vector4-add! to all arrays.
vector4-array-lerp!(arg0: inline-array, arg1: inline-array, arg2: inline-array, arg3: float, arg4: int) => symbolsource
Apply vector4-lerp! to all arrays.
vector4-array-madd!(arg0: inline-array, arg1: inline-array, arg2: inline-array, arg3: float, arg4: int) => nonesource
Apply vector4-madd! to all arrays.
vector4-array-msub!(arg0: inline-array, arg1: inline-array, arg2: inline-array, arg3: float, arg4: int) => nonesource
Apply vector4-msub! to all arrays.
vector4-array-mul!(arg0: inline-array, arg1: inline-array, arg2: inline-array, arg3: int) => nonesource
Apply vector4-mul! to all arrays.
vector4-array-scale!(arg0: inline-array, arg1: inline-array, arg2: float, arg3: int) => nonesource
Apply vector4-scale! to all arrays.
vector4-array-sub!(arg0: inline-array, arg1: inline-array, arg2: inline-array, arg3: int) => nonesource
Apply vector4-sub! to all arrays.
vector4-lerp!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
Interpolate all 4 elements of a vector. Alpha is not clamped
vector4-lerp-clamp!(arg0: vector, arg1: vector, arg2: vector, arg3: float) => vectorsource
Interpolate all 4 elements of a vector. Alpha is clamped to [0, 1]
vector4-madd!(arg0: vector4, arg1: vector4, arg2: vector4, arg3: float) => nonesource
arg0 = arg1 + arg2 * arg3
vector4-msub!(arg0: vector4, arg1: vector4, arg2: vector4, arg3: float) => nonesource
arg0 = arg1 - arg2 * arg3
vector4-mul!(arg0: vector4, arg1: vector4, arg2: vector4) => nonesource
Multiple 2 vector4s
vector4-scale!(arg0: vector4, arg1: vector4, arg2: float) => nonesource
arg0 = arg1 * arg2
vector4-sub!(arg0: vector4, arg1: vector4, arg2: vector4) => nonesource
Subtract 2 vector4s