211 lines
6.3 KiB
Zig
211 lines
6.3 KiB
Zig
const std = @import("std");
|
|
|
|
pub fn Vec3(comptime T: type) type {
|
|
return struct { x: T, y: T, z: T };
|
|
}
|
|
|
|
pub fn vec3Add(comptime T: type, a: Vec3(T), b: Vec3(T)) Vec3(T) {
|
|
return .{
|
|
.x = a.x + b.x,
|
|
.y = a.y + b.y,
|
|
.z = a.z + b.z,
|
|
};
|
|
}
|
|
|
|
pub fn vec3Sub(comptime T: type, a: Vec3(T), b: Vec3(T)) Vec3(T) {
|
|
return .{
|
|
.x = a.x - b.x,
|
|
.y = a.y - b.y,
|
|
.z = a.z - b.z,
|
|
};
|
|
}
|
|
|
|
pub fn vec3Dot(comptime T: type, a: Vec3(T), b: Vec3(T)) T {
|
|
return a.x * b.x + a.y * b.y + a.z * b.z;
|
|
}
|
|
|
|
pub fn vec3Cross(comptime T: type, a: Vec3(T), b: Vec3(T)) Vec3(T) {
|
|
const x = a.y * b.z - a.z * b.y;
|
|
const y = a.z * b.x - a.x * b.z;
|
|
const z = a.x * b.y - a.y * b.x;
|
|
return .{ .x = x, .y = y, .z = z };
|
|
}
|
|
|
|
pub fn Mat3(comptime T: type) type {
|
|
return struct {
|
|
row1: Vec3(T),
|
|
row2: Vec3(T),
|
|
row3: Vec3(T),
|
|
};
|
|
}
|
|
|
|
pub fn mat3Add(comptime T: type, a: Mat3(T), b: Mat3(T)) Mat3(T) {
|
|
return .{
|
|
.row1 = vec3Add(T, a.row1, b.row1),
|
|
.row2 = vec3Add(T, a.row2, b.row2),
|
|
.row3 = vec3Add(T, a.row3, b.row3),
|
|
};
|
|
}
|
|
|
|
pub fn mat3Sub(comptime T: type, a: Mat3(T), b: Mat3(T)) Mat3(T) {
|
|
return .{
|
|
.row1 = vec3Sub(T, a.row1, b.row1),
|
|
.row2 = vec3Sub(T, a.row2, b.row2),
|
|
.row3 = vec3Sub(T, a.row3, b.row3),
|
|
};
|
|
}
|
|
|
|
pub fn mat3Mul(comptime T: type, a: Mat3(T), b: Mat3(T)) Mat3(T) {
|
|
const c_row1: Vec3(T) = .{
|
|
.x = a.row1.x * b.row1.x + a.row1.y * b.row2.x + a.row1.z * b.row3.x,
|
|
.y = a.row1.x * b.row1.y + a.row1.y * b.row2.y + a.row1.z * b.row3.y,
|
|
.z = a.row1.x * b.row1.z + a.row1.y * b.row2.z + a.row1.z * b.row3.z,
|
|
};
|
|
|
|
const c_row2: Vec3(T) = .{
|
|
.x = a.row2.x * b.row1.x + a.row2.y * b.row2.x + a.row2.z * b.row3.x,
|
|
.y = a.row2.x * b.row1.y + a.row2.y * b.row2.y + a.row2.z * b.row3.y,
|
|
.z = a.row2.x * b.row1.z + a.row2.y * b.row2.z + a.row2.z * b.row3.z,
|
|
};
|
|
|
|
const c_row3: Vec3(T) = .{
|
|
.x = a.row3.x * b.row1.x + a.row3.y * b.row2.x + a.row3.z * b.row3.x,
|
|
.y = a.row3.x * b.row1.y + a.row3.y * b.row2.y + a.row3.z * b.row3.y,
|
|
.z = a.row3.x * b.row1.z + a.row3.y * b.row2.z + a.row3.z * b.row3.z,
|
|
};
|
|
|
|
return .{ .row1 = c_row1, .row2 = c_row2, .row3 = c_row3 };
|
|
}
|
|
|
|
pub fn vec3MulMat3(comptime T: type, a: Vec3(T), b: Mat3(T)) Vec3(T) {
|
|
return .{
|
|
.x = a.x * b.row1.x + a.y * b.row2.x + a.z * b.row3.x,
|
|
.y = a.x * b.row1.y + a.y * b.row2.y + a.z * b.row3.y,
|
|
.z = a.x * b.row1.z + a.y * b.row2.z + a.z * b.row3.z,
|
|
};
|
|
}
|
|
|
|
test "vec3Add adds properly" {
|
|
const a: Vec3(i8) = .{ .x = 1, .y = 2, .z = 3 };
|
|
const b: Vec3(i8) = .{ .x = 3, .y = 1, .z = 0 };
|
|
const c = vec3Add(i8, a, b);
|
|
|
|
try std.testing.expect(c.x == 4);
|
|
try std.testing.expect(c.y == 3);
|
|
try std.testing.expect(c.z == 3);
|
|
}
|
|
test "vec3Sub subs properly" {
|
|
const a: Vec3(i8) = .{ .x = 1, .y = 2, .z = 3 };
|
|
const b: Vec3(i8) = .{ .x = 3, .y = 1, .z = 0 };
|
|
const c = vec3Sub(i8, a, b);
|
|
|
|
try std.testing.expect(c.x == -2);
|
|
try std.testing.expect(c.y == 1);
|
|
try std.testing.expect(c.z == 3);
|
|
}
|
|
test "vec3Dot dots properly" {
|
|
const a: Vec3(i8) = .{ .x = 1, .y = 2, .z = 3 };
|
|
const b: Vec3(i8) = .{ .x = 3, .y = 1, .z = 0 };
|
|
try std.testing.expect(vec3Dot(i8, a, b) == 5);
|
|
}
|
|
test "vec3Cross crosses properly" {
|
|
const a: Vec3(i8) = .{ .x = 1, .y = 2, .z = 3 };
|
|
const b: Vec3(i8) = .{ .x = 3, .y = 1, .z = 0 };
|
|
|
|
const c = vec3Cross(i8, a, b);
|
|
|
|
try std.testing.expect(c.x == -3);
|
|
try std.testing.expect(c.y == 9);
|
|
try std.testing.expect(c.z == -5);
|
|
}
|
|
|
|
test "Mat3 add works" {
|
|
const a: Mat3(i8) = .{
|
|
.row1 = .{ .x = 1, .y = 2, .z = 3 },
|
|
.row2 = .{ .x = 0, .y = 1, .z = 5 },
|
|
.row3 = .{ .x = 0, .y = 0, .z = 9 },
|
|
};
|
|
const b: Mat3(i8) = .{
|
|
.row1 = .{ .x = 0, .y = 1, .z = 0 },
|
|
.row2 = .{ .x = 0, .y = 1, .z = 1 },
|
|
.row3 = .{ .x = 0, .y = 0, .z = 1 },
|
|
};
|
|
|
|
const c = mat3Add(i8, a, b);
|
|
|
|
try std.testing.expect(c.row1.x == 1);
|
|
try std.testing.expect(c.row1.y == 3);
|
|
try std.testing.expect(c.row1.z == 3);
|
|
try std.testing.expect(c.row2.x == 0);
|
|
try std.testing.expect(c.row2.y == 2);
|
|
try std.testing.expect(c.row2.z == 6);
|
|
try std.testing.expect(c.row3.x == 0);
|
|
try std.testing.expect(c.row3.y == 0);
|
|
try std.testing.expect(c.row3.z == 10);
|
|
}
|
|
|
|
test "Mat3 sub works" {
|
|
const a: Mat3(i8) = .{
|
|
.row1 = .{ .x = 1, .y = 2, .z = 3 },
|
|
.row2 = .{ .x = 0, .y = 1, .z = 5 },
|
|
.row3 = .{ .x = 0, .y = 0, .z = 9 },
|
|
};
|
|
const b: Mat3(i8) = .{
|
|
.row1 = .{ .x = 0, .y = 1, .z = 0 },
|
|
.row2 = .{ .x = 0, .y = 1, .z = 1 },
|
|
.row3 = .{ .x = 0, .y = 0, .z = 1 },
|
|
};
|
|
|
|
const c = mat3Sub(i8, a, b);
|
|
|
|
try std.testing.expect(c.row1.x == 1);
|
|
try std.testing.expect(c.row1.y == 1);
|
|
try std.testing.expect(c.row1.z == 3);
|
|
try std.testing.expect(c.row2.x == 0);
|
|
try std.testing.expect(c.row2.y == 0);
|
|
try std.testing.expect(c.row2.z == 4);
|
|
try std.testing.expect(c.row3.x == 0);
|
|
try std.testing.expect(c.row3.y == 0);
|
|
try std.testing.expect(c.row3.z == 8);
|
|
}
|
|
|
|
test "Mat3 mul works" {
|
|
const a: Mat3(i8) = .{
|
|
.row1 = .{ .x = 1, .y = 2, .z = 3 },
|
|
.row2 = .{ .x = 0, .y = 1, .z = 5 },
|
|
.row3 = .{ .x = 0, .y = 0, .z = 9 },
|
|
};
|
|
const b: Mat3(i8) = .{
|
|
.row1 = .{ .x = 0, .y = 1, .z = 0 },
|
|
.row2 = .{ .x = 0, .y = 1, .z = 1 },
|
|
.row3 = .{ .x = 0, .y = 0, .z = 1 },
|
|
};
|
|
|
|
const c = mat3Mul(i8, a, b);
|
|
|
|
try std.testing.expect(c.row1.x == 0);
|
|
try std.testing.expect(c.row1.y == 3);
|
|
try std.testing.expect(c.row1.z == 5);
|
|
try std.testing.expect(c.row2.x == 0);
|
|
try std.testing.expect(c.row2.y == 1);
|
|
try std.testing.expect(c.row2.z == 6);
|
|
try std.testing.expect(c.row3.x == 0);
|
|
try std.testing.expect(c.row3.y == 0);
|
|
try std.testing.expect(c.row3.z == 9);
|
|
}
|
|
|
|
test "vec3 mul mat3 works" {
|
|
const a: Vec3(i8) = .{ .x = 1, .y = 2, .z = 3 };
|
|
|
|
const b: Mat3(i8) = .{
|
|
.row1 = .{ .x = 0, .y = 1, .z = 0 },
|
|
.row2 = .{ .x = 0, .y = 1, .z = 1 },
|
|
.row3 = .{ .x = 0, .y = 0, .z = 1 },
|
|
};
|
|
|
|
const c = vec3MulMat3(i8, a, b);
|
|
|
|
try std.testing.expect(c.x == 0);
|
|
try std.testing.expect(c.y == 3);
|
|
try std.testing.expect(c.z == 5);
|
|
}
|