diff --git a/engine/rend/shaders/lit_mesh.frag.hlsl b/engine/rend/shaders/lit_mesh.frag.hlsl index 7407a59..fdcc1e2 100644 --- a/engine/rend/shaders/lit_mesh.frag.hlsl +++ b/engine/rend/shaders/lit_mesh.frag.hlsl @@ -4,17 +4,72 @@ SamplerState Sampler : register(s0, space2); cbuffer Uniforms : register(b0, space3) { float time; + float3 viewPos; }; -float4 main(float2 UV : TEXCOORD0, float3 WorldPos: TEXCOORD1) : SV_Target0 +// from learnopengl.com +float3 BlinnPhong(float3 normal, float3 fragPos, float3 lightPos, float3 lightColor) { - float4 col = pow(Texture.Sample(Sampler, UV), 0.4545); + // diffuse parameter + float3 lightDir = normalize(lightPos - fragPos); + float diff = max(dot(lightDir, normal), 0.0); + float3 diffuse = diff * lightColor; - float SPEEEEEEEEEEEEEED = 0.0001 * time; - float strength = 0.00001; + // specular parameter + float3 viewDir = normalize(fragPos - viewPos); + float3 reflectDir = reflect(-lightDir, normal); + float spec = 0.0; + float3 halfwayDir = normalize(lightDir + viewDir); + spec = pow(max(dot(normal, halfwayDir), 0.0), 30.0); + float3 specular = spec * lightColor * 2; - col.r = col.r + strength * sin(time * SPEEEEEEEEEEEEEED) * WorldPos.x + strength * cos(time * SPEEEEEEEEEEEEEED) * WorldPos.y; + // attenuation + float maxDist = 5; + float cutoff1 = 2; + float cutoff2 = 4; + 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; + } + - return col; + diffuse *= attenuation; + specular *= attenuation; + + return diffuse + specular; + + //return lightColor * 100 * attenuation; + +} + +float4 main( + float2 UV : TEXCOORD0, + float3 WorldPos: TEXCOORD1, + float3 Normal: TEXCOORD2 +) : SV_Target0 +{ + float3 lightPos = float3(0, 20 + -4, -5); + float3 lightColor = float3(0.8, 0.8, 0.5); + float3 ambient = float3(0.01, 0.01, 0.003) * 0.2; + + float4 s = Texture.Sample(Sampler, UV); + float alpha = s.w; + + float3 col = s.xyz; + float3 c2 = col * ambient + col * BlinnPhong(Normal, WorldPos, lightPos, lightColor); + + float4 rv = float4(pow(c2, 1.0 / 2.2), alpha); + return rv; } diff --git a/engine/rend/shaders/lit_mesh.frag.json b/engine/rend/shaders/lit_mesh.frag.json index dc0a6a1..0becd0f 100644 --- a/engine/rend/shaders/lit_mesh.frag.json +++ b/engine/rend/shaders/lit_mesh.frag.json @@ -6,13 +6,18 @@ } ], "types" : { - "_10" : { + "_11" : { "name" : "type.Uniforms", "members" : [ { "name" : "time", "type" : "float", "offset" : 0 + }, + { + "name" : "viewPos", + "type" : "vec3", + "offset" : 4 } ] } @@ -27,6 +32,11 @@ "type" : "vec3", "name" : "in.var.TEXCOORD1", "location" : 1 + }, + { + "type" : "vec3", + "name" : "in.var.TEXCOORD2", + "location" : 2 } ], "outputs" : [ @@ -54,9 +64,9 @@ ], "ubos" : [ { - "type" : "_10", + "type" : "_11", "name" : "type.Uniforms", - "block_size" : 4, + "block_size" : 16, "set" : 3, "binding" : 0 } diff --git a/engine/rend/shaders/meshes.vert.hlsl b/engine/rend/shaders/meshes.vert.hlsl index 59046e0..6fb84fc 100644 --- a/engine/rend/shaders/meshes.vert.hlsl +++ b/engine/rend/shaders/meshes.vert.hlsl @@ -14,6 +14,7 @@ struct Output { float2 TexCoord : TEXCOORD0; float3 WorldPos : TEXCOORD1; + float3 Normal: TEXCOORD2; float4 Position : SV_Position; }; @@ -43,6 +44,7 @@ Output main(Input input) output.Position = mul(ViewProjection, mul(scene[input.Instance].Model, pos)); output.WorldPos = pos.xyz; + output.Normal = input.Normal; return output; } diff --git a/engine/rend/shaders/meshes.vert.json b/engine/rend/shaders/meshes.vert.json index 9abb29a..223906d 100644 --- a/engine/rend/shaders/meshes.vert.json +++ b/engine/rend/shaders/meshes.vert.json @@ -6,7 +6,7 @@ } ], "types" : { - "_9" : { + "_11" : { "name" : "Scene", "members" : [ { @@ -18,12 +18,12 @@ } ] }, - "_8" : { + "_10" : { "name" : "type.StructuredBuffer.Scene", "members" : [ { "name" : "_m0", - "type" : "_9", + "type" : "_11", "array" : [ 0 ], @@ -35,7 +35,7 @@ } ] }, - "_11" : { + "_13" : { "name" : "type.Uniforms", "members" : [ { @@ -59,6 +59,11 @@ "name" : "in.var.TEXCOORD0", "location" : 0 }, + { + "type" : "vec3", + "name" : "in.var.TEXCOORD1", + "location" : 1 + }, { "type" : "vec2", "name" : "in.var.TEXCOORD3", @@ -75,11 +80,16 @@ "type" : "vec3", "name" : "out.var.TEXCOORD1", "location" : 1 + }, + { + "type" : "vec3", + "name" : "out.var.TEXCOORD2", + "location" : 2 } ], "ssbos" : [ { - "type" : "_8", + "type" : "_10", "name" : "scene", "readonly" : true, "block_size" : 0, @@ -89,7 +99,7 @@ ], "ubos" : [ { - "type" : "_11", + "type" : "_13", "name" : "type.Uniforms", "block_size" : 68, "set" : 1, diff --git a/engine/rend/src/camera/CameraComponent.zig b/engine/rend/src/camera/CameraComponent.zig index 1bb8319..b29a911 100644 --- a/engine/rend/src/camera/CameraComponent.zig +++ b/engine/rend/src/camera/CameraComponent.zig @@ -23,6 +23,7 @@ yaw: f32 = 0, pitch: f32 = 0, roll: f32 = 0, +finalPos: core.Vectorf = .{}, final: Mat = zm.identity(), finalAlt: Mat = zm.identity(), @@ -46,6 +47,8 @@ pub fn resolve(self: *@This()) void { self.updateProjections(); var position = scene.getPosition(); + self.finalPos = position; + position.z = -position.z; position.y = -position.y; { diff --git a/engine/rend/src/sgpu/renderer.zig b/engine/rend/src/sgpu/renderer.zig index 536fd33..15afa91 100644 --- a/engine/rend/src/sgpu/renderer.zig +++ b/engine/rend/src/sgpu/renderer.zig @@ -96,6 +96,14 @@ pub const Renderer = struct { ), ); + try assets.load( + assets.MakeImportRefOptions( + "Mesh", + "m_default_cube", + .{ .path = "meshes/primitive_box.obj" }, + ), + ); + var defaultTextureName = core.MakeName("t_default"); self.defaultTexture = getTexture(&defaultTextureName).?; } @@ -369,6 +377,12 @@ pub const Renderer = struct { const ptr: *lit_mesh_frag.Uniforms = @ptrCast(@alignCast(&data)); ptr.time = @floatCast(self.totalTime); + var position: core.Vectorf = .{}; + if (self.activeCamera) |cam| { + position = cam.finalPos; + } + + ptr.viewPos = @bitCast(position); cmd.pushGPUFragmentUniformData(0, &data, @sizeOf(lit_mesh_frag.Uniforms)); } } diff --git a/projects/content/_shaders/dxil/lit_mesh.frag.dxil b/projects/content/_shaders/dxil/lit_mesh.frag.dxil index c742c37..f2b005b 100644 Binary files a/projects/content/_shaders/dxil/lit_mesh.frag.dxil and b/projects/content/_shaders/dxil/lit_mesh.frag.dxil differ diff --git a/projects/content/_shaders/dxil/meshes.vert.dxil b/projects/content/_shaders/dxil/meshes.vert.dxil index 304f9a0..935c502 100644 Binary files a/projects/content/_shaders/dxil/meshes.vert.dxil and b/projects/content/_shaders/dxil/meshes.vert.dxil differ diff --git a/projects/content/_shaders/msl/lit_mesh.frag.msl b/projects/content/_shaders/msl/lit_mesh.frag.msl index a49c3e9..e8c494d 100644 --- a/projects/content/_shaders/msl/lit_mesh.frag.msl +++ b/projects/content/_shaders/msl/lit_mesh.frag.msl @@ -6,6 +6,7 @@ using namespace metal; struct type_Uniforms { float time; + packed_float3 viewPos; }; struct main0_out @@ -17,15 +18,36 @@ struct main0_in { float2 in_var_TEXCOORD0 [[user(locn0)]]; float3 in_var_TEXCOORD1 [[user(locn1)]]; + float3 in_var_TEXCOORD2 [[user(locn2)]]; }; fragment main0_out main0(main0_in in [[stage_in]], constant type_Uniforms& Uniforms [[buffer(0)]], texture2d Texture [[texture(0)]], sampler Sampler [[sampler(0)]]) { main0_out out = {}; - float4 _40 = powr(Texture.sample(Sampler, in.in_var_TEXCOORD0), float4(0.4544999897480010986328125)); - float _45 = Uniforms.time * (9.9999997473787516355514526367188e-05 * Uniforms.time); - _40.x = (_40.x + ((9.9999997473787516355514526367188e-06 * sin(_45)) * in.in_var_TEXCOORD1.x)) + ((9.9999997473787516355514526367188e-06 * cos(_45)) * in.in_var_TEXCOORD1.y); - out.out_var_SV_Target0 = _40; + 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); return out; } diff --git a/projects/content/_shaders/msl/meshes.vert.msl b/projects/content/_shaders/msl/meshes.vert.msl index 068f8c4..d9c90e1 100644 --- a/projects/content/_shaders/msl/meshes.vert.msl +++ b/projects/content/_shaders/msl/meshes.vert.msl @@ -23,22 +23,25 @@ struct main0_out { float2 out_var_TEXCOORD0 [[user(locn0)]]; float3 out_var_TEXCOORD1 [[user(locn1)]]; + float3 out_var_TEXCOORD2 [[user(locn2)]]; float4 gl_Position [[position]]; }; struct main0_in { float3 in_var_TEXCOORD0 [[attribute(0)]]; + float3 in_var_TEXCOORD1 [[attribute(1)]]; float2 in_var_TEXCOORD3 [[attribute(3)]]; }; 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 = {}; - float4 _41 = float4(in.in_var_TEXCOORD0, 1.0); + float4 _44 = float4(in.in_var_TEXCOORD0, 1.0); out.out_var_TEXCOORD0 = in.in_var_TEXCOORD3; - out.out_var_TEXCOORD1 = _41.xyz; - out.gl_Position = Uniforms.ViewProjection * (scene._m0[gl_InstanceIndex].Model * _41); + out.out_var_TEXCOORD1 = _44.xyz; + out.out_var_TEXCOORD2 = in.in_var_TEXCOORD1; + out.gl_Position = Uniforms.ViewProjection * (scene._m0[gl_InstanceIndex].Model * _44); return out; } diff --git a/projects/content/_shaders/spv/lit_mesh.frag.spv b/projects/content/_shaders/spv/lit_mesh.frag.spv index a67a828..57d6a4f 100644 Binary files a/projects/content/_shaders/spv/lit_mesh.frag.spv and b/projects/content/_shaders/spv/lit_mesh.frag.spv differ diff --git a/projects/content/_shaders/spv/meshes.vert.spv b/projects/content/_shaders/spv/meshes.vert.spv index 019eed8..7166783 100644 Binary files a/projects/content/_shaders/spv/meshes.vert.spv and b/projects/content/_shaders/spv/meshes.vert.spv differ diff --git a/projects/sampleGame/main.zig b/projects/sampleGame/main.zig index 3df0012..703dd30 100644 --- a/projects/sampleGame/main.zig +++ b/projects/sampleGame/main.zig @@ -1,7 +1,7 @@ allocator: std.mem.Allocator, camera: core.Entity = undefined, -cameraSpeed: f32 = 100.0, +cameraSpeed: f32 = 10.0, moveInput: *core.Axis2dBinding = undefined, @@ -25,6 +25,11 @@ const assetReferences = [_]assets.AssetImportReference{ "m_empire", .{ .path = "meshes/lost_empire.obj" }, ), + assets.MakeImportRefOptions( + "Mesh", + "m_skybox", + .{ .path = "meshes/skybox.obj" }, + ), assets.MakeImportRefOptions( "Mesh", "m_fox", @@ -80,6 +85,16 @@ pub fn prepare(self: *@This()) !void { mesh.setTexture("t_fox"); } + { + const lightbox = try core.createEntity(); + const scene = lightbox.addComponent(core.Scene).?; + scene.setPosition(.{ .y = 2 }); + scene.setScale(0.1, 0.1, 0.1); + const mesh = lightbox.addComponent(rend.MeshComponent).?; + mesh.setMesh("m_default_cube"); + mesh.setTexture("t_default"); + } + rend.setActiveCamera(camera); self.moveInput = try core.Axis2dBinding.create(core.MakeName("movement"));