Made terrain its own struct
This commit is contained in:
parent
c0b8d021d4
commit
1475fd2101
6 changed files with 93 additions and 26 deletions
|
|
@ -17,6 +17,7 @@ pub const Resources = struct {
|
|||
camera: *Camera,
|
||||
renderer: *Renderer,
|
||||
input: *Input,
|
||||
terrain: rendering.Terrain,
|
||||
delta_time: f32 = 0.0,
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -22,8 +22,6 @@ mesh: Mesh,
|
|||
transforms: std.ArrayList(math.Transform),
|
||||
previous_time: std.time.Instant,
|
||||
current_image: usize,
|
||||
terrain_vertex: vk.Buffer,
|
||||
terrain_index: vk.Buffer,
|
||||
|
||||
pub fn init(allocator: Allocator, instance_handle: vk.c.VkInstance, surface_handle: vk.c.VkSurfaceKHR) !Self {
|
||||
const instance: vk.Instance = .{ .handle = instance_handle };
|
||||
|
|
@ -49,27 +47,7 @@ pub fn init(allocator: Allocator, instance_handle: vk.c.VkInstance, surface_hand
|
|||
const terrain_fragment_shader = try device.initShader("terrain_frag");
|
||||
defer device.deinitShader(terrain_fragment_shader);
|
||||
|
||||
var terrain_pipeline = try vk.TerrainPipeline.init(graphics_pipeline, terrain_vertex_shader, terrain_fragment_shader);
|
||||
|
||||
const perlin: math.PerlinNoise = .{ .seed = 54321 };
|
||||
const heightmap = try allocator.alloc(u32, 700 * 700);
|
||||
defer allocator.free(heightmap);
|
||||
for (0..700) |x| {
|
||||
for (0..700) |y| {
|
||||
const scale = 0.01;
|
||||
var pixel = (perlin.fbm(@as(f64, @floatFromInt(x)) * scale, @as(f64, @floatFromInt(y)) * scale, 8, 3, 0.5) * 3);
|
||||
pixel = std.math.pow(f64, pixel, 1.2);
|
||||
const gray: u32 = @intFromFloat(pixel * 255);
|
||||
const color: u32 = (255 << 24) | (gray << 16) | (gray << 8) | gray;
|
||||
|
||||
heightmap[x*700 + y] = color;
|
||||
}
|
||||
}
|
||||
|
||||
const terrain_vertex, const terrain_index = try Mesh.terrain(allocator, device, 700, 700, 10);
|
||||
const heightmap_texture = try Texture.fromBytes(@alignCast(@ptrCast(heightmap)), device, 700, 700);
|
||||
//const heightmap_texture = try Texture.init("assets/textures/heightmap.png", device);
|
||||
try terrain_pipeline.setHeightmap(device, heightmap_texture);
|
||||
const terrain_pipeline = try vk.TerrainPipeline.init(graphics_pipeline, terrain_vertex_shader, terrain_fragment_shader);
|
||||
const texture = try Texture.init("assets/textures/container.png", device);
|
||||
const diffuse = try Texture.init("assets/textures/container_specular.png", device);
|
||||
|
||||
|
|
@ -116,8 +94,6 @@ pub fn init(allocator: Allocator, instance_handle: vk.c.VkInstance, surface_hand
|
|||
.previous_time = try std.time.Instant.now(),
|
||||
.mesh = mesh,
|
||||
.current_image = undefined,
|
||||
.terrain_vertex = terrain_vertex,
|
||||
.terrain_index = terrain_index,
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
|||
70
src/rendering/Terrain.zig
Normal file
70
src/rendering/Terrain.zig
Normal file
|
|
@ -0,0 +1,70 @@
|
|||
const std = @import("std");
|
||||
const vk = @import("vulkan.zig");
|
||||
const Mesh = @import("Mesh.zig");
|
||||
const math = @import("math");
|
||||
const Self = @This();
|
||||
|
||||
pub const Generator = struct {
|
||||
octaves: u32,
|
||||
lacunarity: f64,
|
||||
gain: f64,
|
||||
scale: f64 = 0.01,
|
||||
multiplier: f64,
|
||||
exponent: f64 = 1.0,
|
||||
|
||||
width: usize,
|
||||
height: usize,
|
||||
seed: u64,
|
||||
resolution: f32 = 1.0,
|
||||
};
|
||||
|
||||
heightmap: []f64,
|
||||
width: usize,
|
||||
height: usize,
|
||||
seed: u64,
|
||||
|
||||
texture: vk.Texture,
|
||||
vertex_buffer: vk.Buffer,
|
||||
index_buffer: vk.Buffer,
|
||||
|
||||
pub fn init(allocator: std.mem.Allocator, device: vk.Device, generator: Generator) !Self {
|
||||
const perlin: math.PerlinNoise = .{ .seed = generator.seed };
|
||||
const heightmap = try allocator.alloc(f64, generator.width * generator.height);
|
||||
const heightmap_data = try allocator.alloc(u32, generator.width * generator.height);
|
||||
defer allocator.free(heightmap_data);
|
||||
for (0..generator.width) |x| {
|
||||
for (0..generator.height) |y| {
|
||||
var pixel = (perlin.fbm(@as(f64, @floatFromInt(x)) * generator.scale, @as(f64, @floatFromInt(y)) * generator.scale, generator.octaves, generator.lacunarity, generator.gain) * generator.multiplier);
|
||||
pixel = std.math.pow(f64, pixel, generator.exponent);
|
||||
const gray: u32 = @intFromFloat(pixel * 255);
|
||||
const color: u32 = (255 << 24) | (gray << 16) | (gray << 8) | gray;
|
||||
|
||||
heightmap[x*generator.width + y] = pixel;
|
||||
heightmap_data[x*generator.width + y] = color;
|
||||
}
|
||||
}
|
||||
|
||||
const vertex_buffer, const index_buffer = try Mesh.terrain(allocator, device, generator.width, generator.height, generator.resolution);
|
||||
const heightmap_texture = try vk.Texture.fromBytes(@alignCast(@ptrCast(heightmap_data)), device, generator.width, generator.height);
|
||||
|
||||
return .{
|
||||
.heightmap = heightmap,
|
||||
.width = generator.width,
|
||||
.height = generator.height,
|
||||
.seed = generator.seed,
|
||||
.vertex_buffer = vertex_buffer,
|
||||
.index_buffer = index_buffer,
|
||||
.texture = heightmap_texture,
|
||||
};
|
||||
}
|
||||
|
||||
pub fn deinit(self: *Self, allocator: std.mem.Allocator, device: vk.Device) !void {
|
||||
allocator.free(self.heightmap);
|
||||
self.vertex_buffer.deinit(device.handle);
|
||||
self.index_buffer.deinit(device.handle);
|
||||
self.texture.deinit(device);
|
||||
}
|
||||
|
||||
pub fn getHeight(self: Self, x: usize, y: usize) f64 {
|
||||
return self.heightmap[x*self.width + y];
|
||||
}
|
||||
|
|
@ -3,3 +3,4 @@ pub const vk = @import("vulkan.zig");
|
|||
pub const Camera = @import("Camera.zig");
|
||||
pub const Renderer = @import("Renderer.zig");
|
||||
pub const lights = @import("lights.zig");
|
||||
pub const Terrain = @import("Terrain.zig");
|
||||
|
|
|
|||
|
|
@ -136,6 +136,7 @@ export fn sideros_init(init: api.GameInit) callconv(.c) void {
|
|||
.camera = &camera,
|
||||
.renderer = undefined,
|
||||
.input = &input,
|
||||
.terrain = undefined,
|
||||
};
|
||||
|
||||
ecs.hooks.init(allocator) catch @panic("TODO: handle this");
|
||||
|
|
@ -143,6 +144,23 @@ export fn sideros_init(init: api.GameInit) callconv(.c) void {
|
|||
pool = ecs.Pool.init(allocator, &resources) catch @panic("TODO: Gracefully handle error");
|
||||
// TODO(ernesto): I think this @ptrCast are unavoidable but maybe not?
|
||||
renderer = Renderer.init(allocator, @ptrCast(init.instance), @ptrCast(init.surface)) catch @panic("TODO: Gracefully handle error");
|
||||
|
||||
resources.terrain = rendering.Terrain.init(allocator, renderer.device, .{
|
||||
.octaves = 8,
|
||||
.lacunarity = 3.0,
|
||||
.gain = 0.5,
|
||||
.scale = 0.01,
|
||||
.multiplier = 3.0,
|
||||
.exponent = 1.2,
|
||||
|
||||
.width = 700,
|
||||
.height = 700,
|
||||
.seed = 12345678,
|
||||
.resolution = 10.0,
|
||||
}) catch @panic("TODO: handle this");
|
||||
|
||||
renderer.terrain_pipeline.setHeightmap(renderer.device, resources.terrain.texture) catch @panic("TODO: handle this");
|
||||
|
||||
pool.addSystemGroup(&[_]ecs.System{systems.render, systems.moveCamera}, true) catch @panic("TODO: Gracefuly handle error");
|
||||
pool.resources.renderer = &renderer;
|
||||
pool.tick();
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@ const Input = ecs.Input;
|
|||
pub fn render(pool: *ecs.Pool) anyerror!void {
|
||||
var renderer = pool.resources.renderer;
|
||||
const camera = pool.resources.camera;
|
||||
const terrain = pool.resources.terrain;
|
||||
|
||||
const now = try std.time.Instant.now();
|
||||
const delta_time: f32 = @as(f32, @floatFromInt(now.since(renderer.previous_time))) / @as(f32, 1_000_000_000.0);
|
||||
|
|
@ -21,7 +22,7 @@ pub fn render(pool: *ecs.Pool) anyerror!void {
|
|||
renderer.setLightCount(2);
|
||||
|
||||
try renderer.beginTerrain();
|
||||
renderer.device.drawTerrain(@as(u32, @intCast(renderer.terrain_index.size/@sizeOf(u32))), renderer.current_frame, renderer.terrain_vertex, renderer.terrain_index);
|
||||
renderer.device.drawTerrain(@as(u32, @intCast(terrain.index_buffer.size/@sizeOf(u32))), renderer.current_frame, terrain.vertex_buffer, terrain.index_buffer);
|
||||
|
||||
try renderer.beginGraphics();
|
||||
for (renderer.transforms.items, 0..) |transform, i| {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue