Commit for 2022.07.28 00-11-47.7z

This commit is contained in:
mrq 2022-07-28 00:11:00 -05:00
parent 40e346f71c
commit 5a12332ad8
27 changed files with 501 additions and 720 deletions

View File

@ -107,7 +107,7 @@
"deferred": true,
"vsync": false,
"hdr": false,
"vxgi": false,
"vxgi": true,
"culling": false,
"occlusion": false,
"bloom": false,

View File

@ -1,6 +1,6 @@
{
// "import": "./rp_downtown_v2.json"
"import": "./ss2_medsci1.json"
// "import": "./sh2_mcdonalds.json"
// "import": "./ss2_medsci1.json"
"import": "./sh2_mcdonalds.json"
// "import": "./gm_construct.json"
}

View File

@ -1,8 +1,8 @@
{
"import": "./base_sourceengine.json",
"assets": [
{ "filename": "./models/ss2_medsci1.glb" }
// { "filename": "./models/ss2_medsci1/graph.json" }
// { "filename": "./models/ss2_medsci1.glb" }
{ "filename": "./models/ss2_medsci1/graph.json" }
],
"metadata": {
"graph": {

View File

@ -196,4 +196,183 @@ vec4 resolve( sampler2DMS t, ivec2 uv ) {
}
resolved /= float(samples);
return resolved;
}
}
//
vec2 encodeBarycentrics( vec3 barycentric ) {
return barycentric.yz;
}
vec3 decodeBarycentrics( vec2 attributes ) {
return vec3(
1.0 - attributes.x - attributes.y,
attributes.x,
attributes.y
);
}
#if DEFERRED_SAMPLING
void populateSurface( InstanceAddresses instanceAddresses, uvec3 indices ) {
Triangle triangle;
Vertex points[3];
if ( 0 < instanceAddresses.vertex ) {
Vertices vertices = Vertices(nonuniformEXT(instanceAddresses.vertex));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_] = vertices.v[/*triangle.*/indices[_]];
} else {
if ( 0 < instanceAddresses.position ) {
VPos buf = VPos(nonuniformEXT(instanceAddresses.position));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].position = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.uv ) {
VUv buf = VUv(nonuniformEXT(instanceAddresses.uv));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].uv = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.st ) {
VSt buf = VSt(nonuniformEXT(instanceAddresses.st));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].st = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.normal ) {
VNormal buf = VNormal(nonuniformEXT(instanceAddresses.normal));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].normal = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.tangent ) {
VTangent buf = VTangent(nonuniformEXT(instanceAddresses.tangent));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].tangent = buf.v[/*triangle.*/indices[_]];
}
}
#if FETCH_BARYCENTRIC
{
const vec3 p = vec3(inverse( surface.instance.model ) * vec4(surface.position.world, 1));
const vec3 a = points[0].position;
const vec3 b = points[1].position;
const vec3 c = points[2].position;
const vec3 v0 = b - a;
const vec3 v1 = c - a;
const vec3 v2 = p - a;
const float d00 = dot(v0, v0);
const float d01 = dot(v0, v1);
const float d11 = dot(v1, v1);
const float d20 = dot(v2, v0);
const float d21 = dot(v2, v1);
const float denom = d00 * d11 - d01 * d01;
const float v = (d11 * d20 - d01 * d21) / denom;
const float w = (d00 * d21 - d01 * d20) / denom;
const float u = 1.0f - v - w;
surface.barycentric = vec3( u, v, w );
}
#endif
triangle.geomNormal = normalize(cross(points[1].position - points[0].position, points[2].position - points[0].position));
triangle.point.normal = /*triangle.*/points[0].normal * surface.barycentric[0] + /*triangle.*/points[1].normal * surface.barycentric[1] + /*triangle.*/points[2].normal * surface.barycentric[2];
triangle.point.position = /*triangle.*/points[0].position * surface.barycentric[0] + /*triangle.*/points[1].position * surface.barycentric[1] + /*triangle.*/points[2].position * surface.barycentric[2];
triangle.point.uv = /*triangle.*/points[0].uv * surface.barycentric[0] + /*triangle.*/points[1].uv * surface.barycentric[1] + /*triangle.*/points[2].uv * surface.barycentric[2];
triangle.point.st = /*triangle.*/points[0].st * surface.barycentric[0] + /*triangle.*/points[1].st * surface.barycentric[1] + /*triangle.*/points[2].st * surface.barycentric[2];
triangle.point.tangent = /*triangle.*/points[0].tangent * surface.barycentric[0] + /*triangle.*/points[1].tangent * surface.barycentric[1] + /*triangle.*/points[2].tangent * surface.barycentric[2];
if ( triangle.point.tangent != vec3(0) ) {
vec3 tangent = normalize(vec3( surface.instance.model * vec4(triangle.point.tangent, 0.0) ));
vec3 bitangent = normalize(vec3( surface.instance.model * vec4(cross( triangle.point.normal, triangle.point.tangent ), 0.0) ));
surface.tbn = mat3(tangent, bitangent, triangle.point.normal);
}
// bind position
#if !FETCH_BARYCENTRIC
{
surface.position.world = vec3( surface.instance.model * vec4(triangle.point.position, 1.0 ) );
surface.position.eye = vec3( ubo.eyes[surface.pass].view * vec4(surface.position.world, 1.0) );
}
#endif
// bind normals
{
surface.normal.world = normalize(vec3( surface.instance.model * vec4(triangle.point.normal, 0.0 ) ));
// surface.normal.eye = vec3( ubo.eyes[surface.pass].view * vec4(surface.normal.world, 0.0) );
}
// bind UVs
{
surface.uv.xy = triangle.point.uv;
surface.uv.z = 0;
surface.st.xy = triangle.point.st;
surface.st.z = 0;
}
const Material material = materials[surface.instance.materialID];
surface.material.albedo = material.colorBase;
surface.material.metallic = material.factorMetallic;
surface.material.roughness = material.factorRoughness;
surface.material.occlusion = material.factorOcclusion;
surface.light = material.colorEmissive;
if ( validTextureIndex( material.indexAlbedo ) ) {
surface.material.albedo *= sampleTexture( material.indexAlbedo );
}
// OPAQUE
if ( material.modeAlpha == 0 ) {
surface.material.albedo.a = 1;
// BLEND
} else if ( material.modeAlpha == 1 ) {
// MASK
} else if ( material.modeAlpha == 2 ) {
}
// Lightmap
if ( (surface.subID++ > 0 || bool(ubo.settings.lighting.useLightmaps)) && validTextureIndex( surface.instance.lightmapID ) ) {
vec4 light = sampleTexture( surface.instance.lightmapID, surface.st );
surface.material.lightmapped = light.a > 0.001;
if ( surface.material.lightmapped ) surface.light += surface.material.albedo * light;
} else {
surface.material.lightmapped = false;
}
// Emissive textures
if ( validTextureIndex( material.indexEmissive ) ) {
surface.light += sampleTexture( material.indexEmissive );
}
// Occlusion map
if ( validTextureIndex( material.indexOcclusion ) ) {
surface.material.occlusion = sampleTexture( material.indexOcclusion ).r;
}
// Metallic/Roughness map
if ( validTextureIndex( material.indexMetallicRoughness ) ) {
vec4 samp = sampleTexture( material.indexMetallicRoughness );
surface.material.metallic = samp.r;
surface.material.roughness = samp.g;
}
// Normals
if ( validTextureIndex( material.indexNormal ) && surface.tangent != vec3(0) ) {
surface.normal.world = surface.tbn * normalize( sampleTexture( material.indexNormal ).xyz * 2.0 - vec3(1.0));
}
{
surface.normal.eye = normalize(vec3( ubo.eyes[surface.pass].view * vec4(surface.normal.world, 0.0) ));
}
}
void populateSurface( uint instanceID, uint primitiveID ) {
surface.fragment = vec4(0);
surface.light = vec4(0);
surface.instance = instances[instanceID];
const InstanceAddresses instanceAddresses = instanceAddresses[instanceID];
if ( !(0 < instanceAddresses.index) ) return;
const DrawCommand drawCommand = Indirects(nonuniformEXT(instanceAddresses.indirect)).dc[instanceAddresses.drawID];
const uint triangleID = primitiveID + (drawCommand.indexID / 3);
uvec3 indices = Indices(nonuniformEXT(instanceAddresses.index)).i[triangleID];
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/indices[_] += drawCommand.vertexID;
populateSurface( instanceAddresses, indices );
}
void populateSurface( RayTracePayload payload ) {
surface.fragment = vec4(0);
surface.light = vec4(0);
surface.instance = instances[payload.instanceID];
if ( !payload.hit ) return;
surface.barycentric = decodeBarycentrics(payload.attributes);
populateSurface( payload.instanceID, payload.primitiveID );
}
#endif

View File

@ -9,9 +9,6 @@
#ifndef MAX_MSAA_SAMPLES
#define MAX_MSAA_SAMPLES 16
#endif
#ifndef DEFERRED_SAMPLING
#define DEFERRED_SAMPLING 1
#endif
#ifndef CAN_DISCARD
#define CAN_DISCARD 1
#endif

View File

@ -187,8 +187,9 @@ struct Surface {
vec3 st;
Space position;
Space normal;
vec3 tangent;
mat3 tbn;
vec3 barycentrics;
vec3 barycentric;
vec2 motion;
Ray ray;

View File

@ -167,7 +167,7 @@ void indirectLighting() {
surface.material.indirect = indirectDiffuse * DIFFUSE_INDIRECT_FACTOR + indirectSpecular * SPECULAR_INDIRECT_FACTOR;
// outFragColor.rgb = surface.material.indirect.rgb; return;
#if DEFERRED_SAMPLING
// deferred sampling doesn't have a blended albedo buffer
// in place we'll just cone trace behind the window
if ( surface.material.albedo.a < 1.0 ) {
@ -177,5 +177,4 @@ void indirectLighting() {
vec4 radiance = voxelConeTrace( ray, surface.material.albedo.a * 0.5 );
surface.fragment.rgb += (1.0 - surface.material.albedo.a) * radiance.rgb;
}
#endif
}

View File

@ -1,7 +1,8 @@
#version 450
#pragma shader_stage(compute)
#define DEFERRED_SAMPLING 1
#define RT 0
#define VXGI 0
#define MULTISAMPLING 0
#include "./comp.h"

View File

@ -1,7 +1,7 @@
#extension GL_EXT_samplerless_texture_functions : require
#extension GL_EXT_nonuniform_qualifier : enable
#if RAYTRACE
#if RT
#extension GL_EXT_ray_query : require
#endif
@ -15,6 +15,8 @@ layout (local_size_x = 8, local_size_y = 8, local_size_z = 2) in;
#define WHITENOISE 0
#define PBR 1
#define BUFFER_REFERENCE 1
#define DEFERRED_SAMPLING 1
#define FETCH_BARYCENTRIC 1
//#define TEXTURE_WORKAROUND 0
#include "../../common/macros.h"
@ -27,17 +29,15 @@ layout (constant_id = 1) const uint CUBEMAPS = 128;
#if !MULTISAMPLING
layout(binding = 0) uniform utexture2D samplerId;
layout(binding = 1) uniform texture2D samplerBary;
layout(binding = 5) uniform texture2D samplerDepth;
layout(binding = 1) uniform texture2D samplerDepth;
#else
layout(binding = 0) uniform utexture2DMS samplerId;
layout(binding = 1) uniform texture2DMS samplerBary;
layout(binding = 5) uniform texture2DMS samplerDepth;
layout(binding = 1) uniform texture2DMS samplerDepth;
#endif
layout(binding = 6, rgba16f) uniform volatile coherent image2D imageColor;
layout(binding = 7, rgba16f) uniform volatile coherent image2D imageBright;
layout(binding = 8, rg16f) uniform volatile coherent image2D imageMotion;
layout(binding = 2, rgba16f) uniform volatile coherent image2D imageColor;
layout(binding = 3, rgba16f) uniform volatile coherent image2D imageBright;
layout(binding = 4, rg16f) uniform volatile coherent image2D imageMotion;
layout( push_constant ) uniform PushBlock {
uint pass;
@ -46,42 +46,42 @@ layout( push_constant ) uniform PushBlock {
#include "../../common/structs.h"
layout (binding = 9) uniform UBO {
layout (binding = 5) uniform UBO {
EyeMatrices eyes[2];
Settings settings;
} ubo;
/*
*/
layout (std140, binding = 10) readonly buffer DrawCommands {
layout (std140, binding = 6) readonly buffer DrawCommands {
DrawCommand drawCommands[];
};
layout (std140, binding = 11) readonly buffer Instances {
layout (std140, binding = 7) readonly buffer Instances {
Instance instances[];
};
layout (std140, binding = 12) readonly buffer InstanceAddresseses {
layout (std140, binding = 8) readonly buffer InstanceAddresseses {
InstanceAddresses instanceAddresses[];
};
layout (std140, binding = 13) readonly buffer Materials {
layout (std140, binding = 9) readonly buffer Materials {
Material materials[];
};
layout (std140, binding = 14) readonly buffer Textures {
layout (std140, binding = 10) readonly buffer Textures {
Texture textures[];
};
layout (std140, binding = 15) readonly buffer Lights {
layout (std140, binding = 11) readonly buffer Lights {
Light lights[];
};
layout (binding = 16) uniform sampler2D samplerTextures[TEXTURES];
layout (binding = 17) uniform samplerCube samplerCubemaps[CUBEMAPS];
layout (binding = 18) uniform sampler3D samplerNoise;
layout (binding = 12) uniform sampler2D samplerTextures[TEXTURES];
layout (binding = 13) uniform samplerCube samplerCubemaps[CUBEMAPS];
layout (binding = 14) uniform sampler3D samplerNoise;
#if VXGI
layout (binding = 19) uniform usampler3D voxelId[CASCADES];
layout (binding = 20) uniform sampler3D voxelNormal[CASCADES];
layout (binding = 21) uniform sampler3D voxelRadiance[CASCADES];
layout (binding = 15) uniform usampler3D voxelId[CASCADES];
layout (binding = 16) uniform sampler3D voxelNormal[CASCADES];
layout (binding = 17) uniform sampler3D voxelRadiance[CASCADES];
#endif
#if RAYTRACE
layout (binding = 22) uniform accelerationStructureEXT tlas;
#if RT
layout (binding = 18) uniform accelerationStructureEXT tlas;
#endif
layout(buffer_reference, scalar) buffer Vertices { Vertex v[]; };
@ -104,8 +104,11 @@ layout(buffer_reference, scalar) buffer VID { uint v[]; };
#include "../../common/vxgi.h"
#endif
#define IMAGE_LOAD(X) texelFetch( X, ivec2(gl_GlobalInvocationID.xy), 0 ) //texelFetch( X, ivec2(gl_GlobalInvocationID.xy), 0 )
#define IMAGE_LOAD_MS(X, I) texelFetch( X, ivec2(gl_GlobalInvocationID.xy), I )
#if MULTISAMPLING
#define IMAGE_LOAD(X) texelFetch( X, ivec2(gl_GlobalInvocationID.xy), msaa.currentID )
#else
#define IMAGE_LOAD(X) texelFetch( X, ivec2(gl_GlobalInvocationID.xy), 0 )
#endif
#define IMAGE_STORE(X, Y) imageStore( X, ivec2(gl_GlobalInvocationID.xy), Y )
@ -129,7 +132,7 @@ void postProcess() {
vec4 outFragColor = vec4(surface.fragment.rgb, 1.0);
IMAGE_STORE( imageColor, outFragColor );
// IMAGE_STORE( imageBright, outFragBright );
IMAGE_STORE( imageBright, outFragBright );
IMAGE_STORE( imageMotion, vec4(outFragMotion, 0, 0) );
}
@ -140,20 +143,6 @@ void populateSurface() {
surface.fragment = vec4(0);
surface.pass = PushConstant.pass;
{
#if !MULTISAMPLING
const float depth = IMAGE_LOAD(samplerDepth).r;
#else
const float depth = IMAGE_LOAD_MS(samplerDepth, msaa.currentID).r; // resolve(samplerDepth, ubo.settings.mode.msaa).r;
#endif
vec2 eUv = inUv * 2.0 - 1.0;
vec4 positionEye = ubo.eyes[surface.pass].iProjection * vec4(eUv, depth, 1.0);
positionEye /= positionEye.w;
surface.position.eye = positionEye.xyz;
surface.position.world = vec3( ubo.eyes[surface.pass].iView * positionEye );
}
{
const mat4 iProjectionView = inverse( ubo.eyes[surface.pass].projection * mat4(mat3(ubo.eyes[surface.pass].view)) );
const vec4 near4 = iProjectionView * (vec4(2.0 * inUv - 1.0, -1.0, 1.0));
@ -165,10 +154,19 @@ void populateSurface() {
surface.ray.origin = ubo.eyes[surface.pass].eyePos.xyz;
}
{
const float depth = IMAGE_LOAD(samplerDepth).r;
vec2 eUv = inUv * 2.0 - 1.0;
vec4 positionEye = ubo.eyes[surface.pass].iProjection * vec4(eUv, depth, 1.0);
positionEye /= positionEye.w;
surface.position.eye = positionEye.xyz;
surface.position.world = vec3( ubo.eyes[surface.pass].iView * positionEye );
}
#if !MULTISAMPLING
const uvec2 ID = uvec2(IMAGE_LOAD(samplerId).xy);
#else
const uvec2 ID = msaa.IDs[msaa.currentID]; // IMAGE_LOAD_MS(samplerId, msaa.currentID).xy; //resolve(samplerId, ubo.settings.mode.msaa).xy;
const uvec2 ID = msaa.IDs[msaa.currentID];
#endif
surface.motion = vec2(0);
@ -177,145 +175,18 @@ void populateSurface() {
surface.fragment.rgb = texture( samplerCubemaps[ubo.settings.lighting.indexSkybox], surface.ray.direction ).rgb;
}
surface.fragment.a = 0.0;
//postProcess();
return;
}
#if !MULTISAMPLING
// surface.barycentrics = IMAGE_LOAD(samplerBary).xyz;
{
vec2 encodedBarycentrics = IMAGE_LOAD(samplerBary).xy;
surface.barycentrics = vec3(
1.0 - encodedBarycentrics.x - encodedBarycentrics.y,
encodedBarycentrics.x,
encodedBarycentrics.y
);
}
#else
// surface.barycentrics = IMAGE_LOAD_MS(samplerBary, msaa.currentID).xyz; // resolve(samplerBary, ubo.settings.mode.msaa).xy;
{
vec2 encodedBarycentrics = IMAGE_LOAD_MS(samplerBary, msaa.currentID).xy; // resolve(samplerBary, ubo.settings.mode.msaa).xy;
surface.barycentrics = vec3(
1.0 - encodedBarycentrics.x - encodedBarycentrics.y,
encodedBarycentrics.x,
encodedBarycentrics.y
);
}
#endif
const uint drawID = ID.x - 1;
const DrawCommand drawCommand = drawCommands[drawID];
const uint instanceID = drawID;
const Instance instance = instances[instanceID];
surface.instance = instance;
{
const uint triangleID = ID.y - 1;
const InstanceAddresses instanceAddresses = instanceAddresses[instanceID];
Triangle triangle;
Vertex points[3];
uvec3 indices = uvec3( triangleID * 3 + 0, triangleID * 3 + 1, triangleID * 3 + 2 );
if ( 0 < instanceAddresses.vertex ) {
Vertices vertices = Vertices(nonuniformEXT(instanceAddresses.vertex));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_] = vertices.v[/*triangle.*/indices[_]];
} else {
if ( 0 < instanceAddresses.position ) {
VPos buf = VPos(nonuniformEXT(instanceAddresses.position));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].position = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.uv ) {
VUv buf = VUv(nonuniformEXT(instanceAddresses.uv));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].uv = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.st ) {
VSt buf = VSt(nonuniformEXT(instanceAddresses.st));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].st = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.normal ) {
VNormal buf = VNormal(nonuniformEXT(instanceAddresses.normal));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].normal = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.tangent ) {
VTangent buf = VTangent(nonuniformEXT(instanceAddresses.tangent));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].tangent = buf.v[/*triangle.*/indices[_]];
}
}
triangle.point.position = /*triangle.*/points[0].position * surface.barycentrics[0] + /*triangle.*/points[1].position * surface.barycentrics[1] + /*triangle.*/points[2].position * surface.barycentrics[2];
triangle.point.uv = /*triangle.*/points[0].uv * surface.barycentrics[0] + /*triangle.*/points[1].uv * surface.barycentrics[1] + /*triangle.*/points[2].uv * surface.barycentrics[2];
triangle.point.st = /*triangle.*/points[0].st * surface.barycentrics[0] + /*triangle.*/points[1].st * surface.barycentrics[1] + /*triangle.*/points[2].st * surface.barycentrics[2];
triangle.point.normal = /*triangle.*/points[0].normal * surface.barycentrics[0] + /*triangle.*/points[1].normal * surface.barycentrics[1] + /*triangle.*/points[2].normal * surface.barycentrics[2];
triangle.point.tangent = /*triangle.*/points[0].tangent * surface.barycentrics[0] + /*triangle.*/points[1].tangent * surface.barycentrics[1] + /*triangle.*/points[2].tangent * surface.barycentrics[2];
// bind position
if ( false ) {
surface.position.world = vec3( instance.model * vec4(triangle.point.position, 1.0 ) );
surface.position.eye = vec3( ubo.eyes[surface.pass].view * vec4(surface.position.world, 1.0) );
}
// bind normals
{
surface.normal.world = normalize(vec3( instance.model * vec4(triangle.point.normal, 0.0 ) ));
surface.normal.eye = vec3( ubo.eyes[surface.pass].view * vec4(surface.normal.world, 0.0) );
}
// bind UVs
{
surface.uv.xy = triangle.point.uv;
surface.uv.z = 0;
surface.st.xy = triangle.point.st;
surface.st.z = 0;
}
}
const Material material = materials[surface.instance.materialID];
surface.material.albedo = material.colorBase;
surface.material.metallic = material.factorMetallic;
surface.material.roughness = material.factorRoughness;
surface.material.occlusion = material.factorOcclusion;
surface.fragment = material.colorEmissive;
if ( validTextureIndex( material.indexAlbedo ) ) {
surface.material.albedo *= sampleTexture( material.indexAlbedo );
}
// OPAQUE
if ( material.modeAlpha == 0 ) {
surface.material.albedo.a = 1;
// BLEND
} else if ( material.modeAlpha == 1 ) {
// MASK
} else if ( material.modeAlpha == 2 ) {
}
// Lightmap
if ( bool(ubo.settings.lighting.useLightmaps) && validTextureIndex( surface.instance.lightmapID ) ) {
vec4 light = sampleTexture( surface.instance.lightmapID, surface.st );
surface.material.lightmapped = light.a > 0.001;
if ( surface.material.lightmapped ) surface.light += surface.material.albedo * light;
} else {
surface.material.lightmapped = false;
}
// Emissive textures
if ( validTextureIndex( material.indexEmissive ) ) {
surface.light += sampleTexture( material.indexEmissive );
}
// Occlusion map
if ( validTextureIndex( material.indexOcclusion ) ) {
surface.material.occlusion = sampleTexture( material.indexOcclusion ).r;
}
// Metallic/Roughness map
if ( validTextureIndex( material.indexMetallicRoughness ) ) {
vec4 samp = sampleTexture( material.indexMetallicRoughness );
surface.material.metallic = samp.r;
surface.material.roughness = samp.g;
const uint triangleID = ID.x - 1;
const uint instanceID = ID.y - 1;
surface.subID = 1;
populateSurface( instanceID, triangleID );
}
{
vec4 pNDC = ubo.eyes[surface.pass].previous * instance.previous * vec4(surface.position.world, 1);
vec4 cNDC = ubo.eyes[surface.pass].model * instance.model * vec4(surface.position.world, 1);
vec4 pNDC = ubo.eyes[surface.pass].previous * surface.instance.previous * vec4(surface.position.world, 1);
vec4 cNDC = ubo.eyes[surface.pass].model * surface.instance.model * vec4(surface.position.world, 1);
pNDC /= pNDC.w;
cNDC /= cNDC.w;
@ -340,7 +211,7 @@ void directLighting() {
void resolveSurfaceFragment() {
for ( int i = 0; i < ubo.settings.mode.msaa; ++i ) {
msaa.currentID = i;
msaa.IDs[i] = uvec3(IMAGE_LOAD_MS(samplerId, msaa.currentID)).xy;
msaa.IDs[i] = uvec3(IMAGE_LOAD(samplerId)).xy;
// check if ID is already used
bool unique = true;

View File

@ -1,7 +1,8 @@
#version 450
#pragma shader_stage(compute)
#define DEFERRED_SAMPLING 1
#define RT 0
#define VXGI 0
#define MULTISAMPLING 1
#include "./comp.h"

View File

@ -1,10 +1,9 @@
#version 450
#pragma shader_stage(compute)
#define VXGI 0
#define DEFERRED_SAMPLING 1
#define MULTISAMPLING 0
#define RT 1
#define VXGI 0
#define MULTISAMPLING 0
#include "./comp.h"
void main() {

View File

@ -1,10 +1,9 @@
#version 450
#pragma shader_stage(compute)
#define VXGI 0
#define DEFERRED_SAMPLING 1
#define MULTISAMPLING 1
#define RT 1
#define VXGI 0
#define MULTISAMPLING 1
#include "./comp.h"
void main() {

View File

@ -1,10 +1,9 @@
#version 450
#pragma shader_stage(compute)
#define VXGI 1
#define DEFERRED_SAMPLING 1
#define MULTISAMPLING 0
#define RT 1
#define VXGI 1
#define MULTISAMPLING 1
#include "./comp.h"
void main() {

View File

@ -1,10 +1,9 @@
#version 450
#pragma shader_stage(compute)
#define VXGI 1
#define DEFERRED_SAMPLING 1
#define MULTISAMPLING 0
#define RT 0
#define VXGI 1
#define MULTISAMPLING 0
#include "./comp.h"
void main() {

View File

@ -1,10 +1,9 @@
#version 450
#pragma shader_stage(compute)
#define VXGI 1
#define DEFERRED_SAMPLING 1
#define MULTISAMPLING 1
#define RT 0
#define VXGI 1
#define MULTISAMPLING 1
#include "./comp.h"
void main() {

View File

@ -1,7 +1,135 @@
#version 450
#pragma shader_stage(compute)
#define MULTISAMPLING 0
#define DEFERRED_SAMPLING 0
#extension GL_EXT_samplerless_texture_functions : require
#extension GL_EXT_nonuniform_qualifier : enable
#include "./comp.h"
layout (local_size_x = 8, local_size_y = 8, local_size_z = 8) in;
#define LAMBERT 0
#define PBR 1
#define VXGI 1
#define COMPUTE 1
layout (constant_id = 0) const uint TEXTURES = 512;
layout (constant_id = 1) const uint CUBEMAPS = 128;
layout (constant_id = 2) const uint CASCADES = 16;
#include "../../common/macros.h"
#include "../../common/structs.h"
layout (binding = 0) uniform UBO {
EyeMatrices matrices[2];
Settings settings;
} ubo;
layout (std140, binding = 1) readonly buffer DrawCommands {
DrawCommand drawCommands[];
};
layout (std140, binding = 2) readonly buffer Instances {
Instance instances[];
};
layout (std140, binding = 3) readonly buffer InstanceAddresseses {
InstanceAddresses instanceAddresses[];
};
layout (std140, binding = 4) readonly buffer Materials {
Material materials[];
};
layout (std140, binding = 5) readonly buffer Textures {
Texture textures[];
};
layout (std140, binding = 6) readonly buffer Lights {
Light lights[];
};
layout (binding = 7) uniform sampler2D samplerTextures[TEXTURES];
layout (binding = 8) uniform samplerCube samplerCubemaps[CUBEMAPS];
layout (binding = 9) uniform sampler3D samplerNoise;
layout (binding = 10, rg16ui) uniform volatile coherent uimage3D voxelId[CASCADES];
layout (binding = 11, rg16f) uniform volatile coherent image3D voxelNormal[CASCADES];
#if VXGI_HDR
layout (binding = 12, rgba32f) uniform volatile coherent image3D voxelRadiance[CASCADES];
#else
layout (binding = 12, rgba16f) uniform volatile coherent image3D voxelRadiance[CASCADES];
#endif
#include "../../common/functions.h"
#include "../../common/light.h"
#undef VXGI
#include "../../common/shadows.h"
void main() {
const vec3 tUvw = gl_GlobalInvocationID.xzy;
for ( uint CASCADE = 0; CASCADE < CASCADES; ++CASCADE ) {
surface.normal.world = decodeNormals( vec2(imageLoad(voxelNormal[CASCADE], ivec3(tUvw) ).xy) );
surface.normal.eye = vec3( ubo.settings.vxgi.matrix * vec4( surface.normal.world, 0.0f ) );
surface.position.eye = (vec3(gl_GlobalInvocationID.xyz) / vec3(imageSize(voxelRadiance[CASCADE])) * 2.0f - 1.0f) * cascadePower(CASCADE);
surface.position.world = vec3( inverse(ubo.settings.vxgi.matrix) * vec4( surface.position.eye, 1.0f ) );
const uvec2 ID = uvec2(imageLoad(voxelId[CASCADE], ivec3(tUvw) ).xy);
const uint drawID = ID.x - 1;
const uint instanceID = ID.y - 1;
if ( ID.x == 0 || ID.y == 0 ) {
imageStore(voxelRadiance[CASCADE], ivec3(tUvw), vec4(0));
continue;
}
const DrawCommand drawCommand = drawCommands[drawID];
surface.instance = instances[instanceID];
const Material material = materials[surface.instance.materialID];
surface.material.albedo = material.colorBase;
surface.fragment = material.colorEmissive;
surface.material.albedo = imageLoad(voxelRadiance[CASCADE], ivec3(tUvw) );
surface.material.metallic = material.factorMetallic;
surface.material.roughness = material.factorRoughness;
surface.material.occlusion = material.factorOcclusion;
const vec3 ambient = ubo.settings.lighting.ambient.rgb * surface.material.occlusion;
if ( validTextureIndex( surface.instance.lightmapID ) ) {
surface.fragment.rgb += surface.material.albedo.rgb;
} else {
surface.fragment.rgb += surface.material.albedo.rgb * ambient;
// corrections
surface.material.roughness *= 4.0;
const vec3 F0 = mix(vec3(0.04), surface.material.albedo.rgb, surface.material.metallic);
const vec3 Lo = normalize( surface.position.world );
const float cosLo = max(0.0, dot(surface.normal.world, Lo));
for ( uint i = 0; i < ubo.settings.lengths.lights; ++i ) {
const Light light = lights[i];
if ( light.power <= LIGHT_POWER_CUTOFF ) continue;
if ( light.type >= 0 && validTextureIndex( surface.instance.lightmapID ) ) continue;
const vec3 Lp = light.position;
const vec3 Liu = light.position - surface.position.world;
const vec3 Li = normalize(Liu);
const float Ls = shadowFactor( light, 0.0 );
const float La = 1.0 / (PI * pow(length(Liu), 2.0));
if ( light.power * La * Ls <= LIGHT_POWER_CUTOFF ) continue;
const float cosLi = max(0.0, dot(surface.normal.world, Li));
const vec3 Lr = light.color.rgb * light.power * La * Ls;
#if LAMBERT
const vec3 diffuse = surface.material.albedo.rgb;
const vec3 specular = vec3(0);
#elif PBR
const vec3 Lh = normalize(Li + Lo);
const float cosLh = max(0.0, dot(surface.normal.world, Lh));
const vec3 F = fresnelSchlick( F0, max( 0.0, dot(Lh, Lo) ) );
const float D = ndfGGX( cosLh, surface.material.roughness );
const float G = gaSchlickGGX(cosLi, cosLo, surface.material.roughness);
const vec3 diffuse = mix( vec3(1.0) - F, vec3(0.0), surface.material.metallic ) * surface.material.albedo.rgb;
const vec3 specular = (F * D * G) / max(EPSILON, 4.0 * cosLi * cosLo);
#endif
// lightmapped, compute only specular
surface.light.rgb += (diffuse + specular) * Lr * cosLi;
surface.light.a += light.power * La * Ls;
}
}
surface.fragment.rgb += surface.light.rgb;
imageStore(voxelRadiance[CASCADE], ivec3(tUvw), vec4(surface.fragment.rgb, surface.material.albedo.a));
}
}

View File

@ -1,132 +0,0 @@
#extension GL_EXT_samplerless_texture_functions : require
#extension GL_EXT_nonuniform_qualifier : enable
layout (local_size_x = 8, local_size_y = 8, local_size_z = 8) in;
#define LAMBERT 0
#define PBR 1
#define VXGI 1
#define COMPUTE 1
layout (constant_id = 0) const uint TEXTURES = 512;
layout (constant_id = 1) const uint CUBEMAPS = 128;
layout (constant_id = 2) const uint CASCADES = 16;
#include "../../common/macros.h"
#include "../../common/structs.h"
layout (binding = 0) uniform UBO {
EyeMatrices matrices[2];
Settings settings;
} ubo;
layout (std140, binding = 1) readonly buffer DrawCommands {
DrawCommand drawCommands[];
};
layout (std140, binding = 2) readonly buffer Instances {
Instance instances[];
};
layout (std140, binding = 3) readonly buffer InstanceAddresseses {
InstanceAddresses instanceAddresses[];
};
layout (std140, binding = 4) readonly buffer Materials {
Material materials[];
};
layout (std140, binding = 5) readonly buffer Textures {
Texture textures[];
};
layout (std140, binding = 6) readonly buffer Lights {
Light lights[];
};
layout (binding = 7) uniform sampler2D samplerTextures[TEXTURES];
layout (binding = 8) uniform samplerCube samplerCubemaps[CUBEMAPS];
layout (binding = 9) uniform sampler3D samplerNoise;
layout (binding = 10, rg16ui) uniform volatile coherent uimage3D voxelId[CASCADES];
layout (binding = 11, rg16f) uniform volatile coherent image3D voxelNormal[CASCADES];
#if VXGI_HDR
layout (binding = 12, rgba32f) uniform volatile coherent image3D voxelRadiance[CASCADES];
#else
layout (binding = 12, rgba16f) uniform volatile coherent image3D voxelRadiance[CASCADES];
#endif
#include "../../common/functions.h"
#include "../../common/light.h"
#undef VXGI
#include "../../common/shadows.h"
void main() {
const vec3 tUvw = gl_GlobalInvocationID.xzy;
for ( uint CASCADE = 0; CASCADE < CASCADES; ++CASCADE ) {
surface.normal.world = decodeNormals( vec2(imageLoad(voxelNormal[CASCADE], ivec3(tUvw) ).xy) );
surface.normal.eye = vec3( ubo.settings.vxgi.matrix * vec4( surface.normal.world, 0.0f ) );
surface.position.eye = (vec3(gl_GlobalInvocationID.xyz) / vec3(imageSize(voxelRadiance[CASCADE])) * 2.0f - 1.0f) * cascadePower(CASCADE);
surface.position.world = vec3( inverse(ubo.settings.vxgi.matrix) * vec4( surface.position.eye, 1.0f ) );
const uvec2 ID = uvec2(imageLoad(voxelId[CASCADE], ivec3(tUvw) ).xy);
const uint drawID = ID.x - 1;
const uint instanceID = ID.y - 1;
if ( ID.x == 0 || ID.y == 0 ) {
imageStore(voxelRadiance[CASCADE], ivec3(tUvw), vec4(0));
continue;
}
const DrawCommand drawCommand = drawCommands[drawID];
surface.instance = instances[instanceID];
const Material material = materials[surface.instance.materialID];
surface.material.albedo = material.colorBase;
surface.fragment = material.colorEmissive;
surface.material.albedo = imageLoad(voxelRadiance[CASCADE], ivec3(tUvw) );
surface.material.metallic = material.factorMetallic;
surface.material.roughness = material.factorRoughness;
surface.material.occlusion = material.factorOcclusion;
const vec3 ambient = ubo.settings.lighting.ambient.rgb * surface.material.occlusion;
if ( validTextureIndex( surface.instance.lightmapID ) ) {
surface.fragment.rgb += surface.material.albedo.rgb;
} else {
surface.fragment.rgb += surface.material.albedo.rgb * ambient;
// corrections
surface.material.roughness *= 4.0;
const vec3 F0 = mix(vec3(0.04), surface.material.albedo.rgb, surface.material.metallic);
const vec3 Lo = normalize( surface.position.world );
const float cosLo = max(0.0, dot(surface.normal.world, Lo));
for ( uint i = 0; i < ubo.settings.lengths.lights; ++i ) {
const Light light = lights[i];
if ( light.power <= LIGHT_POWER_CUTOFF ) continue;
if ( light.type >= 0 && validTextureIndex( surface.instance.lightmapID ) ) continue;
const vec3 Lp = light.position;
const vec3 Liu = light.position - surface.position.world;
const vec3 Li = normalize(Liu);
const float Ls = shadowFactor( light, 0.0 );
const float La = 1.0 / (PI * pow(length(Liu), 2.0));
if ( light.power * La * Ls <= LIGHT_POWER_CUTOFF ) continue;
const float cosLi = max(0.0, dot(surface.normal.world, Li));
const vec3 Lr = light.color.rgb * light.power * La * Ls;
#if LAMBERT
const vec3 diffuse = surface.material.albedo.rgb;
const vec3 specular = vec3(0);
#elif PBR
const vec3 Lh = normalize(Li + Lo);
const float cosLh = max(0.0, dot(surface.normal.world, Lh));
const vec3 F = fresnelSchlick( F0, max( 0.0, dot(Lh, Lo) ) );
const float D = ndfGGX( cosLh, surface.material.roughness );
const float G = gaSchlickGGX(cosLi, cosLo, surface.material.roughness);
const vec3 diffuse = mix( vec3(1.0) - F, vec3(0.0), surface.material.metallic ) * surface.material.albedo.rgb;
const vec3 specular = (F * D * G) / max(EPSILON, 4.0 * cosLi * cosLo);
#endif
// lightmapped, compute only specular
surface.light.rgb += (diffuse + specular) * Lr * cosLi;
surface.light.a += light.power * La * Ls;
}
}
surface.fragment.rgb += surface.light.rgb;
imageStore(voxelRadiance[CASCADE], ivec3(tUvw), vec4(surface.fragment.rgb, surface.material.albedo.a));
}
}

View File

@ -1,7 +0,0 @@
#version 450
#pragma shader_stage(compute)
#define MULTISAMPLING 1
#define DEFERRED_SAMPLING 0
#include "./comp.h"

View File

@ -47,48 +47,44 @@ layout (binding = 13, rgba8) uniform volatile coherent image3D outAlbedos;
#endif
layout (location = 0) flat in uvec4 inId;
layout (location = 1) flat in vec4 inPOS0;
layout (location = 2) in vec4 inPOS1;
layout (location = 3) in vec3 inPosition;
layout (location = 4) in vec2 inUv;
layout (location = 5) in vec4 inColor;
layout (location = 6) in vec2 inSt;
layout (location = 7) in vec3 inNormal;
layout (location = 8) in vec3 inTangent;
layout (location = 1) in vec3 inPosition;
layout (location = 2) in vec2 inUv;
layout (location = 3) in vec4 inColor;
layout (location = 4) in vec2 inSt;
layout (location = 5) in vec3 inNormal;
layout (location = 6) in vec3 inTangent;
layout (location = 0) out vec4 outAlbedo;
void main() {
const uint drawID = uint(inId.x);
const uint triangleID = uint(inId.y);
const uint triangleID = uint(inId.x); // gl_PrimitiveID
const uint drawID = uint(inId.y);
const uint instanceID = uint(inId.z);
const DrawCommand drawCommand = drawCommands[drawID];
const Instance instance = instances[instanceID];
vec3 N = inNormal;
vec3 T = inTangent;
T = normalize(T - dot(T, N) * N);
vec3 B = cross(T, N);
// mat3 TBN = mat3(T, B, N);
mat3 TBN = mat3(N, B, T);
surface.uv.xy = wrap(inUv.xy);
surface.uv.z = mipLevel(dFdx(inUv), dFdy(inUv));
surface.position.world = inPosition;
const Material material = materials[instance.materialID];
vec4 A = material.colorBase;
surface.material.metallic = material.factorMetallic;
surface.material.roughness = material.factorRoughness;
surface.material.occlusion = 1.0f - material.factorOcclusion;
vec3 N = inNormal;
vec3 T = inTangent;
T = normalize(T - dot(T, N) * N);
vec3 B = cross(T, N);
mat3 TBN = mat3(T, B, N);
// mat3 TBN = mat3(N, B, T);
if ( T != vec3(0) && validTextureIndex( material.indexNormal ) ) {
surface.normal.world = TBN * normalize( sampleTexture( material.indexNormal ).xyz * 2.0 - 1.0 );
} else {
surface.normal.world = N;
}
vec4 A = material.colorBase;
surface.material.metallic = material.factorMetallic;
surface.material.roughness = material.factorRoughness;
surface.material.occlusion = 1.0f - material.factorOcclusion;
surface.light = material.colorEmissive;
surface.material.albedo = vec4(1);

View File

@ -2,16 +2,14 @@
#pragma shader_stage(fragment)
//#extension GL_EXT_nonuniform_qualifier : enable
#extension GL_EXT_fragment_shader_barycentric : enable
#extension GL_AMD_shader_explicit_vertex_parameter : enable
#define STABILIZE_BARY 1
#define DEFERRED_SAMPLING 1
#define QUERY_MIPMAP 0
#define EXTRA_ATTRIBUTES 1
#define CUBEMAPS 1
#define FRAGMENT 1
#define CAN_DISCARD 1
#define BARYCENTRIC 0
// #define MAX_TEXTURES TEXTURES
#define MAX_TEXTURES textures.length()
layout (constant_id = 0) const uint TEXTURES = 1;
@ -42,114 +40,49 @@ layout (std140, binding = 11) readonly buffer Lights {
#include "../../common/functions.h"
layout (location = 0) flat in uvec4 inId;
layout (location = 1) flat in vec4 inPOS0;
layout (location = 2) __explicitInterpAMD in vec4 inPOS1;
#if EXTRA_ATTRIBUTES
layout (location = 3) in vec3 inPosition;
layout (location = 4) in vec2 inUv;
layout (location = 5) in vec4 inColor;
layout (location = 6) in vec2 inSt;
layout (location = 7) in vec3 inNormal;
layout (location = 8) in vec3 inTangent;
layout (location = 1) in vec3 inPosition;
layout (location = 2) in vec2 inUv;
layout (location = 3) in vec4 inColor;
layout (location = 4) in vec2 inSt;
layout (location = 5) in vec3 inNormal;
layout (location = 6) in vec3 inTangent;
#endif
layout (location = 0) out uvec2 outId;
layout (location = 1) out vec2 outBary;
#if 0 && EXTRA_ATTRIBUTES
layout (location = 2) out vec2 outMips;
layout (location = 3) out vec2 outNormals;
layout (location = 4) out vec4 outUvs;
#endif
void main() {
const uint drawID = uint(inId.x);
const uint triangleID = uint(inId.y);
const uint triangleID = gl_PrimitiveID; // uint(inId.x);
const uint drawID = uint(inId.y);
const uint instanceID = uint(inId.z);
#if EXTRA_ATTRIBUTES && CAN_DISCARD
const DrawCommand drawCommand = drawCommands[drawID];
const Instance instance = instances[instanceID];
const Material material = materials[instance.materialID];
#if EXTRA_ATTRIBUTES
#if CAN_DISCARD
{
surface.uv.xy = wrap(inUv.xy);
surface.uv.z = mipLevel(dFdx(inUv), dFdy(inUv));
surface.uv.xy = wrap(inUv.xy);
surface.uv.z = mipLevel(dFdx(inUv), dFdy(inUv));
vec4 A = inColor * material.colorBase;
// sample albedo
if ( validTextureIndex( material.indexAlbedo ) ) {
A = sampleTexture( material.indexAlbedo );
// alpha mode OPAQUE
if ( material.modeAlpha == 0 ) {
A.a = 1;
// alpha mode BLEND
} else if ( material.modeAlpha == 1 ) {
vec4 A = inColor * material.colorBase;
// sample albedo
if ( validTextureIndex( material.indexAlbedo ) ) {
A = sampleTexture( material.indexAlbedo );
}
// alpha mode OPAQUE
if ( material.modeAlpha == 0 ) {
A.a = 1;
// alpha mode BLEND
} else if ( material.modeAlpha == 1 ) {
// alpha mode MASK
} else if ( material.modeAlpha == 2 ) {
if ( A.a < abs(material.factorAlphaCutoff) ) discard;
A.a = 1;
}
if ( A.a < 1 ) discard;
}
// alpha mode MASK
} else if ( material.modeAlpha == 2 ) {
if ( A.a < abs(material.factorAlphaCutoff) ) discard;
A.a = 1;
}
#endif
#if 0
{
vec3 T = inTangent;
vec3 N = inNormal;
T = normalize(T - dot(T, N) * N);
vec3 B = cross(T, N);
mat3 TBN = mat3(T, B, N);
// mat3 TBN = mat3(N, B, T);
// sample normal
if ( T != vec3(0) && validTextureIndex( material.indexNormal ) ) {
N = TBN * normalize( sampleTexture( material.indexNormal ).xyz * 2.0 - 1.0 );
}
outUvs.xy = surface.uv.xy;
outUvs.zw = surface.st.xy;
outMips.x = surface.uv.z;
outMips.y = surface.st.z;
outNormals = encodeNormals( normalize( N ) );
}
#endif
if ( A.a < 0.0001 ) discard;
#endif
outId = uvec2(drawID + 1, triangleID + 1);
#if STABILIZE_BARY
vec4 v0 = interpolateAtVertexAMD(inPOS1, 0);
vec4 v1 = interpolateAtVertexAMD(inPOS1, 1);
vec4 v2 = interpolateAtVertexAMD(inPOS1, 2);
#if 0
vec3 bary;
if (v0 == inPOS0) {
bary.y = gl_BaryCoordSmoothAMD.x;
bary.z = gl_BaryCoordSmoothAMD.y;
bary.x = 1 - bary.y - bary.z;
}
else if (v1 == inPOS0) {
bary.x = gl_BaryCoordSmoothAMD.x;
bary.y = gl_BaryCoordSmoothAMD.y;
bary.z = 1 - bary.y - bary.x;
}
else if (v2 == inPOS0) {
bary.z = gl_BaryCoordSmoothAMD.x;
bary.x = gl_BaryCoordSmoothAMD.y;
bary.y = 1 - bary.z - bary.x;
}
outBary = bary.yz;
#else
if (v0 == inPOS0)
outBary = (gl_BaryCoordEXT.yzx).yz;
else if (v1 == inPOS0)
outBary = (gl_BaryCoordEXT.zxy).yz;
else if (v2 == inPOS0)
outBary = (gl_BaryCoordEXT.xyz).yz;
#endif
#else
outBary = gl_BaryCoordEXT.yz;
#endif
// outId = uvec2(triangleID + 1, instanceID + 1);
outId = uvec2(triangleID + 1, instanceID + 1);
}

View File

@ -45,16 +45,13 @@ layout (std140, binding = 2) readonly buffer Instances {
#endif
layout (location = 0) out uvec4 outId;
layout (location = 1) flat out vec4 outPOS0;
layout (location = 2) out vec4 outPOS1;
#if EXTRA_ATTRIBUTES
layout (location = 3) out vec3 outPosition;
layout (location = 4) out vec2 outUv;
layout (location = 5) out vec4 outColor;
layout (location = 6) out vec2 outSt;
layout (location = 7) out vec3 outNormal;
layout (location = 8) out vec3 outTangent;
layout (location = 1) out vec3 outPosition;
layout (location = 2) out vec2 outUv;
layout (location = 3) out vec4 outColor;
layout (location = 4) out vec2 outSt;
layout (location = 5) out vec3 outNormal;
layout (location = 6) out vec3 outTangent;
#endif
vec4 snap(vec4 vertex, vec2 resolution) {
@ -68,11 +65,9 @@ vec4 snap(vec4 vertex, vec2 resolution) {
void main() {
const uint drawID = gl_DrawIDARB;
const uint triangleID = gl_VertexIndex / 3;
const uint instanceID = gl_InstanceIndex;
const DrawCommand drawCommand = drawCommands[drawID];
const uint instanceID = drawCommand.instanceID; // gl_InstanceIndex;
const Instance instance = instances[instanceID];
const uint materialID = instance.materialID;
const uint jointID = instance.jointID;
#if BAKING
@ -96,9 +91,7 @@ void main() {
#else
gl_Position = projection * view * model * vec4(inPos.xyz, 1.0);
#endif
outId = uvec4(drawID, triangleID, instanceID, PushConstant.pass);
outPOS0 = gl_Position;
outPOS1 = gl_Position;
outId = uvec4(triangleID, drawID, instanceID, PushConstant.pass);
#if EXTRA_ATTRIBUTES
outPosition = vec3(model * vec4(inPos.xyz, 1.0));

View File

@ -34,28 +34,28 @@ layout (std140, binding = 11) readonly buffer Lights {
#include "../../common/functions.h"
layout (location = 0) flat in uvec4 inId;
layout (location = 1) flat in vec4 inPOS0;
layout (location = 2) in vec4 inPOS1;
#if EXTRA_ATTRIBUTES
layout (location = 3) in vec3 inPosition;
layout (location = 4) in vec2 inUv;
layout (location = 5) in vec4 inColor;
layout (location = 6) in vec2 inSt;
layout (location = 7) in vec3 inNormal;
layout (location = 8) in vec3 inTangent;
layout (location = 1) in vec3 inPosition;
layout (location = 2) in vec2 inUv;
layout (location = 3) in vec4 inColor;
layout (location = 4) in vec2 inSt;
layout (location = 5) in vec3 inNormal;
layout (location = 6) in vec3 inTangent;
#endif
void main() {
const uint drawID = uint(inId.x);
const uint instanceID = uint(inId.y);
const uint materialID = uint(inId.z);
const vec2 uv = wrap(inUv.xy);
const uint triangleID = uint(inId.x); // gl_PrimitiveID
const uint drawID = uint(inId.y);
const uint instanceID = uint(inId.z);
const Material material = materials[materialID];
vec4 A = material.colorBase;
surface.uv.xy = uv;
const DrawCommand drawCommand = drawCommands[drawID];
const Instance instance = instances[instanceID];
const Material material = materials[instance.materialID];
surface.uv.xy = wrap(inUv.xy);
surface.uv.z = mipLevel(dFdx(inUv), dFdy(inUv));
vec4 A = inColor * material.colorBase;
// sample albedo
if ( validTextureIndex( material.indexAlbedo ) ) {
A = sampleTexture( material.indexAlbedo );
@ -71,5 +71,5 @@ void main() {
if ( A.a < abs(material.factorAlphaCutoff) ) discard;
A.a = 1;
}
// if ( A.a < 1 - 0.00001 ) discard;
if ( A.a < 1 ) discard;
}

View File

@ -48,15 +48,12 @@ layout (binding = 13, rg16f) uniform volatile coherent image3D voxelNormal[CASCA
#endif
layout (location = 0) flat in uvec4 inId;
layout (location = 1) flat in vec4 inPOS0;
layout (location = 2) /*__explicitInterpAMD*/ in vec4 inPOS1;
layout (location = 3) in vec3 inPosition;
layout (location = 4) in vec2 inUv;
layout (location = 5) in vec4 inColor;
layout (location = 6) in vec2 inSt;
layout (location = 7) in vec3 inNormal;
layout (location = 8) in vec3 inTangent;
layout (location = 1) in vec3 inPosition;
layout (location = 2) in vec2 inUv;
layout (location = 3) in vec4 inColor;
layout (location = 4) in vec2 inSt;
layout (location = 5) in vec3 inNormal;
layout (location = 6) in vec3 inTangent;
#include "../../common/functions.h"
@ -66,23 +63,16 @@ void main() {
const vec3 P = inPosition.xzy * 0.5 + 0.5;
if ( abs(P.x) > 1 || abs(P.y) > 1 || abs(P.z) > 1 ) discard;
const uint drawID = uint(inId.x);
const uint triangleID = uint(inId.y);
const uint triangleID = uint(inId.x); // gl_PrimitiveID
const uint drawID = uint(inId.y);
const uint instanceID = uint(inId.z);
const vec2 uv = wrap(inUv.xy);
surface.uv.xy = uv;
surface.uv.xy = wrap(inUv.xy);
surface.uv.z = mipLevel(dFdx(inUv), dFdy(inUv));
surface.st.xy = inSt;
surface.st.z = mipLevel(dFdx(inSt), dFdy(inSt));
vec3 T = inTangent;
vec3 N = inNormal;
T = normalize(T - dot(T, N) * N);
vec3 B = cross(T, N);
// mat3 TBN = mat3(T, B, N);
mat3 TBN = mat3(N, B, T);
const DrawCommand drawCommand = drawCommands[drawID];
const Instance instance = instances[instanceID];
const Material material = materials[instance.materialID];
surface.instance = instance;
@ -95,25 +85,33 @@ void main() {
// sample albedo
if ( validTextureIndex( material.indexAlbedo ) ) {
A = sampleTexture( material.indexAlbedo );
// alpha mode OPAQUE
if ( material.modeAlpha == 0 ) {
A.a = 1;
// alpha mode BLEND
} else if ( material.modeAlpha == 1 ) {
// alpha mode MASK
} else if ( material.modeAlpha == 2 ) {
if ( A.a < abs(material.factorAlphaCutoff) ) discard;
A.a = 1;
}
if ( A.a == 0 ) discard;
}
// alpha mode OPAQUE
if ( material.modeAlpha == 0 ) {
A.a = 1;
// alpha mode BLEND
} else if ( material.modeAlpha == 1 ) {
// alpha mode MASK
} else if ( material.modeAlpha == 2 ) {
if ( A.a < abs(material.factorAlphaCutoff) ) discard;
A.a = 1;
}
if ( A.a == 0 ) discard;
#if USE_LIGHTMAP && !DEFERRED_SAMPLING
if ( validTextureIndex( instance.lightmapID ) ) {
A.rgb *= sampleTexture( instance.lightmapID, inSt ).rgb;
}
#endif
// sample normal
vec3 N = inNormal;
vec3 T = inTangent;
T = normalize(T - dot(T, N) * N);
vec3 B = cross(T, N);
mat3 TBN = mat3(T, B, N);
// mat3 TBN = mat3(N, B, T);
if ( T != vec3(0) && validTextureIndex( material.indexNormal ) ) {
N = TBN * normalize( sampleTexture( material.indexNormal ).xyz * 2.0 - 1.0 );
}

View File

@ -5,24 +5,20 @@ layout(triangles) in;
layout(triangle_strip, max_vertices = 3) out;
layout (location = 0) flat in uvec4 inId[];
layout (location = 1) flat in vec4 inPOS0[];
layout (location = 2) in vec4 inPOS1[];
layout (location = 3) in vec3 inPosition[];
layout (location = 4) in vec2 inUv[];
layout (location = 5) in vec4 inColor[];
layout (location = 6) in vec2 inSt[];
layout (location = 7) in vec3 inNormal[];
layout (location = 8) in vec3 inTangent[];
layout (location = 1) in vec3 inPosition[];
layout (location = 2) in vec2 inUv[];
layout (location = 3) in vec4 inColor[];
layout (location = 4) in vec2 inSt[];
layout (location = 5) in vec3 inNormal[];
layout (location = 6) in vec3 inTangent[];
layout (location = 0) flat out uvec4 outId;
layout (location = 1) flat out vec4 outPOS0;
layout (location = 2) out vec4 outPOS1;
layout (location = 3) out vec3 outPosition;
layout (location = 4) out vec2 outUv;
layout (location = 5) out vec4 outColor;
layout (location = 6) out vec2 outSt;
layout (location = 7) out vec3 outNormal;
layout (location = 8) out vec3 outTangent;
layout (location = 1) out vec3 outPosition;
layout (location = 2) out vec2 outUv;
layout (location = 3) out vec4 outColor;
layout (location = 4) out vec2 outSt;
layout (location = 5) out vec3 outNormal;
layout (location = 6) out vec3 outTangent;
layout (binding = 4) uniform UBO {
mat4 voxel;
@ -67,8 +63,6 @@ void main(){
const vec3 D = normalize( inPosition[i] - C ) * HALF_PIXEL;
outPosition = P[i] + D;
outPOS0 = inPOS0[i];
outPOS1 = inPOS1[i];
outUv = inUv[i];
outSt = inSt[i];
outColor = inColor[i];

View File

@ -1,6 +1,5 @@
#define TEXTURES 1
#define CUBEMAPS 1
#define DEFERRED_SAMPLING 0
#include "../../common/macros.h"
#include "../../common/structs.h"
@ -13,17 +12,7 @@ layout (location = 0) in vec2 inUv;
layout (location = 1) in flat Gui inGui;
layout (location = 7) in flat Glyph inGlyph;
#if 1
layout (location = 0) out vec4 outAlbedo;
#else
layout (location = 0) out uvec2 outId;
layout (location = 1) out vec2 outNormals;
#if DEFERRED_SAMPLING
layout (location = 2) out vec4 outUvs;
#else
layout (location = 2) out vec4 outAlbedo;
#endif
#endif
void main() {
if ( inUv.x < inGui.offset.x || inUv.y < inGui.offset.y || inUv.x > inGui.offset.z || inUv.y > inGui.offset.w ) discard;

View File

@ -20,6 +20,7 @@ layout (constant_id = 3) const uint CASCADES = 1;
#define MAX_TEXTURES TEXTURES
#define TONE_MAP 0
#define GAMMA_CORRECT 0
#define DEFERRED_SAMPLING 1
#include "../common/macros.h"
#include "../common/structs.h"
@ -85,65 +86,6 @@ layout(buffer_reference, scalar) buffer VID { uint v[]; };
#include "../common/vxgi.h"
#endif
Triangle parsePayload( RayTracePayload payload ) {
Triangle triangle;
triangle.instanceID = payload.instanceID;
if ( !payload.hit ) return triangle;
const vec3 bary = vec3(
1.0 - payload.attributes.x - payload.attributes.y,
payload.attributes.x,
payload.attributes.y
);
const InstanceAddresses instanceAddresses = instanceAddresses[triangle.instanceID];
if ( !(0 < instanceAddresses.index) ) return triangle;
const DrawCommand drawCommand = Indirects(nonuniformEXT(instanceAddresses.indirect)).dc[instanceAddresses.drawID];
const uint triangleID = payload.primitiveID + (drawCommand.indexID / 3);
Vertex points[3];
uvec3 indices = Indices(nonuniformEXT(instanceAddresses.index)).i[triangleID];
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/indices[_] += drawCommand.vertexID;
if ( 0 < instanceAddresses.vertex ) {
Vertices vertices = Vertices(nonuniformEXT(instanceAddresses.vertex));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_] = vertices.v[/*triangle.*/indices[_]];
} else {
if ( 0 < instanceAddresses.position ) {
VPos buf = VPos(nonuniformEXT(instanceAddresses.position));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].position = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.uv ) {
VUv buf = VUv(nonuniformEXT(instanceAddresses.uv));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].uv = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.st ) {
VSt buf = VSt(nonuniformEXT(instanceAddresses.st));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].st = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.normal ) {
VNormal buf = VNormal(nonuniformEXT(instanceAddresses.normal));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].normal = buf.v[/*triangle.*/indices[_]];
}
if ( 0 < instanceAddresses.tangent ) {
VTangent buf = VTangent(nonuniformEXT(instanceAddresses.tangent));
for ( uint _ = 0; _ < 3; ++_ ) /*triangle.*/points[_].tangent = buf.v[/*triangle.*/indices[_]];
}
}
triangle.point.position = /*triangle.*/points[0].position * bary[0] + /*triangle.*/points[1].position * bary[1] + /*triangle.*/points[2].position * bary[2];
triangle.point.uv = /*triangle.*/points[0].uv * bary[0] + /*triangle.*/points[1].uv * bary[1] + /*triangle.*/points[2].uv * bary[2];
triangle.point.st = /*triangle.*/points[0].st * bary[0] + /*triangle.*/points[1].st * bary[1] + /*triangle.*/points[2].st * bary[2];
triangle.point.normal = /*triangle.*/points[0].normal * bary[0] + /*triangle.*/points[1].normal * bary[1] + /*triangle.*/points[2].normal * bary[2];
triangle.point.tangent = /*triangle.*/points[0].tangent * bary[0] + /*triangle.*/points[1].tangent * bary[1] + /*triangle.*/points[2].tangent * bary[2];
triangle.geomNormal = normalize(cross(points[1].position - points[0].position, points[2].position - points[0].position));
return triangle;
}
void trace( Ray ray, float tMin, float tMax ) {
uint rayFlags = gl_RayFlagsOpaqueEXT;
uint cullMask = 0xFF;
@ -186,93 +128,6 @@ float shadowFactor( const Light light, float def ) {
return payload.hit ? 0.0 : 1.0;
}
void setupSurface( RayTracePayload payload ) {
const Triangle triangle = parsePayload( payload );
const Instance instance = instances[triangle.instanceID];
surface.instance = instance;
surface.fragment = vec4(0);
surface.light = vec4(0);
// bind position
{
surface.position.world = vec3( instance.model * vec4(triangle.point.position, 1.0 ) );
surface.position.eye = vec3( ubo.eyes[surface.pass].view * vec4(surface.position.world, 1.0) );
}
// bind normals
{
surface.normal.world = normalize(vec3( instance.model * vec4(triangle.point.normal, 0.0 ) ));
// surface.normal.world = faceforward( surface.normal.world, surface.ray.direction, surface.normal.world );
// surface.normal.eye = normalize(vec3( ubo.eyes[surface.pass].view * vec4(surface.normal.world, 0.0) ));
// surface.tbn[0] = normalize(vec3( instance.model * vec4(triangle.tbn[0], 0.0 ) ));
// surface.tbn[1] = normalize(vec3( instance.model * vec4(triangle.tbn[1], 0.0 ) ));
// surface.tbn[2] = surface.normal.world;
vec3 tangent = normalize(vec3( instance.model * vec4(triangle.point.tangent, 0.0) ));
vec3 bitangent = normalize(vec3( instance.model * vec4(cross( triangle.point.normal, triangle.point.tangent ), 0.0) ));
if ( triangle.point.tangent != vec3(0) ) {
surface.tbn = mat3(tangent, bitangent, triangle.point.normal);
} else {
surface.tbn = mat3(1);
}
}
// bind UVs
{
surface.uv.xy = triangle.point.uv;
surface.st.xy = triangle.point.st;
}
const Material material = materials[surface.instance.materialID];
surface.material.albedo = material.colorBase;
surface.material.metallic = material.factorMetallic;
surface.material.roughness = material.factorRoughness;
surface.material.occlusion = material.factorOcclusion;
surface.light = material.colorEmissive;
if ( validTextureIndex( material.indexAlbedo ) ) {
surface.material.albedo *= sampleTexture( material.indexAlbedo );
}
// OPAQUE
if ( material.modeAlpha == 0 ) {
surface.material.albedo.a = 1;
// BLEND
} else if ( material.modeAlpha == 1 ) {
// MASK
} else if ( material.modeAlpha == 2 ) {
}
// Lightmap
if ( (surface.subID++ > 0 || bool(ubo.settings.lighting.useLightmaps)) && validTextureIndex( surface.instance.lightmapID ) ) {
vec4 light = sampleTexture( surface.instance.lightmapID, surface.st );
surface.material.lightmapped = light.a > 0.001;
if ( surface.material.lightmapped ) surface.light += surface.material.albedo * light;
} else {
surface.material.lightmapped = false;
}
// Emissive textures
if ( validTextureIndex( material.indexEmissive ) ) {
surface.light += sampleTexture( material.indexEmissive );
}
// Occlusion map
if ( validTextureIndex( material.indexOcclusion ) ) {
surface.material.occlusion = sampleTexture( material.indexOcclusion ).r;
}
// Metallic/Roughness map
if ( validTextureIndex( material.indexMetallicRoughness ) ) {
vec4 samp = sampleTexture( material.indexMetallicRoughness );
surface.material.metallic = samp.r;
surface.material.roughness = samp.g;
}
// Normals
if ( validTextureIndex( material.indexNormal ) && surface.tbn != mat3(1) ) {
surface.normal.world = surface.tbn * normalize( sampleTexture( material.indexNormal ).xyz * 2.0 - vec3(1.0));
}
{
surface.normal.eye = normalize(vec3( ubo.eyes[surface.pass].view * vec4(surface.normal.world, 0.0) ));
}
}
void directLighting() {
#if VXGI
indirectLighting();
@ -301,7 +156,7 @@ vec4 traceStep( Ray ray ) {
trace( ray );
if ( payload.hit ) {
setupSurface( payload );
populateSurface( payload );
directLighting();
} else if ( 0 <= ubo.settings.lighting.indexSkybox && ubo.settings.lighting.indexSkybox < CUBEMAPS ) {
surface.fragment = texture( samplerCubemaps[ubo.settings.lighting.indexSkybox], ray.direction );
@ -332,7 +187,7 @@ vec4 traceStep( Ray ray ) {
trace( transparency, ubo.settings.rt.alphaTestOffset );
if ( payload.hit ) {
setupSurface( payload );
populateSurface( payload );
directLighting();
} else if ( 0 <= ubo.settings.lighting.indexSkybox && ubo.settings.lighting.indexSkybox < CUBEMAPS ) {
surface.fragment = texture( samplerCubemaps[ubo.settings.lighting.indexSkybox], ray.direction );
@ -346,7 +201,7 @@ vec4 traceStep( Ray ray ) {
eyeDepth = surface.position.eye.z;
payload = surfacePayload;
setupSurface( payload );
populateSurface( payload );
}
#if FOG
{
@ -371,7 +226,7 @@ vec4 traceStep( Ray ray ) {
trace( reflection );
if ( payload.hit ) {
setupSurface( payload );
populateSurface( payload );
directLighting();
} else if ( 0 <= ubo.settings.lighting.indexSkybox && ubo.settings.lighting.indexSkybox < CUBEMAPS ) {
surface.fragment = texture( samplerCubemaps[ubo.settings.lighting.indexSkybox], reflection.direction );
@ -383,7 +238,7 @@ vec4 traceStep( Ray ray ) {
outFrag += REFLECTED_ALBEDO * surface.fragment;
payload = surfacePayload;
setupSurface( payload );
populateSurface( payload );
}
}

View File

@ -37,7 +37,7 @@ void ext::vulkan::DeferredRenderMode::initialize( Device& device ) {
size_t msaa = ext::vulkan::settings::msaa;
struct {
size_t id, bary, mips, normals, uvs, motion, depth, color, bright, scratch, output;
size_t id, depth, color, bright, scratch, motion, output;
} attachments = {};
bool blend = true; // !ext::vulkan::settings::invariant::deferredSampling;
@ -50,13 +50,6 @@ void ext::vulkan::DeferredRenderMode::initialize( Device& device ) {
/*.blend = */false,
/*.samples = */msaa,
});
attachments.bary = renderTarget.attach(RenderTarget::Attachment::Descriptor{
/*.format = */VK_FORMAT_R16G16_SFLOAT,
/*.layout = */ VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
/*.usage = */VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT | VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_TRANSIENT_ATTACHMENT_BIT,
/*.blend = */false,
/*.samples = */msaa,
});
attachments.depth = renderTarget.attach(RenderTarget::Attachment::Descriptor{
/*.format = */ext::vulkan::settings::formats::depth,
/*.layout = */VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
@ -97,7 +90,6 @@ void ext::vulkan::DeferredRenderMode::initialize( Device& device ) {
});
metadata.attachments["id"] = attachments.id;
metadata.attachments["bary"] = attachments.bary;
metadata.attachments["depth"] = attachments.depth;
metadata.attachments["color"] = attachments.color;
@ -111,7 +103,7 @@ void ext::vulkan::DeferredRenderMode::initialize( Device& device ) {
for ( size_t eye = 0; eye < metadata.eyes; ++eye ) {
renderTarget.addPass(
/*.*/ VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT,
/*.colors =*/ { attachments.id, attachments.bary },
/*.colors =*/ { attachments.id },
/*.inputs =*/ {},
/*.resolve =*/{},
/*.depth = */ attachments.depth,
@ -248,7 +240,6 @@ void ext::vulkan::DeferredRenderMode::initialize( Device& device ) {
if ( settings::pipelines::deferred && blitter.material.hasShader("compute", "deferred-compute") ) {
this->textures.clear();
this->textures.emplace_back().aliasAttachment( renderTarget.attachments[metadata.attachments["id"]] );
this->textures.emplace_back().aliasAttachment( renderTarget.attachments[metadata.attachments["bary"]] );
this->textures.emplace_back().aliasAttachment( renderTarget.attachments[metadata.attachments["depth"]] );
{
auto& texture = this->textures.emplace_back();
@ -341,7 +332,6 @@ void ext::vulkan::DeferredRenderMode::tick() {
this->textures.clear();
this->textures.emplace_back().aliasAttachment( renderTarget.attachments[metadata.attachments["id"]] );
this->textures.emplace_back().aliasAttachment( renderTarget.attachments[metadata.attachments["bary"]] );
this->textures.emplace_back().aliasAttachment( renderTarget.attachments[metadata.attachments["depth"]] );
{
auto& texture = this->textures.emplace_back();