Eliminate opposing walls
This commit is contained in:
61
src/Game.zig
61
src/Game.zig
@@ -15,7 +15,7 @@ const Engine = @import("engine/Engine.zig");
|
|||||||
const GenericBuffer = @import("engine/GenericBuffer.zig").GenericBuffer;
|
const GenericBuffer = @import("engine/GenericBuffer.zig").GenericBuffer;
|
||||||
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 Iterator3 = math.Iterator3;
|
const Interator3 = math.Interator3;
|
||||||
const Matrix4x4 = math.Matrix4x4;
|
const Matrix4x4 = math.Matrix4x4;
|
||||||
const Quaternion = math.Quaternion;
|
const Quaternion = math.Quaternion;
|
||||||
const Vector2 = math.Vector2;
|
const Vector2 = math.Vector2;
|
||||||
@@ -117,7 +117,7 @@ index_buffer: IndexBuffer,
|
|||||||
|
|
||||||
global_uniforms: GlobalUniformsBuffer,
|
global_uniforms: GlobalUniformsBuffer,
|
||||||
global_uniforms_staging_buffer: StagingBuffer,
|
global_uniforms_staging_buffer: StagingBuffer,
|
||||||
global_uniforms_transfer_command_buffer: CommandBuffer(.graphics, .persistent),
|
global_uniforms_transfer_command_buffer: CommandBuffer(.transfer, .persistent),
|
||||||
global_uniforms_transfer_semaphores: []vk.Semaphore,
|
global_uniforms_transfer_semaphores: []vk.Semaphore,
|
||||||
point_lights: PointLightBuffer,
|
point_lights: PointLightBuffer,
|
||||||
directional_lights: DirectionalLightBuffer,
|
directional_lights: DirectionalLightBuffer,
|
||||||
@@ -126,7 +126,7 @@ sampler: vk.Sampler,
|
|||||||
blocks: Blocks,
|
blocks: Blocks,
|
||||||
materials: Materials,
|
materials: Materials,
|
||||||
textures: Textures,
|
textures: Textures,
|
||||||
chunks: std.ArrayList(Chunk),
|
chunks: std.AutoHashMapUnmanaged([3]i16, Chunk),
|
||||||
|
|
||||||
camera_position: Vector3 = .init(0, 0, 1.62),
|
camera_position: Vector3 = .init(0, 0, 1.62),
|
||||||
camera_pitch: f32 = 0,
|
camera_pitch: f32 = 0,
|
||||||
@@ -142,7 +142,7 @@ input_down: bool = false,
|
|||||||
const max_textures = 1024;
|
const max_textures = 1024;
|
||||||
const max_point_lights = 1024;
|
const max_point_lights = 1024;
|
||||||
const max_directional_lights = 4;
|
const max_directional_lights = 4;
|
||||||
const max_objects = 1024;
|
const chunk_descriptor_pool = 512;
|
||||||
|
|
||||||
const camera_near_plane = 0.1;
|
const camera_near_plane = 0.1;
|
||||||
const camera_vertical_fov_deg = 80.0;
|
const camera_vertical_fov_deg = 80.0;
|
||||||
@@ -318,7 +318,7 @@ pub fn init(allocator: std.mem.Allocator, engine: *Engine, swapchain: *Swapchain
|
|||||||
});
|
});
|
||||||
errdefer global_uniforms_staging_buffer.deinit(engine);
|
errdefer global_uniforms_staging_buffer.deinit(engine);
|
||||||
|
|
||||||
var global_uniforms_transfer_command_buffer: CommandBuffer(.graphics, .persistent) = try .init(engine);
|
var global_uniforms_transfer_command_buffer: CommandBuffer(.transfer, .persistent) = try .init(engine);
|
||||||
errdefer global_uniforms_transfer_command_buffer.deinit(engine);
|
errdefer global_uniforms_transfer_command_buffer.deinit(engine);
|
||||||
|
|
||||||
try global_uniforms_transfer_command_buffer.beginCommandBuffer(.{});
|
try global_uniforms_transfer_command_buffer.beginCommandBuffer(.{});
|
||||||
@@ -491,7 +491,7 @@ pub fn init(allocator: std.mem.Allocator, engine: *Engine, swapchain: *Swapchain
|
|||||||
engine.setObjectName(pipeline, "P", .{});
|
engine.setObjectName(pipeline, "P", .{});
|
||||||
|
|
||||||
const descriptor_pool = try engine.createDescriptorPool(.{
|
const descriptor_pool = try engine.createDescriptorPool(.{
|
||||||
.max_sets = 1 + 256,
|
.max_sets = 1 + chunk_descriptor_pool,
|
||||||
.pool_sizes = &.{
|
.pool_sizes = &.{
|
||||||
.{
|
.{
|
||||||
.type = .sampler,
|
.type = .sampler,
|
||||||
@@ -507,7 +507,7 @@ pub fn init(allocator: std.mem.Allocator, engine: *Engine, swapchain: *Swapchain
|
|||||||
},
|
},
|
||||||
.{
|
.{
|
||||||
.type = .storage_buffer,
|
.type = .storage_buffer,
|
||||||
.descriptor_count = 3 + 256,
|
.descriptor_count = 3 + chunk_descriptor_pool,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
@@ -603,33 +603,51 @@ pub fn init(allocator: std.mem.Allocator, engine: *Engine, swapchain: *Swapchain
|
|||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
var chunks: std.ArrayList(Chunk) = .empty;
|
var chunks: std.AutoHashMapUnmanaged([3]i16, Chunk) = .empty;
|
||||||
errdefer {
|
errdefer {
|
||||||
for (chunks.items) |*chunk| {
|
var it = chunks.valueIterator();
|
||||||
|
while (it.next()) |chunk| {
|
||||||
chunk.deinit(engine, descriptor_pool);
|
chunk.deinit(engine, descriptor_pool);
|
||||||
}
|
}
|
||||||
chunks.deinit(allocator);
|
chunks.deinit(allocator);
|
||||||
}
|
}
|
||||||
|
|
||||||
var it: Iterator3 = .init(.init(-64, -64, 0), .init(64, 64, 0), .init(16, 16, 16));
|
var it = Interator3(i16).init(-10, -10, 0, 9, 9, 0);
|
||||||
while (it.next()) |origin| {
|
while (it.next()) |chunk_coords| {
|
||||||
|
const origin = Vector3.init(
|
||||||
|
@floatFromInt(chunk_coords[0]),
|
||||||
|
@floatFromInt(chunk_coords[1]),
|
||||||
|
@floatFromInt(chunk_coords[2]),
|
||||||
|
).mulScalar(16);
|
||||||
|
|
||||||
try chunks.ensureUnusedCapacity(allocator, 1);
|
try chunks.ensureUnusedCapacity(allocator, 1);
|
||||||
chunks.appendAssumeCapacity(try Chunk.init(engine, .{
|
chunks.putAssumeCapacityNoClobber(chunk_coords, try Chunk.init(engine, .{
|
||||||
.origin = origin,
|
.origin = origin,
|
||||||
.descriptor_pool = descriptor_pool,
|
.descriptor_pool = descriptor_pool,
|
||||||
.per_batch_descriptor_set_layout = per_batch_descriptor_set_layout,
|
.per_batch_descriptor_set_layout = per_batch_descriptor_set_layout,
|
||||||
}));
|
}));
|
||||||
|
const chunk = chunks.getPtr(chunk_coords).?;
|
||||||
|
|
||||||
const chunk = &chunks.items[chunks.items.len - 1];
|
var it2 = Interator3(usize).init(0, 0, 0, 15, 15, 0);
|
||||||
|
while (it2.next()) |pos| {
|
||||||
var it2 = Iterator3.init(.init(0, 0, 0), .init(1, 1, 0), .{ .vector = @splat(1.0 / 16.0) });
|
const x, const y, const z = pos;
|
||||||
while (it2.next()) |fpos| {
|
|
||||||
const x, const y, const z = fpos.asArrayNorm(u4);
|
|
||||||
const block: Blocks.Id = @enumFromInt(engine.random.intRangeLessThan(u12, 1, @intCast(blocks.blocks.items.len)));
|
const block: Blocks.Id = @enumFromInt(engine.random.intRangeLessThan(u12, 1, @intCast(blocks.blocks.items.len)));
|
||||||
chunk.blocks[z][y][x] = block;
|
chunk.blocks[z][y][x] = block;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
try chunk.refresh(engine, &blocks, allocator);
|
var chunk_it = chunks.iterator();
|
||||||
|
while (chunk_it.next()) |entry| {
|
||||||
|
const x, const y, const z = entry.key_ptr.*;
|
||||||
|
const chunk = entry.value_ptr;
|
||||||
|
try chunk.refresh(engine, &blocks, .{
|
||||||
|
.positive_x = chunks.getPtr(.{ x + 1, y, z }),
|
||||||
|
.negative_x = chunks.getPtr(.{ x - 1, y, z }),
|
||||||
|
.positive_y = chunks.getPtr(.{ x, y + 1, z }),
|
||||||
|
.negative_y = chunks.getPtr(.{ x, y - 1, z }),
|
||||||
|
.positive_z = chunks.getPtr(.{ x, y, z + 1 }),
|
||||||
|
.negative_z = chunks.getPtr(.{ x, y, z - 1 }),
|
||||||
|
}, allocator);
|
||||||
}
|
}
|
||||||
|
|
||||||
const point_lights_data: []const PointLight = &.{};
|
const point_lights_data: []const PointLight = &.{};
|
||||||
@@ -683,7 +701,9 @@ pub fn deinit(self: *Game) void {
|
|||||||
|
|
||||||
self.vertex_buffer.deinit(self.engine);
|
self.vertex_buffer.deinit(self.engine);
|
||||||
self.index_buffer.deinit(self.engine);
|
self.index_buffer.deinit(self.engine);
|
||||||
for (self.chunks.items) |*chunk| {
|
|
||||||
|
var it = self.chunks.valueIterator();
|
||||||
|
while (it.next()) |chunk| {
|
||||||
chunk.deinit(self.engine, self.descriptor_pool);
|
chunk.deinit(self.engine, self.descriptor_pool);
|
||||||
}
|
}
|
||||||
self.chunks.deinit(self.allocator);
|
self.chunks.deinit(self.allocator);
|
||||||
@@ -916,7 +936,8 @@ fn render(self: *Game) !void {
|
|||||||
command_buffer.bindIndexBuffer(self.index_buffer.buffer, 0, .uint16);
|
command_buffer.bindIndexBuffer(self.index_buffer.buffer, 0, .uint16);
|
||||||
command_buffer.bindDescriptorSet(.graphics, self.pipeline_layout, 0, self.global_descriptor_set, null);
|
command_buffer.bindDescriptorSet(.graphics, self.pipeline_layout, 0, self.global_descriptor_set, null);
|
||||||
|
|
||||||
for (self.chunks.items) |chunk| {
|
var it = self.chunks.valueIterator();
|
||||||
|
while (it.next()) |chunk| {
|
||||||
chunk.draw(self.pipeline_layout, command_buffer);
|
chunk.draw(self.pipeline_layout, command_buffer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,8 @@ const CommandBuffer = @import("../engine/CommandBuffer.zig").CommandBuffer;
|
|||||||
const Engine = @import("../engine/Engine.zig");
|
const Engine = @import("../engine/Engine.zig");
|
||||||
const Game = @import("../Game.zig");
|
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 Orientation = @import("../voxel.zig").Orientation;
|
||||||
|
|
||||||
const Matrix4x4 = math.Matrix4x4;
|
const Matrix4x4 = math.Matrix4x4;
|
||||||
const ObjectUniformsBuffer = GenericBuffer(void, Game.ObjectUniforms);
|
const ObjectUniformsBuffer = GenericBuffer(void, Game.ObjectUniforms);
|
||||||
@@ -20,11 +22,15 @@ pub const chunk_size = 16;
|
|||||||
const initial_capacity = 256;
|
const initial_capacity = 256;
|
||||||
var next_chunk_id: std.atomic.Value(u64) = .init(0);
|
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
|
||||||
|
/// 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: Vector3,
|
||||||
descriptor_set: vk.DescriptorSet,
|
descriptor_set: vk.DescriptorSet,
|
||||||
object_buffer: ObjectUniformsBuffer,
|
object_buffer: ObjectUniformsBuffer,
|
||||||
object_count: u32,
|
object_count: u32,
|
||||||
|
|
||||||
|
/// For debug purposes, a unique "name" per chunk instance.
|
||||||
chunk_id: u64,
|
chunk_id: u64,
|
||||||
|
|
||||||
pub const InitInfo = struct {
|
pub const InitInfo = struct {
|
||||||
@@ -33,6 +39,15 @@ pub const InitInfo = struct {
|
|||||||
per_batch_descriptor_set_layout: vk.DescriptorSetLayout,
|
per_batch_descriptor_set_layout: vk.DescriptorSetLayout,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
pub const Neighbors = struct {
|
||||||
|
positive_x: ?*const Chunk,
|
||||||
|
negative_x: ?*const Chunk,
|
||||||
|
positive_y: ?*const Chunk,
|
||||||
|
negative_y: ?*const Chunk,
|
||||||
|
positive_z: ?*const Chunk,
|
||||||
|
negative_z: ?*const Chunk,
|
||||||
|
};
|
||||||
|
|
||||||
pub fn init(engine: *Engine, init_info: InitInfo) !Chunk {
|
pub fn init(engine: *Engine, init_info: InitInfo) !Chunk {
|
||||||
const descriptor_set = try engine.allocateDescriptorSet(.{
|
const descriptor_set = try engine.allocateDescriptorSet(.{
|
||||||
.descriptor_pool = init_info.descriptor_pool,
|
.descriptor_pool = init_info.descriptor_pool,
|
||||||
@@ -89,23 +104,97 @@ pub fn deinit(self: *Chunk, engine: *Engine, descriptor_pool: vk.DescriptorPool)
|
|||||||
self.* = undefined;
|
self.* = undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn refresh(self: *Chunk, engine: *Engine, blocks: *const Blocks, temp_allocator: std.mem.Allocator) !void {
|
pub fn refresh(self: *Chunk, engine: *Engine, blocks: *const Blocks, neighbors: Neighbors, temp_allocator: std.mem.Allocator) !void {
|
||||||
var object_count: u32 = 0;
|
var uniforms: std.ArrayList(Game.ObjectUniforms) = try .initCapacity(temp_allocator, initial_capacity);
|
||||||
|
defer uniforms.deinit(temp_allocator);
|
||||||
|
|
||||||
for (self.blocks) |plane| {
|
for (self.blocks, 0..) |plane, iz| {
|
||||||
for (plane) |row| {
|
const fz: f32 = @floatFromInt(iz);
|
||||||
for (row) |id| {
|
for (plane, 0..) |row, iy| {
|
||||||
|
const fy: f32 = @floatFromInt(iy);
|
||||||
|
for (row, 0..) |id, ix| {
|
||||||
|
const fx: f32 = @floatFromInt(ix);
|
||||||
const block = blocks.getBlock(id).?;
|
const block = blocks.getBlock(id).?;
|
||||||
object_count += @intFromBool(block.positive_x != .empty);
|
|
||||||
object_count += @intFromBool(block.negative_x != .empty);
|
const center = Vector3.add(self.origin, .init(fx, fy, fz));
|
||||||
object_count += @intFromBool(block.positive_y != .empty);
|
const cx, const cy, const cz = center.asArray();
|
||||||
object_count += @intFromBool(block.negative_y != .empty);
|
|
||||||
object_count += @intFromBool(block.positive_z != .empty);
|
if (block.positive_x != .empty and self.getOpposite(.positive_x, ix, iy, iz, blocks, neighbors) == .empty) {
|
||||||
object_count += @intFromBool(block.negative_z != .empty);
|
// zig fmt: off
|
||||||
|
const matrix: Matrix4x4 = .init(
|
||||||
|
0, 1, 0, 0,
|
||||||
|
0, 0, 1, 0,
|
||||||
|
1, 0, 0, 0,
|
||||||
|
cx + 0.5, cy, cz, 1,
|
||||||
|
);
|
||||||
|
// zig fmt: on
|
||||||
|
try uniforms.append(temp_allocator, .init(matrix, matrix, block.positive_x));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (block.negative_x != .empty and self.getOpposite(.negative_x, ix, iy, iz, blocks, neighbors) == .empty) {
|
||||||
|
// zig fmt: off
|
||||||
|
const matrix: Matrix4x4 = .init(
|
||||||
|
0, -1, 0, 0,
|
||||||
|
0, 0, 1, 0,
|
||||||
|
-1, 0, 0, 0,
|
||||||
|
cx - 0.5, cy, cz, 1,
|
||||||
|
);
|
||||||
|
// zig fmt: on
|
||||||
|
try uniforms.append(temp_allocator, .init(matrix, matrix, block.negative_x));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (block.positive_y != .empty and self.getOpposite(.positive_y, ix, iy, iz, blocks, neighbors) == .empty) {
|
||||||
|
// zig fmt: off
|
||||||
|
const matrix: Matrix4x4 = .init(
|
||||||
|
-1, 0, 0, 0,
|
||||||
|
0, 0, 1, 0,
|
||||||
|
0, 1, 0, 0,
|
||||||
|
cx, cy + 0.5, cz, 1,
|
||||||
|
);
|
||||||
|
// zig fmt: on
|
||||||
|
try uniforms.append(temp_allocator, .init(matrix, matrix, block.positive_y));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (block.negative_y != .empty and self.getOpposite(.negative_y, ix, iy, iz, blocks, neighbors) == .empty) {
|
||||||
|
// zig fmt: off
|
||||||
|
const matrix: Matrix4x4 = .init(
|
||||||
|
1, 0, 0, 0,
|
||||||
|
0, 0, 1, 0,
|
||||||
|
0, -1, 0, 0,
|
||||||
|
cx, cy - 0.5, cz, 1,
|
||||||
|
);
|
||||||
|
// zig fmt: on
|
||||||
|
try uniforms.append(temp_allocator, .init(matrix, matrix, block.negative_y));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (block.positive_z != .empty and self.getOpposite(.positive_z, ix, iy, iz, blocks, neighbors) == .empty) {
|
||||||
|
// zig fmt: off
|
||||||
|
const matrix: Matrix4x4 = .init(
|
||||||
|
1, 0, 0, 0,
|
||||||
|
0, 1, 0, 0,
|
||||||
|
0, 0, 1, 0,
|
||||||
|
cx, cy, cz + 0.5, 1,
|
||||||
|
);
|
||||||
|
// zig fmt: on
|
||||||
|
try uniforms.append(temp_allocator, .init(matrix, matrix, block.positive_z));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (block.negative_z != .empty and self.getOpposite(.negative_z, ix, iy, iz, blocks, neighbors) == .empty) {
|
||||||
|
// zig fmt: off
|
||||||
|
const matrix: Matrix4x4 = .init(
|
||||||
|
1, 0, 0, 0,
|
||||||
|
0, -1, 0, 0,
|
||||||
|
0, 0, -1, 0,
|
||||||
|
cx, cy, cz - 0.5, 1,
|
||||||
|
);
|
||||||
|
// zig fmt: on
|
||||||
|
try uniforms.append(temp_allocator, .init(matrix, matrix, block.negative_z));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const object_count: u32 = @intCast(uniforms.items.len);
|
||||||
if (self.object_buffer.array_capacity < object_count) {
|
if (self.object_buffer.array_capacity < object_count) {
|
||||||
const desired_capacity = std.math.ceilPowerOfTwoAssert(u32, object_count);
|
const desired_capacity = std.math.ceilPowerOfTwoAssert(u32, object_count);
|
||||||
const new_object_buffer: ObjectUniformsBuffer = try .init(engine, .{
|
const new_object_buffer: ObjectUniformsBuffer = try .init(engine, .{
|
||||||
@@ -140,105 +229,7 @@ pub fn refresh(self: *Chunk, engine: *Engine, blocks: *const Blocks, temp_alloca
|
|||||||
engine.setObjectName(new_object_buffer.device_memory, "DM Chunk[{d}]", .{self.chunk_id});
|
engine.setObjectName(new_object_buffer.device_memory, "DM Chunk[{d}]", .{self.chunk_id});
|
||||||
}
|
}
|
||||||
|
|
||||||
const uniforms = try temp_allocator.alloc(Game.ObjectUniforms, object_count);
|
try self.object_buffer.write(engine, .{ .elements = uniforms.items });
|
||||||
var object_i: usize = 0;
|
|
||||||
defer temp_allocator.free(uniforms);
|
|
||||||
|
|
||||||
for (self.blocks, 0..) |plane, iz| {
|
|
||||||
const fz: f32 = @floatFromInt(iz);
|
|
||||||
for (plane, 0..) |row, iy| {
|
|
||||||
const fy: f32 = @floatFromInt(iy);
|
|
||||||
for (row, 0..) |id, ix| {
|
|
||||||
const fx: f32 = @floatFromInt(ix);
|
|
||||||
const block = blocks.getBlock(id).?;
|
|
||||||
|
|
||||||
const center = Vector3.add(self.origin, .init(fx, fy, fz));
|
|
||||||
const cx, const cy, const cz = center.asArray();
|
|
||||||
|
|
||||||
if (block.positive_x != .empty) {
|
|
||||||
// zig fmt: off
|
|
||||||
const matrix: Matrix4x4 = .init(
|
|
||||||
0, 1, 0, 0,
|
|
||||||
0, 0, 1, 0,
|
|
||||||
1, 0, 0, 0,
|
|
||||||
cx + 0.5, cy, cz, 1,
|
|
||||||
);
|
|
||||||
// zig fmt: on
|
|
||||||
uniforms[object_i] = .init(matrix, matrix, block.positive_x);
|
|
||||||
object_i += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (block.negative_x != .empty) {
|
|
||||||
// zig fmt: off
|
|
||||||
const matrix: Matrix4x4 = .init(
|
|
||||||
0, -1, 0, 0,
|
|
||||||
0, 0, 1, 0,
|
|
||||||
-1, 0, 0, 0,
|
|
||||||
cx - 0.5, cy, cz, 1,
|
|
||||||
);
|
|
||||||
// zig fmt: on
|
|
||||||
uniforms[object_i] = .init(matrix, matrix, block.negative_x);
|
|
||||||
object_i += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (block.positive_y != .empty) {
|
|
||||||
// zig fmt: off
|
|
||||||
const matrix: Matrix4x4 = .init(
|
|
||||||
-1, 0, 0, 0,
|
|
||||||
0, 0, 1, 0,
|
|
||||||
0, 1, 0, 0,
|
|
||||||
cx, cy + 0.5, cz, 1,
|
|
||||||
);
|
|
||||||
// zig fmt: on
|
|
||||||
uniforms[object_i] = .init(matrix, matrix, block.positive_y);
|
|
||||||
object_i += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (block.negative_y != .empty) {
|
|
||||||
// zig fmt: off
|
|
||||||
const matrix: Matrix4x4 = .init(
|
|
||||||
1, 0, 0, 0,
|
|
||||||
0, 0, 1, 0,
|
|
||||||
0, -1, 0, 0,
|
|
||||||
cx, cy - 0.5, cz, 1,
|
|
||||||
);
|
|
||||||
// zig fmt: on
|
|
||||||
uniforms[object_i] = .init(matrix, matrix, block.negative_y);
|
|
||||||
object_i += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (block.positive_z != .empty) {
|
|
||||||
// zig fmt: off
|
|
||||||
const matrix: Matrix4x4 = .init(
|
|
||||||
1, 0, 0, 0,
|
|
||||||
0, 1, 0, 0,
|
|
||||||
0, 0, 1, 0,
|
|
||||||
cx, cy, cz + 0.5, 1,
|
|
||||||
);
|
|
||||||
// zig fmt: on
|
|
||||||
uniforms[object_i] = .init(matrix, matrix, block.positive_z);
|
|
||||||
object_i += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (block.negative_z != .empty) {
|
|
||||||
// zig fmt: off
|
|
||||||
const matrix: Matrix4x4 = .init(
|
|
||||||
1, 0, 0, 0,
|
|
||||||
0, -1, 0, 0,
|
|
||||||
0, 0, -1, 0,
|
|
||||||
cx, cy, cz - 0.5, 1,
|
|
||||||
);
|
|
||||||
// zig fmt: on
|
|
||||||
uniforms[object_i] = .init(matrix, matrix, block.negative_z);
|
|
||||||
object_i += 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
std.debug.assert(object_i == uniforms.len);
|
|
||||||
|
|
||||||
try self.object_buffer.write(engine, .{ .elements = uniforms });
|
|
||||||
self.object_count = object_count;
|
self.object_count = object_count;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -246,3 +237,44 @@ pub fn draw(self: *const Chunk, layout: vk.PipelineLayout, command_buffer: Comma
|
|||||||
command_buffer.bindDescriptorSets(.graphics, layout, 1, &.{self.descriptor_set}, &.{});
|
command_buffer.bindDescriptorSets(.graphics, layout, 1, &.{self.descriptor_set}, &.{});
|
||||||
command_buffer.drawIndexed(.{ .index_count = 6, .instance_count = self.object_count });
|
command_buffer.drawIndexed(.{ .index_count = 6, .instance_count = self.object_count });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn getOpposite(self: *const Chunk, comptime side: Orientation, x: usize, y: usize, z: usize, blocks: *const Blocks, neighbors: Neighbors) Materials.Id {
|
||||||
|
return switch (side) {
|
||||||
|
.positive_x => if (x + 1 < chunk_size)
|
||||||
|
blocks.getBlock(self.blocks[z][y][x + 1]).?.negative_x
|
||||||
|
else if (neighbors.positive_x) |neighbor|
|
||||||
|
blocks.getBlock(neighbor.blocks[z][y][0]).?.negative_x
|
||||||
|
else
|
||||||
|
.empty,
|
||||||
|
.negative_x => if (x > 0)
|
||||||
|
blocks.getBlock(self.blocks[z][y][x - 1]).?.positive_x
|
||||||
|
else if (neighbors.negative_x) |neighbor|
|
||||||
|
blocks.getBlock(neighbor.blocks[z][y][chunk_size - 1]).?.positive_x
|
||||||
|
else
|
||||||
|
.empty,
|
||||||
|
.positive_y => if (y + 1 < chunk_size)
|
||||||
|
blocks.getBlock(self.blocks[z][y + 1][x]).?.negative_y
|
||||||
|
else if (neighbors.positive_y) |neighbor|
|
||||||
|
blocks.getBlock(neighbor.blocks[z][0][x]).?.negative_y
|
||||||
|
else
|
||||||
|
.empty,
|
||||||
|
.negative_y => if (y > 0)
|
||||||
|
blocks.getBlock(self.blocks[z][y - 1][x]).?.positive_y
|
||||||
|
else if (neighbors.negative_y) |neighbor|
|
||||||
|
blocks.getBlock(neighbor.blocks[z][chunk_size - 1][x]).?.positive_y
|
||||||
|
else
|
||||||
|
.empty,
|
||||||
|
.positive_z => if (z + 1 < chunk_size)
|
||||||
|
blocks.getBlock(self.blocks[z + 1][y][x]).?.negative_z
|
||||||
|
else if (neighbors.positive_z) |neighbor|
|
||||||
|
blocks.getBlock(neighbor.blocks[0][y][x]).?.negative_z
|
||||||
|
else
|
||||||
|
.empty,
|
||||||
|
.negative_z => if (z > 0)
|
||||||
|
blocks.getBlock(self.blocks[z - 1][y][x]).?.positive_z
|
||||||
|
else if (neighbors.negative_z) |neighbor|
|
||||||
|
blocks.getBlock(neighbor.blocks[chunk_size - 1][y][x]).?.positive_z
|
||||||
|
else
|
||||||
|
.empty,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
|
pub const Interator3 = @import("math/Interator3.zig").Interator3;
|
||||||
pub const Iterator3 = @import("math/Iterator3.zig");
|
pub const Iterator3 = @import("math/Iterator3.zig");
|
||||||
pub const Matrix4x4 = @import("math/Matrix4x4.zig").Matrix4x4;
|
pub const Matrix4x4 = @import("math/Matrix4x4.zig").Matrix4x4;
|
||||||
pub const Quaternion = @import("math/Quaternion.zig").Quaternion;
|
pub const Quaternion = @import("math/Quaternion.zig").Quaternion;
|
||||||
|
|||||||
42
src/math/Interator3.zig
Normal file
42
src/math/Interator3.zig
Normal file
@@ -0,0 +1,42 @@
|
|||||||
|
pub fn Interator3(comptime T: type) type {
|
||||||
|
return struct {
|
||||||
|
const Self = @This();
|
||||||
|
const Vector = @Vector(3, T);
|
||||||
|
|
||||||
|
min: Vector,
|
||||||
|
max: Vector,
|
||||||
|
current: ?Vector,
|
||||||
|
|
||||||
|
pub fn init(min_x: T, min_y: T, min_z: T, max_x: T, max_y: T, max_z: T) Self {
|
||||||
|
const min: Vector = .{ min_x, min_y, min_z };
|
||||||
|
const max: Vector = .{ max_x, max_y, max_z };
|
||||||
|
return .{
|
||||||
|
.min = min,
|
||||||
|
.max = max,
|
||||||
|
.current = min,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn next(self: *Self) ?[3]T {
|
||||||
|
const current = self.current orelse return null;
|
||||||
|
var next_current = current;
|
||||||
|
|
||||||
|
next_current[0] = next_current[0] + 1;
|
||||||
|
if (next_current[0] > self.max[0]) {
|
||||||
|
next_current[0] = self.min[0];
|
||||||
|
next_current[1] = next_current[1] + 1;
|
||||||
|
if (next_current[1] > self.max[1]) {
|
||||||
|
next_current[1] = self.min[1];
|
||||||
|
next_current[2] = next_current[2] + 1;
|
||||||
|
if (next_current[2] > self.max[2]) {
|
||||||
|
self.current = null;
|
||||||
|
return current;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
self.current = next_current;
|
||||||
|
return current;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user