Use castle for vecmath (doesn't work fully yet)
This commit is contained in:
3
.gitmodules
vendored
Normal file
3
.gitmodules
vendored
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
[submodule "castle"]
|
||||||
|
path = castle
|
||||||
|
url = https://gitea.renati.me/renati/castle.git
|
||||||
@@ -7,10 +7,12 @@ pub fn build(b: *std.Build) !void {
|
|||||||
const optimize = b.standardOptimizeOption(.{});
|
const optimize = b.standardOptimizeOption(.{});
|
||||||
const llvm = b.option(bool, "llvm", "Use LLVM and LLD") orelse false;
|
const llvm = b.option(bool, "llvm", "Use LLVM and LLD") orelse false;
|
||||||
|
|
||||||
|
const vecmath_dep = b.dependency("vecmath", .{});
|
||||||
const vulkan_dep = b.dependency("vulkan_zig", .{ .registry = b.path("vendor/vk.xml") });
|
const vulkan_dep = b.dependency("vulkan_zig", .{ .registry = b.path("vendor/vk.xml") });
|
||||||
const zglfw_dep = b.dependency("zglfw", .{ .import_vulkan = true });
|
const zglfw_dep = b.dependency("zglfw", .{ .import_vulkan = true });
|
||||||
const zstbi_dep = b.dependency("zstbi", .{});
|
const zstbi_dep = b.dependency("zstbi", .{});
|
||||||
|
|
||||||
|
const vecmath_mod = vecmath_dep.module("vecmath");
|
||||||
const vulkan_mod = vulkan_dep.module("vulkan-zig");
|
const vulkan_mod = vulkan_dep.module("vulkan-zig");
|
||||||
const zglfw_mod = zglfw_dep.module("root");
|
const zglfw_mod = zglfw_dep.module("root");
|
||||||
const zstbi_mod = zstbi_dep.module("root");
|
const zstbi_mod = zstbi_dep.module("root");
|
||||||
@@ -25,6 +27,7 @@ pub fn build(b: *std.Build) !void {
|
|||||||
.optimize = optimize,
|
.optimize = optimize,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
exe_mod.addImport("vecmath", vecmath_mod);
|
||||||
exe_mod.addImport("vulkan", vulkan_mod);
|
exe_mod.addImport("vulkan", vulkan_mod);
|
||||||
exe_mod.addImport("zglfw", zglfw_mod);
|
exe_mod.addImport("zglfw", zglfw_mod);
|
||||||
exe_mod.addImport("zstbi", zstbi_mod);
|
exe_mod.addImport("zstbi", zstbi_mod);
|
||||||
|
|||||||
@@ -5,6 +5,9 @@
|
|||||||
.minimum_zig_version = "0.15.2",
|
.minimum_zig_version = "0.15.2",
|
||||||
|
|
||||||
.dependencies = .{
|
.dependencies = .{
|
||||||
|
.vecmath = .{
|
||||||
|
.path = "castle/packages/vecmath",
|
||||||
|
},
|
||||||
.vulkan_zig = .{
|
.vulkan_zig = .{
|
||||||
.url = "git+https://github.com/Snektron/vulkan-zig.git#1446b0b994c2362264cc24513d7c7ec31b469c50",
|
.url = "git+https://github.com/Snektron/vulkan-zig.git#1446b0b994c2362264cc24513d7c7ec31b469c50",
|
||||||
.hash = "vulkan-0.0.0-r7Ytx_VDAwAiMl0YSu2UOkVMIGJN7CeIQaxJR-hUSfD6",
|
.hash = "vulkan-0.0.0-r7Ytx_VDAwAiMl0YSu2UOkVMIGJN7CeIQaxJR-hUSfD6",
|
||||||
|
|||||||
1
castle
Submodule
1
castle
Submodule
Submodule castle added at 7e8103565d
202
src/Chunks.zig
202
src/Chunks.zig
@@ -4,18 +4,17 @@ const std = @import("std");
|
|||||||
const c = @import("const.zig");
|
const c = @import("const.zig");
|
||||||
const math = @import("math.zig");
|
const math = @import("math.zig");
|
||||||
const vk = @import("vulkan");
|
const vk = @import("vulkan");
|
||||||
|
const vm = @import("vecmath");
|
||||||
|
|
||||||
const Blocks = @import("assets/Blocks.zig");
|
const Blocks = @import("assets/Blocks.zig");
|
||||||
const Chunk = @import("assets/Chunk.zig");
|
const Chunk = @import("assets/Chunk.zig");
|
||||||
const Engine = @import("engine/Engine.zig");
|
const Engine = @import("engine/Engine.zig");
|
||||||
const Iterator2 = math.Iterator2;
|
const Iterator2 = math.Iterator2;
|
||||||
const Vector2Int = math.Vector2Int;
|
|
||||||
const Vector3Int = math.Vector3Int;
|
|
||||||
|
|
||||||
chunks: std.AutoHashMapUnmanaged([3]i16, Chunk),
|
chunks: std.AutoHashMapUnmanaged([3]i16, Chunk),
|
||||||
|
|
||||||
const RaycastHit = struct {
|
const RaycastHit = struct {
|
||||||
normal_frac: Vector3Int,
|
normal_frac: vm.Vector3Int,
|
||||||
projected_distance_sv: i32,
|
projected_distance_sv: i32,
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -28,40 +27,41 @@ pub fn deinit(self: *Chunks, engine: *Engine, descriptor_pool: vk.DescriptorPool
|
|||||||
self.* = undefined;
|
self.* = undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn getVoxelAt(self: *const Chunks, vx: Vector3Int) ?Blocks.Id {
|
pub fn getVoxelAt(self: *const Chunks, vx: vm.Vector3Int) ?Blocks.Id {
|
||||||
const min_ck = Vector3Int.initScalar(std.math.minInt(i16));
|
const min_ck = vm.Vector3Int.initScalar(std.math.minInt(i16));
|
||||||
const max_ck = Vector3Int.initScalar(std.math.maxInt(i16));
|
const max_ck = vm.Vector3Int.initScalar(std.math.maxInt(i16));
|
||||||
const ck = vx.divScalar(c.vx_per_ck);
|
const ck = vx.divScalar(c.vx_per_ck);
|
||||||
if (@reduce(.Or, (ck.vector < min_ck.vector) | (ck.vector > max_ck.vector))) {
|
if ((ck.x < min_ck.x) | (ck.y < min_ck.y) | (ck.z < min_ck.z) | (ck.x > max_ck.x) | (ck.y > max_ck.y) | (ck.z > max_ck.z)) {
|
||||||
|
@branchHint(.unlikely);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (self.chunks.get(.{
|
if (self.chunks.get(.{
|
||||||
@intCast(ck.getX()),
|
@intCast(ck.x),
|
||||||
@intCast(ck.getY()),
|
@intCast(ck.y),
|
||||||
@intCast(ck.getZ()),
|
@intCast(ck.z),
|
||||||
})) |chunk| {
|
})) |chunk| {
|
||||||
const ckvx = vx.modScalar(c.vx_per_ck);
|
const ckvx = vx.modScalar(c.vx_per_ck);
|
||||||
return chunk.blocks[@intCast(ckvx.getZ())][@intCast(ckvx.getY())][@intCast(ckvx.getX())];
|
return chunk.blocks[@intCast(ckvx.z)][@intCast(ckvx.y)][@intCast(ckvx.x)];
|
||||||
} else {
|
} else {
|
||||||
return .air;
|
return .air;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn isSolid(self: *const Chunks, vx: Vector3Int) bool {
|
pub fn isSolid(self: *const Chunks, vx: vm.Vector3Int) bool {
|
||||||
const maybe_id = getVoxelAt(self, vx);
|
const maybe_id = getVoxelAt(self, vx);
|
||||||
// NOTE `null` is considered solid, as it's out of bounds.
|
// NOTE `null` is considered solid, as it's out of bounds.
|
||||||
return maybe_id != .air;
|
return maybe_id != .air;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn sweepCastDown(self: *const Chunks, min_sv: Vector3Int, max_sv: Vector3Int, distance_sv: i32) ?RaycastHit {
|
pub fn sweepCastDown(self: *const Chunks, min_sv: vm.Vector3Int, max_sv: vm.Vector3Int, distance_sv: i32) ?RaycastHit {
|
||||||
const min_x_vx = c.subvoxelsToVoxels(.border_up, min_sv.getX());
|
const min_x_vx = c.subvoxelsToVoxels(.border_up, min_sv.x);
|
||||||
const min_y_vx = c.subvoxelsToVoxels(.border_up, min_sv.getY());
|
const min_y_vx = c.subvoxelsToVoxels(.border_up, min_sv.y);
|
||||||
const max_x_vx = c.subvoxelsToVoxels(.border_down, max_sv.getX());
|
const max_x_vx = c.subvoxelsToVoxels(.border_down, max_sv.x);
|
||||||
const max_y_vx = c.subvoxelsToVoxels(.border_down, max_sv.getY());
|
const max_y_vx = c.subvoxelsToVoxels(.border_down, max_sv.y);
|
||||||
|
|
||||||
const start_z_vx = c.subvoxelsToVoxels(.border_up, min_sv.getZ()) - 1;
|
const start_z_vx = c.subvoxelsToVoxels(.border_up, min_sv.z) - 1;
|
||||||
const end_z_vx = c.subvoxelsToVoxels(.border_up, min_sv.getZ() - distance_sv);
|
const end_z_vx = c.subvoxelsToVoxels(.border_up, min_sv.z - distance_sv);
|
||||||
|
|
||||||
var z_vx: i32 = start_z_vx;
|
var z_vx: i32 = start_z_vx;
|
||||||
while (z_vx >= end_z_vx) : (z_vx -= 1) {
|
while (z_vx >= end_z_vx) : (z_vx -= 1) {
|
||||||
@@ -75,8 +75,8 @@ pub fn sweepCastDown(self: *const Chunks, min_sv: Vector3Int, max_sv: Vector3Int
|
|||||||
if (!self.isSolid(.init(x_vx, y_vx, z_vx))) continue;
|
if (!self.isSolid(.init(x_vx, y_vx, z_vx))) continue;
|
||||||
|
|
||||||
return .{
|
return .{
|
||||||
.projected_distance_sv = distance_sv - (min_sv.getZ() - z_sv),
|
.projected_distance_sv = distance_sv - (min_sv.z - z_sv),
|
||||||
.normal_frac = .unit_z_frac,
|
.normal_frac = .init(0, 0, std.math.maxInt(i32)),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -84,14 +84,14 @@ pub fn sweepCastDown(self: *const Chunks, min_sv: Vector3Int, max_sv: Vector3Int
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn sweepCastUp(self: *const Chunks, min_sv: Vector3Int, max_sv: Vector3Int, distance_sv: i32) ?RaycastHit {
|
pub fn sweepCastUp(self: *const Chunks, min_sv: vm.Vector3Int, max_sv: vm.Vector3Int, distance_sv: i32) ?RaycastHit {
|
||||||
const min_x_vx = c.subvoxelsToVoxels(.border_up, min_sv.getX());
|
const min_x_vx = c.subvoxelsToVoxels(.border_up, min_sv.x);
|
||||||
const min_y_vx = c.subvoxelsToVoxels(.border_up, min_sv.getY());
|
const min_y_vx = c.subvoxelsToVoxels(.border_up, min_sv.y);
|
||||||
const max_x_vx = c.subvoxelsToVoxels(.border_down, max_sv.getX());
|
const max_x_vx = c.subvoxelsToVoxels(.border_down, max_sv.x);
|
||||||
const max_y_vx = c.subvoxelsToVoxels(.border_down, max_sv.getY());
|
const max_y_vx = c.subvoxelsToVoxels(.border_down, max_sv.y);
|
||||||
|
|
||||||
const start_z_vx = c.subvoxelsToVoxels(.border_down, max_sv.getZ()) + 1;
|
const start_z_vx = c.subvoxelsToVoxels(.border_down, max_sv.z) + 1;
|
||||||
const end_z_vx = c.subvoxelsToVoxels(.border_down, max_sv.getZ() + distance_sv);
|
const end_z_vx = c.subvoxelsToVoxels(.border_down, max_sv.z + distance_sv);
|
||||||
|
|
||||||
var z_vx: i32 = start_z_vx;
|
var z_vx: i32 = start_z_vx;
|
||||||
while (z_vx <= end_z_vx) : (z_vx += 1) {
|
while (z_vx <= end_z_vx) : (z_vx += 1) {
|
||||||
@@ -105,8 +105,8 @@ pub fn sweepCastUp(self: *const Chunks, min_sv: Vector3Int, max_sv: Vector3Int,
|
|||||||
if (!self.isSolid(.init(x_vx, y_vx, z_vx))) continue;
|
if (!self.isSolid(.init(x_vx, y_vx, z_vx))) continue;
|
||||||
|
|
||||||
return .{
|
return .{
|
||||||
.projected_distance_sv = distance_sv - (z_sv - max_sv.getZ()),
|
.projected_distance_sv = distance_sv - (z_sv - max_sv.z),
|
||||||
.normal_frac = .unit_nz_frac,
|
.normal_frac = .init(0, 0, -std.math.maxInt(i32)),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -114,30 +114,30 @@ pub fn sweepCastUp(self: *const Chunks, min_sv: Vector3Int, max_sv: Vector3Int,
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vector3Int, ray_sv: Vector2Int) ?RaycastHit {
|
pub fn sweepCastHorizontal(self: *const Chunks, min_sv: vm.Vector3Int, max_sv: vm.Vector3Int, ray_sv: vm.Vector2Int) ?RaycastHit {
|
||||||
const min_z_vx = c.subvoxelsToVoxels(.border_up, min_sv.getZ());
|
const min_z_vx = c.subvoxelsToVoxels(.border_up, min_sv.z);
|
||||||
const max_z_vx = c.subvoxelsToVoxels(.border_down, max_sv.getZ());
|
const max_z_vx = c.subvoxelsToVoxels(.border_down, max_sv.z);
|
||||||
|
|
||||||
var hit: ?RaycastHit = null;
|
var hit: ?RaycastHit = null;
|
||||||
var hit_distance_squared = std.math.inf(f32);
|
var hit_distance_squared = std.math.inf(f32);
|
||||||
|
|
||||||
const fdydx: f32 = @as(f32, @floatFromInt(ray_sv.getY())) / @as(f32, @floatFromInt(ray_sv.getX()));
|
const fdydx: f32 = @as(f32, @floatFromInt(ray_sv.y)) / @as(f32, @floatFromInt(ray_sv.x));
|
||||||
const fdxdy: f32 = @as(f32, @floatFromInt(ray_sv.getX())) / @as(f32, @floatFromInt(ray_sv.getY()));
|
const fdxdy: f32 = @as(f32, @floatFromInt(ray_sv.x)) / @as(f32, @floatFromInt(ray_sv.y));
|
||||||
|
|
||||||
// Positive X
|
// Positive X
|
||||||
if (ray_sv.getX() > 0) {
|
if (ray_sv.x > 0) {
|
||||||
const x0_sv = max_sv.getX();
|
const x0_sv = max_sv.x;
|
||||||
const y0_sv = min_sv.getY();
|
const y0_sv = min_sv.y;
|
||||||
const y1_sv = max_sv.getY();
|
const y1_sv = max_sv.y;
|
||||||
|
|
||||||
const start_x_vx = c.subvoxelsToVoxels(.border_down, x0_sv) + 1;
|
const start_x_vx = c.subvoxelsToVoxels(.border_down, x0_sv) + 1;
|
||||||
const end_x_vx = c.subvoxelsToVoxels(.border_down, x0_sv + ray_sv.getX());
|
const end_x_vx = c.subvoxelsToVoxels(.border_down, x0_sv + ray_sv.x);
|
||||||
|
|
||||||
var x_vx: i32 = start_x_vx;
|
var x_vx: i32 = start_x_vx;
|
||||||
px: while (x_vx <= end_x_vx) : (x_vx += 1) {
|
px: while (x_vx <= end_x_vx) : (x_vx += 1) {
|
||||||
const x_sv = c.voxelsToSubvoxels(x_vx);
|
const x_sv = c.voxelsToSubvoxels(x_vx);
|
||||||
const min_y_vx = c.subvoxelsToVoxels(.border_up, math.wideMulDivFloor(x_sv - x0_sv, ray_sv.getY(), ray_sv.getX()) + y0_sv);
|
const min_y_vx = c.subvoxelsToVoxels(.border_up, math.wideMulDivFloor(x_sv - x0_sv, ray_sv.y, ray_sv.x) + y0_sv);
|
||||||
const max_y_vx = c.subvoxelsToVoxels(.border_down, math.wideMulDivCeil(x_sv - x0_sv, ray_sv.getY(), ray_sv.getX()) + y1_sv);
|
const max_y_vx = c.subvoxelsToVoxels(.border_down, math.wideMulDivCeil(x_sv - x0_sv, ray_sv.y, ray_sv.x) + y1_sv);
|
||||||
var it = Iterator2(i32).init(.{
|
var it = Iterator2(i32).init(.{
|
||||||
.min = .{ min_y_vx, min_z_vx },
|
.min = .{ min_y_vx, min_z_vx },
|
||||||
.max = .{ max_y_vx, max_z_vx },
|
.max = .{ max_y_vx, max_z_vx },
|
||||||
@@ -151,8 +151,8 @@ pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vect
|
|||||||
const fdy: f32 = fdx * fdydx;
|
const fdy: f32 = fdx * fdydx;
|
||||||
|
|
||||||
hit = .{
|
hit = .{
|
||||||
.projected_distance_sv = ray_sv.getX() - dx,
|
.projected_distance_sv = ray_sv.x - dx,
|
||||||
.normal_frac = .unit_nx_frac,
|
.normal_frac = .init(-std.math.maxInt(i32), 0, 0),
|
||||||
};
|
};
|
||||||
hit_distance_squared = fdx * fdx + fdy * fdy;
|
hit_distance_squared = fdx * fdx + fdy * fdy;
|
||||||
// std.debug.print("HIT +X ({X}->{X}) at ({X}, {X}, {X}) [VX] | min_sv={X} max_sv={X} ray_sv={X} | proj_dist={X} \n", .{ start_x_vx, end_x_vx, x_vx, y_vx, z_vx, min_sv.vector, max_sv.vector, ray_sv.vector, hit.?.projected_distance_sv });
|
// std.debug.print("HIT +X ({X}->{X}) at ({X}, {X}, {X}) [VX] | min_sv={X} max_sv={X} ray_sv={X} | proj_dist={X} \n", .{ start_x_vx, end_x_vx, x_vx, y_vx, z_vx, min_sv.vector, max_sv.vector, ray_sv.vector, hit.?.projected_distance_sv });
|
||||||
@@ -163,19 +163,19 @@ pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vect
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Negative X
|
// Negative X
|
||||||
if (ray_sv.getX() < 0) {
|
if (ray_sv.x < 0) {
|
||||||
const x0_sv = min_sv.getX();
|
const x0_sv = min_sv.x;
|
||||||
const y0_sv = min_sv.getY();
|
const y0_sv = min_sv.y;
|
||||||
const y1_sv = max_sv.getY();
|
const y1_sv = max_sv.y;
|
||||||
|
|
||||||
const start_x_vx = c.subvoxelsToVoxels(.border_up, x0_sv) - 1;
|
const start_x_vx = c.subvoxelsToVoxels(.border_up, x0_sv) - 1;
|
||||||
const end_x_vx = c.subvoxelsToVoxels(.border_up, x0_sv + ray_sv.getX());
|
const end_x_vx = c.subvoxelsToVoxels(.border_up, x0_sv + ray_sv.x);
|
||||||
|
|
||||||
var x_vx: i32 = start_x_vx;
|
var x_vx: i32 = start_x_vx;
|
||||||
nx: while (x_vx >= end_x_vx) : (x_vx -= 1) {
|
nx: while (x_vx >= end_x_vx) : (x_vx -= 1) {
|
||||||
const x_sv = c.voxelsToSubvoxels(x_vx + 1);
|
const x_sv = c.voxelsToSubvoxels(x_vx + 1);
|
||||||
const min_y_vx = c.subvoxelsToVoxels(.border_up, math.wideMulDivFloor(x_sv - x0_sv, ray_sv.getY(), ray_sv.getX()) + y0_sv);
|
const min_y_vx = c.subvoxelsToVoxels(.border_up, math.wideMulDivFloor(x_sv - x0_sv, ray_sv.y, ray_sv.x) + y0_sv);
|
||||||
const max_y_vx = c.subvoxelsToVoxels(.border_down, math.wideMulDivCeil(x_sv - x0_sv, ray_sv.getY(), ray_sv.getX()) + y1_sv);
|
const max_y_vx = c.subvoxelsToVoxels(.border_down, math.wideMulDivCeil(x_sv - x0_sv, ray_sv.y, ray_sv.x) + y1_sv);
|
||||||
var it = Iterator2(i32).init(.{
|
var it = Iterator2(i32).init(.{
|
||||||
.min = .{ min_y_vx, min_z_vx },
|
.min = .{ min_y_vx, min_z_vx },
|
||||||
.max = .{ max_y_vx, max_z_vx },
|
.max = .{ max_y_vx, max_z_vx },
|
||||||
@@ -189,8 +189,8 @@ pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vect
|
|||||||
const fdy: f32 = fdx * fdydx;
|
const fdy: f32 = fdx * fdydx;
|
||||||
|
|
||||||
hit = .{
|
hit = .{
|
||||||
.projected_distance_sv = -(ray_sv.getX() - dx),
|
.projected_distance_sv = -(ray_sv.x - dx),
|
||||||
.normal_frac = .unit_x_frac,
|
.normal_frac = .init(std.math.maxInt(i32), 0, 0),
|
||||||
};
|
};
|
||||||
hit_distance_squared = fdx * fdx + fdy * fdy;
|
hit_distance_squared = fdx * fdx + fdy * fdy;
|
||||||
// std.debug.print("HIT -X ({X}->{X}) at ({X}, {X}, {X}) [VX] | min_sv={X} max_sv={X} ray_sv={X} | proj_dist={X} \n", .{ start_x_vx, end_x_vx, x_vx, y_vx, z_vx, min_sv.vector, max_sv.vector, ray_sv.vector, hit.?.projected_distance_sv });
|
// std.debug.print("HIT -X ({X}->{X}) at ({X}, {X}, {X}) [VX] | min_sv={X} max_sv={X} ray_sv={X} | proj_dist={X} \n", .{ start_x_vx, end_x_vx, x_vx, y_vx, z_vx, min_sv.vector, max_sv.vector, ray_sv.vector, hit.?.projected_distance_sv });
|
||||||
@@ -201,19 +201,19 @@ pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vect
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Positive Y
|
// Positive Y
|
||||||
if (ray_sv.getY() > 0) {
|
if (ray_sv.y > 0) {
|
||||||
const y0_sv = max_sv.getY();
|
const y0_sv = max_sv.y;
|
||||||
const x0_sv = min_sv.getX();
|
const x0_sv = min_sv.x;
|
||||||
const x1_sv = max_sv.getX();
|
const x1_sv = max_sv.x;
|
||||||
|
|
||||||
const start_y_vx = c.subvoxelsToVoxels(.border_down, y0_sv) + 1;
|
const start_y_vx = c.subvoxelsToVoxels(.border_down, y0_sv) + 1;
|
||||||
const end_y_vx = c.subvoxelsToVoxels(.border_down, y0_sv + ray_sv.getY());
|
const end_y_vx = c.subvoxelsToVoxels(.border_down, y0_sv + ray_sv.y);
|
||||||
|
|
||||||
var y_vx = start_y_vx;
|
var y_vx = start_y_vx;
|
||||||
py: while (y_vx <= end_y_vx) : (y_vx += 1) {
|
py: while (y_vx <= end_y_vx) : (y_vx += 1) {
|
||||||
const y_sv = c.voxelsToSubvoxels(y_vx);
|
const y_sv = c.voxelsToSubvoxels(y_vx);
|
||||||
const min_x_vx = c.subvoxelsToVoxels(.border_up, math.wideMulDivFloor(y_sv - y0_sv, ray_sv.getX(), ray_sv.getY()) + x0_sv);
|
const min_x_vx = c.subvoxelsToVoxels(.border_up, math.wideMulDivFloor(y_sv - y0_sv, ray_sv.x, ray_sv.y) + x0_sv);
|
||||||
const max_x_vx = c.subvoxelsToVoxels(.border_down, math.wideMulDivCeil(y_sv - y0_sv, ray_sv.getX(), ray_sv.getY()) + x1_sv);
|
const max_x_vx = c.subvoxelsToVoxels(.border_down, math.wideMulDivCeil(y_sv - y0_sv, ray_sv.x, ray_sv.y) + x1_sv);
|
||||||
var it = Iterator2(i32).init(.{
|
var it = Iterator2(i32).init(.{
|
||||||
.min = .{ min_x_vx, min_z_vx },
|
.min = .{ min_x_vx, min_z_vx },
|
||||||
.max = .{ max_x_vx, max_z_vx },
|
.max = .{ max_x_vx, max_z_vx },
|
||||||
@@ -229,8 +229,8 @@ pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vect
|
|||||||
const this_hit_distance_squared = fdx * fdx + fdy * fdy;
|
const this_hit_distance_squared = fdx * fdx + fdy * fdy;
|
||||||
if (this_hit_distance_squared < hit_distance_squared) {
|
if (this_hit_distance_squared < hit_distance_squared) {
|
||||||
hit = .{
|
hit = .{
|
||||||
.projected_distance_sv = ray_sv.getY() - dy,
|
.projected_distance_sv = ray_sv.y - dy,
|
||||||
.normal_frac = .unit_ny_frac,
|
.normal_frac = .init(0, -std.math.maxInt(i32), 0),
|
||||||
};
|
};
|
||||||
hit_distance_squared = this_hit_distance_squared;
|
hit_distance_squared = this_hit_distance_squared;
|
||||||
// std.debug.print("HIT +Y ({X}->{X}) at ({X}, {X}, {X}) [VX] | min_sv={X} max_sv={X} ray_sv={X} | proj_dist={X} \n", .{ start_y_vx, end_y_vx, x_vx, y_vx, z_vx, min_sv.vector, max_sv.vector, ray_sv.vector, hit.?.projected_distance_sv });
|
// std.debug.print("HIT +Y ({X}->{X}) at ({X}, {X}, {X}) [VX] | min_sv={X} max_sv={X} ray_sv={X} | proj_dist={X} \n", .{ start_y_vx, end_y_vx, x_vx, y_vx, z_vx, min_sv.vector, max_sv.vector, ray_sv.vector, hit.?.projected_distance_sv });
|
||||||
@@ -242,19 +242,19 @@ pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vect
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Negative Y
|
// Negative Y
|
||||||
if (ray_sv.getY() < 0.0) {
|
if (ray_sv.y < 0.0) {
|
||||||
const y0_sv = min_sv.getY();
|
const y0_sv = min_sv.y;
|
||||||
const x0_sv = min_sv.getX();
|
const x0_sv = min_sv.x;
|
||||||
const x1_sv = max_sv.getX();
|
const x1_sv = max_sv.x;
|
||||||
|
|
||||||
const start_y_vx = c.subvoxelsToVoxels(.border_up, y0_sv) - 1;
|
const start_y_vx = c.subvoxelsToVoxels(.border_up, y0_sv) - 1;
|
||||||
const end_y_vx = c.subvoxelsToVoxels(.border_up, y0_sv + ray_sv.getY());
|
const end_y_vx = c.subvoxelsToVoxels(.border_up, y0_sv + ray_sv.y);
|
||||||
|
|
||||||
var y_vx = start_y_vx;
|
var y_vx = start_y_vx;
|
||||||
ny: while (y_vx >= end_y_vx) : (y_vx -= 1) {
|
ny: while (y_vx >= end_y_vx) : (y_vx -= 1) {
|
||||||
const y_sv = c.voxelsToSubvoxels(y_vx + 1);
|
const y_sv = c.voxelsToSubvoxels(y_vx + 1);
|
||||||
const min_x_vx = c.subvoxelsToVoxels(.border_up, math.wideMulDivFloor(y_sv - y0_sv, ray_sv.getX(), ray_sv.getY()) + x0_sv);
|
const min_x_vx = c.subvoxelsToVoxels(.border_up, math.wideMulDivFloor(y_sv - y0_sv, ray_sv.x, ray_sv.y) + x0_sv);
|
||||||
const max_x_vx = c.subvoxelsToVoxels(.border_down, math.wideMulDivCeil(y_sv - y0_sv, ray_sv.getX(), ray_sv.getY()) + x1_sv);
|
const max_x_vx = c.subvoxelsToVoxels(.border_down, math.wideMulDivCeil(y_sv - y0_sv, ray_sv.x, ray_sv.y) + x1_sv);
|
||||||
var it = Iterator2(i32).init(.{
|
var it = Iterator2(i32).init(.{
|
||||||
.min = .{ min_x_vx, min_z_vx },
|
.min = .{ min_x_vx, min_z_vx },
|
||||||
.max = .{ max_x_vx, max_z_vx },
|
.max = .{ max_x_vx, max_z_vx },
|
||||||
@@ -270,8 +270,8 @@ pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vect
|
|||||||
const this_hit_distance_squared = fdx * fdx + fdy * fdy;
|
const this_hit_distance_squared = fdx * fdx + fdy * fdy;
|
||||||
if (this_hit_distance_squared < hit_distance_squared) {
|
if (this_hit_distance_squared < hit_distance_squared) {
|
||||||
hit = .{
|
hit = .{
|
||||||
.projected_distance_sv = -(ray_sv.getY() - dy),
|
.projected_distance_sv = -(ray_sv.y - dy),
|
||||||
.normal_frac = .unit_y_frac,
|
.normal_frac = .init(0, std.math.maxInt(i32), 0),
|
||||||
};
|
};
|
||||||
hit_distance_squared = this_hit_distance_squared;
|
hit_distance_squared = this_hit_distance_squared;
|
||||||
// std.debug.print("HIT -Y ({X}->{X}) at ({X}, {X}, {X}) [VX] | min_sv={X} max_sv={X} ray_sv={X} | proj_dist={X} \n", .{ start_y_vx, end_y_vx, x_vx, y_vx, z_vx, min_sv.vector, max_sv.vector, ray_sv.vector, hit.?.projected_distance_sv });
|
// std.debug.print("HIT -Y ({X}->{X}) at ({X}, {X}, {X}) [VX] | min_sv={X} max_sv={X} ray_sv={X} | proj_dist={X} \n", .{ start_y_vx, end_y_vx, x_vx, y_vx, z_vx, min_sv.vector, max_sv.vector, ray_sv.vector, hit.?.projected_distance_sv });
|
||||||
@@ -285,64 +285,64 @@ pub fn sweepCastHorizontal(self: *const Chunks, min_sv: Vector3Int, max_sv: Vect
|
|||||||
return hit;
|
return hit;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn raycast(self: *const Chunks, origin_sv: Vector3Int, ray_sv: Vector3Int) ?RaycastHit {
|
pub fn raycast(self: *const Chunks, origin_sv: vm.Vector3Int, ray_sv: vm.Vector3Int) ?RaycastHit {
|
||||||
const end_sv = origin_sv.add(ray_sv);
|
const end_sv = origin_sv.add(ray_sv);
|
||||||
|
|
||||||
std.debug.print("Raycast from ({d}:{X}, {d}:{X}, {d}:{X}) to ({d}:{X}, {d}:{X}, {d}:{X})\n", .{
|
std.debug.print("Raycast from ({d}:{X}, {d}:{X}, {d}:{X}) to ({d}:{X}, {d}:{X}, {d}:{X})\n", .{
|
||||||
c.subvoxelsToVoxels(.border_up, origin_sv.getX()),
|
c.subvoxelsToVoxels(.border_up, origin_sv.x),
|
||||||
c.subvoxelsToVoxelSubvoxels(origin_sv.getX()),
|
c.subvoxelsToVoxelSubvoxels(origin_sv.x),
|
||||||
c.subvoxelsToVoxels(.border_up, origin_sv.getY()),
|
c.subvoxelsToVoxels(.border_up, origin_sv.y),
|
||||||
c.subvoxelsToVoxelSubvoxels(origin_sv.getY()),
|
c.subvoxelsToVoxelSubvoxels(origin_sv.y),
|
||||||
c.subvoxelsToVoxels(.border_up, origin_sv.getZ()),
|
c.subvoxelsToVoxels(.border_up, origin_sv.z),
|
||||||
c.subvoxelsToVoxelSubvoxels(origin_sv.getZ()),
|
c.subvoxelsToVoxelSubvoxels(origin_sv.z),
|
||||||
c.subvoxelsToVoxels(.border_up, end_sv.getX()),
|
c.subvoxelsToVoxels(.border_up, end_sv.x),
|
||||||
c.subvoxelsToVoxelSubvoxels(end_sv.getX()),
|
c.subvoxelsToVoxelSubvoxels(end_sv.x),
|
||||||
c.subvoxelsToVoxels(.border_up, end_sv.getY()),
|
c.subvoxelsToVoxels(.border_up, end_sv.y),
|
||||||
c.subvoxelsToVoxelSubvoxels(end_sv.getY()),
|
c.subvoxelsToVoxelSubvoxels(end_sv.y),
|
||||||
c.subvoxelsToVoxels(.border_up, end_sv.getZ()),
|
c.subvoxelsToVoxels(.border_up, end_sv.z),
|
||||||
c.subvoxelsToVoxelSubvoxels(end_sv.getZ()),
|
c.subvoxelsToVoxelSubvoxels(end_sv.z),
|
||||||
});
|
});
|
||||||
|
|
||||||
const zero = Vector3Int.zero.vector;
|
const zero = vm.epi32(0);
|
||||||
const one = Vector3Int.one.vector;
|
const one = vm.epi32(1);
|
||||||
|
|
||||||
const ray_positive: Vector3Int = .{ .vector = @select(i32, ray_sv.vector > zero, one, zero) };
|
const ray_positive: vm.Vector3Int = .{ .vector = @select(i32, ray_sv.vector > zero, one, zero) };
|
||||||
const ray_negative: Vector3Int = .{ .vector = @select(i32, ray_sv.vector < zero, one, zero) };
|
const ray_negative: vm.Vector3Int = .{ .vector = @select(i32, ray_sv.vector < zero, one, zero) };
|
||||||
const ray_sign: Vector3Int = .sub(ray_positive, ray_negative);
|
const ray_sign: vm.Vector3Int = .sub(ray_positive, ray_negative);
|
||||||
|
|
||||||
const start_vx = origin_sv.sub(ray_positive).divScalar(c.sv_per_vx).add(ray_sign);
|
const start_vx = origin_sv.sub(ray_positive).divScalar(c.sv_per_vx).add(ray_sign);
|
||||||
const end_vx = end_sv.sub(ray_positive).divScalar(c.sv_per_vx);
|
const end_vx = end_sv.sub(ray_positive).divScalar(c.sv_per_vx);
|
||||||
const abs_ray_sv = ray_sv.abs();
|
const abs_ray_sv = ray_sv.abs();
|
||||||
|
|
||||||
std.debug.print("Start [VX]: ({d}, {d}, {d}) | End [VX]: ({d}, {d}, {d})\n", .{
|
std.debug.print("Start [VX]: ({d}, {d}, {d}) | End [VX]: ({d}, {d}, {d})\n", .{
|
||||||
start_vx.getX(),
|
start_vx.x,
|
||||||
start_vx.getY(),
|
start_vx.y,
|
||||||
start_vx.getZ(),
|
start_vx.z,
|
||||||
end_vx.getX(),
|
end_vx.x,
|
||||||
end_vx.getY(),
|
end_vx.y,
|
||||||
end_vx.getZ(),
|
end_vx.z,
|
||||||
});
|
});
|
||||||
|
|
||||||
var i_index: usize = undefined;
|
var i_index: usize = undefined;
|
||||||
var j_index: usize = undefined;
|
var j_index: usize = undefined;
|
||||||
var k_index: usize = undefined;
|
var k_index: usize = undefined;
|
||||||
|
|
||||||
if (abs_ray_sv.getX() > abs_ray_sv.getY() and abs_ray_sv.getX() > abs_ray_sv.getZ()) {
|
if (abs_ray_sv.x > abs_ray_sv.y and abs_ray_sv.x > abs_ray_sv.z) {
|
||||||
// Main axis: ±X
|
// Main axis: ±X
|
||||||
i_index, j_index, k_index = .{ 0, 1, 2 };
|
i_index, j_index, k_index = .{ 0, 1, 2 };
|
||||||
std.debug.print("Order is (X, Y, Z)\n", .{});
|
std.debug.print("Order is (X, Y, Z)\n", .{});
|
||||||
} else if (abs_ray_sv.getY() > abs_ray_sv.getZ()) {
|
} else if (abs_ray_sv.y > abs_ray_sv.z) {
|
||||||
// Main axis: ±Y
|
// Main axis: ±Y
|
||||||
i_index, j_index, k_index = .{ 1, 2, 0 };
|
i_index, j_index, k_index = .{ 1, 2, 0 };
|
||||||
std.debug.print("Order is (Y, Z, X)\n", .{});
|
std.debug.print("Order is (Y, Z, X)\n", .{});
|
||||||
} else if (abs_ray_sv.getZ() > 0) {
|
} else if (abs_ray_sv.z > 0) {
|
||||||
// Main axis: ±Z
|
// Main axis: ±Z
|
||||||
i_index, j_index, k_index = .{ 2, 0, 1 };
|
i_index, j_index, k_index = .{ 2, 0, 1 };
|
||||||
std.debug.print("Order is (Z, X, Y)\n", .{});
|
std.debug.print("Order is (Z, X, Y)\n", .{});
|
||||||
} else {
|
} else {
|
||||||
std.debug.assert(abs_ray_sv.getX() == 0);
|
std.debug.assert(abs_ray_sv.x == 0);
|
||||||
std.debug.assert(abs_ray_sv.getY() == 0);
|
std.debug.assert(abs_ray_sv.y == 0);
|
||||||
std.debug.assert(abs_ray_sv.getZ() == 0);
|
std.debug.assert(abs_ray_sv.z == 0);
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
56
src/Game.zig
56
src/Game.zig
@@ -6,6 +6,7 @@ const glfw = @import("zglfw");
|
|||||||
const math = @import("math.zig");
|
const math = @import("math.zig");
|
||||||
const shaders = @import("shaders.zig");
|
const shaders = @import("shaders.zig");
|
||||||
const vk = @import("vulkan");
|
const vk = @import("vulkan");
|
||||||
|
const vm = @import("vecmath");
|
||||||
const worldgen = @import("worldgen.zig");
|
const worldgen = @import("worldgen.zig");
|
||||||
|
|
||||||
const Blocks = @import("assets/Blocks.zig");
|
const Blocks = @import("assets/Blocks.zig");
|
||||||
@@ -15,17 +16,11 @@ const CommandBuffer = @import("engine/CommandBuffer.zig");
|
|||||||
const Engine = @import("engine/Engine.zig");
|
const Engine = @import("engine/Engine.zig");
|
||||||
const Iterator2 = math.Iterator2;
|
const Iterator2 = math.Iterator2;
|
||||||
const Materials = @import("assets/Materials.zig");
|
const Materials = @import("assets/Materials.zig");
|
||||||
const Matrix4x4 = math.Matrix4x4;
|
|
||||||
const Player = @import("Player.zig");
|
const Player = @import("Player.zig");
|
||||||
const Quaternion = math.Quaternion;
|
|
||||||
const Skybox = @import("engine/Skybox.zig");
|
const Skybox = @import("engine/Skybox.zig");
|
||||||
const StagingBuffer = @import("engine/StagingBuffer.zig");
|
const StagingBuffer = @import("engine/StagingBuffer.zig");
|
||||||
const Swapchain = @import("engine/Swapchain.zig");
|
const Swapchain = @import("engine/Swapchain.zig");
|
||||||
const Textures = @import("assets/Textures.zig");
|
const Textures = @import("assets/Textures.zig");
|
||||||
const Vector2 = math.Vector2;
|
|
||||||
const Vector2x8 = math.Vector2x8;
|
|
||||||
const Vector3 = math.Vector3;
|
|
||||||
const Vector3Int = math.Vector3Int;
|
|
||||||
|
|
||||||
allocator: std.mem.Allocator,
|
allocator: std.mem.Allocator,
|
||||||
engine: *Engine,
|
engine: *Engine,
|
||||||
@@ -545,7 +540,7 @@ pub fn init(allocator: std.mem.Allocator, engine: *Engine, swapchain: *Swapchain
|
|||||||
while (it.next()) |chunk_coords2| {
|
while (it.next()) |chunk_coords2| {
|
||||||
const chunk_coords3 = chunk_coords2 ++ [_]i16{0};
|
const chunk_coords3 = chunk_coords2 ++ [_]i16{0};
|
||||||
|
|
||||||
const origin = Vector3.init(
|
const origin = vm.Vector3.init(
|
||||||
@floatFromInt(chunk_coords3[0]),
|
@floatFromInt(chunk_coords3[0]),
|
||||||
@floatFromInt(chunk_coords3[1]),
|
@floatFromInt(chunk_coords3[1]),
|
||||||
@floatFromInt(chunk_coords3[2]),
|
@floatFromInt(chunk_coords3[2]),
|
||||||
@@ -564,14 +559,14 @@ pub fn init(allocator: std.mem.Allocator, engine: *Engine, swapchain: *Swapchain
|
|||||||
|
|
||||||
var y: usize = 0;
|
var y: usize = 0;
|
||||||
while (y < 16) : (y += 1) {
|
while (y < 16) : (y += 1) {
|
||||||
const fpos0 = Vector2x8.initScalars(
|
const fpos0 = vm.Vector2x8.init(
|
||||||
.{ 0, 1, 2, 3, 4, 5, 6, 7 },
|
.{ 0, 1, 2, 3, 4, 5, 6, 7 },
|
||||||
@splat(@floatFromInt(y)),
|
@splat(@floatFromInt(y)),
|
||||||
).add(.initVector(origin.asVector2()));
|
).add(.splat(origin.dropZ()));
|
||||||
const fpos1 = Vector2x8.initScalars(
|
const fpos1 = vm.Vector2x8.init(
|
||||||
.{ 8, 9, 10, 11, 12, 13, 14, 15 },
|
.{ 8, 9, 10, 11, 12, 13, 14, 15 },
|
||||||
@splat(@floatFromInt(y)),
|
@splat(@floatFromInt(y)),
|
||||||
).add(.initVector(origin.asVector2()));
|
).add(.splat(origin.dropZ()));
|
||||||
|
|
||||||
const iheight0 = worldgen.heightIv(world_seed, fpos0);
|
const iheight0 = worldgen.heightIv(world_seed, fpos0);
|
||||||
const iheight1 = worldgen.heightIv(world_seed, fpos1);
|
const iheight1 = worldgen.heightIv(world_seed, fpos1);
|
||||||
@@ -596,7 +591,7 @@ pub fn init(allocator: std.mem.Allocator, engine: *Engine, swapchain: *Swapchain
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const player_position_vx = Vector3Int.init(0, 0, worldgen.heightI(world_seed, .zero) + 1);
|
const player_position_vx = vm.Vector3Int.init(0, 0, worldgen.heightI(world_seed, .zero) + 1);
|
||||||
const player_position_sv = player_position_vx
|
const player_position_sv = player_position_vx
|
||||||
.mulScalar(c.sv_per_vx)
|
.mulScalar(c.sv_per_vx)
|
||||||
.add(.init(c.sv_per_vx / 2, c.sv_per_vx / 2, 0));
|
.add(.init(c.sv_per_vx / 2, c.sv_per_vx / 2, 0));
|
||||||
@@ -623,8 +618,8 @@ pub fn init(allocator: std.mem.Allocator, engine: *Engine, swapchain: *Swapchain
|
|||||||
|
|
||||||
const directional_lights_data: []const shaders.DirectionalLight = &.{
|
const directional_lights_data: []const shaders.DirectionalLight = &.{
|
||||||
.{
|
.{
|
||||||
.directionWS = .{ 0, 0, -1 },
|
.directionWS = .unit_nz,
|
||||||
.color = .{ 0.3, 0.3, 0.3 },
|
.color = .init(0.3, 0.3, 0.3),
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
try directional_lights.write(engine, .{
|
try directional_lights.write(engine, .{
|
||||||
@@ -765,30 +760,33 @@ fn render(self: *Game) !void {
|
|||||||
|
|
||||||
const extent = self.swapchain.extent;
|
const extent = self.swapchain.extent;
|
||||||
|
|
||||||
const framebuffer_size = Vector2.init(
|
const framebuffer_size = vm.Vector2.init(
|
||||||
@floatFromInt(extent.width),
|
@floatFromInt(extent.width),
|
||||||
@floatFromInt(extent.height),
|
@floatFromInt(extent.height),
|
||||||
);
|
);
|
||||||
|
|
||||||
const camera_position = self.player.position_sv
|
const camera_position = vm.Vector3.init(
|
||||||
.asVector3()
|
@floatFromInt(self.player.position_sv.x),
|
||||||
|
@floatFromInt(self.player.position_sv.y),
|
||||||
|
@floatFromInt(self.player.position_sv.z),
|
||||||
|
)
|
||||||
.divScalar(c.sv_per_vx)
|
.divScalar(c.sv_per_vx)
|
||||||
.add(.init(0, 0, Player.camera_height_vx));
|
.add(.init(0, 0, Player.camera_height_vx));
|
||||||
const camera_rotation = Quaternion.mulQuaternion(
|
const camera_rotation = vm.Quaternion.mulQuaternion(
|
||||||
.initRotationXY(self.player.yaw_rad),
|
.initRotation(.XY, self.player.yaw_turns),
|
||||||
.initRotationYZ(self.player.pitch_rad),
|
.initRotation(.YZ, self.player.pitch_turns),
|
||||||
);
|
);
|
||||||
const camera_aspect_ratio = framebuffer_size.getX() / framebuffer_size.getY();
|
const camera_aspect_ratio = framebuffer_size.x / framebuffer_size.y;
|
||||||
const camera_yscale = 1.0 / @tan(0.5 * self.player.vertical_fov_deg * std.math.rad_per_deg);
|
const camera_yscale = 1.0 / @tan(0.5 * self.player.vertical_fov_deg * std.math.rad_per_deg);
|
||||||
const camera_xscale = camera_yscale / camera_aspect_ratio;
|
const camera_xscale = camera_yscale / camera_aspect_ratio;
|
||||||
|
|
||||||
const matrix_ws_to_vs = Matrix4x4.mulMatrix(
|
const matrix_ws_to_vs = vm.Matrix4x4.mulMatrixAffine(
|
||||||
Matrix4x4.initRotation(camera_rotation.conjugate()),
|
.initRotation(camera_rotation.inverseUnit()),
|
||||||
Matrix4x4.initTranslation(camera_position.negate()),
|
.initTranslation(camera_position.negate()),
|
||||||
);
|
);
|
||||||
|
|
||||||
// zig fmt: off
|
// zig fmt: off
|
||||||
const matrix_vs_to_cs = Matrix4x4.init(
|
const matrix_vs_to_cs = vm.Matrix4x4.init(
|
||||||
camera_xscale, 0, 0, 0,
|
camera_xscale, 0, 0, 0,
|
||||||
0, 0, 0, 1,
|
0, 0, 0, 1,
|
||||||
0, -camera_yscale, 0, 0,
|
0, -camera_yscale, 0, 0,
|
||||||
@@ -796,12 +794,12 @@ fn render(self: *Game) !void {
|
|||||||
);
|
);
|
||||||
// zig fmt: on
|
// zig fmt: on
|
||||||
|
|
||||||
const ambient_light = Vector3.init(0.01, 0.01, 0.01);
|
const ambient_light = vm.Vector3.init(0.01, 0.01, 0.01);
|
||||||
|
|
||||||
const global_uniforms_data: shaders.GlobalUniforms = .{
|
const global_uniforms_data: shaders.GlobalUniforms = .{
|
||||||
.matrixWStoVS = matrix_ws_to_vs.asArray(),
|
.matrixWStoVS = matrix_ws_to_vs,
|
||||||
.matrixVStoCS = matrix_vs_to_cs.asArray(),
|
.matrixVStoCS = matrix_vs_to_cs,
|
||||||
.ambientLight = ambient_light.asArray(),
|
.ambientLight = ambient_light,
|
||||||
};
|
};
|
||||||
|
|
||||||
const staging_memory = try self.global_uniforms_staging_buffer.map(self.engine);
|
const staging_memory = try self.global_uniforms_staging_buffer.map(self.engine);
|
||||||
|
|||||||
@@ -4,15 +4,11 @@ const std = @import("std");
|
|||||||
const c = @import("const.zig");
|
const c = @import("const.zig");
|
||||||
const glfw = @import("zglfw");
|
const glfw = @import("zglfw");
|
||||||
const math = @import("math.zig");
|
const math = @import("math.zig");
|
||||||
|
const vm = @import("vecmath");
|
||||||
|
|
||||||
const Blocks = @import("assets/Blocks.zig");
|
const Blocks = @import("assets/Blocks.zig");
|
||||||
const Chunks = @import("Chunks.zig");
|
const Chunks = @import("Chunks.zig");
|
||||||
const Iterator2 = math.Iterator2;
|
const Iterator2 = math.Iterator2;
|
||||||
const Quaternion = math.Quaternion;
|
|
||||||
const Vector2 = math.Vector2;
|
|
||||||
const Vector3 = math.Vector3;
|
|
||||||
const Vector2Int = math.Vector2Int;
|
|
||||||
const Vector3Int = math.Vector3Int;
|
|
||||||
|
|
||||||
const AxisState = enum {
|
const AxisState = enum {
|
||||||
none,
|
none,
|
||||||
@@ -157,25 +153,25 @@ const Button = struct {
|
|||||||
|
|
||||||
const MovementState = union(enum) {
|
const MovementState = union(enum) {
|
||||||
ground: struct {
|
ground: struct {
|
||||||
horizontal_velocity_sv: Vector2Int,
|
horizontal_velocity_sv: vm.Vector2Int,
|
||||||
},
|
},
|
||||||
air: struct {
|
air: struct {
|
||||||
horizontal_velocity_sv: Vector2Int,
|
horizontal_velocity_sv: vm.Vector2Int,
|
||||||
vertical_velocity_sv: i32,
|
vertical_velocity_sv: i32,
|
||||||
},
|
},
|
||||||
flight: void,
|
flight: void,
|
||||||
};
|
};
|
||||||
|
|
||||||
position_sv: Vector3Int,
|
position_sv: vm.Vector3Int,
|
||||||
pitch_rad: f32,
|
pitch_turns: f32,
|
||||||
yaw_rad: f32,
|
yaw_turns: f32,
|
||||||
|
|
||||||
x_input: Axis = .init(.d, .a),
|
x_input: Axis = .init(.d, .a),
|
||||||
y_input: Axis = .init(.w, .s),
|
y_input: Axis = .init(.w, .s),
|
||||||
z_input: Axis = .init(.space, .left_shift),
|
z_input: Axis = .init(.space, .left_shift),
|
||||||
jump_input: Button = .init(.space),
|
jump_input: Button = .init(.space),
|
||||||
|
|
||||||
mouse_sensitivity: f32 = 0.002,
|
mouse_sensitivity: f32 = 0.0003,
|
||||||
vertical_fov_deg: f32 = 80,
|
vertical_fov_deg: f32 = 80,
|
||||||
|
|
||||||
movement_state: MovementState,
|
movement_state: MovementState,
|
||||||
@@ -185,8 +181,8 @@ pub const camera_height_vx = 1.62;
|
|||||||
pub const horizontal_speed_sv = sv(11.0);
|
pub const horizontal_speed_sv = sv(11.0);
|
||||||
pub const vertical_speed_sv = sv(7.49);
|
pub const vertical_speed_sv = sv(7.49);
|
||||||
|
|
||||||
pub const min_pitch_rad = -0.5 * std.math.pi;
|
pub const min_pitch_turns = -0.25;
|
||||||
pub const max_pitch_rad = 0.5 * std.math.pi;
|
pub const max_pitch_turns = 0.25;
|
||||||
|
|
||||||
pub const collision_half_width_sv = sv(0.4);
|
pub const collision_half_width_sv = sv(0.4);
|
||||||
pub const collision_height_sv = sv(1.8);
|
pub const collision_height_sv = sv(1.8);
|
||||||
@@ -203,11 +199,11 @@ pub const air_speed_limit_sv = sv(0.5612);
|
|||||||
|
|
||||||
pub const raycast_length_sv = sv(5.0);
|
pub const raycast_length_sv = sv(5.0);
|
||||||
|
|
||||||
pub fn init(position_sv: Vector3Int, pitch_rad: f32, yaw_rad: f32) Player {
|
pub fn init(position_sv: vm.Vector3Int, pitch_turns: f32, yaw_turns: f32) Player {
|
||||||
return .{
|
return .{
|
||||||
.position_sv = position_sv,
|
.position_sv = position_sv,
|
||||||
.pitch_rad = pitch_rad,
|
.pitch_turns = pitch_turns,
|
||||||
.yaw_rad = yaw_rad,
|
.yaw_turns = yaw_turns,
|
||||||
.movement_state = .flight,
|
.movement_state = .flight,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -225,8 +221,8 @@ pub fn onKeyUp(self: *Player, key: glfw.Key) void {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn onMouseMove(self: *Player, dx: f32, dy: f32) void {
|
pub fn onMouseMove(self: *Player, dx: f32, dy: f32) void {
|
||||||
self.pitch_rad = std.math.clamp(self.pitch_rad - dy * self.mouse_sensitivity, min_pitch_rad, max_pitch_rad);
|
self.pitch_turns = std.math.clamp(self.pitch_turns - dy * self.mouse_sensitivity, min_pitch_turns, max_pitch_turns);
|
||||||
self.yaw_rad = @mod(self.yaw_rad - dx * self.mouse_sensitivity, std.math.tau);
|
self.yaw_turns = @mod(self.yaw_turns - dx * self.mouse_sensitivity, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn update(self: *Player, dt: f32, chunks: *const Chunks) void {
|
pub fn update(self: *Player, dt: f32, chunks: *const Chunks) void {
|
||||||
@@ -234,11 +230,11 @@ pub fn update(self: *Player, dt: f32, chunks: *const Chunks) void {
|
|||||||
|
|
||||||
//const raycast_origin_sv = self.position_sv
|
//const raycast_origin_sv = self.position_sv
|
||||||
// .add(.init(0, 0, @intFromFloat(@round(c.sv_per_vx * camera_height_vx))));
|
// .add(.init(0, 0, @intFromFloat(@round(c.sv_per_vx * camera_height_vx))));
|
||||||
//const raycast_ray_sv = Vector3
|
//const raycast_ray_sv = vm.Vector3
|
||||||
// .init(0, raycast_length_sv, 0)
|
// .init(0, raycast_length_sv, 0)
|
||||||
// .rotate(.mulQuaternion(
|
// .rotate(.mulQuaternion(
|
||||||
// .initRotationXY(self.yaw_rad),
|
// .initRotation(.XY, self.yaw_turns),
|
||||||
// .initRotationYZ(self.pitch_rad),
|
// .initRotation(.YZ, self.pitch_turns),
|
||||||
// ))
|
// ))
|
||||||
// .asVector3Int();
|
// .asVector3Int();
|
||||||
//const raycast_hit = chunks.raycast(raycast_origin_sv, raycast_ray_sv);
|
//const raycast_hit = chunks.raycast(raycast_origin_sv, raycast_ray_sv);
|
||||||
@@ -246,14 +242,14 @@ pub fn update(self: *Player, dt: f32, chunks: *const Chunks) void {
|
|||||||
// --- GATHER INPUTS -------------------------------------------------------
|
// --- GATHER INPUTS -------------------------------------------------------
|
||||||
|
|
||||||
const horizontal_input_vector_frac = blk: {
|
const horizontal_input_vector_frac = blk: {
|
||||||
var ret = Vector2
|
var ret = vm.Vector2
|
||||||
.init(self.x_input.getComponentFloat(), self.y_input.getComponentFloat())
|
.init(self.x_input.getComponentFloat(), self.y_input.getComponentFloat())
|
||||||
.rotate(self.yaw_rad);
|
.rotate(.initRotation(self.yaw_turns));
|
||||||
const len_squared = ret.lenSquared();
|
const len_squared = ret.lenSquared();
|
||||||
if (len_squared > 1) {
|
if (len_squared > 1) {
|
||||||
ret = ret.divScalar(@sqrt(len_squared));
|
ret = ret.divScalar(@sqrt(len_squared));
|
||||||
}
|
}
|
||||||
break :blk ret.asVector2IntFrac();
|
break :blk math.asIntFrac2(ret);
|
||||||
};
|
};
|
||||||
const vertical_input_vector_frac = self.z_input.getComponentIntFrac();
|
const vertical_input_vector_frac = self.z_input.getComponentIntFrac();
|
||||||
|
|
||||||
@@ -279,10 +275,10 @@ pub fn update(self: *Player, dt: f32, chunks: *const Chunks) void {
|
|||||||
.ground => {},
|
.ground => {},
|
||||||
.air => {},
|
.air => {},
|
||||||
.flight => {
|
.flight => {
|
||||||
const horizontal_velocity_sv = horizontal_input_vector_frac.mulScalarFrac(horizontal_speed_sv);
|
const horizontal_velocity_sv = math.mulFrac2(horizontal_input_vector_frac, horizontal_speed_sv);
|
||||||
const vertical_velocity_sv = math.mulFrac(vertical_input_vector_frac, vertical_speed_sv);
|
const vertical_velocity_sv = math.mulFrac(vertical_input_vector_frac, vertical_speed_sv);
|
||||||
|
|
||||||
var horizontal_displacement_sv = horizontal_velocity_sv.mulScalarFloat(dt);
|
var horizontal_displacement_sv = math.mulIntFloat2(horizontal_velocity_sv, dt);
|
||||||
var vertical_displacement_sv = math.mulIntFloat(vertical_velocity_sv, dt);
|
var vertical_displacement_sv = math.mulIntFloat(vertical_velocity_sv, dt);
|
||||||
|
|
||||||
var position_sv = self.position_sv;
|
var position_sv = self.position_sv;
|
||||||
@@ -301,9 +297,7 @@ pub fn update(self: *Player, dt: f32, chunks: *const Chunks) void {
|
|||||||
var i: usize = 0;
|
var i: usize = 0;
|
||||||
while (i < 2) : (i += 1) {
|
while (i < 2) : (i += 1) {
|
||||||
if (chunks.sweepCastHorizontal(min_sv, max_sv, horizontal_displacement_sv)) |hit| {
|
if (chunks.sweepCastHorizontal(min_sv, max_sv, horizontal_displacement_sv)) |hit| {
|
||||||
const adjustment = hit.normal_frac
|
const adjustment = math.mulFrac2(hit.normal_frac.dropZ(), hit.projected_distance_sv);
|
||||||
.asVector2Int()
|
|
||||||
.mulScalarFrac(hit.projected_distance_sv);
|
|
||||||
horizontal_displacement_sv = .add(
|
horizontal_displacement_sv = .add(
|
||||||
horizontal_displacement_sv,
|
horizontal_displacement_sv,
|
||||||
adjustment,
|
adjustment,
|
||||||
@@ -312,11 +306,11 @@ pub fn update(self: *Player, dt: f32, chunks: *const Chunks) void {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
position_sv = .add(position_sv, horizontal_displacement_sv.asVector3Int(0));
|
position_sv = .add(position_sv, horizontal_displacement_sv.withZ(0));
|
||||||
|
|
||||||
if (vertical_displacement_sv < 0.0) {
|
if (vertical_displacement_sv < 0.0) {
|
||||||
min_sv = .add(min_sv, horizontal_displacement_sv.asVector3Int(0));
|
min_sv = .add(min_sv, horizontal_displacement_sv.withZ(0));
|
||||||
max_sv = .add(max_sv, horizontal_displacement_sv.asVector3Int(0));
|
max_sv = .add(max_sv, horizontal_displacement_sv.withZ(0));
|
||||||
if (chunks.sweepCastDown(min_sv, max_sv, -vertical_displacement_sv)) |hit| {
|
if (chunks.sweepCastDown(min_sv, max_sv, -vertical_displacement_sv)) |hit| {
|
||||||
vertical_displacement_sv += hit.projected_distance_sv;
|
vertical_displacement_sv += hit.projected_distance_sv;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ const std = @import("std");
|
|||||||
const math = @import("../math.zig");
|
const math = @import("../math.zig");
|
||||||
const shaders = @import("../shaders.zig");
|
const shaders = @import("../shaders.zig");
|
||||||
const vk = @import("vulkan");
|
const vk = @import("vulkan");
|
||||||
|
const vm = @import("vecmath");
|
||||||
const voxels = @import("../voxels.zig");
|
const voxels = @import("../voxels.zig");
|
||||||
|
|
||||||
const Blocks = @import("Blocks.zig");
|
const Blocks = @import("Blocks.zig");
|
||||||
@@ -13,9 +14,7 @@ const Game = @import("../Game.zig");
|
|||||||
const GenericBuffer = @import("../engine/GenericBuffer.zig").GenericBuffer;
|
const GenericBuffer = @import("../engine/GenericBuffer.zig").GenericBuffer;
|
||||||
const Materials = @import("Materials.zig");
|
const Materials = @import("Materials.zig");
|
||||||
|
|
||||||
const Matrix4x4 = math.Matrix4x4;
|
|
||||||
const ObjectUniformsBuffer = GenericBuffer(void, shaders.ObjectUniforms);
|
const ObjectUniformsBuffer = GenericBuffer(void, shaders.ObjectUniforms);
|
||||||
const Vector3 = math.Vector3;
|
|
||||||
|
|
||||||
pub const chunk_size = 16;
|
pub const chunk_size = 16;
|
||||||
|
|
||||||
@@ -25,7 +24,7 @@ var next_chunk_id: std.atomic.Value(u64) = .init(0);
|
|||||||
/// To get the block at coordinates (x, y, z) relative to the chunk, read the
|
/// To get the block at coordinates (x, y, z) relative to the chunk, read the
|
||||||
/// value at `blocks[z][y][x]`.
|
/// value at `blocks[z][y][x]`.
|
||||||
blocks: [chunk_size][chunk_size][chunk_size]Blocks.Id,
|
blocks: [chunk_size][chunk_size][chunk_size]Blocks.Id,
|
||||||
origin: Vector3,
|
origin: vm.Vector3,
|
||||||
descriptor_set: vk.DescriptorSet,
|
descriptor_set: vk.DescriptorSet,
|
||||||
object_buffer: ObjectUniformsBuffer,
|
object_buffer: ObjectUniformsBuffer,
|
||||||
object_count: u32,
|
object_count: u32,
|
||||||
@@ -34,7 +33,7 @@ object_count: u32,
|
|||||||
chunk_id: u64,
|
chunk_id: u64,
|
||||||
|
|
||||||
pub const InitInfo = struct {
|
pub const InitInfo = struct {
|
||||||
origin: Vector3,
|
origin: vm.Vector3,
|
||||||
descriptor_pool: vk.DescriptorPool,
|
descriptor_pool: vk.DescriptorPool,
|
||||||
per_batch_descriptor_set_layout: vk.DescriptorSetLayout,
|
per_batch_descriptor_set_layout: vk.DescriptorSetLayout,
|
||||||
};
|
};
|
||||||
@@ -110,14 +109,18 @@ pub fn refresh(self: *Chunk, engine: *Engine, blocks: *const Blocks, neighbors:
|
|||||||
for (row, 0..) |id, ix| {
|
for (row, 0..) |id, ix| {
|
||||||
const fx: f32 = @floatFromInt(ix);
|
const fx: f32 = @floatFromInt(ix);
|
||||||
const block: *const Blocks.Definition = &blocks.array.items[id.toInt()];
|
const block: *const Blocks.Definition = &blocks.array.items[id.toInt()];
|
||||||
const origin = Vector3.add(self.origin, .init(fx, fy, fz));
|
const origin = vm.Vector3.add(self.origin, .init(fx, fy, fz));
|
||||||
|
|
||||||
inline for (@typeInfo(voxels.Orientation).@"enum".fields) |field| {
|
inline for (@typeInfo(voxels.Orientation).@"enum".fields) |field| {
|
||||||
const side = @field(voxels.Orientation, field.name);
|
const side = @field(voxels.Orientation, field.name);
|
||||||
const material = @field(block.walls, field.name).material;
|
const material = @field(block.walls, field.name).material;
|
||||||
if (material != .empty and self.getOpposite(side, ix, iy, iz, blocks, neighbors) == .empty) {
|
if (material != .empty and self.getOpposite(side, ix, iy, iz, blocks, neighbors) == .empty) {
|
||||||
const matrix = getMatrix(side, origin);
|
const matrix = getMatrix(side, origin);
|
||||||
try uniforms.append(temp_allocator, .init(matrix, matrix, material));
|
try uniforms.append(temp_allocator, .{
|
||||||
|
.matrixOStoWS = matrix,
|
||||||
|
.matrixOStoWSNormal = matrix,
|
||||||
|
.material = material,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -209,44 +212,44 @@ fn getOpposite(self: *const Chunk, comptime side: voxels.Orientation, x: usize,
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
fn getMatrix(comptime side: voxels.Orientation, origin: Vector3) Matrix4x4 {
|
fn getMatrix(comptime side: voxels.Orientation, origin: vm.Vector3) vm.Matrix4x4 {
|
||||||
return switch (side) {
|
return switch (side) {
|
||||||
// zig fmt: off
|
// zig fmt: off
|
||||||
.positive_x => .init(
|
.positive_x => .init(
|
||||||
0, 1, 0, 0,
|
0, 1, 0, 0,
|
||||||
0, 0, 1, 0,
|
0, 0, 1, 0,
|
||||||
1, 0, 0, 0,
|
1, 0, 0, 0,
|
||||||
origin.getX() + 1, origin.getY(), origin.getZ(), 1,
|
origin.x + 1, origin.y, origin.z, 1,
|
||||||
),
|
),
|
||||||
.negative_x => .init(
|
.negative_x => .init(
|
||||||
0, -1, 0, 0,
|
0, -1, 0, 0,
|
||||||
0, 0, 1, 0,
|
0, 0, 1, 0,
|
||||||
-1, 0, 0, 0,
|
-1, 0, 0, 0,
|
||||||
origin.getX(), origin.getY() + 1, origin.getZ(), 1,
|
origin.x, origin.y + 1, origin.z, 1,
|
||||||
),
|
),
|
||||||
.positive_y => .init(
|
.positive_y => .init(
|
||||||
-1, 0, 0, 0,
|
-1, 0, 0, 0,
|
||||||
0, 0, 1, 0,
|
0, 0, 1, 0,
|
||||||
0, 1, 0, 0,
|
0, 1, 0, 0,
|
||||||
origin.getX() + 1, origin.getY() + 1, origin.getZ(), 1,
|
origin.x + 1, origin.y + 1, origin.z, 1,
|
||||||
),
|
),
|
||||||
.negative_y => .init(
|
.negative_y => .init(
|
||||||
1, 0, 0, 0,
|
1, 0, 0, 0,
|
||||||
0, 0, 1, 0,
|
0, 0, 1, 0,
|
||||||
0, -1, 0, 0,
|
0, -1, 0, 0,
|
||||||
origin.getX(), origin.getY(), origin.getZ(), 1,
|
origin.x, origin.y, origin.z, 1,
|
||||||
),
|
),
|
||||||
.positive_z => .init(
|
.positive_z => .init(
|
||||||
1, 0, 0, 0,
|
1, 0, 0, 0,
|
||||||
0, 1, 0, 0,
|
0, 1, 0, 0,
|
||||||
0, 0, 1, 0,
|
0, 0, 1, 0,
|
||||||
origin.getX(), origin.getY(), origin.getZ() + 1, 1,
|
origin.x, origin.y, origin.z + 1, 1,
|
||||||
),
|
),
|
||||||
.negative_z => .init(
|
.negative_z => .init(
|
||||||
1, 0, 0, 0,
|
-1, 0, 0, 0,
|
||||||
0, -1, 0, 0,
|
0, -1, 0, 0,
|
||||||
0, 0, -1, 0,
|
0, 0, 1, 0,
|
||||||
origin.getX() + 1, origin.getY() + 1, origin.getZ(), 1,
|
origin.x + 1, origin.y + 1, origin.z, 1,
|
||||||
),
|
),
|
||||||
// zig fmt: on
|
// zig fmt: on
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -80,8 +80,8 @@ pub fn init(engine: *Engine, allocator: std.mem.Allocator) !Materials {
|
|||||||
.element_offset = Id.empty.toInt(),
|
.element_offset = Id.empty.toInt(),
|
||||||
.elements = &.{
|
.elements = &.{
|
||||||
.{
|
.{
|
||||||
.base_color = .{ 0, 0, 0 },
|
.base_color = .zero,
|
||||||
.emissive = .{ 1, 0, 1 },
|
.emissive = .init(1, 0, 1),
|
||||||
.ior = 1.45,
|
.ior = 1.45,
|
||||||
.metallic = 0,
|
.metallic = 0,
|
||||||
.normal_scale = 1,
|
.normal_scale = 1,
|
||||||
@@ -295,8 +295,8 @@ fn loadMaterial(self: *Materials, engine: *Engine, textures: *Textures, filename
|
|||||||
.element_offset = index,
|
.element_offset = index,
|
||||||
.elements = &.{
|
.elements = &.{
|
||||||
.{
|
.{
|
||||||
.base_color = material_json.baseColor,
|
.base_color = .initArray(material_json.baseColor),
|
||||||
.emissive = material_json.emissive,
|
.emissive = .initArray(material_json.emissive),
|
||||||
.ior = material_json.ior,
|
.ior = material_json.ior,
|
||||||
.metallic = material_json.metallic,
|
.metallic = material_json.metallic,
|
||||||
.normal_scale = material_json.normalScale,
|
.normal_scale = material_json.normalScale,
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
const std = @import("std");
|
const std = @import("std");
|
||||||
|
const vm = @import("vecmath");
|
||||||
const Vector2Int = @import("math.zig").Vector2Int;
|
|
||||||
|
|
||||||
pub const app_name = "voxel-game";
|
pub const app_name = "voxel-game";
|
||||||
pub const app_version_string = @import("config").version;
|
pub const app_version_string = @import("config").version;
|
||||||
@@ -11,11 +10,11 @@ pub const max_frametime = 1.0 / min_framerate;
|
|||||||
|
|
||||||
pub const default_window_width = 1280;
|
pub const default_window_width = 1280;
|
||||||
pub const default_window_height = 720;
|
pub const default_window_height = 720;
|
||||||
pub const default_window_size = Vector2Int.init(default_window_width, default_window_height);
|
pub const default_window_size = vm.Vector2Int.init(default_window_width, default_window_height);
|
||||||
|
|
||||||
pub const min_window_width = 640;
|
pub const min_window_width = 640;
|
||||||
pub const min_window_height = 360;
|
pub const min_window_height = 360;
|
||||||
pub const min_window_size = Vector2Int.init(default_window_width, default_window_height);
|
pub const min_window_size = vm.Vector2Int.init(default_window_width, default_window_height);
|
||||||
|
|
||||||
pub const window_title = "Voxel Game";
|
pub const window_title = "Voxel Game";
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ const std = @import("std");
|
|||||||
const shaders = @import("../shaders.zig");
|
const shaders = @import("../shaders.zig");
|
||||||
const stbi = @import("zstbi");
|
const stbi = @import("zstbi");
|
||||||
const vk = @import("vulkan");
|
const vk = @import("vulkan");
|
||||||
|
const vm = @import("vecmath");
|
||||||
|
|
||||||
const CommandBuffer = @import("CommandBuffer.zig");
|
const CommandBuffer = @import("CommandBuffer.zig");
|
||||||
const Engine = @import("Engine.zig");
|
const Engine = @import("Engine.zig");
|
||||||
@@ -14,7 +15,7 @@ image: vk.Image,
|
|||||||
image_view: vk.ImageView,
|
image_view: vk.ImageView,
|
||||||
device_memory: vk.DeviceMemory,
|
device_memory: vk.DeviceMemory,
|
||||||
|
|
||||||
vertex_buffer: GenericBuffer(void, [3]f32),
|
vertex_buffer: GenericBuffer(void, vm.Vector3),
|
||||||
index_buffer: shaders.IndexBuffer,
|
index_buffer: shaders.IndexBuffer,
|
||||||
sampler: vk.Sampler,
|
sampler: vk.Sampler,
|
||||||
|
|
||||||
@@ -468,7 +469,7 @@ pub fn load(filename: []const u8, engine: *Engine, cube_size: u32, global_unifor
|
|||||||
|
|
||||||
// --- SKYBOX PIPELINE -----------------------------------------------------
|
// --- SKYBOX PIPELINE -----------------------------------------------------
|
||||||
|
|
||||||
var vertex_buffer = try GenericBuffer(void, [3]f32).init(engine, .{
|
var vertex_buffer = try GenericBuffer(void, vm.Vector3).init(engine, .{
|
||||||
.usage = .vertex,
|
.usage = .vertex,
|
||||||
.target_queue = .graphics,
|
.target_queue = .graphics,
|
||||||
.array_capacity = 8,
|
.array_capacity = 8,
|
||||||
@@ -485,14 +486,14 @@ pub fn load(filename: []const u8, engine: *Engine, cube_size: u32, global_unifor
|
|||||||
|
|
||||||
try vertex_buffer.write(engine, .{
|
try vertex_buffer.write(engine, .{
|
||||||
.elements = &.{
|
.elements = &.{
|
||||||
.{ -1, -1, -1 },
|
.init(-1, -1, -1),
|
||||||
.{ 1, -1, -1 },
|
.init(1, -1, -1),
|
||||||
.{ -1, 1, -1 },
|
.init(-1, 1, -1),
|
||||||
.{ 1, 1, -1 },
|
.init(1, 1, -1),
|
||||||
.{ -1, -1, 1 },
|
.init(-1, -1, 1),
|
||||||
.{ 1, -1, 1 },
|
.init(1, -1, 1),
|
||||||
.{ -1, 1, 1 },
|
.init(-1, 1, 1),
|
||||||
.{ 1, 1, 1 },
|
.init(1, 1, 1),
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
155
src/math.zig
155
src/math.zig
@@ -1,41 +1,8 @@
|
|||||||
const std = @import("std");
|
const std = @import("std");
|
||||||
|
const vm = @import("vecmath");
|
||||||
|
|
||||||
pub const Iterator2 = @import("math/Iterator2.zig").Iterator2;
|
pub const Iterator2 = @import("math/Iterator2.zig").Iterator2;
|
||||||
pub const Iterator3 = @import("math/Iterator3.zig").Iterator3;
|
pub const Iterator3 = @import("math/Iterator3.zig").Iterator3;
|
||||||
pub const Matrix4x4 = @import("math/Matrix4x4.zig").Matrix4x4;
|
|
||||||
pub const Quaternion = @import("math/Quaternion.zig").Quaternion;
|
|
||||||
pub const Vector2 = @import("math/Vector2.zig").Vector2;
|
|
||||||
pub const Vector2Int = @import("math/Vector2Int.zig").Vector2Int;
|
|
||||||
pub const Vector2x8 = @import("math/Vector2x8.zig").Vector2x8;
|
|
||||||
pub const Vector3 = @import("math/Vector3.zig").Vector3;
|
|
||||||
pub const Vector3Int = @import("math/Vector3Int.zig").Vector3Int;
|
|
||||||
pub const Vector4 = @import("math/Vector4.zig").Vector4;
|
|
||||||
|
|
||||||
pub const f32x8 = @Vector(8, f32);
|
|
||||||
pub const i32x8 = @Vector(8, i32);
|
|
||||||
pub const u32x8 = @Vector(8, u32);
|
|
||||||
pub const u64x8 = @Vector(8, u64);
|
|
||||||
|
|
||||||
pub inline fn ps(value: f32) f32x8 {
|
|
||||||
return @splat(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn epi32(value: i32) i32x8 {
|
|
||||||
return @splat(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn epu32(value: u32) u32x8 {
|
|
||||||
return @splat(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn epu64x2(value: u64) u64x8 {
|
|
||||||
return @splat(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lerp(a: f32, b: f32, t: f32) f32 {
|
|
||||||
const s = 1.0 - t;
|
|
||||||
return a * s + b * t;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub const noise2 = @import("math/noise.zig").noise2;
|
pub const noise2 = @import("math/noise.zig").noise2;
|
||||||
pub const noise2x8 = @import("math/noise.zig").noise2x8;
|
pub const noise2x8 = @import("math/noise.zig").noise2x8;
|
||||||
@@ -46,18 +13,90 @@ pub inline fn asFloatFrac(frac: i32) f32 {
|
|||||||
return @floatCast(numerator / denominator);
|
return @floatCast(numerator / denominator);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub inline fn asFloatFrac2(frac: vm.Vector2Int) vm.Vector2 {
|
||||||
|
return .init(
|
||||||
|
asFloatFrac(frac.x),
|
||||||
|
asFloatFrac(frac.y),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn asFloatFrac3(frac: vm.Vector3Int) vm.Vector3 {
|
||||||
|
return .init(
|
||||||
|
asFloatFrac(frac.x),
|
||||||
|
asFloatFrac(frac.y),
|
||||||
|
asFloatFrac(frac.z),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn asFloatFrac4(frac: vm.Vector4Int) vm.Vector4 {
|
||||||
|
return .init(
|
||||||
|
asFloatFrac(frac.x),
|
||||||
|
asFloatFrac(frac.y),
|
||||||
|
asFloatFrac(frac.z),
|
||||||
|
asFloatFrac(frac.w),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
pub inline fn asIntFrac(frac: f32) i32 {
|
pub inline fn asIntFrac(frac: f32) i32 {
|
||||||
const fraction: f64 = @floatCast(frac);
|
const fraction: f64 = @floatCast(frac);
|
||||||
const scale: f64 = std.math.maxInt(i32);
|
const scale: f64 = std.math.maxInt(i32);
|
||||||
return @intFromFloat(@round(fraction * scale));
|
return @intFromFloat(@round(fraction * scale));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub inline fn asIntFrac2(frac: vm.Vector2) vm.Vector2Int {
|
||||||
|
return .init(
|
||||||
|
asIntFrac(frac.x),
|
||||||
|
asIntFrac(frac.y),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn asIntFrac3(frac: vm.Vector3) vm.Vector3Int {
|
||||||
|
return .init(
|
||||||
|
asIntFrac(frac.x),
|
||||||
|
asIntFrac(frac.y),
|
||||||
|
asIntFrac(frac.z),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn asIntFrac4(frac: vm.Vector4) vm.Vector4Int {
|
||||||
|
return .init(
|
||||||
|
asIntFrac(frac.x),
|
||||||
|
asIntFrac(frac.y),
|
||||||
|
asIntFrac(frac.z),
|
||||||
|
asIntFrac(frac.w),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
pub inline fn mulIntFloat(int: i32, float: f32) i32 {
|
pub inline fn mulIntFloat(int: i32, float: f32) i32 {
|
||||||
const int_float: f64 = @floatFromInt(int);
|
const int_float: f64 = @floatFromInt(int);
|
||||||
const float_wide: f64 = @floatCast(float);
|
const float_wide: f64 = @floatCast(float);
|
||||||
return @intFromFloat(@round(int_float * float_wide));
|
return @intFromFloat(@round(int_float * float_wide));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub inline fn mulIntFloat2(int: vm.Vector2Int, float: f32) vm.Vector2Int {
|
||||||
|
return .init(
|
||||||
|
mulIntFloat(int.x, float),
|
||||||
|
mulIntFloat(int.y, float),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn mulIntFloat3(int: vm.Vector3Int, float: f32) vm.Vector3Int {
|
||||||
|
return .init(
|
||||||
|
mulIntFloat(int.x, float),
|
||||||
|
mulIntFloat(int.y, float),
|
||||||
|
mulIntFloat(int.z, float),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn mulIntFloat4(int: vm.Vector4Int, float: f32) vm.Vector4Int {
|
||||||
|
return .init(
|
||||||
|
mulIntFloat(int.x, float),
|
||||||
|
mulIntFloat(int.y, float),
|
||||||
|
mulIntFloat(int.z, float),
|
||||||
|
mulIntFloat(int.w, float),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
pub inline fn mulFrac(a: i32, b: i32) i32 {
|
pub inline fn mulFrac(a: i32, b: i32) i32 {
|
||||||
const denominator: i64 = std.math.maxInt(i32);
|
const denominator: i64 = std.math.maxInt(i32);
|
||||||
const rounding_bias: i64 = denominator >> 1;
|
const rounding_bias: i64 = denominator >> 1;
|
||||||
@@ -66,6 +105,30 @@ pub inline fn mulFrac(a: i32, b: i32) i32 {
|
|||||||
return @intCast(@divFloor(a_wide * b_wide + rounding_bias, denominator));
|
return @intCast(@divFloor(a_wide * b_wide + rounding_bias, denominator));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub inline fn mulFrac2(a: vm.Vector2Int, b: i32) vm.Vector2Int {
|
||||||
|
return .init(
|
||||||
|
mulFrac(a.x, b),
|
||||||
|
mulFrac(a.y, b),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn mulFrac3(a: vm.Vector3Int, b: i32) vm.Vector3Int {
|
||||||
|
return .init(
|
||||||
|
mulFrac(a.x, b),
|
||||||
|
mulFrac(a.y, b),
|
||||||
|
mulFrac(a.z, b),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn mulFrac4(a: vm.Vector4Int, b: i32) vm.Vector4Int {
|
||||||
|
return .init(
|
||||||
|
mulFrac(a.x, b),
|
||||||
|
mulFrac(a.y, b),
|
||||||
|
mulFrac(a.z, b),
|
||||||
|
mulFrac(a.w, b),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
pub inline fn mulFracFrac(a: i32, b: i32) i32 {
|
pub inline fn mulFracFrac(a: i32, b: i32) i32 {
|
||||||
const denominator: i64 = std.math.maxInt(i32) * std.math.maxInt(i32);
|
const denominator: i64 = std.math.maxInt(i32) * std.math.maxInt(i32);
|
||||||
const rounding_bias: i64 = denominator >> 1;
|
const rounding_bias: i64 = denominator >> 1;
|
||||||
@@ -74,6 +137,30 @@ pub inline fn mulFracFrac(a: i32, b: i32) i32 {
|
|||||||
return .{ .vector = @intCast(@divFloor(a_wide * b_wide + rounding_bias, denominator)) };
|
return .{ .vector = @intCast(@divFloor(a_wide * b_wide + rounding_bias, denominator)) };
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub inline fn mulFracFrac2(a: vm.Vector2Int, b: i32) vm.Vector2Int {
|
||||||
|
return .init(
|
||||||
|
mulFracFrac(a.x, b),
|
||||||
|
mulFracFrac(a.y, b),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn mulFracFrac3(a: vm.Vector3Int, b: i32) vm.Vector3Int {
|
||||||
|
return .init(
|
||||||
|
mulFracFrac(a.x, b),
|
||||||
|
mulFracFrac(a.y, b),
|
||||||
|
mulFracFrac(a.z, b),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub inline fn mulFracFrac4(a: vm.Vector4Int, b: i32) vm.Vector4Int {
|
||||||
|
return .init(
|
||||||
|
mulFracFrac(a.x, b),
|
||||||
|
mulFracFrac(a.y, b),
|
||||||
|
mulFracFrac(a.z, b),
|
||||||
|
mulFracFrac(a.w, b),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
pub inline fn wideMulDivFloor(a: i32, mul: i32, div: i32) i32 {
|
pub inline fn wideMulDivFloor(a: i32, mul: i32, div: i32) i32 {
|
||||||
return @intCast(@divFloor(@as(i64, a) * @as(i64, mul), div));
|
return @intCast(@divFloor(@as(i64, a) * @as(i64, mul), div));
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,283 +0,0 @@
|
|||||||
const Vector3 = @import("Vector3.zig").Vector3;
|
|
||||||
const Vector4 = @import("Vector4.zig").Vector4;
|
|
||||||
const Quaternion = @import("Quaternion.zig").Quaternion;
|
|
||||||
|
|
||||||
pub const Matrix4x4 = extern struct {
|
|
||||||
i: Vector4,
|
|
||||||
j: Vector4,
|
|
||||||
k: Vector4,
|
|
||||||
t: Vector4,
|
|
||||||
|
|
||||||
pub const identity = Matrix4x4.init(
|
|
||||||
// zig fmt: off
|
|
||||||
1, 0, 0, 0,
|
|
||||||
0, 1, 0, 0,
|
|
||||||
0, 0, 1, 0,
|
|
||||||
0, 0, 0, 1,
|
|
||||||
// zig fmt: on
|
|
||||||
);
|
|
||||||
|
|
||||||
// --- INIT ---
|
|
||||||
|
|
||||||
pub inline fn init(
|
|
||||||
// zig fmt: off
|
|
||||||
ix: f32, iy: f32, iz: f32, iw: f32,
|
|
||||||
jx: f32, jy: f32, jz: f32, jw: f32,
|
|
||||||
kx: f32, ky: f32, kz: f32, kw: f32,
|
|
||||||
tx: f32, ty: f32, tz: f32, tw: f32,
|
|
||||||
// zig fmt: on
|
|
||||||
) Matrix4x4 {
|
|
||||||
return .{
|
|
||||||
.i = .init(ix, iy, iz, iw),
|
|
||||||
.j = .init(jx, jy, jz, jw),
|
|
||||||
.k = .init(kx, ky, kz, kw),
|
|
||||||
.t = .init(tx, ty, tz, tw),
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initArray(array: [16]f32) Matrix4x4 {
|
|
||||||
return .{
|
|
||||||
.i = .initArray(array[0..4].*),
|
|
||||||
.j = .initArray(array[4..8].*),
|
|
||||||
.k = .initArray(array[8..12].*),
|
|
||||||
.t = .initArray(array[12..16].*),
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initVector4(i: Vector4, j: Vector4, k: Vector4, t: Vector4) Matrix4x4 {
|
|
||||||
return .{ .i = i, .j = j, .k = k, .t = t };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initTranslation(translation: Vector3) Matrix4x4 {
|
|
||||||
return .initVector4(
|
|
||||||
.unit_x,
|
|
||||||
.unit_y,
|
|
||||||
.unit_z,
|
|
||||||
translation.asVector4(1),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initRotation(rotation: Quaternion) Matrix4x4 {
|
|
||||||
const xx = rotation.vector.getX() * rotation.vector.getX();
|
|
||||||
const xy = rotation.vector.getX() * rotation.vector.getY();
|
|
||||||
const xz = rotation.vector.getX() * rotation.vector.getZ();
|
|
||||||
const xw = rotation.vector.getX() * rotation.vector.getW();
|
|
||||||
const yy = rotation.vector.getY() * rotation.vector.getY();
|
|
||||||
const yz = rotation.vector.getY() * rotation.vector.getZ();
|
|
||||||
const yw = rotation.vector.getY() * rotation.vector.getW();
|
|
||||||
const zz = rotation.vector.getZ() * rotation.vector.getZ();
|
|
||||||
const zw = rotation.vector.getZ() * rotation.vector.getW();
|
|
||||||
|
|
||||||
return .init(
|
|
||||||
// zig fmt: off
|
|
||||||
1 - 2 * (yy + zz), 2 * (xy + zw), 2 * (xz - yw), 0,
|
|
||||||
2 * (xy - zw), 1 - 2 * (xx + zz), 2 * (yz + xw), 0,
|
|
||||||
2 * (xz + yw), 2 * (yz - xw), 1 - 2 * (xx + yy), 0,
|
|
||||||
0, 0, 0, 1,
|
|
||||||
// zig fmt: on
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initScale(scale: Vector3) Matrix4x4 {
|
|
||||||
return .init(
|
|
||||||
// zig fmt: off
|
|
||||||
scale.getX(), 0, 0, 0,
|
|
||||||
0, scale.getY(), 0, 0,
|
|
||||||
0, 0, scale.getZ(), 0,
|
|
||||||
0, 0, 0, 1,
|
|
||||||
// zig fmt: on
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initTranslationRotationScale(
|
|
||||||
translation: Vector3,
|
|
||||||
rotation: Quaternion,
|
|
||||||
scale: Vector3,
|
|
||||||
) Matrix4x4 {
|
|
||||||
const xx = rotation.vector.getX() * rotation.vector.getX();
|
|
||||||
const xy = rotation.vector.getX() * rotation.vector.getY();
|
|
||||||
const xz = rotation.vector.getX() * rotation.vector.getZ();
|
|
||||||
const xw = rotation.vector.getX() * rotation.vector.getW();
|
|
||||||
const yy = rotation.vector.getY() * rotation.vector.getY();
|
|
||||||
const yz = rotation.vector.getY() * rotation.vector.getZ();
|
|
||||||
const yw = rotation.vector.getY() * rotation.vector.getW();
|
|
||||||
const zz = rotation.vector.getZ() * rotation.vector.getZ();
|
|
||||||
const zw = rotation.vector.getZ() * rotation.vector.getW();
|
|
||||||
|
|
||||||
const rotation_i = Vector4.init((1 - 2 * (yy + zz)), 2 * (xy + zw), 2 * (xz - yw), 0);
|
|
||||||
const rotation_j = Vector4.init(2 * (xy - zw), (1 - 2 * (xx + zz)), 2 * (yz + xw), 0);
|
|
||||||
const rotation_k = Vector4.init(2 * (xz + yw), 2 * (yz - xw), (1 - 2 * (xx + yy)), 0);
|
|
||||||
|
|
||||||
return .initVector4(
|
|
||||||
.mulScalar(rotation_i, scale.getX()),
|
|
||||||
.mulScalar(rotation_j, scale.getY()),
|
|
||||||
.mulScalar(rotation_k, scale.getZ()),
|
|
||||||
translation.asVector4(1),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- CONVERSION ---
|
|
||||||
|
|
||||||
pub inline fn asArray(self: Matrix4x4) [16]f32 {
|
|
||||||
return self.i.asArray() ++ self.j.asArray() ++ self.k.asArray() ++ self.t.asArray();
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector4(self: Matrix4x4) [4]Vector4 {
|
|
||||||
return .{ self.i, self.j, self.k, self.t };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- COMPONENT-WISE ---
|
|
||||||
|
|
||||||
pub inline fn add(self: Matrix4x4, other: Matrix4x4) Matrix4x4 {
|
|
||||||
return .initVector4(
|
|
||||||
.add(self.i, other.i),
|
|
||||||
.add(self.j, other.j),
|
|
||||||
.add(self.k, other.k),
|
|
||||||
.add(self.t, other.t),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sub(self: Matrix4x4, other: Matrix4x4) Matrix4x4 {
|
|
||||||
return .initVector4(
|
|
||||||
.sub(self.i, other.i),
|
|
||||||
.sub(self.j, other.j),
|
|
||||||
.sub(self.k, other.k),
|
|
||||||
.sub(self.t, other.t),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn negate(self: Matrix4x4) Matrix4x4 {
|
|
||||||
return .initVector4(
|
|
||||||
.negate(self.i),
|
|
||||||
.negate(self.j),
|
|
||||||
.negate(self.k),
|
|
||||||
.negate(self.t),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalar(self: Matrix4x4, scalar: f32) Matrix4x4 {
|
|
||||||
return .initVector4(
|
|
||||||
.mulScalar(self.i, scalar),
|
|
||||||
.mulScalar(self.j, scalar),
|
|
||||||
.mulScalar(self.k, scalar),
|
|
||||||
.mulScalar(self.t, scalar),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalar(self: Matrix4x4, scalar: f32) Matrix4x4 {
|
|
||||||
const inv_scalar = 1 / scalar;
|
|
||||||
return .initVector4(
|
|
||||||
.mulScalar(self.i, inv_scalar),
|
|
||||||
.mulScalar(self.j, inv_scalar),
|
|
||||||
.mulScalar(self.k, inv_scalar),
|
|
||||||
.mulScalar(self.t, inv_scalar),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- OTHER ---
|
|
||||||
|
|
||||||
pub inline fn mulMatrix(self: Matrix4x4, other: Matrix4x4) Matrix4x4 {
|
|
||||||
return .initVector4(
|
|
||||||
self.i.mulScalar(other.i.getX())
|
|
||||||
.add(self.j.mulScalar(other.i.getY()))
|
|
||||||
.add(self.k.mulScalar(other.i.getZ()))
|
|
||||||
.add(self.t.mulScalar(other.i.getW())),
|
|
||||||
self.i.mulScalar(other.j.getX())
|
|
||||||
.add(self.j.mulScalar(other.j.getY()))
|
|
||||||
.add(self.k.mulScalar(other.j.getZ()))
|
|
||||||
.add(self.t.mulScalar(other.j.getW())),
|
|
||||||
self.i.mulScalar(other.k.getX())
|
|
||||||
.add(self.j.mulScalar(other.k.getY()))
|
|
||||||
.add(self.k.mulScalar(other.k.getZ()))
|
|
||||||
.add(self.t.mulScalar(other.k.getW())),
|
|
||||||
self.i.mulScalar(other.t.getX())
|
|
||||||
.add(self.j.mulScalar(other.t.getY()))
|
|
||||||
.add(self.k.mulScalar(other.t.getZ()))
|
|
||||||
.add(self.t.mulScalar(other.t.getW())),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn inverseAffine(self: Matrix4x4) Matrix4x4 {
|
|
||||||
// zig fmt: off
|
|
||||||
const det = self.i.getX() * self.j.getY() * self.k.getZ()
|
|
||||||
+ self.i.getY() * self.j.getZ() * self.k.getX()
|
|
||||||
+ self.i.getZ() * self.j.getX() * self.k.getY()
|
|
||||||
- self.i.getX() * self.j.getZ() * self.k.getY()
|
|
||||||
- self.i.getY() * self.j.getX() * self.k.getZ()
|
|
||||||
- self.i.getZ() * self.j.getY() * self.k.getX();
|
|
||||||
// zig fmt: on
|
|
||||||
const inv_det = 1 / det;
|
|
||||||
|
|
||||||
const i = Vector3.init(
|
|
||||||
self.j.getY() * self.k.getZ() - self.j.getZ() * self.k.getY(),
|
|
||||||
self.i.getZ() * self.k.getY() - self.i.getY() * self.k.getZ(),
|
|
||||||
self.i.getY() * self.j.getZ() - self.i.getZ() * self.j.getY(),
|
|
||||||
).mulScalar(inv_det);
|
|
||||||
|
|
||||||
const j = Vector3.init(
|
|
||||||
self.j.getZ() * self.k.getX() - self.j.getX() * self.k.getZ(),
|
|
||||||
self.i.getX() * self.k.getZ() - self.i.getZ() * self.k.getX(),
|
|
||||||
self.i.getZ() * self.j.getX() - self.i.getX() * self.j.getZ(),
|
|
||||||
).mulScalar(inv_det);
|
|
||||||
|
|
||||||
const k = Vector3.init(
|
|
||||||
self.j.getX() * self.k.getY() - self.j.getY() * self.k.getX(),
|
|
||||||
self.i.getY() * self.k.getX() - self.i.getX() * self.k.getY(),
|
|
||||||
self.i.getX() * self.j.getY() - self.i.getY() * self.j.getX(),
|
|
||||||
).mulScalar(inv_det);
|
|
||||||
|
|
||||||
const t = self.i.asVector3().mulScalar(self.t.getX())
|
|
||||||
.add(self.j.asVector3().mulScalar(self.t.getY()))
|
|
||||||
.add(self.k.asVector3().mulScalar(self.t.getZ()))
|
|
||||||
.negate();
|
|
||||||
|
|
||||||
return .initVector4(
|
|
||||||
i.asVector4(0),
|
|
||||||
j.asVector4(0),
|
|
||||||
k.asVector4(0),
|
|
||||||
t.asVector4(1),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn inverseTransposeAffine(self: Matrix4x4) Matrix4x4 {
|
|
||||||
// zig fmt: off
|
|
||||||
const det = self.i.getX() * self.j.getY() * self.k.getZ()
|
|
||||||
+ self.i.getY() * self.j.getZ() * self.k.getX()
|
|
||||||
+ self.i.getZ() * self.j.getX() * self.k.getY()
|
|
||||||
- self.i.getX() * self.j.getZ() * self.k.getY()
|
|
||||||
- self.i.getY() * self.j.getX() * self.k.getZ()
|
|
||||||
- self.i.getZ() * self.j.getY() * self.k.getX();
|
|
||||||
// zig fmt: on
|
|
||||||
const inv_det = 1 / det;
|
|
||||||
|
|
||||||
const i = Vector3.init(
|
|
||||||
self.j.getY() * self.k.getZ() - self.j.getZ() * self.k.getY(),
|
|
||||||
self.j.getZ() * self.k.getX() - self.j.getX() * self.k.getZ(),
|
|
||||||
self.j.getX() * self.k.getY() - self.j.getY() * self.k.getX(),
|
|
||||||
).mulScalar(inv_det);
|
|
||||||
|
|
||||||
const j = Vector3.init(
|
|
||||||
self.i.getZ() * self.k.getY() - self.i.getY() * self.k.getZ(),
|
|
||||||
self.i.getX() * self.k.getZ() - self.i.getZ() * self.k.getX(),
|
|
||||||
self.i.getY() * self.k.getX() - self.i.getX() * self.k.getY(),
|
|
||||||
).mulScalar(inv_det);
|
|
||||||
|
|
||||||
const k = Vector3.init(
|
|
||||||
self.i.getY() * self.j.getZ() - self.i.getZ() * self.j.getY(),
|
|
||||||
self.i.getZ() * self.j.getX() - self.i.getX() * self.j.getZ(),
|
|
||||||
self.i.getX() * self.j.getY() - self.i.getY() * self.j.getX(),
|
|
||||||
).mulScalar(inv_det);
|
|
||||||
|
|
||||||
const t = self.i.asVector3().mulScalar(self.t.getX())
|
|
||||||
.add(self.j.asVector3().mulScalar(self.t.getY()))
|
|
||||||
.add(self.k.asVector3().mulScalar(self.t.getZ()))
|
|
||||||
.negate();
|
|
||||||
|
|
||||||
return .initVector4(
|
|
||||||
i.asVector4(0),
|
|
||||||
j.asVector4(0),
|
|
||||||
k.asVector4(0),
|
|
||||||
t.asVector4(1),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,155 +0,0 @@
|
|||||||
const Vector3 = @import("Vector3.zig").Vector3;
|
|
||||||
const Vector4 = @import("Vector4.zig").Vector4;
|
|
||||||
|
|
||||||
pub const Quaternion = extern struct {
|
|
||||||
vector: Vector4,
|
|
||||||
|
|
||||||
pub const identity = Quaternion.init(0, 0, 0, 1);
|
|
||||||
|
|
||||||
// --- INIT ---
|
|
||||||
|
|
||||||
pub inline fn init(x: f32, y: f32, z: f32, w: f32) Quaternion {
|
|
||||||
return .{ .vector = .init(x, y, z, w) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initArray(array: [4]f32) Quaternion {
|
|
||||||
return .{ .vector = .initArray(array) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initVector4(vector: Vector4) Quaternion {
|
|
||||||
return .{ .vector = vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initRotationXY(angle_rad: f32) Quaternion {
|
|
||||||
const half_angle_rad = 0.5 * angle_rad;
|
|
||||||
const c = @cos(half_angle_rad);
|
|
||||||
const s = @sin(half_angle_rad);
|
|
||||||
return .init(0, 0, s, c);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initRotationXZ(angle_rad: f32) Quaternion {
|
|
||||||
const half_angle_rad = 0.5 * angle_rad;
|
|
||||||
const c = @cos(half_angle_rad);
|
|
||||||
const s = @sin(half_angle_rad);
|
|
||||||
return .init(0, -s, 0, c);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initRotationYX(angle_rad: f32) Quaternion {
|
|
||||||
const half_angle_rad = 0.5 * angle_rad;
|
|
||||||
const c = @cos(half_angle_rad);
|
|
||||||
const s = @sin(half_angle_rad);
|
|
||||||
return .init(0, 0, -s, c);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initRotationYZ(angle_rad: f32) Quaternion {
|
|
||||||
const half_angle_rad = 0.5 * angle_rad;
|
|
||||||
const c = @cos(half_angle_rad);
|
|
||||||
const s = @sin(half_angle_rad);
|
|
||||||
return .init(s, 0, 0, c);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initRotationZX(angle_rad: f32) Quaternion {
|
|
||||||
const half_angle_rad = 0.5 * angle_rad;
|
|
||||||
const c = @cos(half_angle_rad);
|
|
||||||
const s = @sin(half_angle_rad);
|
|
||||||
return .init(0, s, 0, c);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initRotationZY(angle_rad: f32) Quaternion {
|
|
||||||
const half_angle_rad = 0.5 * angle_rad;
|
|
||||||
const c = @cos(half_angle_rad);
|
|
||||||
const s = @sin(half_angle_rad);
|
|
||||||
return .init(-s, 0, 0, c);
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- CONVERSION ---
|
|
||||||
|
|
||||||
pub inline fn asArray(self: Quaternion) [4]f32 {
|
|
||||||
return self.vector.vector;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector4(self: Quaternion) Vector4 {
|
|
||||||
return self.vector;
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- ACCESSORS ---
|
|
||||||
|
|
||||||
pub inline fn getVector(self: Quaternion) Vector3 {
|
|
||||||
return self.vector.asVector3();
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getScalar(self: Quaternion) f32 {
|
|
||||||
return self.vector.getW();
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setVector(self: Quaternion, vector: Vector3) Quaternion {
|
|
||||||
return .{
|
|
||||||
.vector = .{
|
|
||||||
.vector = @shuffle(f32, self.vector.vector, vector.vector, .{ ~@as(i32, 0), ~@as(i32, 1), ~@as(i32, 2), 3 }),
|
|
||||||
},
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setScalar(self: Quaternion, scalar: f32) Quaternion {
|
|
||||||
return .initVector4(self.vector.setW(scalar));
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- COMPONENT-WISE ---
|
|
||||||
|
|
||||||
pub inline fn add(self: Quaternion, other: Quaternion) Quaternion {
|
|
||||||
return .initVector4(.add(self.vector, other.vector));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sub(self: Quaternion, other: Quaternion) Quaternion {
|
|
||||||
return .initVector4(.sub(self.vector, other.vector));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn negate(self: Quaternion) Quaternion {
|
|
||||||
return .initVector4(.negate(self.vector));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn conjugate(self: Quaternion) Quaternion {
|
|
||||||
return .initVector4(.mul(self.vector, .init(-1, -1, -1, 1)));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalar(self: Quaternion, scalar: f32) Quaternion {
|
|
||||||
return .initVector4(.mulScalar(self.vector, scalar));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalar(self: Quaternion, scalar: f32) Quaternion {
|
|
||||||
return .initVector4(.divScalar(self.vector, scalar));
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- OTHER ---
|
|
||||||
|
|
||||||
pub inline fn len(self: Quaternion) f32 {
|
|
||||||
return self.vector.len();
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lenSquared(self: Quaternion) f32 {
|
|
||||||
return self.vector.lenSquared();
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn normalize(self: Quaternion) Quaternion {
|
|
||||||
return .initVector4(.normalize(self.vector));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn dot(self: Quaternion, other: Quaternion) f32 {
|
|
||||||
return Vector4.dot(self.vector, other.vector);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lerp(self: Quaternion, other: Quaternion, t: f32) Quaternion {
|
|
||||||
return .initVector4(.lerp(self.vector, other.vector, t));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulQuaternion(self: Quaternion, other: Quaternion) Quaternion {
|
|
||||||
const x1, const y1, const z1, const w1 = self.vector.vector;
|
|
||||||
const x2, const y2, const z2, const w2 = other.vector.vector;
|
|
||||||
return .init(
|
|
||||||
w1 * x2 + x1 * w2 + y1 * z2 - z1 * y2,
|
|
||||||
w1 * y2 - x1 * z2 + y1 * w2 + z1 * x2,
|
|
||||||
w1 * z2 + x1 * y2 - y1 * x2 + z1 * w2,
|
|
||||||
w1 * w2 - x1 * x2 - y1 * y2 - z1 * z2,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,172 +0,0 @@
|
|||||||
const std = @import("std");
|
|
||||||
|
|
||||||
const Vector2Int = @import("Vector2Int.zig").Vector2Int;
|
|
||||||
const Vector3 = @import("Vector3.zig").Vector3;
|
|
||||||
const Vector4 = @import("Vector3.zig").Vector4;
|
|
||||||
|
|
||||||
pub const Vector2 = extern struct {
|
|
||||||
vector: Vector,
|
|
||||||
|
|
||||||
pub const Vector = @Vector(2, f32);
|
|
||||||
pub const Array = [2]f32;
|
|
||||||
pub const Mask = enum(i32) { x = 0, y = 1 };
|
|
||||||
|
|
||||||
pub const zero = Vector2.initScalar(0);
|
|
||||||
pub const one = Vector2.initScalar(1);
|
|
||||||
pub const unit_x = Vector2.init(1, 0);
|
|
||||||
pub const unit_y = Vector2.init(0, 1);
|
|
||||||
pub const unit_nx = Vector2.init(-1, 0);
|
|
||||||
pub const unit_ny = Vector2.init(0, -1);
|
|
||||||
|
|
||||||
// --- INIT ---
|
|
||||||
|
|
||||||
pub inline fn initScalar(scalar: f32) Vector2 {
|
|
||||||
return .{ .vector = @splat(scalar) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn init(x: f32, y: f32) Vector2 {
|
|
||||||
return .{ .vector = .{ x, y } };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initArray(array: Array) Vector2 {
|
|
||||||
return .{ .vector = array };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- CONVERSION ---
|
|
||||||
|
|
||||||
pub inline fn asArray(self: Vector2) Array {
|
|
||||||
return self.vector;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asArrayNorm(self: Vector2, comptime T: type) [2]T {
|
|
||||||
const scale_vector: Vector = @splat(std.math.maxInt(T));
|
|
||||||
return @as(@Vector(2, T), @intFromFloat(@round(self.vector * scale_vector)));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector2Int(self: Vector2) Vector2Int {
|
|
||||||
return .{ .vector = @intFromFloat(@round(self.vector)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector2IntFrac(self: Vector2) Vector2Int {
|
|
||||||
const fraction: @Vector(2, f64) = @floatCast(self.vector);
|
|
||||||
const scale: @Vector(2, f64) = @splat(std.math.maxInt(i32));
|
|
||||||
return .{ .vector = @intFromFloat(@round(fraction * scale)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector3(self: Vector2, z: f32) Vector3 {
|
|
||||||
const z_vector: @Vector(3, f32) = .{ undefined, undefined, z };
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, z_vector, [_]i32{ 0, 1, ~@as(i32, 2) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector4(self: Vector4, z: f32, w: f32) Vector4 {
|
|
||||||
const zw_vector: @Vector(4, f32) = .{ undefined, undefined, z, w };
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, zw_vector, [_]i32{ 0, 1, ~@as(i32, 2), ~@as(i32, 3) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- ACCESSORS ---
|
|
||||||
|
|
||||||
pub inline fn getX(self: Vector2) f32 {
|
|
||||||
return self.vector[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getY(self: Vector2) f32 {
|
|
||||||
return self.vector[1];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setX(self: Vector2, x: f32) Vector2 {
|
|
||||||
const x_vector: Vector = @splat(x);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, x_vector, .{ ~@as(i32, 0), 1 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setY(self: Vector2, y: f32) Vector2 {
|
|
||||||
const y_vector: Vector = @splat(y);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, y_vector, .{ 0, ~@as(i32, 1) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- COMPONENT-WISE ---
|
|
||||||
|
|
||||||
pub inline fn add(self: Vector2, other: Vector2) Vector2 {
|
|
||||||
return .{ .vector = self.vector + other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sub(self: Vector2, other: Vector2) Vector2 {
|
|
||||||
return .{ .vector = self.vector - other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mul(self: Vector2, other: Vector2) Vector2 {
|
|
||||||
return .{ .vector = self.vector * other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn div(self: Vector2, other: Vector2) Vector2 {
|
|
||||||
return .{ .vector = self.vector / other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn negate(self: Vector2) Vector2 {
|
|
||||||
return .{ .vector = -self.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalar(self: Vector2, scalar: f32) Vector2 {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = self.vector * scalar_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalar(self: Vector2, scalar: f32) Vector2 {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = self.vector / scalar_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- SWIZZLE ---
|
|
||||||
|
|
||||||
pub inline fn swizzle2(self: Vector2, comptime mask: [2]Mask) Vector2 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([2]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn swizzle3(self: Vector2, comptime mask: [3]Mask) Vector3 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([3]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn swizzle4(self: Vector2, comptime mask: [4]Mask) Vector4 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([4]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- OTHER ---
|
|
||||||
|
|
||||||
pub inline fn len(self: Vector2) f32 {
|
|
||||||
return @sqrt(@reduce(.Add, self.vector * self.vector));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lenSquared(self: Vector2) f32 {
|
|
||||||
return @reduce(.Add, self.vector * self.vector);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn normalize(self: Vector2) Vector2 {
|
|
||||||
const len_vector: Vector = @splat(@sqrt(@reduce(.Add, self.vector * self.vector)));
|
|
||||||
return .{ .vector = self.vector / len_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn dot(self: Vector2, other: Vector2) f32 {
|
|
||||||
return @reduce(.Add, self.vector * other.vector);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn cross(self: Vector2, other: Vector2) f32 {
|
|
||||||
return self.getX() * other.getY() - self.getY() * other.getX();
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lerp(self: Vector2, other: Vector2, t: f32) Vector2 {
|
|
||||||
const s = 1.0 - t;
|
|
||||||
const t_vector: Vector = @splat(t);
|
|
||||||
const s_vector: Vector = @splat(s);
|
|
||||||
return .{ .vector = self * s_vector + other * t_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn rotate(self: Vector2, angle_rad: f32) Vector2 {
|
|
||||||
const c = @cos(angle_rad);
|
|
||||||
const s = @sin(angle_rad);
|
|
||||||
return .{
|
|
||||||
.vector = .{
|
|
||||||
self.getX() * c - self.getY() * s,
|
|
||||||
self.getX() * s + self.getY() * c,
|
|
||||||
},
|
|
||||||
};
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,199 +0,0 @@
|
|||||||
const std = @import("std");
|
|
||||||
|
|
||||||
const Vector2 = @import("Vector2.zig").Vector2;
|
|
||||||
const Vector3Int = @import("Vector3Int.zig").Vector3Int;
|
|
||||||
|
|
||||||
pub const Vector2Int = extern struct {
|
|
||||||
vector: Vector,
|
|
||||||
|
|
||||||
pub const Vector = @Vector(2, i32);
|
|
||||||
pub const Array = [2]i32;
|
|
||||||
pub const Mask = enum(i32) { x = 0, y = 1 };
|
|
||||||
|
|
||||||
pub const zero = Vector2Int.initScalar(0);
|
|
||||||
pub const one = Vector2Int.initScalar(1);
|
|
||||||
pub const one_frac = Vector2Int.initScalar(std.math.maxInt(i32));
|
|
||||||
pub const unit_x = Vector2Int.init(1, 0);
|
|
||||||
pub const unit_y = Vector2Int.init(0, 1);
|
|
||||||
pub const unit_nx = Vector2Int.init(-1, 0);
|
|
||||||
pub const unit_ny = Vector2Int.init(0, -1);
|
|
||||||
pub const unit_x_frac = Vector2Int.init(std.math.maxInt(i32), 0);
|
|
||||||
pub const unit_y_frac = Vector2Int.init(0, std.math.maxInt(i32));
|
|
||||||
pub const unit_nx_frac = Vector2Int.init(-std.math.maxInt(i32), 0);
|
|
||||||
pub const unit_ny_frac = Vector2Int.init(0, -std.math.maxInt(i32));
|
|
||||||
|
|
||||||
// --- INIT ---
|
|
||||||
|
|
||||||
pub inline fn initScalar(scalar: i32) Vector2Int {
|
|
||||||
return .{ .vector = @splat(scalar) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn init(x: i32, y: i32) Vector2Int {
|
|
||||||
return .{ .vector = .{ x, y } };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initArray(array: Array) Vector2Int {
|
|
||||||
return .{ .vector = array };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- CONVERSION ---
|
|
||||||
|
|
||||||
pub inline fn asArray(self: Vector2Int) Array {
|
|
||||||
return self.vector;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector2(self: Vector2Int) Vector2 {
|
|
||||||
return .{ .vector = @floatFromInt(self.vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector2Frac(self: Vector2Int) Vector2 {
|
|
||||||
const numerator: @Vector(2, f64) = @floatFromInt(self.vector);
|
|
||||||
const denominator: @Vector(2, f64) = @splat(std.math.maxInt(i32));
|
|
||||||
return .{ .vector = @floatCast(numerator / denominator) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector3Int(self: Vector2Int, z: i32) Vector3Int {
|
|
||||||
const z_vector: @Vector(3, i32) = .{ undefined, undefined, z };
|
|
||||||
return .{ .vector = @shuffle(i32, self.vector, z_vector, [_]i32{ 0, 1, ~@as(i32, 2) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- ACCESSORS ---
|
|
||||||
|
|
||||||
pub inline fn getX(self: Vector2Int) i32 {
|
|
||||||
return self.vector[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getY(self: Vector2Int) i32 {
|
|
||||||
return self.vector[1];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setX(self: Vector2Int, x: i32) Vector2Int {
|
|
||||||
const x_vector: Vector = @splat(x);
|
|
||||||
return .{ .vector = @shuffle(i32, self.vector, x_vector, .{ ~@as(i32, 0), 1 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setY(self: Vector2Int, y: i32) Vector2Int {
|
|
||||||
const y_vector: Vector = @splat(y);
|
|
||||||
return .{ .vector = @shuffle(i32, self.vector, y_vector, .{ 0, ~@as(i32, 1) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- COMPONENT-WISE ---
|
|
||||||
|
|
||||||
pub inline fn add(self: Vector2Int, other: Vector2Int) Vector2Int {
|
|
||||||
return .{ .vector = self.vector + other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sub(self: Vector2Int, other: Vector2Int) Vector2Int {
|
|
||||||
return .{ .vector = self.vector - other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mul(self: Vector2Int, other: Vector2Int) Vector2Int {
|
|
||||||
return .{ .vector = self.vector * other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulFrac(self: Vector2Int, other: Vector2Int) Vector2Int {
|
|
||||||
const denominator: @Vector(2, i64) = @splat(std.math.maxInt(i32));
|
|
||||||
const rounding_bias: @Vector(2, i64) = denominator >> @as(@Vector(2, u6), @splat(1));
|
|
||||||
const self_wide: @Vector(2, i64) = self.vector;
|
|
||||||
const other_wide: @Vector(2, i64) = other.vector;
|
|
||||||
return .{ .vector = @intCast(@divFloor(self_wide * other_wide + rounding_bias, denominator)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulFracFrac(self: Vector2Int, other: Vector2Int) Vector2Int {
|
|
||||||
const denominator: @Vector(2, i64) = @splat(std.math.maxInt(i32) * std.math.maxInt(i32));
|
|
||||||
const rounding_bias: @Vector(2, i64) = denominator >> @as(@Vector(2, u6), @splat(1));
|
|
||||||
const self_wide: @Vector(2, i64) = self.vector;
|
|
||||||
const other_wide: @Vector(2, i64) = other.vector;
|
|
||||||
return .{ .vector = @intCast(@divFloor(self_wide * other_wide + rounding_bias, denominator)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn div(self: Vector2Int, other: Vector2Int) Vector2Int {
|
|
||||||
return .{ .vector = @divFloor(self.vector, other.vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mod(self: Vector2Int, other: Vector2Int) Vector2Int {
|
|
||||||
return .{ .vector = @mod(self.vector, other.vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn negate(self: Vector2Int) Vector2Int {
|
|
||||||
return .{ .vector = -self.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalar(self: Vector2Int, scalar: i32) Vector2Int {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = self.vector * scalar_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalarFloat(self: Vector2Int, scalar: f32) Vector2Int {
|
|
||||||
const self_float: @Vector(2, f64) = @floatFromInt(self.vector);
|
|
||||||
const scalar_vector_float: @Vector(2, f64) = @splat(scalar);
|
|
||||||
return .{ .vector = @intFromFloat(@round(self_float * scalar_vector_float)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalarFrac(self: Vector2Int, scalar: i32) Vector2Int {
|
|
||||||
const denominator: @Vector(2, i64) = @splat(std.math.maxInt(i32));
|
|
||||||
const rounding_bias: @Vector(2, i64) = denominator >> @as(@Vector(2, u6), @splat(1));
|
|
||||||
const self_wide: @Vector(2, i64) = self.vector;
|
|
||||||
const scalar_wide: @Vector(2, i64) = @splat(scalar);
|
|
||||||
return .{ .vector = @intCast(@divFloor(self_wide * scalar_wide + rounding_bias, denominator)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalarFracFrac(self: Vector2Int, scalar: i32) Vector2Int {
|
|
||||||
const denominator: @Vector(2, i64) = @splat(std.math.maxInt(i32) * std.math.maxInt(i32));
|
|
||||||
const rounding_bias: @Vector(2, i64) = denominator >> @as(@Vector(2, u6), @splat(1));
|
|
||||||
const self_wide: @Vector(2, i64) = self.vector;
|
|
||||||
const scalar_wide: @Vector(2, i64) = @splat(scalar);
|
|
||||||
return .{ .vector = @intCast(@divFloor(self_wide * scalar_wide + rounding_bias, denominator)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalar(self: Vector2Int, scalar: i32) Vector2Int {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = @divFloor(self.vector, scalar_vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalarFloat(self: Vector2Int, scalar: f32) Vector2Int {
|
|
||||||
const self_float: @Vector(2, f64) = @floatFromInt(self.vector);
|
|
||||||
const scalar_vector_float: @Vector(2, f64) = @splat(scalar);
|
|
||||||
return .{ .vector = @intFromFloat(@round(self_float / scalar_vector_float)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn modScalar(self: Vector2Int, scalar: i32) Vector2Int {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = @mod(self.vector, scalar_vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn abs(self: Vector2Int) Vector2Int {
|
|
||||||
return .{ .vector = @intCast(@abs(self.vector)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sign(self: Vector2Int) Vector2Int {
|
|
||||||
return .{ .vector = std.math.sign(self.vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- SWIZZLE ---
|
|
||||||
|
|
||||||
pub inline fn swizzle2(self: Vector2Int, comptime mask: [2]Mask) Vector2Int {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([2]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn swizzle3(self: Vector2Int, comptime mask: [3]Mask) Vector3Int {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([3]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- OTHER ---
|
|
||||||
|
|
||||||
pub inline fn lenSquared(self: Vector2Int) i64 {
|
|
||||||
const self_wide: @Vector(2, i64) = self.vector;
|
|
||||||
return @reduce(.Add, self_wide * self_wide);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn dot(self: Vector2Int, other: Vector2Int) i64 {
|
|
||||||
const self_wide: @Vector(2, i64) = self.vector;
|
|
||||||
const other_wide: @Vector(2, i64) = other.vector;
|
|
||||||
return @reduce(.Add, self_wide * other_wide);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn cross(self: Vector2Int, other: Vector2Int) i64 {
|
|
||||||
return @as(i64, self.getX()) * @as(i64, other.getY()) - @as(i64, self.getY()) * @as(i64, other.getX());
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,166 +0,0 @@
|
|||||||
const std = @import("std");
|
|
||||||
const math = @import("../math.zig");
|
|
||||||
|
|
||||||
const Vector2 = @import("Vector2.zig").Vector2;
|
|
||||||
|
|
||||||
const f32x8 = math.f32x8;
|
|
||||||
const ps = math.ps;
|
|
||||||
|
|
||||||
pub const Vector2x8 = extern struct {
|
|
||||||
x: f32x8,
|
|
||||||
y: f32x8,
|
|
||||||
|
|
||||||
pub const zero = Vector2x8.init(ps(0), ps(0));
|
|
||||||
pub const one = Vector2x8.init(ps(1), ps(1));
|
|
||||||
pub const unit_x = Vector2x8.init(ps(1), ps(0));
|
|
||||||
pub const unit_y = Vector2x8.init(ps(0), ps(1));
|
|
||||||
pub const unit_nx = Vector2x8.init(ps(-1), ps(0));
|
|
||||||
pub const unit_ny = Vector2x8.init(ps(0), ps(-1));
|
|
||||||
|
|
||||||
// --- INIT ---
|
|
||||||
|
|
||||||
pub inline fn initScalar(x: f32, y: f32) Vector2x8 {
|
|
||||||
return .{ .x = ps(x), .y = ps(y) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initScalars(x: f32x8, y: f32x8) Vector2x8 {
|
|
||||||
return .{ .x = x, .y = y };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initVector(vector: Vector2) Vector2x8 {
|
|
||||||
return .{ .x = ps(vector.getX()), .y = ps(vector.getY()) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initVectors(vectors: [8]Vector2) Vector2x8 {
|
|
||||||
const v0: f32x8 = @as([8]f32, @bitCast(vectors[0..4].*));
|
|
||||||
const v1: f32x8 = @as([8]f32, @bitCast(vectors[4..8].*));
|
|
||||||
const x: f32x8 = @shuffle(f32, v0, v1, [_]i32{ 0, 2, 4, 6, ~@as(i32, 0), ~@as(i32, 2), ~@as(i32, 4), ~@as(i32, 6) });
|
|
||||||
const y: f32x8 = @shuffle(f32, v0, v1, [_]i32{ 1, 3, 5, 7, ~@as(i32, 1), ~@as(i32, 3), ~@as(i32, 5), ~@as(i32, 7) });
|
|
||||||
return .{ .x = x, .y = y };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- CONVERSION ---
|
|
||||||
|
|
||||||
pub inline fn asVectors(self: Vector2x8) [8]Vector2 {
|
|
||||||
const v0: f32x8 = @shuffle(f32, self.x, self.y, [_]i32{ 0, ~@as(i32, 0), 1, ~@as(i32, 1), 2, ~@as(i32, 2), 3, ~@as(i32, 3) });
|
|
||||||
const v1: f32x8 = @shuffle(f32, self.x, self.y, [_]i32{ 4, ~@as(i32, 4), 5, ~@as(i32, 5), 6, ~@as(i32, 6), 7, ~@as(i32, 7) });
|
|
||||||
return @as([4]Vector2, @bitCast(@as([8]f32, v0))) ++ @as([4]Vector2, @bitCast(@as([8]f32, v1)));
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- COMPONENT-WISE ---
|
|
||||||
|
|
||||||
pub inline fn add(self: Vector2x8, other: Vector2x8) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = self.x + other.x,
|
|
||||||
.y = self.y + other.y,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sub(self: Vector2x8, other: Vector2x8) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = self.x - other.x,
|
|
||||||
.y = self.y - other.y,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mul(self: Vector2x8, other: Vector2x8) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = self.x * other.x,
|
|
||||||
.y = self.y * other.y,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn div(self: Vector2x8, other: Vector2x8) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = self.x / other.x,
|
|
||||||
.y = self.y / other.y,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn negate(self: Vector2x8) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = -self.x,
|
|
||||||
.y = -self.y,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalar(self: Vector2x8, scalar: f32) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = self.x * ps(scalar),
|
|
||||||
.y = self.y * ps(scalar),
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalars(self: Vector2x8, scalar: f32x8) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = self.x * scalar,
|
|
||||||
.y = self.y * scalar,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalar(self: Vector2x8, scalar: f32) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = self.x / ps(scalar),
|
|
||||||
.y = self.y / ps(scalar),
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalars(self: Vector2x8, scalar: f32x8) Vector2x8 {
|
|
||||||
return .{
|
|
||||||
.x = self.x / scalar,
|
|
||||||
.y = self.y / scalar,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- OTHER ---
|
|
||||||
|
|
||||||
pub inline fn len(self: Vector2x8) f32x8 {
|
|
||||||
return @sqrt(self.x * self.x + self.y * self.y);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lenSquared(self: Vector2x8) f32x8 {
|
|
||||||
return self.x * self.x + self.y * self.y;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn normalize(self: Vector2x8) Vector2x8 {
|
|
||||||
const len_vector: f32x8 = @sqrt(self.x * self.x + self.y * self.y);
|
|
||||||
return .{
|
|
||||||
.x = self.x / len_vector,
|
|
||||||
.y = self.y / len_vector,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn dot(self: Vector2x8, other: Vector2x8) f32x8 {
|
|
||||||
return self.x * other.x + self.y * other.y;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn cross(self: Vector2x8, other: Vector2x8) f32x8 {
|
|
||||||
return self.x * other.y - self.y * other.x;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lerp(self: Vector2x8, other: Vector2x8, t: f32x8) Vector2x8 {
|
|
||||||
const s: f32x8 = ps(1.0) - t;
|
|
||||||
return .{
|
|
||||||
.x = self.x * s + other.x * t,
|
|
||||||
.y = self.y * s + other.y * t,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn rotate(self: Vector2x8, angle_rad: f32) Vector2x8 {
|
|
||||||
const c = @cos(angle_rad);
|
|
||||||
const s = @sin(angle_rad);
|
|
||||||
return .{
|
|
||||||
.x = self.x * ps(c) - self.y * ps(s),
|
|
||||||
.y = self.x * ps(s) + self.y * ps(c),
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn rotatev(self: Vector2x8, angle_rad: f32x8) Vector2x8 {
|
|
||||||
const c = @cos(angle_rad);
|
|
||||||
const s = @sin(angle_rad);
|
|
||||||
return .{
|
|
||||||
.x = self.x * c - self.y * s,
|
|
||||||
.y = self.x * s + self.y * c,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,188 +0,0 @@
|
|||||||
const std = @import("std");
|
|
||||||
|
|
||||||
const Quaternion = @import("Quaternion.zig").Quaternion;
|
|
||||||
const Vector2 = @import("Vector2.zig").Vector2;
|
|
||||||
const Vector3Int = @import("Vector3Int.zig").Vector3Int;
|
|
||||||
const Vector4 = @import("Vector4.zig").Vector4;
|
|
||||||
|
|
||||||
pub const Vector3 = extern struct {
|
|
||||||
vector: Vector,
|
|
||||||
|
|
||||||
pub const Vector = @Vector(3, f32);
|
|
||||||
pub const Array = [3]f32;
|
|
||||||
pub const Mask = enum(i32) { x = 0, y = 1, z = 2 };
|
|
||||||
|
|
||||||
pub const zero = Vector3.initScalar(0);
|
|
||||||
pub const one = Vector3.initScalar(1);
|
|
||||||
pub const unit_x = Vector3.init(1, 0, 0);
|
|
||||||
pub const unit_y = Vector3.init(0, 1, 0);
|
|
||||||
pub const unit_z = Vector3.init(0, 0, 1);
|
|
||||||
pub const unit_nx = Vector3.init(-1, 0, 0);
|
|
||||||
pub const unit_ny = Vector3.init(0, -1, 0);
|
|
||||||
pub const unit_nz = Vector3.init(0, 0, -1);
|
|
||||||
|
|
||||||
// --- INIT ---
|
|
||||||
|
|
||||||
pub inline fn initScalar(scalar: f32) Vector3 {
|
|
||||||
return .{ .vector = @splat(scalar) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn init(x: f32, y: f32, z: f32) Vector3 {
|
|
||||||
return .{ .vector = .{ x, y, z } };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initArray(array: Array) Vector3 {
|
|
||||||
return .{ .vector = array };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- CONVERSION ---
|
|
||||||
|
|
||||||
pub inline fn asArray(self: Vector3) Array {
|
|
||||||
return self.vector;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asArrayNorm(self: Vector3, comptime T: type) [3]T {
|
|
||||||
const scale_vector: Vector = @splat(std.math.maxInt(T));
|
|
||||||
return @as(@Vector(3, T), @intFromFloat(@round(self.vector * scale_vector)));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector3Int(self: Vector3) Vector3Int {
|
|
||||||
return .{ .vector = @intFromFloat(@round(self.vector)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector2IntFrac(self: Vector3) Vector3Int {
|
|
||||||
const fraction: @Vector(3, f64) = @floatCast(self.vector);
|
|
||||||
const scale: @Vector(3, f64) = @splat(std.math.maxInt(i32));
|
|
||||||
return .{ .vector = @intFromFloat(@round(fraction * scale)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector2(self: Vector3) Vector2 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, [_]i32{ 0, 1 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector4(self: Vector3, w: f32) Vector4 {
|
|
||||||
const w_vector: @Vector(4, f32) = .{ undefined, undefined, undefined, w };
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, w_vector, [_]i32{ 0, 1, 2, ~@as(i32, 3) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- ACCESSORS ---
|
|
||||||
|
|
||||||
pub inline fn getX(self: Vector3) f32 {
|
|
||||||
return self.vector[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getY(self: Vector3) f32 {
|
|
||||||
return self.vector[1];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getZ(self: Vector3) f32 {
|
|
||||||
return self.vector[2];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setX(self: Vector3, x: f32) Vector3 {
|
|
||||||
const x_vector: Vector = @splat(x);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, x_vector, [_]i32{ ~@as(i32, 0), 1, 2 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setY(self: Vector3, y: f32) Vector3 {
|
|
||||||
const y_vector: Vector = @splat(y);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, y_vector, [_]i32{ 0, ~@as(i32, 1), 2 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setZ(self: Vector3, z: f32) Vector3 {
|
|
||||||
const z_vector: Vector = @splat(z);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, z_vector, [_]i32{ 0, 1, ~@as(i32, 2) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- COMPONENT-WISE ---
|
|
||||||
|
|
||||||
pub inline fn add(self: Vector3, other: Vector3) Vector3 {
|
|
||||||
return .{ .vector = self.vector + other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sub(self: Vector3, other: Vector3) Vector3 {
|
|
||||||
return .{ .vector = self.vector - other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mul(self: Vector3, other: Vector3) Vector3 {
|
|
||||||
return .{ .vector = self.vector * other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn div(self: Vector3, other: Vector3) Vector3 {
|
|
||||||
return .{ .vector = self.vector / other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn negate(self: Vector3) Vector3 {
|
|
||||||
return .{ .vector = -self.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalar(self: Vector3, scalar: f32) Vector3 {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = self.vector * scalar_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalar(self: Vector3, scalar: f32) Vector3 {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = self.vector / scalar_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- SWIZZLE ---
|
|
||||||
|
|
||||||
pub inline fn swizzle2(self: Vector3, comptime mask: [2]Mask) Vector2 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([2]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn swizzle3(self: Vector3, comptime mask: [3]Mask) Vector3 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([3]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn swizzle4(self: Vector3, comptime mask: [4]Mask) Vector4 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([4]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- OTHER ---
|
|
||||||
|
|
||||||
pub inline fn len(self: Vector3) f32 {
|
|
||||||
return @sqrt(@reduce(.Add, self.vector * self.vector));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lenSquared(self: Vector3) f32 {
|
|
||||||
return @reduce(.Add, self.vector * self.vector);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn normalize(self: Vector3) Vector3 {
|
|
||||||
const len_vector: Vector = @splat(@sqrt(@reduce(.Add, self.vector * self.vector)));
|
|
||||||
return .{ .vector = self.vector / len_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn dot(self: Vector3, other: Vector3) f32 {
|
|
||||||
return @reduce(.Add, self.vector * other.vector);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn cross(self: Vector3, other: Vector3) Vector3 {
|
|
||||||
return .{
|
|
||||||
.vector = .{
|
|
||||||
self.getY() * other.getZ() - self.getZ() * other.getY(),
|
|
||||||
self.getZ() * other.getX() - self.getX() * other.getZ(),
|
|
||||||
self.getX() * other.getY() - self.getY() * other.getX(),
|
|
||||||
},
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lerp(self: Vector3, other: Vector3, t: f32) Vector3 {
|
|
||||||
const s = 1.0 - t;
|
|
||||||
const t_vector: Vector = @splat(t);
|
|
||||||
const s_vector: Vector = @splat(s);
|
|
||||||
return .{ .vector = self * s_vector + other * t_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn rotate(self: Vector3, quaternion: Quaternion) Vector3 {
|
|
||||||
const quaternion_scalar = quaternion.getScalar();
|
|
||||||
const quaternion_vector = quaternion.getVector();
|
|
||||||
|
|
||||||
return .add(self, .cross(
|
|
||||||
.add(quaternion_vector, quaternion_vector),
|
|
||||||
.add(.cross(quaternion_vector, self), .mulScalar(self, quaternion_scalar)),
|
|
||||||
));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,207 +0,0 @@
|
|||||||
const std = @import("std");
|
|
||||||
|
|
||||||
const Vector2Int = @import("Vector2Int.zig").Vector2Int;
|
|
||||||
const Vector3 = @import("Vector3.zig").Vector3;
|
|
||||||
|
|
||||||
pub const Vector3Int = extern struct {
|
|
||||||
vector: Vector,
|
|
||||||
|
|
||||||
pub const Vector = @Vector(3, i32);
|
|
||||||
pub const Array = [3]i32;
|
|
||||||
pub const Mask = enum(i32) { x = 0, y = 1, z = 2 };
|
|
||||||
|
|
||||||
pub const zero = Vector3Int.initScalar(0);
|
|
||||||
pub const one = Vector3Int.initScalar(1);
|
|
||||||
pub const one_frac = Vector3Int.initScalar(std.math.maxInt(i32));
|
|
||||||
pub const unit_x = Vector3Int.init(1, 0, 0);
|
|
||||||
pub const unit_y = Vector3Int.init(0, 1, 0);
|
|
||||||
pub const unit_z = Vector3Int.init(0, 0, 1);
|
|
||||||
pub const unit_nx = Vector3Int.init(-1, 0, 0);
|
|
||||||
pub const unit_ny = Vector3Int.init(0, -1, 0);
|
|
||||||
pub const unit_nz = Vector3Int.init(0, 0, -1);
|
|
||||||
pub const unit_x_frac = Vector3Int.init(std.math.maxInt(i32), 0, 0);
|
|
||||||
pub const unit_y_frac = Vector3Int.init(0, std.math.maxInt(i32), 0);
|
|
||||||
pub const unit_z_frac = Vector3Int.init(0, 0, std.math.maxInt(i32));
|
|
||||||
pub const unit_nx_frac = Vector3Int.init(-std.math.maxInt(i32), 0, 0);
|
|
||||||
pub const unit_ny_frac = Vector3Int.init(0, -std.math.maxInt(i32), 0);
|
|
||||||
pub const unit_nz_frac = Vector3Int.init(0, 0, -std.math.maxInt(i32));
|
|
||||||
|
|
||||||
// --- INIT ---
|
|
||||||
|
|
||||||
pub inline fn initScalar(scalar: i32) Vector3Int {
|
|
||||||
return .{ .vector = @splat(scalar) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn init(x: i32, y: i32, z: i32) Vector3Int {
|
|
||||||
return .{ .vector = .{ x, y, z } };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initArray(array: Array) Vector3Int {
|
|
||||||
return .{ .vector = array };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- CONVERSION ---
|
|
||||||
|
|
||||||
pub inline fn asArray(self: Vector3Int) Array {
|
|
||||||
return self.vector;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector3(self: Vector3Int) Vector3 {
|
|
||||||
return .{ .vector = @floatFromInt(self.vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector3Frac(self: Vector3Int) Vector3 {
|
|
||||||
const numerator: @Vector(3, f64) = @floatFromInt(self.vector);
|
|
||||||
const denominator: @Vector(3, f64) = @splat(std.math.maxInt(i32));
|
|
||||||
return .{ .vector = @floatCast(numerator / denominator) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector2Int(self: Vector3Int) Vector2Int {
|
|
||||||
return .{ .vector = @shuffle(i32, self.vector, undefined, [_]i32{ 0, 1 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- ACCESSORS ---
|
|
||||||
|
|
||||||
pub inline fn getX(self: Vector3Int) i32 {
|
|
||||||
return self.vector[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getY(self: Vector3Int) i32 {
|
|
||||||
return self.vector[1];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getZ(self: Vector3Int) i32 {
|
|
||||||
return self.vector[2];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setX(self: Vector3Int, x: i32) Vector3Int {
|
|
||||||
const x_vector: Vector = @splat(x);
|
|
||||||
return .{ .vector = @shuffle(i32, self.vector, x_vector, [_]i32{ ~@as(i32, 0), 1, 2 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setY(self: Vector3Int, y: i32) Vector3Int {
|
|
||||||
const y_vector: Vector = @splat(y);
|
|
||||||
return .{ .vector = @shuffle(i32, self.vector, y_vector, [_]i32{ 0, ~@as(i32, 1), 2 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setZ(self: Vector3Int, z: i32) Vector3Int {
|
|
||||||
const z_vector: Vector = @splat(z);
|
|
||||||
return .{ .vector = @shuffle(i32, self.vector, z_vector, [_]i32{ 0, 1, ~@as(i32, 2) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- COMPONENT-WISE ---
|
|
||||||
|
|
||||||
pub inline fn add(self: Vector3Int, other: Vector3Int) Vector3Int {
|
|
||||||
return .{ .vector = self.vector + other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sub(self: Vector3Int, other: Vector3Int) Vector3Int {
|
|
||||||
return .{ .vector = self.vector - other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mul(self: Vector3Int, other: Vector3Int) Vector3Int {
|
|
||||||
return .{ .vector = self.vector * other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulFrac(self: Vector3Int, other: Vector3Int) Vector3Int {
|
|
||||||
const denominator: @Vector(3, i64) = @splat(std.math.maxInt(i32));
|
|
||||||
const rounding_bias: @Vector(3, i64) = denominator >> @as(@Vector(2, u6), @splat(1));
|
|
||||||
const self_wide: @Vector(3, i64) = self.vector;
|
|
||||||
const other_wide: @Vector(3, i64) = other.vector;
|
|
||||||
return .{ .vector = @intCast(@divFloor(self_wide * other_wide + rounding_bias, denominator)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulFracFrac(self: Vector3Int, other: Vector3Int) Vector3Int {
|
|
||||||
const denominator: @Vector(3, i64) = @splat(std.math.maxInt(i32) * std.math.maxInt(i32));
|
|
||||||
const rounding_bias: @Vector(3, i64) = denominator >> @as(@Vector(2, u6), @splat(1));
|
|
||||||
const self_wide: @Vector(3, i64) = self.vector;
|
|
||||||
const other_wide: @Vector(3, i64) = other.vector;
|
|
||||||
return .{ .vector = @intCast(@divFloor(self_wide * other_wide + rounding_bias, denominator)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn div(self: Vector3Int, other: Vector3Int) Vector3Int {
|
|
||||||
return .{ .vector = @divFloor(self.vector, other.vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mod(self: Vector3Int, other: Vector3Int) Vector3Int {
|
|
||||||
return .{ .vector = @mod(self.vector, other.vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn negate(self: Vector3Int) Vector3Int {
|
|
||||||
return .{ .vector = -self.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalar(self: Vector3Int, scalar: i32) Vector3Int {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = self.vector * scalar_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalarFloat(self: Vector3Int, scalar: f32) Vector3Int {
|
|
||||||
const self_float: @Vector(3, f64) = @floatFromInt(self.vector);
|
|
||||||
const scalar_vector_float: @Vector(3, f64) = @splat(scalar);
|
|
||||||
return .{ .vector = @intFromFloat(@round(self_float * scalar_vector_float)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalarFrac(self: Vector3Int, scalar: i32) Vector3Int {
|
|
||||||
const denominator: @Vector(3, i64) = @splat(std.math.maxInt(i32));
|
|
||||||
const rounding_bias: @Vector(3, i64) = denominator >> @as(@Vector(3, u6), @splat(1));
|
|
||||||
const self_wide: @Vector(3, i64) = self;
|
|
||||||
const scalar_wide: @Vector(3, i64) = @splat(scalar);
|
|
||||||
return .{ .vector = @intCast(@divFloor(self_wide * scalar_wide + rounding_bias, denominator)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalarFracFrac(self: Vector3Int, scalar: i32) Vector3Int {
|
|
||||||
const denominator: @Vector(3, i64) = @splat(std.math.maxInt(i32) * std.math.maxInt(i32));
|
|
||||||
const rounding_bias: @Vector(3, i64) = denominator >> @as(@Vector(3, u6), @splat(1));
|
|
||||||
const self_wide: @Vector(3, i64) = self;
|
|
||||||
const scalar_wide: @Vector(3, i64) = @splat(scalar);
|
|
||||||
return .{ .vector = @intCast(@divFloor(self_wide * scalar_wide + rounding_bias, denominator)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalar(self: Vector3Int, scalar: i32) Vector3Int {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = @divFloor(self.vector, scalar_vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalarFloat(self: Vector3Int, scalar: f32) Vector3Int {
|
|
||||||
const self_float: @Vector(3, f64) = @floatFromInt(self.vector);
|
|
||||||
const scalar_vector_float: @Vector(3, f64) = @splat(scalar);
|
|
||||||
return .{ .vector = @intFromFloat(@round(self_float / scalar_vector_float)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn modScalar(self: Vector3Int, scalar: i32) Vector3Int {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = @mod(self.vector, scalar_vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn abs(self: Vector3Int) Vector3Int {
|
|
||||||
return .{ .vector = @intCast(@abs(self.vector)) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sign(self: Vector3Int) Vector3Int {
|
|
||||||
return .{ .vector = std.math.sign(self.vector) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- SWIZZLE ---
|
|
||||||
|
|
||||||
pub inline fn swizzle2(self: Vector3Int, comptime mask: [2]Mask) Vector2Int {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([2]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn swizzle3(self: Vector3Int, comptime mask: [3]Mask) Vector3Int {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([3]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- OTHER ---
|
|
||||||
|
|
||||||
pub inline fn lenSquared(self: Vector3Int) i64 {
|
|
||||||
const self_wide: @Vector(2, i64) = self.vector;
|
|
||||||
return @reduce(.Add, self_wide * self_wide);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn dot(self: Vector3Int, other: Vector3Int) i64 {
|
|
||||||
const self_wide: @Vector(3, i64) = self.vector;
|
|
||||||
const other_wide: @Vector(3, i64) = other.vector;
|
|
||||||
return @reduce(.Add, self_wide * other_wide);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,166 +0,0 @@
|
|||||||
const std = @import("std");
|
|
||||||
|
|
||||||
const Vector2 = @import("Vector2.zig").Vector2;
|
|
||||||
const Vector3 = @import("Vector3.zig").Vector3;
|
|
||||||
|
|
||||||
pub const Vector4 = extern struct {
|
|
||||||
vector: Vector,
|
|
||||||
|
|
||||||
pub const Vector = @Vector(4, f32);
|
|
||||||
pub const Array = [4]f32;
|
|
||||||
pub const Mask = enum(i32) { x = 0, y = 1, z = 2, w = 3 };
|
|
||||||
|
|
||||||
pub const zero = Vector4.initScalar(0);
|
|
||||||
pub const one = Vector4.initScalar(1);
|
|
||||||
pub const unit_x = Vector4.init(1, 0, 0, 0);
|
|
||||||
pub const unit_y = Vector4.init(0, 1, 0, 0);
|
|
||||||
pub const unit_z = Vector4.init(0, 0, 1, 0);
|
|
||||||
pub const unit_w = Vector4.init(0, 0, 0, 1);
|
|
||||||
pub const unit_nx = Vector4.init(-1, 0, 0, 0);
|
|
||||||
pub const unit_ny = Vector4.init(0, -1, 0, 0);
|
|
||||||
pub const unit_nz = Vector4.init(0, 0, -1, 0);
|
|
||||||
pub const unit_nw = Vector4.init(0, 0, 0, -1);
|
|
||||||
|
|
||||||
// --- INIT ---
|
|
||||||
|
|
||||||
pub inline fn initScalar(scalar: f32) Vector4 {
|
|
||||||
return .{ .vector = @splat(scalar) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn init(x: f32, y: f32, z: f32, w: f32) Vector4 {
|
|
||||||
return .{ .vector = .{ x, y, z, w } };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn initArray(array: Array) Vector4 {
|
|
||||||
return .{ .vector = array };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- CONVERSION ---
|
|
||||||
|
|
||||||
pub inline fn asArray(self: Vector4) Array {
|
|
||||||
return self.vector;
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asArrayNorm(self: Vector4, comptime T: type) [4]T {
|
|
||||||
const scale_vector: Vector = @splat(std.math.maxInt(T));
|
|
||||||
return @as(@Vector(4, T), @intFromFloat(@round(self.vector * scale_vector)));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector2(self: Vector4) Vector2 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, [_]i32{ 0, 1 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn asVector3(self: Vector4) Vector3 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, [_]i32{ 0, 1, 2 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- ACCESSORS ---
|
|
||||||
|
|
||||||
pub inline fn getX(self: Vector4) f32 {
|
|
||||||
return self.vector[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getY(self: Vector4) f32 {
|
|
||||||
return self.vector[1];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getZ(self: Vector4) f32 {
|
|
||||||
return self.vector[2];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn getW(self: Vector4) f32 {
|
|
||||||
return self.vector[3];
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setX(self: Vector4, x: f32) Vector4 {
|
|
||||||
const x_vector: Vector = @splat(x);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, x_vector, [_]i32{ ~@as(i32, 0), 1, 2, 3 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setY(self: Vector4, y: f32) Vector4 {
|
|
||||||
const y_vector: Vector = @splat(y);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, y_vector, [_]i32{ 0, ~@as(i32, 1), 2, 3 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setZ(self: Vector4, z: f32) Vector4 {
|
|
||||||
const z_vector: Vector = @splat(z);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, z_vector, [_]i32{ 0, 1, ~@as(i32, 2), 3 }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn setW(self: Vector4, w: f32) Vector4 {
|
|
||||||
const w_vector: Vector = @splat(w);
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, w_vector, [_]i32{ 0, 1, 2, ~@as(i32, 3) }) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- COMPONENT-WISE ---
|
|
||||||
|
|
||||||
pub inline fn add(self: Vector4, other: Vector4) Vector4 {
|
|
||||||
return .{ .vector = self.vector + other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn sub(self: Vector4, other: Vector4) Vector4 {
|
|
||||||
return .{ .vector = self.vector - other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mul(self: Vector4, other: Vector4) Vector4 {
|
|
||||||
return .{ .vector = self.vector * other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn div(self: Vector4, other: Vector4) Vector4 {
|
|
||||||
return .{ .vector = self.vector / other.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn negate(self: Vector4) Vector4 {
|
|
||||||
return .{ .vector = -self.vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn mulScalar(self: Vector4, scalar: f32) Vector4 {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = self.vector * scalar_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn divScalar(self: Vector4, scalar: f32) Vector4 {
|
|
||||||
const scalar_vector: Vector = @splat(scalar);
|
|
||||||
return .{ .vector = self.vector / scalar_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- SWIZZLE ---
|
|
||||||
|
|
||||||
pub inline fn swizzle2(self: Vector4, comptime mask: [2]Mask) Vector2 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([2]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn swizzle3(self: Vector4, comptime mask: [3]Mask) Vector3 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([3]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn swizzle4(self: Vector4, comptime mask: [4]Mask) Vector4 {
|
|
||||||
return .{ .vector = @shuffle(f32, self.vector, undefined, @as([4]i32, @bitCast(mask))) };
|
|
||||||
}
|
|
||||||
|
|
||||||
// --- OTHER ---
|
|
||||||
|
|
||||||
pub inline fn len(self: Vector4) f32 {
|
|
||||||
return @sqrt(@reduce(.Add, self.vector * self.vector));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lenSquared(self: Vector4) f32 {
|
|
||||||
return @reduce(.Add, self.vector * self.vector);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn normalize(self: Vector4) Vector4 {
|
|
||||||
const len_vector: Vector = @splat(@sqrt(@reduce(.Add, self.vector * self.vector)));
|
|
||||||
return .{ .vector = self.vector / len_vector };
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn dot(self: Vector4, other: Vector4) f32 {
|
|
||||||
return @reduce(.Add, self.vector * other.vector);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub inline fn lerp(self: Vector4, other: Vector4, t: f32) Vector4 {
|
|
||||||
const s = 1.0 - t;
|
|
||||||
const t_vector: Vector = @splat(t);
|
|
||||||
const s_vector: Vector = @splat(s);
|
|
||||||
return .{ .vector = self * s_vector + other * t_vector };
|
|
||||||
}
|
|
||||||
};
|
|
||||||
@@ -1,26 +1,13 @@
|
|||||||
const std = @import("std");
|
const std = @import("std");
|
||||||
const math = @import("../math.zig");
|
const vm = @import("vecmath");
|
||||||
|
|
||||||
const Vector2 = math.Vector2;
|
|
||||||
const Vector2x8 = math.Vector2x8;
|
|
||||||
|
|
||||||
const f32x8 = math.f32x8;
|
|
||||||
const i32x8 = math.i32x8;
|
|
||||||
const u32x8 = math.u32x8;
|
|
||||||
const u64x8 = math.u64x8;
|
|
||||||
|
|
||||||
const ps = math.ps;
|
|
||||||
const epi32 = math.epi32;
|
|
||||||
const epu32 = math.epu32;
|
|
||||||
const epu64x2 = math.epu64x2;
|
|
||||||
|
|
||||||
const prime_x: u64 = 17061574742423305691;
|
const prime_x: u64 = 17061574742423305691;
|
||||||
const prime_y: u64 = 10555943830568207707;
|
const prime_y: u64 = 10555943830568207707;
|
||||||
const prime_perm: u64 = 15540206209889782181;
|
const prime_perm: u64 = 15540206209889782181;
|
||||||
|
|
||||||
const prime_xv: u64x8 = epu64x2(prime_x);
|
const prime_xv: @Vector(8, u64) = @splat(prime_x);
|
||||||
const prime_yv: u64x8 = epu64x2(prime_y);
|
const prime_yv: @Vector(8, u64) = @splat(prime_y);
|
||||||
const prime_permv: u64x8 = epu64x2(prime_perm);
|
const prime_permv: @Vector(8, u64) = @splat(prime_perm);
|
||||||
|
|
||||||
fn perm(seed: u64, x: i32, y: i32) i32 {
|
fn perm(seed: u64, x: i32, y: i32) i32 {
|
||||||
var hash: u64 = seed;
|
var hash: u64 = seed;
|
||||||
@@ -31,13 +18,13 @@ fn perm(seed: u64, x: i32, y: i32) i32 {
|
|||||||
return @bitCast(@as(u32, @truncate(hash)));
|
return @bitCast(@as(u32, @truncate(hash)));
|
||||||
}
|
}
|
||||||
|
|
||||||
fn permv(seed: u64, x: i32x8, y: i32x8) i32x8 {
|
fn permv(seed: u64, x: vm.i32x8, y: vm.i32x8) vm.i32x8 {
|
||||||
var hash: u64x8 = epu64x2(seed);
|
var hash: @Vector(8, u64) = @splat(seed);
|
||||||
hash ^= prime_xv *% @as(u32x8, @bitCast(x));
|
hash ^= prime_xv *% @as(vm.u32x8, @bitCast(x));
|
||||||
hash ^= prime_yv *% @as(u32x8, @bitCast(y));
|
hash ^= prime_yv *% @as(vm.u32x8, @bitCast(y));
|
||||||
hash = hash *% hash *% hash *% prime_permv;
|
hash = hash *% hash *% hash *% prime_permv;
|
||||||
hash = (hash >> @splat(26)) ^ hash;
|
hash = (hash >> @splat(26)) ^ hash;
|
||||||
return @bitCast(@as(u32x8, @truncate(hash)));
|
return @bitCast(@as(vm.u32x8, @truncate(hash)));
|
||||||
}
|
}
|
||||||
|
|
||||||
fn grad2(hash: i32, x: f32, y: f32) f32 {
|
fn grad2(hash: i32, x: f32, y: f32) f32 {
|
||||||
@@ -47,26 +34,26 @@ fn grad2(hash: i32, x: f32, y: f32) f32 {
|
|||||||
return (if (h & 0b001 != 0) -u else u) + (if (h & 0b010 != 0) -2 * v else 2 * v);
|
return (if (h & 0b001 != 0) -u else u) + (if (h & 0b010 != 0) -2 * v else 2 * v);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn grad2x8(hash: i32x8, x: f32x8, y: f32x8) f32x8 {
|
fn grad2x8(hash: vm.i32x8, x: vm.f32x8, y: vm.f32x8) vm.f32x8 {
|
||||||
const h: i32x8 = hash & epi32(0b111);
|
const h: vm.i32x8 = hash & vm.epi32(0b111);
|
||||||
const u: f32x8 = @select(f32, h < epi32(4), x, y);
|
const u: vm.f32x8 = @select(f32, h < vm.epi32(4), x, y);
|
||||||
const v: f32x8 = @select(f32, h < epi32(4), y, x);
|
const v: vm.f32x8 = @select(f32, h < vm.epi32(4), y, x);
|
||||||
const r1: f32x8 = @select(f32, h & epi32(0b001) != epi32(0), -u, u);
|
const r1: vm.f32x8 = @select(f32, h & vm.epi32(0b001) != vm.epi32(0), -u, u);
|
||||||
const r2: f32x8 = @select(f32, h & epi32(0b010) != epi32(0), ps(-2) * v, ps(2) * v);
|
const r2: vm.f32x8 = @select(f32, h & vm.epi32(0b010) != vm.epi32(0), vm.ps(-2) * v, vm.ps(2) * v);
|
||||||
return r1 + r2;
|
return r1 + r2;
|
||||||
}
|
}
|
||||||
|
|
||||||
const F2: f32 = (@sqrt(@as(f32, 3)) - 1) / 2;
|
const F2: f32 = (@sqrt(@as(f32, 3)) - 1) / 2;
|
||||||
const G2: f32 = (3 - @sqrt(@as(f32, 3))) / 6;
|
const G2: f32 = (3 - @sqrt(@as(f32, 3))) / 6;
|
||||||
|
|
||||||
const F2v: f32x8 = ps(F2);
|
const F2v: vm.f32x8 = vm.ps(F2);
|
||||||
const G2v: f32x8 = ps(G2);
|
const G2v: vm.f32x8 = vm.ps(G2);
|
||||||
|
|
||||||
// NOTE No idea why this value, derived experimentally
|
// NOTE No idea why this value, derived experimentally
|
||||||
const noise2_scale: f32 = 34.11;
|
const noise2_scale: f32 = 34.11;
|
||||||
const noise2x8_scale: f32x8 = ps(noise2_scale);
|
const noise2x8_scale: vm.f32x8 = vm.ps(noise2_scale);
|
||||||
|
|
||||||
pub fn noise2(seed: u64, v: Vector2) f32 {
|
pub fn noise2(seed: u64, v: vm.Vector2) f32 {
|
||||||
const x: f32, const y: f32 = v.asArray();
|
const x: f32, const y: f32 = v.asArray();
|
||||||
|
|
||||||
const s: f32 = (x + y) * F2;
|
const s: f32 = (x + y) * F2;
|
||||||
@@ -106,43 +93,43 @@ pub fn noise2(seed: u64, v: Vector2) f32 {
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn noise2x8(seed: u64, v: Vector2x8) f32x8 {
|
pub fn noise2x8(seed: u64, v: vm.Vector2x8) vm.f32x8 {
|
||||||
const x: f32x8 = v.x;
|
const x: vm.f32x8 = v.x;
|
||||||
const y: f32x8 = v.y;
|
const y: vm.f32x8 = v.y;
|
||||||
|
|
||||||
const s: f32x8 = (x + y) * F2v;
|
const s: vm.f32x8 = (x + y) * F2v;
|
||||||
const xs: f32x8 = x + s;
|
const xs: vm.f32x8 = x + s;
|
||||||
const ys: f32x8 = y + s;
|
const ys: vm.f32x8 = y + s;
|
||||||
const i: i32x8 = @intFromFloat(@floor(xs));
|
const i: vm.i32x8 = @intFromFloat(@floor(xs));
|
||||||
const j: i32x8 = @intFromFloat(@floor(ys));
|
const j: vm.i32x8 = @intFromFloat(@floor(ys));
|
||||||
|
|
||||||
const t: f32x8 = @as(f32x8, @floatFromInt(i + j)) * G2v;
|
const t: vm.f32x8 = @as(vm.f32x8, @floatFromInt(i + j)) * G2v;
|
||||||
const X0: f32x8 = @as(f32x8, @floatFromInt(i)) - t;
|
const X0: vm.f32x8 = @as(vm.f32x8, @floatFromInt(i)) - t;
|
||||||
const Y0: f32x8 = @as(f32x8, @floatFromInt(j)) - t;
|
const Y0: vm.f32x8 = @as(vm.f32x8, @floatFromInt(j)) - t;
|
||||||
const x0: f32x8 = x - X0;
|
const x0: vm.f32x8 = x - X0;
|
||||||
const y0: f32x8 = y - Y0;
|
const y0: vm.f32x8 = y - Y0;
|
||||||
|
|
||||||
const _i1: i32x8 = @select(i32, x0 > y0, epi32(1), epi32(0));
|
const _i1: vm.i32x8 = @select(i32, x0 > y0, vm.epi32(1), vm.epi32(0));
|
||||||
const _j1: i32x8 = @select(i32, x0 > y0, epi32(0), epi32(1));
|
const _j1: vm.i32x8 = @select(i32, x0 > y0, vm.epi32(0), vm.epi32(1));
|
||||||
|
|
||||||
const x1: f32x8 = x0 - @as(f32x8, @floatFromInt(_i1)) + G2v;
|
const x1: vm.f32x8 = x0 - @as(vm.f32x8, @floatFromInt(_i1)) + G2v;
|
||||||
const y1: f32x8 = y0 - @as(f32x8, @floatFromInt(_j1)) + G2v;
|
const y1: vm.f32x8 = y0 - @as(vm.f32x8, @floatFromInt(_j1)) + G2v;
|
||||||
const x2: f32x8 = x0 - ps(1) + ps(2) * G2v;
|
const x2: vm.f32x8 = x0 - vm.ps(1) + vm.ps(2) * G2v;
|
||||||
const y2: f32x8 = y0 - ps(1) + ps(2) * G2v;
|
const y2: vm.f32x8 = y0 - vm.ps(1) + vm.ps(2) * G2v;
|
||||||
|
|
||||||
const t0: f32x8 = ps(0.5) - x0 * x0 - y0 * y0;
|
const t0: vm.f32x8 = vm.ps(0.5) - x0 * x0 - y0 * y0;
|
||||||
const t1: f32x8 = ps(0.5) - x1 * x1 - y1 * y1;
|
const t1: vm.f32x8 = vm.ps(0.5) - x1 * x1 - y1 * y1;
|
||||||
const t2: f32x8 = ps(0.5) - x2 * x2 - y2 * y2;
|
const t2: vm.f32x8 = vm.ps(0.5) - x2 * x2 - y2 * y2;
|
||||||
|
|
||||||
const gi0: i32x8 = permv(seed, i, j);
|
const gi0: vm.i32x8 = permv(seed, i, j);
|
||||||
const gi1: i32x8 = permv(seed, i + _i1, j + _j1);
|
const gi1: vm.i32x8 = permv(seed, i + _i1, j + _j1);
|
||||||
const gi2: i32x8 = permv(seed, i + epi32(1), j + epi32(1));
|
const gi2: vm.i32x8 = permv(seed, i + vm.epi32(1), j + vm.epi32(1));
|
||||||
|
|
||||||
const n0: f32x8 = @select(f32, t0 < ps(0), ps(0), (t0 * t0) * (t0 * t0) * grad2x8(gi0, x0, y0));
|
const n0: vm.f32x8 = @select(f32, t0 < vm.ps(0), vm.ps(0), (t0 * t0) * (t0 * t0) * grad2x8(gi0, x0, y0));
|
||||||
const n1: f32x8 = @select(f32, t1 < ps(0), ps(0), (t1 * t1) * (t1 * t1) * grad2x8(gi1, x1, y1));
|
const n1: vm.f32x8 = @select(f32, t1 < vm.ps(0), vm.ps(0), (t1 * t1) * (t1 * t1) * grad2x8(gi1, x1, y1));
|
||||||
const n2: f32x8 = @select(f32, t2 < ps(0), ps(0), (t2 * t2) * (t2 * t2) * grad2x8(gi2, x2, y2));
|
const n2: vm.f32x8 = @select(f32, t2 < vm.ps(0), vm.ps(0), (t2 * t2) * (t2 * t2) * grad2x8(gi2, x2, y2));
|
||||||
|
|
||||||
const ret: f32x8 = noise2x8_scale * (n0 + n1 + n2);
|
const ret: vm.f32x8 = noise2x8_scale * (n0 + n1 + n2);
|
||||||
std.debug.assert(@reduce(.And, ret >= ps(-1)) and @reduce(.And, ret <= ps(1)));
|
std.debug.assert(@reduce(.And, (ret >= vm.ps(-1)) & (ret <= vm.ps(1))));
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,12 +1,9 @@
|
|||||||
const math = @import("math.zig");
|
const std = @import("std");
|
||||||
|
const vm = @import("vecmath");
|
||||||
|
|
||||||
const Materials = @import("assets/Materials.zig");
|
const Materials = @import("assets/Materials.zig");
|
||||||
const Matrix4x4 = math.Matrix4x4;
|
|
||||||
const GenericBuffer = @import("engine/GenericBuffer.zig").GenericBuffer;
|
const GenericBuffer = @import("engine/GenericBuffer.zig").GenericBuffer;
|
||||||
const Textures = @import("assets/Textures.zig");
|
const Textures = @import("assets/Textures.zig");
|
||||||
const Vector2 = math.Vector2;
|
|
||||||
const Vector3 = math.Vector3;
|
|
||||||
const Vector4 = math.Vector4;
|
|
||||||
|
|
||||||
pub const VertexBuffer = GenericBuffer(void, Vertex);
|
pub const VertexBuffer = GenericBuffer(void, Vertex);
|
||||||
pub const IndexBuffer = GenericBuffer(void, Index);
|
pub const IndexBuffer = GenericBuffer(void, Index);
|
||||||
@@ -17,17 +14,29 @@ pub const MaterialBuffer = GenericBuffer(void, Material);
|
|||||||
pub const ObjectUniformsBuffer = GenericBuffer(void, ObjectUniforms);
|
pub const ObjectUniformsBuffer = GenericBuffer(void, ObjectUniforms);
|
||||||
|
|
||||||
pub const Vertex = extern struct {
|
pub const Vertex = extern struct {
|
||||||
positionOS: [3]f32,
|
positionOS: vm.Vector3,
|
||||||
texCoord: [2]u16,
|
texCoord: [2]u16,
|
||||||
normalOS: [3]i8,
|
normalOS: [3]i8,
|
||||||
tangentOS: [4]i8,
|
tangentOS: [4]i8,
|
||||||
|
|
||||||
pub fn init(position_os: Vector3, tex_coord: Vector2, normal_os: Vector3, tangent_os: Vector4) Vertex {
|
pub fn init(position_os: vm.Vector3, tex_coord: vm.Vector2, normal_os: vm.Vector3, tangent_os: vm.Vector4) Vertex {
|
||||||
return .{
|
return .{
|
||||||
.positionOS = position_os.asArray(),
|
.positionOS = position_os,
|
||||||
.texCoord = tex_coord.asArrayNorm(u16),
|
.texCoord = [_]u16{
|
||||||
.normalOS = normal_os.asArrayNorm(i8),
|
@intFromFloat(@round(tex_coord.x * std.math.maxInt(u16))),
|
||||||
.tangentOS = tangent_os.asArrayNorm(i8),
|
@intFromFloat(@round(tex_coord.y * std.math.maxInt(u16))),
|
||||||
|
},
|
||||||
|
.normalOS = [_]i8{
|
||||||
|
@intFromFloat(@round(normal_os.x * std.math.maxInt(i8))),
|
||||||
|
@intFromFloat(@round(normal_os.y * std.math.maxInt(i8))),
|
||||||
|
@intFromFloat(@round(normal_os.z * std.math.maxInt(i8))),
|
||||||
|
},
|
||||||
|
.tangentOS = [_]i8{
|
||||||
|
@intFromFloat(@round(tangent_os.x * std.math.maxInt(i8))),
|
||||||
|
@intFromFloat(@round(tangent_os.y * std.math.maxInt(i8))),
|
||||||
|
@intFromFloat(@round(tangent_os.z * std.math.maxInt(i8))),
|
||||||
|
@intFromFloat(@round(tangent_os.w * std.math.maxInt(i8))),
|
||||||
|
},
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@@ -35,46 +44,38 @@ pub const Vertex = extern struct {
|
|||||||
pub const Index = u16;
|
pub const Index = u16;
|
||||||
|
|
||||||
pub const GlobalUniforms = extern struct {
|
pub const GlobalUniforms = extern struct {
|
||||||
matrixWStoVS: [16]f32,
|
matrixWStoVS: vm.Matrix4x4,
|
||||||
matrixVStoCS: [16]f32,
|
matrixVStoCS: vm.Matrix4x4,
|
||||||
ambientLight: [3]f32,
|
ambientLight: vm.Vector3,
|
||||||
|
|
||||||
pub fn init(matrix_ws_to_vs: Matrix4x4, matrix_vs_to_cs: Matrix4x4, ambient_light: Vector3) GlobalUniforms {
|
|
||||||
return .{
|
|
||||||
.matrixWStoVS = matrix_ws_to_vs.asArray(),
|
|
||||||
.matrixVStoCS = matrix_vs_to_cs.asArray(),
|
|
||||||
.ambientLight = ambient_light.asArray(),
|
|
||||||
};
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const PointLight = extern struct {
|
pub const PointLight = extern struct {
|
||||||
positionWS: [3]f32,
|
positionWS: vm.Vector3,
|
||||||
color: [3]f32,
|
color: vm.Vector3,
|
||||||
|
|
||||||
pub fn init(position_ws: Vector3, color: Vector3) PointLight {
|
pub fn init(position_ws: vm.Vector3, color: vm.Vector3) PointLight {
|
||||||
return .{
|
return .{
|
||||||
.positionWS = position_ws.asArray(),
|
.positionWS = position_ws,
|
||||||
.color = color.asArray(),
|
.color = color,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const DirectionalLight = extern struct {
|
pub const DirectionalLight = extern struct {
|
||||||
directionWS: [3]f32,
|
directionWS: vm.Vector3,
|
||||||
color: [3]f32,
|
color: vm.Vector3,
|
||||||
|
|
||||||
pub fn init(direction_ws: Vector3, color: Vector3) DirectionalLight {
|
pub fn init(direction_ws: vm.Vector3, color: vm.Vector3) DirectionalLight {
|
||||||
return .{
|
return .{
|
||||||
.directionWS = direction_ws.asArray(),
|
.directionWS = direction_ws,
|
||||||
.color = color.asArray(),
|
.color = color,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const Material = extern struct {
|
pub const Material = extern struct {
|
||||||
base_color: [3]f32,
|
base_color: vm.Vector3,
|
||||||
emissive: [3]f32,
|
emissive: vm.Vector3,
|
||||||
ior: f32,
|
ior: f32,
|
||||||
metallic: f32,
|
metallic: f32,
|
||||||
normal_scale: f32,
|
normal_scale: f32,
|
||||||
@@ -88,18 +89,10 @@ pub const Material = extern struct {
|
|||||||
};
|
};
|
||||||
|
|
||||||
pub const ObjectUniforms = extern struct {
|
pub const ObjectUniforms = extern struct {
|
||||||
matrixOStoWS: [16]f32,
|
matrixOStoWS: vm.Matrix4x4,
|
||||||
matrixOStoWSNormal: [16]f32,
|
matrixOStoWSNormal: vm.Matrix4x4,
|
||||||
|
|
||||||
material: Materials.Id,
|
material: Materials.Id,
|
||||||
|
|
||||||
pub fn init(matrix_os_to_ws: Matrix4x4, matrix_ow_to_ws_normal: Matrix4x4, material: Materials.Id) ObjectUniforms {
|
|
||||||
return .{
|
|
||||||
.matrixOStoWS = matrix_os_to_ws.asArray(),
|
|
||||||
.matrixOStoWSNormal = matrix_ow_to_ws_normal.asArray(),
|
|
||||||
.material = material,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
pub const equirect_to_cube_comp_spv align(4) = @embedFile("shaders/equirect_to_cube_comp.spv").*;
|
pub const equirect_to_cube_comp_spv align(4) = @embedFile("shaders/equirect_to_cube_comp.spv").*;
|
||||||
|
|||||||
@@ -1,25 +1,19 @@
|
|||||||
const std = @import("std");
|
const std = @import("std");
|
||||||
|
|
||||||
const math = @import("math.zig");
|
const math = @import("math.zig");
|
||||||
|
const vm = @import("vecmath");
|
||||||
const Vector2 = math.Vector2;
|
|
||||||
const Vector2x8 = math.Vector2x8;
|
|
||||||
|
|
||||||
const f32x8 = math.f32x8;
|
|
||||||
const i32x8 = math.i32x8;
|
|
||||||
|
|
||||||
const ps = math.ps;
|
|
||||||
|
|
||||||
const Noise = struct {
|
const Noise = struct {
|
||||||
horizontal_scale: f32,
|
horizontal_scale: f32,
|
||||||
value_median: f32,
|
value_median: f32,
|
||||||
value_amplitude: f32,
|
value_amplitude: f32,
|
||||||
|
|
||||||
pub fn sample(self: Noise, seed: u64, pos: Vector2) f32 {
|
pub fn sample(self: Noise, seed: u64, pos: vm.Vector2) f32 {
|
||||||
return math.noise2(seed, pos.divScalar(self.horizontal_scale)) * self.value_amplitude + self.value_median;
|
return math.noise2(seed, pos.divScalar(self.horizontal_scale)) * self.value_amplitude + self.value_median;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn samplev(self: Noise, seed: u64, pos: Vector2x8) f32x8 {
|
pub fn samplev(self: Noise, seed: u64, pos: vm.Vector2x8) vm.f32x8 {
|
||||||
return math.noise2x8(seed, pos.divScalar(self.horizontal_scale)) * ps(self.value_amplitude) + ps(self.value_median);
|
return math.noise2x8(seed, pos.divScalarSingle(self.horizontal_scale)) * vm.ps(self.value_amplitude) + vm.ps(self.value_median);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -35,22 +29,22 @@ const noise_secondary: Noise = .{
|
|||||||
.value_amplitude = 0.5,
|
.value_amplitude = 0.5,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub fn heightF(seed: u64, pos: Vector2) f32 {
|
pub fn heightF(seed: u64, pos: vm.Vector2) f32 {
|
||||||
const main = noise_main.sample(seed, pos);
|
const main = noise_main.sample(seed, pos);
|
||||||
const secondary = noise_secondary.sample(seed, pos);
|
const secondary = noise_secondary.sample(seed, pos);
|
||||||
return @round(main + secondary);
|
return @round(main + secondary);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn heightFv(seed: u64, pos: Vector2x8) f32x8 {
|
pub fn heightFv(seed: u64, pos: vm.Vector2x8) vm.f32x8 {
|
||||||
const main = noise_main.samplev(seed, pos);
|
const main = noise_main.samplev(seed, pos);
|
||||||
const secondary = noise_secondary.samplev(seed, pos);
|
const secondary = noise_secondary.samplev(seed, pos);
|
||||||
return @round(main + secondary);
|
return @round(main + secondary);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn heightI(seed: u64, pos: Vector2) i32 {
|
pub fn heightI(seed: u64, pos: vm.Vector2) i32 {
|
||||||
return @intFromFloat(heightF(seed, pos));
|
return @intFromFloat(heightF(seed, pos));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn heightIv(seed: u64, pos: Vector2x8) i32x8 {
|
pub fn heightIv(seed: u64, pos: vm.Vector2x8) vm.i32x8 {
|
||||||
return @intFromFloat(heightFv(seed, pos));
|
return @intFromFloat(heightFv(seed, pos));
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user