Skip to content

Commit

Permalink
Refactor material. (#122)
Browse files Browse the repository at this point in the history
  • Loading branch information
roeas committed Feb 18, 2023
1 parent 6d54e98 commit 8e04650
Show file tree
Hide file tree
Showing 9 changed files with 429 additions and 231 deletions.
25 changes: 19 additions & 6 deletions private/Consumers/CDConsumer/CDConsumerImpl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -141,13 +141,26 @@ void CDConsumerImpl::ExportXmlBinary(const cd::SceneDatabase* pSceneDatabase)
WriteNodeStringAttribute(pMaterialNode, "Name", material.GetName());

XmlNode* pMaterialDataNode = WriteNode("Data");
WriteNodeU32Attribute(pMaterialDataNode, "TextureCount", static_cast<uint32_t>(material.GetTextureIDMap().size()));

XmlNode* pTextureListNode = WriteNode("TextureList");
for (const auto& [materialTextureType, textureID] : material.GetTextureIDMap())
XmlNode *pTextureListNode = WriteNode("TextureList");

std::vector<cd::MaterialTextureType> textureTypes = {
cd::MaterialTextureType::BaseColor,
cd::MaterialTextureType::Occlusion,
cd::MaterialTextureType::Roughness,
cd::MaterialTextureType::Metallic,
cd::MaterialTextureType::Emissive,
cd::MaterialTextureType::Normal,
};

for (const auto &type : textureTypes)
{
XmlNode* pTextureNode = WriteNode(GetMaterialTextureTypeName(materialTextureType), std::to_string(textureID.Data()).c_str());
pTextureListNode->append_node(pTextureNode);
if (material.IsTextureSetup(type))
{
std::stringstream ss;
ss << material.GetTextureID(type).value().Data();
XmlNode *pTextureNode = WriteNode(GetMaterialPropertyGroupName(type), ss.str().c_str());
pTextureListNode->append_node(pTextureNode);
}
}

pMaterialNode->append_node(pMaterialDataNode);
Expand Down
39 changes: 29 additions & 10 deletions private/Producers/GenericProducer/GenericProducerImpl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -70,15 +70,32 @@ void DumpSceneDatabase(const cd::SceneDatabase& sceneDatabase)
}
}

std::vector<cd::MaterialTextureType> textureTypes = {
cd::MaterialTextureType::BaseColor,
cd::MaterialTextureType::Occlusion,
cd::MaterialTextureType::Roughness,
cd::MaterialTextureType::Metallic,
cd::MaterialTextureType::Emissive,
cd::MaterialTextureType::Normal,
};

for (const auto& material : sceneDatabase.GetMaterials())
{
printf("[MaterialID %u] %s\n", material.GetID().Data(), material.GetName());

for (const auto& [materialTextureType, textureID] : material.GetTextureIDMap())
for (const auto &type : textureTypes)
{
const auto& texture = sceneDatabase.GetTexture(textureID.Data());
printf("\t[TextureID %u] %s - %s\n", textureID.Data(),
GetMaterialTextureTypeName(materialTextureType), texture.GetPath());
if (material.IsTextureSetup(type))
{
const auto &textureID = material.GetTextureID(type);
const auto &texture = sceneDatabase.GetTexture(textureID.value().Data());
printf("\t[TextureID %u] %s - %s\n", textureID.value(),
cd::GetMaterialPropertyGroupName(type), texture.GetPath());
}
else
{
// printf("\t[warnning] Can not find texture id by textureKey %s\n", textureKey.c_str());
}
}
}

Expand Down Expand Up @@ -139,10 +156,10 @@ cd::MaterialID GenericProducerImpl::AddMaterial(cd::SceneDatabase* pSceneDatabas
materialTextureMapping[aiTextureType_NORMAL_CAMERA] = cd::MaterialTextureType::Normal;
materialTextureMapping[aiTextureType_EMISSIVE] = cd::MaterialTextureType::Emissive;
materialTextureMapping[aiTextureType_EMISSION_COLOR] = cd::MaterialTextureType::Emissive;
materialTextureMapping[aiTextureType_METALNESS] = cd::MaterialTextureType::Metalness;
materialTextureMapping[aiTextureType_METALNESS] = cd::MaterialTextureType::Metallic;
materialTextureMapping[aiTextureType_DIFFUSE_ROUGHNESS] = cd::MaterialTextureType::Roughness;
materialTextureMapping[aiTextureType_AMBIENT_OCCLUSION] = cd::MaterialTextureType::AO;
materialTextureMapping[aiTextureType_LIGHTMAP] = cd::MaterialTextureType::AO;
materialTextureMapping[aiTextureType_AMBIENT_OCCLUSION] = cd::MaterialTextureType::Occlusion;
materialTextureMapping[aiTextureType_LIGHTMAP] = cd::MaterialTextureType::Occlusion;
}

aiString materialName;
Expand Down Expand Up @@ -174,14 +191,16 @@ cd::MaterialID GenericProducerImpl::AddMaterial(cd::SceneDatabase* pSceneDatabas
}

//printf("\t[MaterialID %u] %s\n", materialID.Data(), finalMaterialName.c_str());
cd::Material material(materialID, finalMaterialName.c_str());

// Create a base PBR material type by default.
cd::Material material(materialID, finalMaterialName.c_str(), cd::MaterialType::BasePBR);

// Process all textures
for (const auto& [textureType, materialTextureType] : materialTextureMapping)
{
// Multiple assimp texture types will map to the same texture to increase the successful rate.
// Setup means one assimp texture type already added. Just skip remain assimp texture types.
if (material.IsTextureTypeSetup(materialTextureType))
if (material.IsTextureSetup(materialTextureType))
{
continue;
}
Expand Down Expand Up @@ -221,7 +240,7 @@ cd::MaterialID GenericProducerImpl::AddMaterial(cd::SceneDatabase* pSceneDatabas
std::filesystem::path textureAbsolutePath = m_folderPath;
textureAbsolutePath.append(ai_path.C_Str());

material.SetTextureID(materialTextureType, textureID);
material.AddTextureID(materialTextureType, textureID);

// Reused textures don't need to add to SceneDatabase again.
if (!isTextureReused)
Expand Down
6 changes: 3 additions & 3 deletions private/Producers/TerrainProducer/TerrainProducerImpl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -217,20 +217,20 @@ void TerrainProducerImpl::GenerateMaterialAndTextures(cd::SceneDatabase* pSceneD
const std::string materialName = string_format("TerrainMaterial({}, {})", sector_x, sector_z);
MaterialID::ValueType materialHash = StringHash<MaterialID::ValueType>(materialName);
MaterialID materialID = m_materialIDGenerator.AllocateID(materialHash);
Material terrainSectorMaterial(materialID, materialName.c_str());
Material terrainSectorMaterial(materialID, materialName.c_str(), MaterialType::BasePBR);

// Base color texture
std::string textureName = "TerrainDirtTexture";
TextureID::ValueType textureHash = StringHash<TextureID::ValueType>(textureName);
TextureID textureID = m_textureIDGenerator.AllocateID(textureHash);
terrainSectorMaterial.SetTextureID(MaterialTextureType::BaseColor, textureID);
terrainSectorMaterial.AddTextureID(MaterialTextureType::BaseColor, textureID);
pSceneDatabase->AddTexture(Texture(textureID, MaterialTextureType::BaseColor, textureName.c_str()));

// ElevationMap texture
textureName = string_format("TerrainElevationMap({}, {})", sector_x, sector_z);
textureHash = StringHash<TextureID::ValueType>(textureName);
textureID = m_textureIDGenerator.AllocateID(textureHash);
terrainSectorMaterial.SetTextureID(MaterialTextureType::Roughness, textureID);
terrainSectorMaterial.AddTextureID(MaterialTextureType::Roughness, textureID);
Texture elevationTexture = Texture(textureID, MaterialTextureType::Roughness, textureName.c_str());
elevationTexture.SetRawTexture(elevationMap, TextureFormat::R32I);
pSceneDatabase->AddTexture(MoveTemp(elevationTexture));
Expand Down
21 changes: 10 additions & 11 deletions private/Scene/Material.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,9 @@ Material::Material(InputArchiveSwapBytes& inputArchive)
m_pMaterialImpl = new MaterialImpl(inputArchive);
}

Material::Material(MaterialID materialID, const char* pMaterialName)
Material::Material(MaterialID materialID, const char* pMaterialName, MaterialType type)
{
m_pMaterialImpl = new MaterialImpl(materialID, pMaterialName);
m_pMaterialImpl = new MaterialImpl(materialID, pMaterialName, type);
}

Material::Material(Material&& rhs)
Expand All @@ -39,9 +39,9 @@ Material::~Material()
}
}

void Material::Init(MaterialID materialID, const char* pMaterialName)
void Material::Init(MaterialID materialID, const char* pMaterialName, MaterialType type)
{
m_pMaterialImpl->Init(materialID, pMaterialName);
m_pMaterialImpl->Init(materialID, pMaterialName, type);
}

const MaterialID& Material::GetID() const
Expand All @@ -54,24 +54,23 @@ const char* Material::GetName() const
return m_pMaterialImpl->GetName().c_str();
}

void Material::SetTextureID(MaterialTextureType textureType, TextureID textureID)
void Material::AddTextureID(MaterialTextureType textureType, TextureID textureID)
{
m_pMaterialImpl->SetTextureID(textureType, textureID);
m_pMaterialImpl->AddTextureID(textureType, textureID);
}

std::optional<TextureID> Material::GetTextureID(MaterialTextureType textureType) const
{
return m_pMaterialImpl->GetTextureID(textureType);
}

const Material::TextureIDMap& Material::GetTextureIDMap() const
{
return m_pMaterialImpl->GetTextureIDMap();
const PropertyMap& Material::GetPropertyGroups() const {
return m_pMaterialImpl->GetPropertyGroups();
}

bool Material::IsTextureTypeSetup(MaterialTextureType textureType) const
bool Material::IsTextureSetup(MaterialTextureType textureType) const
{
return m_pMaterialImpl->IsTextureTypeSetup(textureType);
return m_pMaterialImpl->IsTextureSetup(textureType);
}

Material& Material::operator<<(InputArchive& inputArchive)
Expand Down
75 changes: 55 additions & 20 deletions private/Scene/MaterialImpl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,42 +5,77 @@
namespace cd
{

MaterialImpl::MaterialImpl(MaterialID materialID, std::string materialName)
MaterialImpl::MaterialImpl(MaterialID materialID, std::string materialName, MaterialType materialType)
{
Init(materialID, MoveTemp(materialName));
Init(materialID, MoveTemp(materialName), materialType);

switch (materialType)
{
case MaterialType::BasePBR:
InitBasePBR();
break;

default:
printf("Unknow material type!\n");
break;
}
}

void MaterialImpl::Init(MaterialID materialID, std::string materialName)
void MaterialImpl::Init(MaterialID materialID, std::string materialName, MaterialType materialType)
{
m_id = materialID;
m_name = MoveTemp(materialName);
m_type = materialType;
}

void MaterialImpl::SetTextureID(MaterialTextureType textureType, TextureID textureID)
void MaterialImpl::InitBasePBR()
{
TextureIDMap::iterator itTexture = m_textureIDs.find(textureType);
if(itTexture != m_textureIDs.end())
{
// Existed!
if(textureID == itTexture->second)
{
// Same
return;
}
}
AddProperty(MaterialPropertyGroup::BaseColor, MaterialProperty::Color, Vec3f(1.0f, 1.0f, 1.0f));
// Factor for blending Color and Texture.
// Or if there is no Texture, then this simply scales the Color value.
AddProperty(MaterialPropertyGroup::BaseColor, MaterialProperty::Factor, 0.0f);
AddProperty(MaterialPropertyGroup::BaseColor, MaterialProperty::UseTexture, true);

AddProperty(MaterialPropertyGroup::Occlusion, MaterialProperty::Factor, 0.0f);
AddProperty(MaterialPropertyGroup::Occlusion, MaterialProperty::UseTexture, true);

AddProperty(MaterialPropertyGroup::Roughness, MaterialProperty::Factor, 0.9f);
AddProperty(MaterialPropertyGroup::Roughness, MaterialProperty::UseTexture, true);

AddProperty(MaterialPropertyGroup::Metallic, MaterialProperty::Factor, 0.1f);
AddProperty(MaterialPropertyGroup::Metallic, MaterialProperty::UseTexture, true);

m_textureIDs[textureType] = textureID;
AddProperty(MaterialPropertyGroup::Normal, MaterialProperty::UseTexture, true);

AddProperty(MaterialPropertyGroup::General, MaterialProperty::EnableDirectionalLights, true);
AddProperty(MaterialPropertyGroup::General, MaterialProperty::EnablePunctualLights, true);
AddProperty(MaterialPropertyGroup::General, MaterialProperty::EnableAreaLights, false);
AddProperty(MaterialPropertyGroup::General, MaterialProperty::EnableIBL, true);
}

void MaterialImpl::AddTextureID(MaterialPropertyGroup propertyGroup, TextureID textureID)
{
static_assert(sizeof(TextureID) == sizeof(uint32_t));
AddProperty(propertyGroup, MaterialProperty::Texture, textureID.Data());
}

std::optional<TextureID> MaterialImpl::GetTextureID(MaterialTextureType textureType) const
std::optional<TextureID> MaterialImpl::GetTextureID(MaterialPropertyGroup propertyGroup) const
{
TextureIDMap::const_iterator itTexture = m_textureIDs.find(textureType);
if(itTexture != m_textureIDs.end())
static_assert(sizeof(TextureID) == sizeof(uint32_t));
auto textureID = GetProperty<uint32_t>(propertyGroup, MaterialProperty::Texture);
if (textureID.has_value())
{
return itTexture->second;
return TextureID(textureID.value());
}
else
{
return std::nullopt;
}
}

return std::nullopt;
bool MaterialImpl::IsTextureSetup(MaterialPropertyGroup propertyGroup) const
{
return ExistProperty(propertyGroup, MaterialProperty::Texture);
}

}
Loading

0 comments on commit 8e04650

Please sign in to comment.