diff --git a/Seele.natvis b/Seele.natvis
index 6921e5f..2c863d3 100644
--- a/Seele.natvis
+++ b/Seele.natvis
@@ -30,7 +30,7 @@
- value
-
+
{{ size={_size} }
- _size
diff --git a/external/slang b/external/slang
index cc22270..4547125 160000
--- a/external/slang
+++ b/external/slang
@@ -1 +1 @@
-Subproject commit cc222702a8d7a1fccf8ad14b256570bcec1554ae
+Subproject commit 4547125ce945140dc10542e9606b225dd06159b8
diff --git a/res/shaders/BasePass.slang b/res/shaders/BasePass.slang
index 11ecd29..659670b 100644
--- a/res/shaders/BasePass.slang
+++ b/res/shaders/BasePass.slang
@@ -15,7 +15,7 @@ layout(set=5)
ParameterBlock pLightCullingData;
[shader("pixel")]
-float4 pixelMain(in MaterialParameter params : PARAMETER) : SV_Target
+float4 fragmentMain(in MaterialParameter params : PARAMETER) : SV_Target
{
let brdf = pMaterial.prepare(params);
float3 result = float3(0, 0, 0);
@@ -27,5 +27,5 @@ float4 pixelMain(in MaterialParameter params : PARAMETER) : SV_Target
{
result += pLightEnv.pointLights[i].illuminate(params, brdf);
}
- return float4(1, 1, 0, 1.0f);
+ return float4(result, 1.0f);
}
diff --git a/res/shaders/Placeholder.json b/res/shaders/Placeholder.json
index 89e2329..08d2e12 100644
--- a/res/shaders/Placeholder.json
+++ b/res/shaders/Placeholder.json
@@ -1,5 +1,5 @@
{
- "name": "TerrainMaterial",
+ "name": "Placeholder",
"params": {
},
"code": [
diff --git a/res/shaders/lib/MaterialParameter.slang b/res/shaders/lib/MaterialParameter.slang
index 77ae5a6..1659ad5 100644
--- a/res/shaders/lib/MaterialParameter.slang
+++ b/res/shaders/lib/MaterialParameter.slang
@@ -7,6 +7,7 @@ struct MaterialParameter
float3 tangent;
float3 biTangent;
float3 viewDir_TS;
+ float3 vertexColor;
}
struct VertexAttributes
diff --git a/res/shaders/lib/StaticMeshVertexData.slang b/res/shaders/lib/StaticMeshVertexData.slang
index c20d491..dd89d60 100644
--- a/res/shaders/lib/StaticMeshVertexData.slang
+++ b/res/shaders/lib/StaticMeshVertexData.slang
@@ -17,6 +17,7 @@ struct StaticMeshVertexData : IVertexData
params.normal = float3(normals[3 * index + 0], normals[3 * index + 1], normals[3 * index + 2]);
params.tangent = float3(tangents[3 * index + 0], tangents[3 * index + 1], tangents[3 * index + 2]);
params.biTangent = float3(biTangents[3 * index + 0], biTangents[3 * index + 1], biTangents[3 * index + 2]);
+ params.vertexColor = float3(color[3 * index + 0], color[3 * index + 1], color[3 * index + 2]);
attributes.parameter = params;
attributes.clipPosition = clipPos;
return attributes;
@@ -26,4 +27,5 @@ struct StaticMeshVertexData : IVertexData
StructuredBuffer normals;
StructuredBuffer tangents;
StructuredBuffer biTangents;
+ StructuredBuffer color;
};
diff --git a/src/Editor/Asset/MaterialLoader.cpp b/src/Editor/Asset/MaterialLoader.cpp
index 0fc8483..b6e1ac1 100644
--- a/src/Editor/Asset/MaterialLoader.cpp
+++ b/src/Editor/Asset/MaterialLoader.cpp
@@ -51,7 +51,7 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
uint32 uniformBufferOffset = 0;
uint32 bindingCounter = 0; // Uniform buffers are always binding 0
int32 uniformBinding = -1;
- Map expressions;
+ Array expressions;
uint32 key = 0;
uint32 auxKey = 0;
Array parameters;
@@ -74,7 +74,7 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
p->data = std::stof(defaultValue.value().get());
}
parameters.add(p->key);
- expressions[param.key()] = std::move(p);
+ expressions.add(std::move(p));
}
// TODO: ALIGNMENT RULES
else if(type.compare("float3") == 0)
@@ -91,7 +91,7 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
p->data = parseVector(defaultValue.value().get().c_str());
}
parameters.add(p->key);
- expressions[param.key()] = std::move(p);
+ expressions.add(std::move(p));
}
else if(type.compare("Texture2D") == 0)
{
@@ -107,7 +107,7 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
p->data = AssetRegistry::findTexture(""); // this will return placeholder texture
}
parameters.add(p->key);
- expressions[param.key()] = std::move(p);
+ expressions.add(std::move(p));
}
else if(type.compare("SamplerState") == 0)
{
@@ -115,7 +115,7 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
layout->addDescriptorBinding(bindingCounter++, Gfx::SE_DESCRIPTOR_TYPE_SAMPLER);
p->data = graphics->createSamplerState({});
parameters.add(p->key);
- expressions[param.key()] = std::move(p);
+ expressions.add(std::move(p));
}
else
{
@@ -128,14 +128,14 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
if(obj.is_string())
{
std::string str = obj.get();
- if (expressions.contains(str))
+ if (expressions.find([&str, &expressions](const OShaderExpression& exp) {return exp->key == str; }) != expressions.end())
{
return str;
}
OConstantExpression c = new ConstantExpression(str, ExpressionType::UNKNOWN);
std::string name = std::format("Const{0}", auxKey++);
c->key = name;
- expressions[name] = std::move(c);
+ expressions.add(std::move(c));
return name;
}
else
@@ -156,7 +156,7 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
p->key = name;
p->inputs["lhs"].source = referenceExpression(obj["lhs"]);
p->inputs["rhs"].source = referenceExpression(obj["rhs"]);
- expressions[name] = std::move(p);
+ expressions.add(std::move(p));
}
if(exp.compare("Sub") == 0)
{
@@ -165,7 +165,7 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
p->key = name;
p->inputs["lhs"].source = referenceExpression(obj["lhs"]);
p->inputs["rhs"].source = referenceExpression(obj["rhs"]);
- expressions[name] = std::move(p);
+ expressions.add(std::move(p));
}
if(exp.compare("Mul") == 0)
{
@@ -174,12 +174,12 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
p->key = name;
p->inputs["lhs"].source = referenceExpression(obj["lhs"]);
p->inputs["rhs"].source = referenceExpression(obj["rhs"]);
- expressions[name] = std::move(p);
+ expressions.add(std::move(p));
}
if(exp.compare("Swizzle") == 0)
{
OSwizzleExpression p = new SwizzleExpression();
- std::string name = std::format("{0}", key);
+ std::string name = std::format("{0}", key++);
p->key = name;
p->inputs["target"].source = referenceExpression(obj["target"]);
int32 i = 0;
@@ -187,17 +187,17 @@ void MaterialLoader::import(MaterialImportArgs args, PMaterialAsset asset)
{
p->comp[i++] = c.value().get();
}
- expressions[name] = std::move(p);
+ expressions.add(std::move(p));
}
if(exp.compare("Sample") == 0)
{
OSampleExpression p = new SampleExpression();
- std::string name = std::format("{0}", key);
+ std::string name = std::format("{0}", key++);
p->key = name;
p->inputs["texture"].source = referenceExpression(obj["texture"]);
p->inputs["sampler"].source = referenceExpression(obj["sampler"]);
p->inputs["coords"].source = referenceExpression(obj["coords"]);
- expressions[name] = std::move(p);
+ expressions.add(std::move(p));
}
if(exp.compare("BRDF") == 0)
{
diff --git a/src/Editor/Asset/MeshLoader.cpp b/src/Editor/Asset/MeshLoader.cpp
index 340e37d..687eec0 100644
--- a/src/Editor/Asset/MeshLoader.cpp
+++ b/src/Editor/Asset/MeshLoader.cpp
@@ -155,6 +155,7 @@ void MeshLoader::loadGlobalMeshes(const aiScene* scene, const Array normals(mesh->mNumVertices);
Array tangents(mesh->mNumVertices);
Array biTangents(mesh->mNumVertices);
+ Array colors(mesh->mNumVertices);
StaticMeshVertexData* vertexData = StaticMeshVertexData::getInstance();
@@ -165,6 +166,14 @@ void MeshLoader::loadGlobalMeshes(const aiScene* scene, const ArraymNormals[i].x, mesh->mNormals[i].y, mesh->mNormals[i].z);
tangents[i] = Vector(mesh->mTangents[i].x, mesh->mTangents[i].y, mesh->mTangents[i].z);
biTangents[i] = Vector(mesh->mBitangents[i].x, mesh->mBitangents[i].y, mesh->mBitangents[i].z);
+ if(mesh->HasVertexColors(0))
+ {
+ colors[i] = Vector(mesh->mColors[0][i].r, mesh->mColors[0][i].g, mesh->mColors[0][i].b);
+ }
+ else
+ {
+ colors[i] = Vector(1, 1, 1);
+ }
}
MeshId id = vertexData->allocateVertexData(mesh->mNumVertices);
@@ -173,6 +182,7 @@ void MeshLoader::loadGlobalMeshes(const aiScene* scene, const ArrayloadNormals(id, normals);
vertexData->loadTangents(id, tangents);
vertexData->loadBiTangents(id, biTangents);
+ vertexData->loadColors(id, colors);
Array indices(mesh->mNumFaces * 3);
for (size_t faceIndex = 0; faceIndex < mesh->mNumFaces; ++faceIndex)
diff --git a/src/Engine/Graphics/Shader.cpp b/src/Engine/Graphics/Shader.cpp
index c5e4d0a..c217dca 100644
--- a/src/Engine/Graphics/Shader.cpp
+++ b/src/Engine/Graphics/Shader.cpp
@@ -50,10 +50,17 @@ void ShaderCompiler::registerRenderPass(std::string name, std::string mainFile,
void ShaderCompiler::compile()
{
- ShaderPermutation permutation;
for (const auto& [name, pass] : passes)
{
- std::strncpy(permutation.vertexMeshFile, pass.mainFile.c_str(), sizeof(permutation.vertexMeshFile));
+ ShaderPermutation permutation;
+ if (pass.useMeshShading)
+ {
+ permutation.setMeshFile(pass.mainFile);
+ }
+ else
+ {
+ permutation.setVertexFile(pass.mainFile);
+ }
if (pass.hasFragmentShader)
{
permutation.setFragmentFile(pass.fragmentFile);
@@ -81,19 +88,22 @@ void ShaderCompiler::compile()
}
}
-ShaderCollection& ShaderCompiler::createShaders(ShaderPermutation permutation)
+void ShaderCompiler::createShaders(ShaderPermutation permutation)
{
std::scoped_lock lock(shadersLock);
+ PermutationId perm = PermutationId(permutation);
+ if (shaders.contains(perm))
+ return;
ShaderCollection collection;
ShaderCreateInfo createInfo;
- createInfo.typeParameter = { Pair("IVertexData", permutation.vertexDataName) };
createInfo.name = std::format("Material {0}", permutation.materialName);
if (std::strlen(permutation.materialName) > 0)
{
createInfo.additionalModules.add(permutation.materialName);
createInfo.typeParameter.add(Pair("IMaterial", permutation.materialName));
}
+ createInfo.typeParameter.add({ Pair("IVertexData", permutation.vertexDataName) });
createInfo.additionalModules.add(permutation.vertexDataName);
createInfo.additionalModules.add(permutation.vertexMeshFile);
if (permutation.hasFragment)
@@ -131,8 +141,5 @@ ShaderCollection& ShaderCompiler::createShaders(ShaderPermutation permutation)
collection.fragmentShader = graphics->createFragmentShader(createInfo);
}
collection.vertexDeclaration = graphics->createVertexDeclaration(Array());
- PermutationId perm = PermutationId(permutation);
shaders[perm] = std::move(collection);
-
- return shaders[perm];
}
\ No newline at end of file
diff --git a/src/Engine/Graphics/Shader.h b/src/Engine/Graphics/Shader.h
index a41d67f..2adda51 100644
--- a/src/Engine/Graphics/Shader.h
+++ b/src/Engine/Graphics/Shader.h
@@ -148,7 +148,7 @@ public:
std::string taskFile = "");
private:
void compile();
- ShaderCollection& createShaders(ShaderPermutation permutation);
+ void createShaders(ShaderPermutation permutation);
std::mutex shadersLock;
Map shaders;
Map materials;
diff --git a/src/Engine/Graphics/StaticMeshVertexData.cpp b/src/Engine/Graphics/StaticMeshVertexData.cpp
index 77f36dc..1fefcbf 100644
--- a/src/Engine/Graphics/StaticMeshVertexData.cpp
+++ b/src/Engine/Graphics/StaticMeshVertexData.cpp
@@ -61,6 +61,14 @@ void StaticMeshVertexData::loadBiTangents(MeshId id, const Array& data)
dirty = true;
}
+void Seele::StaticMeshVertexData::loadColors(MeshId id, const Array& data)
+{
+ uint64 offset = meshOffsets[id];
+ assert(offset + data.size() <= head);
+ std::memcpy(colorData.data() + offset, data.data(), data.size() * sizeof(Vector));
+ dirty = true;
+}
+
void StaticMeshVertexData::serializeMesh(MeshId id, uint64 numVertices, ArchiveBuffer& buffer)
{
uint64 offset = meshOffsets[id];
@@ -69,16 +77,19 @@ void StaticMeshVertexData::serializeMesh(MeshId id, uint64 numVertices, ArchiveB
Array nor(numVertices);
Array tan(numVertices);
Array bit(numVertices);
+ Array col(numVertices);
std::copy(positionData.begin() + offset, positionData.begin() + offset + numVertices, pos.begin());
std::copy(texCoordsData.begin() + offset, texCoordsData.begin() + offset + numVertices, tex.begin());
std::copy(normalData.begin() + offset, normalData.begin() + offset + numVertices, nor.begin());
std::copy(tangentData.begin() + offset, tangentData.begin() + offset + numVertices, tan.begin());
std::copy(biTangentData.begin() + offset, biTangentData.begin() + offset + numVertices, bit.begin());
+ std::copy(colorData.begin() + offset, colorData.begin() + offset + numVertices, col.begin());
Serialization::save(buffer, pos);
Serialization::save(buffer, tex);
Serialization::save(buffer, nor);
Serialization::save(buffer, tan);
Serialization::save(buffer, bit);
+ Serialization::save(buffer, col);
}
void StaticMeshVertexData::deserializeMesh(MeshId id, ArchiveBuffer& buffer)
@@ -88,16 +99,19 @@ void StaticMeshVertexData::deserializeMesh(MeshId id, ArchiveBuffer& buffer)
Array nor;
Array tan;
Array bit;
+ Array col;
Serialization::load(buffer, pos);
Serialization::load(buffer, tex);
Serialization::load(buffer, nor);
Serialization::load(buffer, tan);
Serialization::load(buffer, bit);
+ Serialization::load(buffer, col);
loadPositions(id, pos);
loadTexCoords(id, tex);
loadNormals(id, nor);
loadTangents(id, tan);
loadBiTangents(id, bit);
+ loadBiTangents(id, col);
}
void StaticMeshVertexData::init(Gfx::PGraphics graphics)
@@ -109,6 +123,7 @@ void StaticMeshVertexData::init(Gfx::PGraphics graphics)
descriptorLayout->addDescriptorBinding(2, Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER);
descriptorLayout->addDescriptorBinding(3, Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER);
descriptorLayout->addDescriptorBinding(4, Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER);
+ descriptorLayout->addDescriptorBinding(5, Gfx::SE_DESCRIPTOR_TYPE_STORAGE_BUFFER);
descriptorLayout->create();
descriptorSet = descriptorLayout->allocateDescriptorSet();
}
@@ -141,6 +156,7 @@ void StaticMeshVertexData::resizeBuffers()
normals = graphics->createShaderBuffer(createInfo);
tangents = graphics->createShaderBuffer(createInfo);
biTangents = graphics->createShaderBuffer(createInfo);
+ colors = graphics->createShaderBuffer(createInfo);
createInfo.sourceData.size = verticesAllocated * sizeof(Vector2);
createInfo.stride = sizeof(Vector2);
texCoords = graphics->createShaderBuffer(createInfo);
@@ -150,6 +166,7 @@ void StaticMeshVertexData::resizeBuffers()
normalData.resize(verticesAllocated);
tangentData.resize(verticesAllocated);
biTangentData.resize(verticesAllocated);
+ colorData.resize(verticesAllocated);
}
void StaticMeshVertexData::updateBuffers()
@@ -174,6 +191,10 @@ void StaticMeshVertexData::updateBuffers()
.size = biTangentData.size() * sizeof(Vector),
.data = (uint8*)biTangentData.data(),
});
+ colors->updateContents(DataSource{
+ .size = colorData.size() * sizeof(Vector),
+ .data = (uint8*)colorData.data()
+ });
descriptorLayout->reset();
descriptorSet = descriptorLayout->allocateDescriptorSet();
descriptorSet->updateBuffer(0, positions);
@@ -181,5 +202,6 @@ void StaticMeshVertexData::updateBuffers()
descriptorSet->updateBuffer(2, normals);
descriptorSet->updateBuffer(3, tangents);
descriptorSet->updateBuffer(4, biTangents);
+ descriptorSet->updateBuffer(5, colors);
descriptorSet->writeChanges();
}
diff --git a/src/Engine/Graphics/StaticMeshVertexData.h b/src/Engine/Graphics/StaticMeshVertexData.h
index 2aacdfc..9729373 100644
--- a/src/Engine/Graphics/StaticMeshVertexData.h
+++ b/src/Engine/Graphics/StaticMeshVertexData.h
@@ -16,6 +16,7 @@ public:
void loadNormals(MeshId id, const Array& data);
void loadTangents(MeshId id, const Array& data);
void loadBiTangents(MeshId id, const Array& data);
+ void loadColors(MeshId id, const Array& data);
virtual void serializeMesh(MeshId id, uint64 numVertices, ArchiveBuffer& buffer) override;
virtual void deserializeMesh(MeshId id, ArchiveBuffer& buffer) override;
virtual void init(Gfx::PGraphics graphics) override;
@@ -36,6 +37,8 @@ private:
Array tangentData;
Gfx::OShaderBuffer biTangents;
Array biTangentData;
+ Gfx::OShaderBuffer colors;
+ Array colorData;
Gfx::ODescriptorLayout descriptorLayout;
Gfx::PDescriptorSet descriptorSet;
};
diff --git a/src/Engine/Graphics/VertexData.cpp b/src/Engine/Graphics/VertexData.cpp
index 26f7e23..9f30742 100644
--- a/src/Engine/Graphics/VertexData.cpp
+++ b/src/Engine/Graphics/VertexData.cpp
@@ -33,6 +33,8 @@ void VertexData::updateMesh(const Component::Transform& transform, PMesh mesh)
},
.indexBuffer = mesh->indexBuffer,
});
+ matInstanceData.materialInstance = mesh->referencedMaterial->getHandle();
+ matInstanceData.materialInstance->updateDescriptor();
matInstanceData.numMeshes += meshData[mesh->id].size();
}
diff --git a/src/Engine/Material/Material.cpp b/src/Engine/Material/Material.cpp
index 45cbc2b..81ff385 100644
--- a/src/Engine/Material/Material.cpp
+++ b/src/Engine/Material/Material.cpp
@@ -14,7 +14,7 @@ Material::Material(Gfx::PGraphics graphics,
uint32 uniformDataSize,
uint32 uniformBinding,
std::string materialName,
- Map expressions,
+ Array expressions,
Array parameter,
MaterialNode brdf)
: graphics(graphics)
@@ -112,14 +112,15 @@ void Material::compile()
codeStream << "struct " << materialName << " : IMaterial {\n";
for(const auto& parameter : parameters)
{
- PShaderParameter handle = PShaderExpression(codeExpressions[parameter]);
+ PShaderParameter handle = PShaderExpression(*codeExpressions.find([¶meter](const OShaderExpression& exp) {return exp->key == parameter; }));
handle->generateDeclaration(codeStream);
}
codeStream << "\ttypedef " << brdf.profile << " BRDF;\n";
codeStream << "\t" << brdf.profile << " prepare(MaterialParameter input) {\n";
codeStream << "\t\t" << brdf.profile << " result;\n";
Map varState;
- for(const auto& [_, expr] :codeExpressions)
+ // initialize variable state
+ for(const auto& expr :codeExpressions)
{
codeStream << expr->evaluate(varState);
}
diff --git a/src/Engine/Material/Material.h b/src/Engine/Material/Material.h
index 65e4bba..46aaa6a 100644
--- a/src/Engine/Material/Material.h
+++ b/src/Engine/Material/Material.h
@@ -14,7 +14,7 @@ public:
uint32 uniformDataSize,
uint32 uniformBinding,
std::string materialName,
- Map expressions,
+ Array expressions,
Array parameter,
MaterialNode brdf);
~Material();
@@ -34,7 +34,7 @@ private:
uint64 instanceId;
Gfx::ODescriptorLayout layout;
std::string materialName;
- Map codeExpressions;
+ Array codeExpressions;
Array parameters;
MaterialNode brdf;
};
diff --git a/src/Engine/Material/MaterialInstance.cpp b/src/Engine/Material/MaterialInstance.cpp
index 62fc021..2c84115 100644
--- a/src/Engine/Material/MaterialInstance.cpp
+++ b/src/Engine/Material/MaterialInstance.cpp
@@ -10,7 +10,7 @@ MaterialInstance::MaterialInstance()
MaterialInstance::MaterialInstance(uint64 id,
Gfx::PGraphics graphics,
- Map& expressions,
+ Array& expressions,
Array params,
uint32 uniformBinding,
uint32 uniformSize)
@@ -33,7 +33,8 @@ MaterialInstance::MaterialInstance(uint64 id,
parameters.reserve(params.size());
for (size_t i = 0; i < params.size(); ++i)
{
- Serialization::save(buffer, expressions[params[i]]);
+ const std::string& name = params[i];
+ Serialization::save(buffer, *expressions.find([&name](const OShaderExpression& p) {return p->key == name; }));
buffer.rewind();
OShaderParameter param;
Serialization::load(buffer, param);
diff --git a/src/Engine/Material/MaterialInstance.h b/src/Engine/Material/MaterialInstance.h
index d663dd5..578ce6e 100644
--- a/src/Engine/Material/MaterialInstance.h
+++ b/src/Engine/Material/MaterialInstance.h
@@ -11,7 +11,7 @@ public:
MaterialInstance();
MaterialInstance(uint64 id,
Gfx::PGraphics graphics,
- Map& expressions,
+ Array& expressions,
Array params,
uint32 uniformBinding,
uint32 uniformSize);
diff --git a/src/Engine/Material/ShaderExpression.h b/src/Engine/Material/ShaderExpression.h
index 46b53fb..9badcf0 100644
--- a/src/Engine/Material/ShaderExpression.h
+++ b/src/Engine/Material/ShaderExpression.h
@@ -109,7 +109,7 @@ DECLARE_NAME_REF(Gfx, SamplerState)
struct SamplerParameter : public ShaderParameter
{
static constexpr uint64 IDENTIFIER = 0x08;
- Gfx::PSamplerState data;
+ Gfx::OSamplerState data;
SamplerParameter() {}
SamplerParameter(std::string name, uint32 byteOffset, uint32 binding);
virtual ~SamplerParameter();