debug draw sysstem!!!11
This commit is contained in:
parent
b216506166
commit
3419f1e28e
|
|
@ -36,6 +36,9 @@ pub fn build(b: *std.Build) void {
|
|||
sdl3.shaderDefintion(b, mod, "../../lib/sdl3", optimize, "meshes.vert", b.path("shaders/meshes.vert.json"));
|
||||
sdl3.shaderDefintion(b, mod, "../../lib/sdl3", optimize, "lit_mesh.frag", b.path("shaders/lit_mesh.frag.json"));
|
||||
|
||||
sdl3.shaderDefintion(b, mod, "../../lib/sdl3", optimize, "debug.frag", b.path("shaders/debug.frag.json"));
|
||||
sdl3.shaderDefintion(b, mod, "../../lib/sdl3", optimize, "debug.vert", b.path("shaders/debug.vert.json"));
|
||||
|
||||
// ========== tests ==========
|
||||
const tests = b.addTest(.{
|
||||
.target = target,
|
||||
|
|
|
|||
|
|
@ -0,0 +1,4 @@
|
|||
float4 main(float3 Color : TEXCOORD0) : SV_Target0
|
||||
{
|
||||
return float4(Color, 1.0);
|
||||
}
|
||||
|
|
@ -0,0 +1,22 @@
|
|||
{
|
||||
"entryPoints" : [
|
||||
{
|
||||
"name" : "main",
|
||||
"mode" : "frag"
|
||||
}
|
||||
],
|
||||
"inputs" : [
|
||||
{
|
||||
"type" : "vec3",
|
||||
"name" : "in.var.TEXCOORD0",
|
||||
"location" : 0
|
||||
}
|
||||
],
|
||||
"outputs" : [
|
||||
{
|
||||
"type" : "vec4",
|
||||
"name" : "out.var.SV_Target0",
|
||||
"location" : 0
|
||||
}
|
||||
]
|
||||
}
|
||||
|
|
@ -0,0 +1,38 @@
|
|||
struct Input
|
||||
{
|
||||
float3 Position : TEXCOORD0;
|
||||
|
||||
uint Instance : SV_InstanceID;
|
||||
};
|
||||
|
||||
struct Output
|
||||
{
|
||||
float3 Color : TEXCOORD0;
|
||||
float4 Position : SV_Position;
|
||||
};
|
||||
|
||||
struct Scene
|
||||
{
|
||||
float4x4 Model;
|
||||
float3 Color;
|
||||
};
|
||||
|
||||
StructuredBuffer<Scene> scene: register(t0, space0);
|
||||
|
||||
cbuffer Uniforms : register(b0, space1)
|
||||
{
|
||||
float4x4 ViewProjection;
|
||||
};
|
||||
|
||||
Output main(Input input)
|
||||
{
|
||||
Output output;
|
||||
|
||||
float4 pos = float4(input.Position, 1.0);
|
||||
|
||||
output.Position = mul(ViewProjection, mul(scene[input.Instance].Model, pos));
|
||||
output.Color = scene[input.Instance].Color;
|
||||
|
||||
return output;
|
||||
}
|
||||
|
||||
|
|
@ -0,0 +1,89 @@
|
|||
{
|
||||
"entryPoints" : [
|
||||
{
|
||||
"name" : "main",
|
||||
"mode" : "vert"
|
||||
}
|
||||
],
|
||||
"types" : {
|
||||
"_7" : {
|
||||
"name" : "Scene",
|
||||
"members" : [
|
||||
{
|
||||
"name" : "Model",
|
||||
"type" : "mat4",
|
||||
"offset" : 0,
|
||||
"matrix_stride" : 16,
|
||||
"row_major" : true
|
||||
},
|
||||
{
|
||||
"name" : "Color",
|
||||
"type" : "vec3",
|
||||
"offset" : 64
|
||||
}
|
||||
]
|
||||
},
|
||||
"_6" : {
|
||||
"name" : "type.StructuredBuffer.Scene",
|
||||
"members" : [
|
||||
{
|
||||
"name" : "_m0",
|
||||
"type" : "_7",
|
||||
"array" : [
|
||||
0
|
||||
],
|
||||
"array_size_is_literal" : [
|
||||
true
|
||||
],
|
||||
"offset" : 0,
|
||||
"array_stride" : 80
|
||||
}
|
||||
]
|
||||
},
|
||||
"_9" : {
|
||||
"name" : "type.Uniforms",
|
||||
"members" : [
|
||||
{
|
||||
"name" : "ViewProjection",
|
||||
"type" : "mat4",
|
||||
"offset" : 0,
|
||||
"matrix_stride" : 16,
|
||||
"row_major" : true
|
||||
}
|
||||
]
|
||||
}
|
||||
},
|
||||
"inputs" : [
|
||||
{
|
||||
"type" : "vec3",
|
||||
"name" : "in.var.TEXCOORD0",
|
||||
"location" : 0
|
||||
}
|
||||
],
|
||||
"outputs" : [
|
||||
{
|
||||
"type" : "vec3",
|
||||
"name" : "out.var.TEXCOORD0",
|
||||
"location" : 0
|
||||
}
|
||||
],
|
||||
"ssbos" : [
|
||||
{
|
||||
"type" : "_6",
|
||||
"name" : "scene",
|
||||
"readonly" : true,
|
||||
"block_size" : 0,
|
||||
"set" : 0,
|
||||
"binding" : 0
|
||||
}
|
||||
],
|
||||
"ubos" : [
|
||||
{
|
||||
"type" : "_9",
|
||||
"name" : "type.Uniforms",
|
||||
"block_size" : 64,
|
||||
"set" : 1,
|
||||
"binding" : 0
|
||||
}
|
||||
]
|
||||
}
|
||||
|
|
@ -30,18 +30,18 @@ float3 BlinnPhong(float3 normal, float3 fragPos, float3 lightPos, float3 lightCo
|
|||
float cutoffFactor = 0.5;
|
||||
float dist = length(lightPos - fragPos);
|
||||
float attenuation = 1.0 / (dist * 2);
|
||||
if (dist > cutoff1)
|
||||
{
|
||||
attenuation *= cutoffFactor;
|
||||
}
|
||||
if (dist > cutoff2)
|
||||
{
|
||||
attenuation *= cutoffFactor;
|
||||
}
|
||||
if (dist > maxDist)
|
||||
{
|
||||
attenuation = 0;
|
||||
}
|
||||
//if (dist > cutoff1)
|
||||
//{
|
||||
// attenuation *= cutoffFactor;
|
||||
//}
|
||||
//if (dist > cutoff2)
|
||||
//{
|
||||
// attenuation *= cutoffFactor;
|
||||
//}
|
||||
//if (dist > maxDist)
|
||||
//{
|
||||
// attenuation = 0;
|
||||
//}
|
||||
|
||||
|
||||
diffuse *= attenuation;
|
||||
|
|
|
|||
|
|
@ -1,7 +1,21 @@
|
|||
pub var NeonObjectTable: core.EngineObjectVTable = core.EngineObjectVTable.from(@This());
|
||||
|
||||
allocator: std.mem.Allocator,
|
||||
debugDraws: core.RingQueueU(DebugPrimitive),
|
||||
|
||||
device: *gpu.GPUDevice = undefined,
|
||||
renderer: *Renderer = undefined,
|
||||
pipeline: *gpu.GPUGraphicsPipeline = undefined,
|
||||
|
||||
ssbo: *gpu.GPUBuffer = undefined,
|
||||
ssobUpload: *gpu.GPUTransferBuffer = undefined,
|
||||
|
||||
meshes: [@as(usize, @intCast(@intFromEnum(DebugPrimitiveType.box) + 1))]?rend.IndexedMesh = .{ null, null, null },
|
||||
deltaTime: f64 = 0,
|
||||
|
||||
drawsThisFrame: std.ArrayListUnmanaged(DebugPrimitive) = .{},
|
||||
|
||||
pub const MaxObjectCount = 4096;
|
||||
|
||||
const assetReferences = [_]assets.AssetImportReference{
|
||||
assets.MakeImportRefOptions(
|
||||
|
|
@ -24,6 +38,7 @@ const assetReferences = [_]assets.AssetImportReference{
|
|||
pub fn create(allocator: std.mem.Allocator) !*@This() {
|
||||
const self = try allocator.create(@This());
|
||||
self.* = .{
|
||||
.debugDraws = try core.RingQueueU(DebugPrimitive).init(allocator, MaxObjectCount),
|
||||
.allocator = allocator,
|
||||
};
|
||||
core.engine_logs("[DebugDrawSystem] starting up...");
|
||||
|
|
@ -34,53 +49,327 @@ pub fn create(allocator: std.mem.Allocator) !*@This() {
|
|||
|
||||
try assets.loadList(assetReferences);
|
||||
|
||||
gDebugDrawSys = self;
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn updateMeshes(self: *@This()) void {
|
||||
|
||||
// line = 0,
|
||||
// sphere = 1,
|
||||
// box = 2,
|
||||
const list: [3][]const u8 = .{
|
||||
"m_debug_line", // 0
|
||||
"m_debug_sphere", // 1
|
||||
"m_debug_box", // 2
|
||||
};
|
||||
|
||||
for (list, 0..) |path, i| {
|
||||
self.meshes[i] = rend.getMesh(path);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn tick(self: *@This(), dt: f64) void {
|
||||
self.deltaTime = dt;
|
||||
|
||||
if (self.meshes[0] == null) {
|
||||
self.updateMeshes();
|
||||
}
|
||||
}
|
||||
|
||||
// ========= Rendering section =========
|
||||
pub fn onUpload(p: *anyopaque, copyPass: *gpu.GPUCopyPass) void {
|
||||
const self: *@This() = @ptrCast(@alignCast(p));
|
||||
|
||||
const count = self.debugDraws.count();
|
||||
{
|
||||
const uploadMapped: [*]debug_vert.Scene = @ptrCast(@alignCast(self.device.mapGPUTransferBuffer(self.ssobUpload, true)));
|
||||
defer self.device.unmapGPUTransferBuffer(self.ssobUpload);
|
||||
|
||||
var offset: usize = 0;
|
||||
|
||||
self.drawsThisFrame.clearRetainingCapacity();
|
||||
|
||||
while (offset < count) {
|
||||
var primitive: DebugPrimitive = self.debugDraws.pop().?;
|
||||
uploadMapped[offset] = .{
|
||||
.Model = primitive.resolve(),
|
||||
.Color = @bitCast(primitive.color),
|
||||
};
|
||||
|
||||
self.drawsThisFrame.append(self.allocator, primitive) catch unreachable;
|
||||
|
||||
primitive.duration -= @as(f32, @floatCast(self.deltaTime));
|
||||
offset += 1;
|
||||
if (primitive.duration >= 0) {
|
||||
// push this primitive so that it goes to the next frame
|
||||
self.debugDraws.push(primitive) catch continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (count > 0) {
|
||||
copyPass.uploadToGPUBuffer(&.{ .transfer_buffer = self.ssobUpload, .offset = 0 }, &.{
|
||||
.buffer = self.ssbo,
|
||||
.offset = 0,
|
||||
.size = @intCast(count * @sizeOf(debug_vert.Scene)),
|
||||
}, true);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn postMesh(p: *anyopaque, cmd: *gpu.GPUCommandBuffer, renderpass: *gpu.GPURenderPass) void {
|
||||
const self: *@This() = @ptrCast(@alignCast(p));
|
||||
|
||||
if (self.meshes[0] == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
renderpass.bindGPUGraphicsPipeline(self.pipeline);
|
||||
renderpass.bindGPUVertexStorageBuffers(0, &self.ssbo, 1);
|
||||
|
||||
for (self.drawsThisFrame.items, 0..) |draw, i| {
|
||||
var mesh: rend.IndexedMesh = undefined;
|
||||
switch (draw.primitive) {
|
||||
.box => {
|
||||
mesh = self.meshes[2].?;
|
||||
},
|
||||
.sphere => {
|
||||
mesh = self.meshes[1].?;
|
||||
},
|
||||
.line => {
|
||||
mesh = self.meshes[0].?;
|
||||
},
|
||||
}
|
||||
|
||||
renderpass.drawGPUIndexedPrimitives(mesh.index.size, 1, mesh.index.start, @intCast(mesh.vertex.start), @intCast(i));
|
||||
}
|
||||
_ = cmd;
|
||||
}
|
||||
// ========= End of Rendering section =========
|
||||
|
||||
pub fn createBuffers(self: *@This()) !void {
|
||||
self.ssbo = self.device.createGPUBuffer(&.{
|
||||
.usage = .{ .bufferusageGraphicsStorageRead = true, .bufferusageVertex = true },
|
||||
.size = MaxObjectCount * @sizeOf(debug_vert.Scene),
|
||||
.props = 0,
|
||||
});
|
||||
|
||||
self.ssobUpload = self.device.createGPUTransferBuffer(&.{
|
||||
.usage = .transferbufferusageUpload,
|
||||
.size = MaxObjectCount * @sizeOf(debug_vert.Scene),
|
||||
.props = 0,
|
||||
});
|
||||
}
|
||||
|
||||
pub fn createPipeline(self: *@This()) !*gpu.GPUGraphicsPipeline {
|
||||
const vertex = try rend.context().loadShader("debug.vert", debug_vert.LoadArgs);
|
||||
const fragment = try rend.context().loadShader("debug.frag", debug_frag.LoadArgs);
|
||||
|
||||
var pci = std.mem.zeroes(gpu.GPUGraphicsPipelineCreateInfo);
|
||||
pci.vertex_shader = vertex;
|
||||
pci.fragment_shader = fragment;
|
||||
|
||||
var attributes = std.ArrayList(gpu.GPUVertexAttribute).init(self.allocator);
|
||||
defer attributes.deinit();
|
||||
|
||||
var offset: u32 = 0;
|
||||
{
|
||||
try addAttribute(&attributes, &offset, @sizeOf(f32) * 3, .vertexelementformatFloat3);
|
||||
}
|
||||
|
||||
pci.vertex_input_state = .{
|
||||
.num_vertex_buffers = 1,
|
||||
.vertex_buffer_descriptions = &[_]gpu.GPUVertexBufferDescription{
|
||||
.{ .slot = 0, .pitch = @sizeOf(rend.MeshVertex), .input_rate = .vertexinputrateVertex, .instance_step_rate = 0 },
|
||||
},
|
||||
.num_vertex_attributes = @intCast(attributes.items.len),
|
||||
.vertex_attributes = @ptrCast(attributes.items.ptr),
|
||||
};
|
||||
|
||||
pci.depth_stencil_state.compare_op = .compareopLess;
|
||||
pci.depth_stencil_state.enable_depth_test = true;
|
||||
pci.depth_stencil_state.enable_depth_write = true;
|
||||
pci.depth_stencil_state.write_mask = 0xff;
|
||||
|
||||
pci.target_info.has_depth_stencil_target = true;
|
||||
pci.target_info.depth_stencil_format = .textureformatD32Float;
|
||||
pci.target_info.num_color_targets = 1;
|
||||
pci.target_info.color_target_descriptions = &[_]gpu.GPUColorTargetDescription{
|
||||
.{
|
||||
.format = self.device.getGPUSwapchainTextureFormat(rend.context().window),
|
||||
.blend_state = std.mem.zeroes(gpu.GPUColorTargetBlendState),
|
||||
},
|
||||
};
|
||||
|
||||
pci.rasterizer_state.fill_mode = .fillmodeLine;
|
||||
const pipe = self.device.createGPUGraphicsPipeline(&pci);
|
||||
|
||||
return pipe;
|
||||
}
|
||||
|
||||
fn addAttribute(list: *std.ArrayList(gpu.GPUVertexAttribute), offset: *u32, size: u32, format: gpu.GPUVertexElementFormat) !void {
|
||||
try list.append(.{ .location = @intCast(list.items.len), .offset = offset.*, .format = format, .buffer_slot = 0 });
|
||||
offset.* = offset.* + size;
|
||||
}
|
||||
|
||||
pub fn setup(self: *@This(), device: *gpu.GPUDevice) !void {
|
||||
core.engine_logs("[DebugDrawSystem] registering to renderer...");
|
||||
self.device = device;
|
||||
self.renderer = rend.context();
|
||||
self.pipeline = try self.createPipeline();
|
||||
try self.createBuffers();
|
||||
|
||||
//core.installDebugDrawInterface(self.allocator, newInterface: DebugDrawInterface);
|
||||
try core.installDebugDrawInterface(self.allocator, .{
|
||||
.debugSphereFn = debugSphere, // : *const fn (pos: core.Vectorf, radius: f32, DebugDrawParams) void,
|
||||
.debugBoxFn = debugBox, // : *const fn (pos: core.Vectorf, extents: core.Vectorf, DebugDrawParams) void,
|
||||
.debugLineFn = debugLine, // : *const fn (start: core.Vectorf, end: core.Vectorf, DebugDrawParams) void,
|
||||
});
|
||||
}
|
||||
|
||||
pub fn destroy(self: *@This()) void {
|
||||
self.debugDraws.deinit(self.allocator);
|
||||
self.drawsThisFrame.deinit(self.allocator);
|
||||
self.allocator.destroy(self);
|
||||
}
|
||||
|
||||
// ==================== Primitives ===================
|
||||
|
||||
pub const DebugLine = struct {
|
||||
start: core.Vectorf,
|
||||
end: core.Vectorf,
|
||||
|
||||
pub fn resolve(self: @This(), _: anytype) core.Transform {
|
||||
var delta = self.start.sub(self.end);
|
||||
const d = delta.normalize();
|
||||
const axz = std.math.atan2(-d.z, d.x) + core.radians(180.0);
|
||||
const ay = -std.math.asin(d.y);
|
||||
const mat1 = core.zm.matFromRollPitchYaw(0, 0, ay);
|
||||
const mat2 = core.zm.rotationY(axz);
|
||||
const len = delta.length();
|
||||
return core.zm.mul(core.zm.mul(
|
||||
core.zm.mul(mat1, mat2),
|
||||
core.zm.scaling(len, len, len),
|
||||
), core.zm.translationV(self.start.toZm()));
|
||||
}
|
||||
};
|
||||
|
||||
pub const DebugSphere = struct {
|
||||
position: core.Vectorf,
|
||||
radius: f32,
|
||||
rotation: core.Quat,
|
||||
|
||||
pub fn resolve(self: @This(), _: anytype) core.Transform {
|
||||
return core.zm.mul(core.zm.mul(
|
||||
core.zm.matFromQuat(self.rotation),
|
||||
core.zm.scaling(self.radius, self.radius, self.radius),
|
||||
), core.zm.translationV(self.position.toZm()));
|
||||
}
|
||||
};
|
||||
|
||||
pub const DebugBox = struct {
|
||||
position: core.Vectorf,
|
||||
extents: core.Vectorf,
|
||||
rotation: core.Quat,
|
||||
|
||||
pub fn resolve(self: @This(), _: anytype) core.Transform {
|
||||
return core.zm.mul(core.zm.mul(
|
||||
core.zm.matFromQuat(self.rotation),
|
||||
core.zm.scalingV(self.extents.toZm()),
|
||||
), core.zm.translationV(self.position.toZm()));
|
||||
}
|
||||
};
|
||||
|
||||
const DebugPrimitiveType = enum(u8) {
|
||||
line = 0,
|
||||
sphere = 1,
|
||||
box = 2,
|
||||
};
|
||||
|
||||
pub const DebugPrimitive = struct {
|
||||
primitive: union(DebugPrimitiveType) {
|
||||
line: DebugLine,
|
||||
sphere: DebugSphere,
|
||||
box: DebugBox,
|
||||
},
|
||||
color: core.Vectorf = .{ .x = 0.0, .y = 1.0, .z = 0.0 },
|
||||
duration: f32 = 0.0,
|
||||
|
||||
pub fn resolve(self: @This()) core.Transform {
|
||||
// comptime core.asserts(@sizeOf(DebugPrimitiveGpu) == DebugPrimitiveGpu.TargetSize, "");
|
||||
|
||||
switch (self.primitive) {
|
||||
.line => |inner| {
|
||||
return inner.resolve(.{});
|
||||
},
|
||||
.sphere => |inner| {
|
||||
return inner.resolve(.{});
|
||||
},
|
||||
.box => |inner| {
|
||||
return inner.resolve(.{});
|
||||
},
|
||||
}
|
||||
unreachable;
|
||||
|
||||
// return core.implement_func_for_tagged_union_nonull(self.primitive, "resolve", core.Transform, .{});
|
||||
}
|
||||
};
|
||||
|
||||
const DebugPrimitiveGpu = struct {
|
||||
const UnpaddedSize = @sizeOf(core.Transform) + @sizeOf(core.Vectorf);
|
||||
const TargetSize = 80;
|
||||
|
||||
model: core.Transform,
|
||||
color: core.Vectorf,
|
||||
|
||||
pad: [TargetSize - UnpaddedSize]u8 = std.mem.zeroes([TargetSize - UnpaddedSize]u8),
|
||||
};
|
||||
|
||||
const DebugDrawSharedInstance = struct {};
|
||||
|
||||
const DebugSharedData = struct {
|
||||
drawsThisFrame: std.ArrayListUnmanaged(DebugPrimitive) = .{},
|
||||
lock: std.Thread.Mutex = .{},
|
||||
|
||||
pub fn deinit(self: *@This(), allocator: std.mem.Allocator) void {
|
||||
self.drawsThisFrame.deinit(allocator);
|
||||
}
|
||||
};
|
||||
|
||||
const objectCount = 2048;
|
||||
|
||||
// ==================== End of primitives ============
|
||||
|
||||
var gDebugDrawSys: *@This() = undefined;
|
||||
|
||||
pub fn debugSphere(position: core.Vectorf, radius: f32, params: DebugDrawParams) void {
|
||||
_ = position;
|
||||
_ = radius;
|
||||
_ = params;
|
||||
// gDebugDrawSys.debugDraws.push(.{
|
||||
// .primitive = .{ .sphere = .{ .position = position, .radius = radius, .rotation = params.rotation } },
|
||||
// .color = params.color,
|
||||
// .duration = params.duration,
|
||||
// }) catch return;
|
||||
gDebugDrawSys.debugDraws.push(.{
|
||||
.primitive = .{ .sphere = .{ .position = position, .radius = radius, .rotation = params.rotation } },
|
||||
.color = params.color,
|
||||
.duration = params.duration,
|
||||
}) catch return;
|
||||
}
|
||||
|
||||
pub fn debugLine(start: core.Vectorf, end: core.Vectorf, params: DebugDrawParams) void {
|
||||
_ = start;
|
||||
_ = end;
|
||||
_ = params;
|
||||
// gDebugDrawSys.debugDraws.push(.{
|
||||
// .primitive = .{ .line = .{
|
||||
// .start = start,
|
||||
// .end = end,
|
||||
// } },
|
||||
// .color = params.color,
|
||||
// .duration = params.duration,
|
||||
// }) catch return;
|
||||
gDebugDrawSys.debugDraws.push(.{
|
||||
.primitive = .{ .line = .{
|
||||
.start = start,
|
||||
.end = end,
|
||||
} },
|
||||
.color = params.color,
|
||||
.duration = params.duration,
|
||||
}) catch return;
|
||||
}
|
||||
|
||||
pub fn debugBox(position: core.Vectorf, extents: core.Vectorf, params: DebugDrawParams) void {
|
||||
_ = position;
|
||||
_ = extents;
|
||||
_ = params;
|
||||
// gDebugDrawSys.debugDraws.push(.{
|
||||
// .primitive = .{
|
||||
// .box = .{ .position = position, .extents = extents, .rotation = params.rotation },
|
||||
// },
|
||||
// .color = params.color,
|
||||
// .duration = params.duration,
|
||||
// }) catch return;
|
||||
gDebugDrawSys.debugDraws.push(.{
|
||||
.primitive = .{
|
||||
.box = .{ .position = position, .extents = extents, .rotation = params.rotation },
|
||||
},
|
||||
.color = params.color,
|
||||
.duration = params.duration,
|
||||
}) catch return;
|
||||
}
|
||||
|
||||
const DebugDrawParams = core.DebugDrawParams;
|
||||
|
|
@ -93,6 +382,9 @@ const sdl3 = @import("sdl3");
|
|||
const gpu = sdl3.gpu;
|
||||
const std = @import("std");
|
||||
|
||||
const debug_frag = @import("debug.frag");
|
||||
const debug_vert = @import("debug.vert");
|
||||
const Renderer = @import("renderer.zig").Renderer;
|
||||
const primitive_box align(8) = @embedFile("embedded/primitive_box.obj").*;
|
||||
const primitive_line align(8) = @embedFile("embedded/primitive_line.obj").*;
|
||||
const primitive_sphere align(8) = @embedFile("embedded/primitive_sphere.obj").*;
|
||||
|
|
|
|||
|
|
@ -170,7 +170,6 @@ pub fn getMesh(name: []const u8) ?rend.IndexedMesh {
|
|||
}
|
||||
|
||||
pub fn getMeshByName(name: *core.Name) ?rend.IndexedMesh {
|
||||
core.engine_log("getMeshByName {d}", .{name.handle()});
|
||||
return gMeshPool.installedMeshes.get(name.handle());
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -31,6 +31,7 @@ pub const Renderer = struct {
|
|||
uploads: std.ArrayListUnmanaged(struct { ptr: *anyopaque, func: *const fn (*anyopaque, *gpu.GPUCopyPass) void }) = .{},
|
||||
uploadCleanup: std.ArrayListUnmanaged(struct { ptr: *anyopaque, func: *const fn (*anyopaque) void }) = .{},
|
||||
|
||||
postMesh: std.ArrayListUnmanaged(struct { ptr: *anyopaque, func: *const fn (*anyopaque, *gpu.GPUCommandBuffer, *gpu.GPURenderPass) void }) = .{},
|
||||
postRenders: std.ArrayListUnmanaged(struct { ptr: *anyopaque, func: *const fn (*anyopaque, *gpu.GPUCommandBuffer) void }) = .{},
|
||||
destroys: std.ArrayListUnmanaged(struct { ptr: *anyopaque, func: *const fn (*anyopaque) void }) = .{},
|
||||
preDraws: std.ArrayListUnmanaged(struct { ptr: *anyopaque, func: *const fn (*anyopaque, *gpu.GPUCommandBuffer) void }) = .{},
|
||||
|
|
@ -80,8 +81,8 @@ pub const Renderer = struct {
|
|||
|
||||
core.engine_log("sgpu device created, using shader format: {s}", .{self.shaderSuffix});
|
||||
|
||||
// try self.createPipeline();
|
||||
try self.createMeshPipeline();
|
||||
try self.createBuffers();
|
||||
try self.createDepthTexture();
|
||||
|
||||
self.meshPool = try self.createRendererObject(MeshPool);
|
||||
|
|
@ -108,7 +109,7 @@ pub const Renderer = struct {
|
|||
var defaultTextureName = core.MakeName("t_default");
|
||||
self.defaultTexture = getTexture(&defaultTextureName).?;
|
||||
|
||||
self.debugDrawSys = try core.createObject(DebugDrawSystem, .{});
|
||||
self.debugDrawSys = try self.createRendererEngineObject(DebugDrawSystem);
|
||||
}
|
||||
|
||||
pub fn createSamplers(self: *@This()) !void {
|
||||
|
|
@ -137,6 +138,10 @@ pub const Renderer = struct {
|
|||
try self.postRenders.append(self.allocator, .{ .ptr = object, .func = T.postRender });
|
||||
}
|
||||
|
||||
if (@hasDecl(T, "postMesh")) {
|
||||
try self.postMesh.append(self.allocator, .{ .ptr = object, .func = T.postMesh });
|
||||
}
|
||||
|
||||
if (@hasDecl(T, "onPreDraw")) {
|
||||
try self.preDraws.append(self.allocator, .{ .ptr = object, .func = T.onPreDraw });
|
||||
}
|
||||
|
|
@ -146,6 +151,8 @@ pub const Renderer = struct {
|
|||
const object = try core.createObject(T, .{});
|
||||
try object.setup(self.device);
|
||||
|
||||
try self.registerRendererObject(T, object);
|
||||
|
||||
return object;
|
||||
}
|
||||
|
||||
|
|
@ -243,6 +250,9 @@ pub const Renderer = struct {
|
|||
|
||||
pci.rasterizer_state.fill_mode = .fillmodeFill;
|
||||
self.meshPipe = self.device.createGPUGraphicsPipeline(&pci);
|
||||
}
|
||||
|
||||
pub fn createBuffers(self: *@This()) !void {
|
||||
|
||||
// ssbo buffer
|
||||
|
||||
|
|
@ -261,20 +271,23 @@ pub const Renderer = struct {
|
|||
}
|
||||
|
||||
pub fn uploadSSBOs(self: *@This(), copyPass: *gpu.GPUCopyPass) !void {
|
||||
const uploadMapped: [*]meshes_vert.Scene = @ptrCast(@alignCast(self.device.mapGPUTransferBuffer(self.ssboSceneUpload, true)));
|
||||
self.device.unmapGPUTransferBuffer(self.ssboSceneUpload);
|
||||
|
||||
const container = rend.MeshComponent.BaseContainer;
|
||||
const uploadCount: usize = @min(container.dense.items.len, MaxObjectCount);
|
||||
for (0..uploadCount) |i| {
|
||||
// const object = &container.dense.items[i].value;
|
||||
const objectId = container.dense.items[i].sparseIndex;
|
||||
var transform = core.zm.identity();
|
||||
{
|
||||
const uploadMapped: [*]meshes_vert.Scene = @ptrCast(@alignCast(self.device.mapGPUTransferBuffer(self.ssboSceneUpload, true)));
|
||||
defer self.device.unmapGPUTransferBuffer(self.ssboSceneUpload);
|
||||
|
||||
if (core.Scene.SceneObjectContainer.get(objectId, ._repr)) |repr| {
|
||||
transform = repr.transform;
|
||||
// iterate over MeshComponents
|
||||
for (0..uploadCount) |i| {
|
||||
// const object = &container.dense.items[i].value;
|
||||
const objectId = container.dense.items[i].sparseIndex;
|
||||
var transform = core.zm.identity();
|
||||
|
||||
if (core.Scene.SceneObjectContainer.get(objectId, ._repr)) |repr| {
|
||||
transform = repr.transform;
|
||||
}
|
||||
uploadMapped[i].Model = @bitCast(transform);
|
||||
}
|
||||
uploadMapped[i].Model = @bitCast(transform);
|
||||
}
|
||||
|
||||
if (uploadCount == 0)
|
||||
|
|
@ -287,40 +300,6 @@ pub const Renderer = struct {
|
|||
}, true);
|
||||
}
|
||||
|
||||
pub fn createPipeline(self: *@This()) !void {
|
||||
const vertex = try self.loadShader("sample.vert", sample_vert.LoadArgs);
|
||||
const fragment = try self.loadShader("sample.frag", .{});
|
||||
|
||||
var pci = std.mem.zeroes(gpu.GPUGraphicsPipelineCreateInfo);
|
||||
pci.fragment_shader = fragment;
|
||||
pci.vertex_shader = vertex;
|
||||
|
||||
pci.target_info.num_color_targets = 1;
|
||||
pci.target_info.has_depth_stencil_target = true;
|
||||
pci.target_info.depth_stencil_format = .textureformatD32Float;
|
||||
pci.target_info.color_target_descriptions = &[_]gpu.GPUColorTargetDescription{
|
||||
.{
|
||||
.format = self.device.getGPUSwapchainTextureFormat(self.window),
|
||||
.blend_state = std.mem.zeroes(gpu.GPUColorTargetBlendState),
|
||||
},
|
||||
};
|
||||
|
||||
pci.rasterizer_state.fill_mode = .fillmodeFill;
|
||||
self.testPipeline = self.device.createGPUGraphicsPipeline(&pci);
|
||||
|
||||
self.colorBuffer = self.device.createGPUBuffer(&.{
|
||||
.usage = .{ .bufferusageVertex = true, .bufferusageGraphicsStorageRead = true },
|
||||
.size = 8192 * 2,
|
||||
.props = 0,
|
||||
});
|
||||
|
||||
self.colorBufferTransfer = self.device.createGPUTransferBuffer(&.{
|
||||
.usage = .transferbufferusageUpload,
|
||||
.size = 8192 * 2,
|
||||
.props = 0,
|
||||
});
|
||||
}
|
||||
|
||||
pub fn loadShader(
|
||||
self: *@This(),
|
||||
shaderName: []const u8,
|
||||
|
|
@ -458,6 +437,7 @@ pub const Renderer = struct {
|
|||
|
||||
const renderpass = cmd.beginGPURenderPass(&targetInfo, 1, &depthTarget);
|
||||
//renderpass.bindGPUGraphicsPipeline(self.testPipeline);
|
||||
|
||||
renderpass.bindGPUGraphicsPipeline(self.meshPipe);
|
||||
|
||||
renderpass.bindGPUVertexStorageBuffers(0, &self.ssboScene, 1);
|
||||
|
|
@ -498,6 +478,10 @@ pub const Renderer = struct {
|
|||
}
|
||||
}
|
||||
|
||||
for (self.postMesh.items) |interface| {
|
||||
interface.func(interface.ptr, cmd, renderpass);
|
||||
}
|
||||
|
||||
renderpass.endGPURenderPass();
|
||||
|
||||
for (self.postRenders.items) |interface| {
|
||||
|
|
@ -517,6 +501,8 @@ pub const Renderer = struct {
|
|||
for (self.destroys.items) |d| {
|
||||
d.func(d.ptr);
|
||||
}
|
||||
|
||||
self.postMesh.deinit(self.allocator);
|
||||
self.uploadCleanup.deinit(self.allocator);
|
||||
self.preDraws.deinit(self.allocator);
|
||||
self.postRenders.deinit(self.allocator);
|
||||
|
|
|
|||
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
|
@ -0,0 +1,22 @@
|
|||
#include <metal_stdlib>
|
||||
#include <simd/simd.h>
|
||||
|
||||
using namespace metal;
|
||||
|
||||
struct main0_out
|
||||
{
|
||||
float4 out_var_SV_Target0 [[color(0)]];
|
||||
};
|
||||
|
||||
struct main0_in
|
||||
{
|
||||
float3 in_var_TEXCOORD0 [[user(locn0)]];
|
||||
};
|
||||
|
||||
fragment main0_out main0(main0_in in [[stage_in]])
|
||||
{
|
||||
main0_out out = {};
|
||||
out.out_var_SV_Target0 = float4(in.in_var_TEXCOORD0, 1.0);
|
||||
return out;
|
||||
}
|
||||
|
||||
|
|
@ -0,0 +1,40 @@
|
|||
#include <metal_stdlib>
|
||||
#include <simd/simd.h>
|
||||
|
||||
using namespace metal;
|
||||
|
||||
struct Scene
|
||||
{
|
||||
float4x4 Model;
|
||||
float3 Color;
|
||||
};
|
||||
|
||||
struct type_StructuredBuffer_Scene
|
||||
{
|
||||
Scene _m0[1];
|
||||
};
|
||||
|
||||
struct type_Uniforms
|
||||
{
|
||||
float4x4 ViewProjection;
|
||||
};
|
||||
|
||||
struct main0_out
|
||||
{
|
||||
float3 out_var_TEXCOORD0 [[user(locn0)]];
|
||||
float4 gl_Position [[position]];
|
||||
};
|
||||
|
||||
struct main0_in
|
||||
{
|
||||
float3 in_var_TEXCOORD0 [[attribute(0)]];
|
||||
};
|
||||
|
||||
vertex main0_out main0(main0_in in [[stage_in]], constant type_Uniforms& Uniforms [[buffer(0)]], const device type_StructuredBuffer_Scene& scene [[buffer(1)]], uint gl_InstanceIndex [[instance_id]])
|
||||
{
|
||||
main0_out out = {};
|
||||
out.out_var_TEXCOORD0 = scene._m0[gl_InstanceIndex].Color;
|
||||
out.gl_Position = Uniforms.ViewProjection * (scene._m0[gl_InstanceIndex].Model * float4(in.in_var_TEXCOORD0, 1.0));
|
||||
return out;
|
||||
}
|
||||
|
||||
|
|
@ -24,30 +24,11 @@ struct main0_in
|
|||
fragment main0_out main0(main0_in in [[stage_in]], constant type_Uniforms& Uniforms [[buffer(0)]], texture2d<float> Texture [[texture(0)]], sampler Sampler [[sampler(0)]])
|
||||
{
|
||||
main0_out out = {};
|
||||
float4 _54 = Texture.sample(Sampler, in.in_var_TEXCOORD0);
|
||||
float3 _57 = float3(0.0, 16.0, -5.0) - in.in_var_TEXCOORD1;
|
||||
float3 _58 = fast::normalize(_57);
|
||||
float _73 = length(_57);
|
||||
float _79;
|
||||
if (_73 > 2.0)
|
||||
{
|
||||
_79 = 0.25 / _73;
|
||||
}
|
||||
else
|
||||
{
|
||||
_79 = 0.5 / _73;
|
||||
}
|
||||
float _84;
|
||||
if (_73 > 4.0)
|
||||
{
|
||||
_84 = _79 * 0.5;
|
||||
}
|
||||
else
|
||||
{
|
||||
_84 = _79;
|
||||
}
|
||||
float _86 = (_73 > 5.0) ? 0.0 : _84;
|
||||
out.out_var_SV_Target0 = float4(powr(_54.xyz * (float3(0.00200000009499490261077880859375, 0.00200000009499490261077880859375, 0.000600000028498470783233642578125) + (((float3(0.800000011920928955078125, 0.800000011920928955078125, 0.5) * precise::max(dot(_58, in.in_var_TEXCOORD2), 0.0)) * _86) + (((float3(0.800000011920928955078125, 0.800000011920928955078125, 0.5) * powr(precise::max(dot(in.in_var_TEXCOORD2, fast::normalize(_58 + fast::normalize(in.in_var_TEXCOORD1 - float3(Uniforms.viewPos)))), 0.0), 30.0)) * 2.0) * _86))), float3(0.4545454680919647216796875)), _54.w);
|
||||
float4 _56 = Texture.sample(Sampler, in.in_var_TEXCOORD0);
|
||||
float3 _59 = float3(0.0, 16.0, -5.0) - in.in_var_TEXCOORD1;
|
||||
float3 _60 = fast::normalize(_59);
|
||||
float _76 = 0.5 / length(_59);
|
||||
out.out_var_SV_Target0 = float4(powr(_56.xyz * (mix(float3(0.00999999977648258209228515625, 0.00999999977648258209228515625, 0.0030000000260770320892333984375), float3(0.0040000001899898052215576171875, 0.0040000001899898052215576171875, 0.0599999986588954925537109375), float3(in.in_var_TEXCOORD2.y)) + (((float3(0.800000011920928955078125, 0.800000011920928955078125, 0.5) * precise::max(dot(_60, in.in_var_TEXCOORD2), 0.0)) * _76) + (((float3(0.800000011920928955078125, 0.800000011920928955078125, 0.5) * powr(precise::max(dot(in.in_var_TEXCOORD2, fast::normalize(_60 + fast::normalize(in.in_var_TEXCOORD1 - float3(Uniforms.viewPos)))), 0.0), 30.0)) * 2.0) * _76))), float3(0.4545454680919647216796875)), _56.w);
|
||||
return out;
|
||||
}
|
||||
|
||||
|
|
|
|||
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
|
@ -63,7 +63,8 @@ pub fn prepare(self: *@This()) !void {
|
|||
exitInput.activate();
|
||||
|
||||
self.camera = try core.createEntity();
|
||||
_ = self.camera.addComponent(core.Scene).?;
|
||||
const cameraScene = self.camera.addComponent(core.Scene).?;
|
||||
cameraScene.setPosition(.{ .z = -15 });
|
||||
const camera = self.camera.addComponent(rend.CameraComponent).?;
|
||||
|
||||
{
|
||||
|
|
@ -155,6 +156,8 @@ pub fn tick(self: *@This(), dt: f64) void {
|
|||
// core.engine_log(" camera position >> {any}", .{scene.getPosRot().position});
|
||||
}
|
||||
|
||||
core.debugSphere(.{ .y = 0 }, 4, .{});
|
||||
|
||||
var show: bool = true;
|
||||
|
||||
ig.showDemoWindow(&show);
|
||||
|
|
|
|||
Loading…
Reference in New Issue