Current section
Files
Jump to
Current section
Files
src/matrix@mat2f.erl
-module(matrix@mat2f).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/matrix/mat2f.gleam").
-export([new/4, from_cols/2, from_diagonal/1, from_scale_angle/2, from_angle/1, transpose/1, diagonal/1, determinant/1, inverse/1, mul_vec2/2, mul_transpose_vec2/2, negate/1, absolute_value/1, add/2, subtract/2, multiply/2, divide/2, scale/2, scale_diagonal/2, reciprocal/1, sum/1, product/1]).
-if(?OTP_RELEASE >= 27).
-define(MODULEDOC(Str), -moduledoc(Str)).
-define(DOC(Str), -doc(Str)).
-else.
-define(MODULEDOC(Str), -compile([])).
-define(DOC(Str), -compile([])).
-endif.
?MODULEDOC(" 2x2 matrices of floats\n").
-file("src/matrix/mat2f.gleam", 25).
?DOC(
" Constructs a `Mat2f` from its components:\n"
" ```text\n"
" | a c |\n"
" | b d |\n"
" ```\n"
).
-spec new(float(), float(), float(), float()) -> vec@vec2:vec2(vec@vec2:vec2(float())).
new(A, B, C, D) ->
{vec2, {vec2, A, B}, {vec2, C, D}}.
-file("src/matrix/mat2f.gleam", 34).
?DOC(
" Constructs a `Mat2f` from its two columns.\n"
" ```text\n"
" | ax bx |\n"
" | ay by |\n"
" ```\n"
).
-spec from_cols(vec@vec2:vec2(float()), vec@vec2:vec2(float())) -> vec@vec2:vec2(vec@vec2:vec2(float())).
from_cols(A, B) ->
{vec2, A, B}.
-file("src/matrix/mat2f.gleam", 43).
?DOC(
" Constructs a `Mat2f` with the given diagonal and all other entries set to 0.\n"
" ```text\n"
" | x 0.0 |\n"
" | 0.0 y |\n"
" ```\n"
).
-spec from_diagonal(vec@vec2:vec2(float())) -> vec@vec2:vec2(vec@vec2:vec2(float())).
from_diagonal(Diag) ->
new(erlang:element(2, Diag), +0.0, +0.0, erlang:element(3, Diag)).
-file("src/matrix/mat2f.gleam", 48).
?DOC(" Constructs a `Mat2f` from scale factor (as a `Vec2f`) and a rotation in radians.\n").
-spec from_scale_angle(vec@vec2:vec2(float()), float()) -> vec@vec2:vec2(vec@vec2:vec2(float())).
from_scale_angle(Scale, Angle) ->
Sin = gleam_community@maths:sin(Angle),
Cos = gleam_community@maths:cos(Angle),
new(
Cos * erlang:element(2, Scale),
Sin * erlang:element(2, Scale),
(-1.0 * Sin) * erlang:element(3, Scale),
Cos * erlang:element(3, Scale)
).
-file("src/matrix/mat2f.gleam", 55).
?DOC(" Constructs a `Mat2f` from a rotation angle in radians.\n").
-spec from_angle(float()) -> vec@vec2:vec2(vec@vec2:vec2(float())).
from_angle(Angle) ->
Sin = gleam_community@maths:sin(Angle),
Cos = gleam_community@maths:cos(Angle),
new(Cos, Sin, -1.0 * Sin, Cos).
-file("src/matrix/mat2f.gleam", 62).
?DOC(" Transposes the `Mat2f` along the diagonal.\n").
-spec transpose(vec@vec2:vec2(vec@vec2:vec2(float()))) -> vec@vec2:vec2(vec@vec2:vec2(float())).
transpose(Mat) ->
new(
erlang:element(2, erlang:element(2, Mat)),
erlang:element(2, erlang:element(3, Mat)),
erlang:element(3, erlang:element(2, Mat)),
erlang:element(3, erlang:element(3, Mat))
).
-file("src/matrix/mat2f.gleam", 67).
?DOC(" Returns the diagonal of the `Mat2f`\n").
-spec diagonal(vec@vec2:vec2(vec@vec2:vec2(float()))) -> vec@vec2:vec2(float()).
diagonal(Mat) ->
{vec2,
erlang:element(2, erlang:element(2, Mat)),
erlang:element(3, erlang:element(3, Mat))}.
-file("src/matrix/mat2f.gleam", 72).
?DOC(" Returns the determinant for the `Mat2f`.\n").
-spec determinant(vec@vec2:vec2(vec@vec2:vec2(float()))) -> float().
determinant(Mat) ->
(erlang:element(2, erlang:element(2, Mat)) * erlang:element(
3,
erlang:element(3, Mat)
))
- (erlang:element(3, erlang:element(2, Mat)) * erlang:element(
2,
erlang:element(3, Mat)
)).
-file("src/matrix/mat2f.gleam", 77).
?DOC(" Inverts the `Mat2f`, returning an error if the determinant is zero.\n").
-spec inverse(vec@vec2:vec2(vec@vec2:vec2(float()))) -> {ok,
vec@vec2:vec2(vec@vec2:vec2(float()))} |
{error, nil}.
inverse(Mat) ->
gleam@result:map(
gleam@float:divide(1.0, determinant(Mat)),
fun(Inv_det) ->
new(
erlang:element(3, erlang:element(3, Mat)) * Inv_det,
(erlang:element(3, erlang:element(2, Mat)) * Inv_det) * -1.0,
(erlang:element(2, erlang:element(3, Mat)) * Inv_det) * -1.0,
erlang:element(2, erlang:element(2, Mat)) * Inv_det
)
end
).
-file("src/matrix/mat2f.gleam", 88).
?DOC(" Transforms a `Vec2f` by this `Mat2f`.\n").
-spec mul_vec2(vec@vec2:vec2(vec@vec2:vec2(float())), vec@vec2:vec2(float())) -> vec@vec2:vec2(float()).
mul_vec2(Mat, Rhs) ->
{vec2,
(erlang:element(2, erlang:element(2, Mat)) * erlang:element(2, Rhs)) + (erlang:element(
2,
erlang:element(3, Mat)
)
* erlang:element(3, Rhs)),
(erlang:element(3, erlang:element(2, Mat)) * erlang:element(2, Rhs)) + (erlang:element(
3,
erlang:element(3, Mat)
)
* erlang:element(3, Rhs))}.
-file("src/matrix/mat2f.gleam", 96).
?DOC(" Transforms a `Vec2f` by the transpose of this `Mat2f`.\n").
-spec mul_transpose_vec2(
vec@vec2:vec2(vec@vec2:vec2(float())),
vec@vec2:vec2(float())
) -> vec@vec2:vec2(float()).
mul_transpose_vec2(Mat, Rhs) ->
vec@vec2:map(Mat, fun(_capture) -> vec@vec2f:dot(_capture, Rhs) end).
-file("src/matrix/mat2f.gleam", 101).
?DOC(" Negates all elements of the `Mat2f`\n").
-spec negate(vec@vec2:vec2(vec@vec2:vec2(float()))) -> vec@vec2:vec2(vec@vec2:vec2(float())).
negate(Mat) ->
vec@vec2:map(Mat, fun vec@vec2f:negate/1).
-file("src/matrix/mat2f.gleam", 106).
?DOC(" Takes the absolute value of each element in the `Mat2f`.\n").
-spec absolute_value(vec@vec2:vec2(vec@vec2:vec2(float()))) -> vec@vec2:vec2(vec@vec2:vec2(float())).
absolute_value(Mat) ->
vec@vec2:map(Mat, fun vec@vec2f:absolute_value/1).
-file("src/matrix/mat2f.gleam", 111).
?DOC(" Adds two `Mat2f` together.\n").
-spec add(
vec@vec2:vec2(vec@vec2:vec2(float())),
vec@vec2:vec2(vec@vec2:vec2(float()))
) -> vec@vec2:vec2(vec@vec2:vec2(float())).
add(A, B) ->
vec@vec2:map2(A, B, fun vec@vec2f:add/2).
-file("src/matrix/mat2f.gleam", 116).
?DOC(" Subtracts one `Mat2f` from the other.\n").
-spec subtract(
vec@vec2:vec2(vec@vec2:vec2(float())),
vec@vec2:vec2(vec@vec2:vec2(float()))
) -> vec@vec2:vec2(vec@vec2:vec2(float())).
subtract(A, B) ->
vec@vec2:map2(A, B, fun vec@vec2f:subtract/2).
-file("src/matrix/mat2f.gleam", 121).
?DOC(" Multiplies two `Mat2f` together.\n").
-spec multiply(
vec@vec2:vec2(vec@vec2:vec2(float())),
vec@vec2:vec2(vec@vec2:vec2(float()))
) -> vec@vec2:vec2(vec@vec2:vec2(float())).
multiply(A, B) ->
vec@vec2:map(B, fun(_capture) -> mul_vec2(A, _capture) end).
-file("src/matrix/mat2f.gleam", 126).
?DOC(" Divides one `Mat2f` by another. Equivalent to multiplying the inverse of the second matrix.\n").
-spec divide(
vec@vec2:vec2(vec@vec2:vec2(float())),
vec@vec2:vec2(vec@vec2:vec2(float()))
) -> {ok, vec@vec2:vec2(vec@vec2:vec2(float()))} | {error, nil}.
divide(A, B) ->
gleam@result:map(inverse(B), fun(Inv_b) -> multiply(A, Inv_b) end).
-file("src/matrix/mat2f.gleam", 132).
?DOC(" Scales the `Mat2f` by a `Float` factor.\n").
-spec scale(vec@vec2:vec2(vec@vec2:vec2(float())), float()) -> vec@vec2:vec2(vec@vec2:vec2(float())).
scale(Mat, Scale) ->
vec@vec2:map(Mat, fun(_capture) -> vec@vec2f:scale(_capture, Scale) end).
-file("src/matrix/mat2f.gleam", 139).
?DOC(
" Scales the `Mat2f` by a `Vec2f`.\n"
"\n"
" This is faster than creating a diagonal scaling matrix and then multiplying that.\n"
).
-spec scale_diagonal(
vec@vec2:vec2(vec@vec2:vec2(float())),
vec@vec2:vec2(float())
) -> vec@vec2:vec2(vec@vec2:vec2(float())).
scale_diagonal(Mat, Scale) ->
vec@vec2:map2(Mat, Scale, fun vec@vec2f:scale/2).
-file("src/matrix/mat2f.gleam", 146).
?DOC(
" Returns a matrix containing the reciprocal of each element of the `Mat2f`.\n"
"\n"
" If any of the elements is zero, an error is returned.\n"
).
-spec reciprocal(vec@vec2:vec2(vec@vec2:vec2(float()))) -> {ok,
vec@vec2:vec2(vec@vec2:vec2(float()))} |
{error, nil}.
reciprocal(Mat) ->
_pipe@2 = vec@vec2:map(Mat, fun(Column) -> _pipe = Column,
_pipe@1 = vec@vec2:map(
_pipe,
fun(_capture) -> gleam@float:divide(1.0, _capture) end
),
vec@vec2:result(_pipe@1) end),
vec@vec2:result(_pipe@2).
-file("src/matrix/mat2f.gleam", 156).
?DOC(" Sums a list of `Mat2f`s.\n").
-spec sum(list(vec@vec2:vec2(vec@vec2:vec2(float())))) -> vec@vec2:vec2(vec@vec2:vec2(float())).
sum(Mats) ->
gleam@list:fold(
Mats,
{vec2, {vec2, +0.0, +0.0}, {vec2, +0.0, +0.0}},
fun add/2
).
-file("src/matrix/mat2f.gleam", 161).
?DOC(" Multiplies a list of `Mat2f`s.\n").
-spec product(list(vec@vec2:vec2(vec@vec2:vec2(float())))) -> vec@vec2:vec2(vec@vec2:vec2(float())).
product(Mats) ->
gleam@list:fold(
Mats,
{vec2, {vec2, 1.0, +0.0}, {vec2, +0.0, 1.0}},
fun multiply/2
).