Implemented KRContext::getResources
FBX Importing toolchain now detects need for vertex tangent vectors based on presence of Normal maps, and only imports them when needed. If tangent vectors are needed, but not present in the FBX file, they are calculated during the import process. Importing tangents increases the size of the vertex data and reduces the ability to share vertexes for multiple faces when using indexed triangle rendering; therefore, they are imported sparingly.
This commit is contained in:
@@ -104,6 +104,11 @@ void KRAudioManager::initAudio()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unordered_map<std::string, KRAudioSample *> &KRAudioManager::getSounds()
|
||||||
|
{
|
||||||
|
return m_sounds;
|
||||||
|
}
|
||||||
|
|
||||||
bool KRAudioManager::getEnableAudio()
|
bool KRAudioManager::getEnableAudio()
|
||||||
{
|
{
|
||||||
return m_enable_audio;
|
return m_enable_audio;
|
||||||
|
|||||||
@@ -80,6 +80,8 @@ public:
|
|||||||
KRAudioManager(KRContext &context);
|
KRAudioManager(KRContext &context);
|
||||||
virtual ~KRAudioManager();
|
virtual ~KRAudioManager();
|
||||||
|
|
||||||
|
unordered_map<std::string, KRAudioSample *> &getSounds();
|
||||||
|
|
||||||
void add(KRAudioSample *Sound);
|
void add(KRAudioSample *Sound);
|
||||||
|
|
||||||
KRAudioSample *load(const std::string &name, const std::string &extension, KRDataBlock *data);
|
KRAudioSample *load(const std::string &name, const std::string &extension, KRDataBlock *data);
|
||||||
|
|||||||
@@ -131,6 +131,45 @@ KRUnknownManager *KRContext::getUnknownManager() {
|
|||||||
return m_pUnknownManager;
|
return m_pUnknownManager;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::vector<KRResource *> KRContext::getResources()
|
||||||
|
{
|
||||||
|
|
||||||
|
std::vector<KRResource *> resources;
|
||||||
|
|
||||||
|
for(unordered_map<std::string, KRScene *>::iterator itr = m_pSceneManager->getScenes().begin(); itr != m_pSceneManager->getScenes().end(); itr++) {
|
||||||
|
resources.push_back((*itr).second);
|
||||||
|
}
|
||||||
|
for(unordered_map<std::string, KRTexture *>::iterator itr = m_pTextureManager->getTextures().begin(); itr != m_pTextureManager->getTextures().end(); itr++) {
|
||||||
|
resources.push_back((*itr).second);
|
||||||
|
}
|
||||||
|
for(unordered_map<std::string, KRMaterial *>::iterator itr = m_pMaterialManager->getMaterials().begin(); itr != m_pMaterialManager->getMaterials().end(); itr++) {
|
||||||
|
resources.push_back((*itr).second);
|
||||||
|
}
|
||||||
|
for(unordered_multimap<std::string, KRMesh *>::iterator itr = m_pModelManager->getModels().begin(); itr != m_pModelManager->getModels().end(); itr++) {
|
||||||
|
resources.push_back((*itr).second);
|
||||||
|
}
|
||||||
|
for(unordered_map<std::string, KRAnimation *>::iterator itr = m_pAnimationManager->getAnimations().begin(); itr != m_pAnimationManager->getAnimations().end(); itr++) {
|
||||||
|
resources.push_back((*itr).second);
|
||||||
|
}
|
||||||
|
for(unordered_map<std::string, KRAnimationCurve *>::iterator itr = m_pAnimationCurveManager->getAnimationCurves().begin(); itr != m_pAnimationCurveManager->getAnimationCurves().end(); itr++) {
|
||||||
|
resources.push_back((*itr).second);
|
||||||
|
}
|
||||||
|
for(unordered_map<std::string, KRAudioSample *>::iterator itr = m_pSoundManager->getSounds().begin(); itr != m_pSoundManager->getSounds().end(); itr++) {
|
||||||
|
resources.push_back((*itr).second);
|
||||||
|
}
|
||||||
|
|
||||||
|
unordered_map<std::string, unordered_map<std::string, KRUnknown *> > unknowns = m_pUnknownManager->getUnknowns();
|
||||||
|
for(unordered_map<std::string, unordered_map<std::string, KRUnknown *> >::iterator itr = unknowns.begin(); itr != unknowns.end(); itr++) {
|
||||||
|
for(unordered_map<std::string, KRUnknown *>::iterator itr2 = (*itr).second.begin(); itr2 != (*itr).second.end(); itr++) {
|
||||||
|
resources.push_back((*itr2).second);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// FINDME, TODO - Not yet exporting shaders, as they are currently only being used as standard Kraken assets. In the future people may want their custom shaders to be exported.
|
||||||
|
|
||||||
|
return resources;
|
||||||
|
}
|
||||||
|
|
||||||
void KRContext::loadResource(const std::string &file_name, KRDataBlock *data) {
|
void KRContext::loadResource(const std::string &file_name, KRDataBlock *data) {
|
||||||
std::string name = KRResource::GetFileBase(file_name);
|
std::string name = KRResource::GetFileBase(file_name);
|
||||||
std::string extension = KRResource::GetFileExtension(file_name);
|
std::string extension = KRResource::GetFileExtension(file_name);
|
||||||
|
|||||||
@@ -72,6 +72,8 @@ public:
|
|||||||
|
|
||||||
long getAbsoluteTimeMilliseconds();
|
long getAbsoluteTimeMilliseconds();
|
||||||
|
|
||||||
|
std::vector<KRResource *> getResources();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
KRBundleManager *m_pBundleManager;
|
KRBundleManager *m_pBundleManager;
|
||||||
KRSceneManager *m_pSceneManager;
|
KRSceneManager *m_pSceneManager;
|
||||||
|
|||||||
@@ -75,6 +75,11 @@ std::string KRMaterial::getExtension() {
|
|||||||
return "mtl";
|
return "mtl";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool KRMaterial::needsVertexTangents()
|
||||||
|
{
|
||||||
|
return m_normalMap.size() > 0;
|
||||||
|
}
|
||||||
|
|
||||||
bool KRMaterial::save(KRDataBlock &data) {
|
bool KRMaterial::save(KRDataBlock &data) {
|
||||||
std::stringstream stream;
|
std::stringstream stream;
|
||||||
stream.precision(std::numeric_limits<long double>::digits10);
|
stream.precision(std::numeric_limits<long double>::digits10);
|
||||||
|
|||||||
@@ -85,6 +85,8 @@ public:
|
|||||||
|
|
||||||
bool bind(KRMaterial **prevBoundMaterial, char *szPrevShaderKey, KRCamera *pCamera, std::vector<KRPointLight *> &point_lights, std::vector<KRDirectionalLight *> &directional_lights, std::vector<KRSpotLight *>&spot_lights, const std::vector<KRBone *> &bones, const KRViewport &viewport, const KRMat4 &matModel, KRTexture *pLightMap, KRNode::RenderPass renderPass);
|
bool bind(KRMaterial **prevBoundMaterial, char *szPrevShaderKey, KRCamera *pCamera, std::vector<KRPointLight *> &point_lights, std::vector<KRDirectionalLight *> &directional_lights, std::vector<KRSpotLight *>&spot_lights, const std::vector<KRBone *> &bones, const KRViewport &viewport, const KRMat4 &matModel, KRTexture *pLightMap, KRNode::RenderPass renderPass);
|
||||||
|
|
||||||
|
bool needsVertexTangents();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::string m_name;
|
std::string m_name;
|
||||||
|
|
||||||
|
|||||||
@@ -44,6 +44,11 @@ KRMaterialManager::~KRMaterialManager() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
unordered_map<std::string, KRMaterial *> &KRMaterialManager::getMaterials()
|
||||||
|
{
|
||||||
|
return m_materials;
|
||||||
|
}
|
||||||
|
|
||||||
void KRMaterialManager::configure(bool blend_enable, GLenum blend_src, GLenum blend_dest, bool depth_test_enable, GLenum depth_func, bool depth_write_enable) {
|
void KRMaterialManager::configure(bool blend_enable, GLenum blend_src, GLenum blend_dest, bool depth_test_enable, GLenum depth_func, bool depth_write_enable) {
|
||||||
if(blend_enable) {
|
if(blend_enable) {
|
||||||
GLDEBUG(glEnable(GL_BLEND));
|
GLDEBUG(glEnable(GL_BLEND));
|
||||||
@@ -67,21 +72,31 @@ void KRMaterialManager::configure(bool blend_enable, GLenum blend_src, GLenum bl
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
KRMaterial *KRMaterialManager::getMaterial(const char *szName) {
|
KRMaterial *KRMaterialManager::getMaterial(const std::string &name) {
|
||||||
std::string lowerName = szName;
|
std::string lowerName = name;
|
||||||
std::transform(lowerName.begin(), lowerName.end(),
|
std::transform(lowerName.begin(), lowerName.end(),
|
||||||
lowerName.begin(), ::tolower);
|
lowerName.begin(), ::tolower);
|
||||||
|
|
||||||
|
|
||||||
unordered_map<std::string, KRMaterial *>::iterator itr = m_materials.find(lowerName);
|
unordered_map<std::string, KRMaterial *>::iterator itr = m_materials.find(lowerName);
|
||||||
if(itr == m_materials.end()) {
|
if(itr == m_materials.end()) {
|
||||||
fprintf(stderr, "Material not found: %s\n", szName);
|
fprintf(stderr, "Material not found: %s\n", name.c_str());
|
||||||
// Not found
|
// Not found
|
||||||
return NULL;
|
return NULL;
|
||||||
} else {
|
} else {
|
||||||
return (*itr).second;
|
return (*itr).second;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void KRMaterialManager::add(KRMaterial *new_material) {
|
||||||
|
// FINDME, TODO - Potential memory leak if multiple materials with the same name are added
|
||||||
|
std::string lowerName = new_material->getName();
|
||||||
|
std::transform(lowerName.begin(), lowerName.end(),
|
||||||
|
lowerName.begin(), ::tolower);
|
||||||
|
|
||||||
|
m_materials[lowerName] = new_material;
|
||||||
|
}
|
||||||
|
|
||||||
bool KRMaterialManager::load(const char *szName, KRDataBlock *data) {
|
bool KRMaterialManager::load(const char *szName, KRDataBlock *data) {
|
||||||
KRMaterial *pMaterial = NULL;
|
KRMaterial *pMaterial = NULL;
|
||||||
char szSymbol[16][256];
|
char szSymbol[16][256];
|
||||||
|
|||||||
@@ -50,10 +50,14 @@ public:
|
|||||||
virtual ~KRMaterialManager();
|
virtual ~KRMaterialManager();
|
||||||
|
|
||||||
bool load(const char *szName, KRDataBlock *data);
|
bool load(const char *szName, KRDataBlock *data);
|
||||||
KRMaterial *getMaterial(const char *szName);
|
void add(KRMaterial *new_material);
|
||||||
|
KRMaterial *getMaterial(const std::string &name);
|
||||||
|
|
||||||
void configure(bool blend_enable, GLenum blend_src, GLenum blend_dest, bool depth_test_enable, GLenum depth_func, bool depth_write_enable);
|
void configure(bool blend_enable, GLenum blend_src, GLenum blend_dest, bool depth_test_enable, GLenum depth_func, bool depth_write_enable);
|
||||||
|
|
||||||
|
|
||||||
|
unordered_map<std::string, KRMaterial *> &getMaterials();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
unordered_map<std::string, KRMaterial *> m_materials;
|
unordered_map<std::string, KRMaterial *> m_materials;
|
||||||
KRTextureManager *m_pTextureManager;
|
KRTextureManager *m_pTextureManager;
|
||||||
|
|||||||
@@ -122,6 +122,15 @@ std::vector<KRResource *> KRResource::LoadFbx(KRContext &context, const std::str
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ----====---- Import Materials ----====----
|
||||||
|
int material_count = pFbxScene->GetSrcObjectCount<FbxSurfaceMaterial>();
|
||||||
|
printf("\nLoading materials...\n");
|
||||||
|
for(int i=0; i < material_count; i++) {
|
||||||
|
FbxSurfaceMaterial *material = pFbxScene->GetSrcObject<FbxSurfaceMaterial>(i);
|
||||||
|
printf(" Material %i of %i: %s\n", i+1, material_count, material->GetName());
|
||||||
|
LoadMaterial(context, resources, material);
|
||||||
|
}
|
||||||
|
|
||||||
// ----====---- Import Meshes ----====----
|
// ----====---- Import Meshes ----====----
|
||||||
int mesh_count = pFbxScene->GetSrcObjectCount<FbxMesh>();
|
int mesh_count = pFbxScene->GetSrcObjectCount<FbxMesh>();
|
||||||
printf("\nLoading meshes...\n");
|
printf("\nLoading meshes...\n");
|
||||||
@@ -132,15 +141,6 @@ std::vector<KRResource *> KRResource::LoadFbx(KRContext &context, const std::str
|
|||||||
LoadMesh(context, resources, pGeometryConverter, mesh);
|
LoadMesh(context, resources, pGeometryConverter, mesh);
|
||||||
}
|
}
|
||||||
|
|
||||||
// ----====---- Import Materials ----====----
|
|
||||||
int material_count = pFbxScene->GetSrcObjectCount<FbxSurfaceMaterial>();
|
|
||||||
printf("\nLoading materials...\n");
|
|
||||||
for(int i=0; i < material_count; i++) {
|
|
||||||
FbxSurfaceMaterial *material = pFbxScene->GetSrcObject<FbxSurfaceMaterial>(i);
|
|
||||||
printf(" Material %i of %i: %s\n", i+1, material_count, material->GetName());
|
|
||||||
LoadMaterial(context, resources, material);
|
|
||||||
}
|
|
||||||
|
|
||||||
// ----====---- Import Textures ----====----
|
// ----====---- Import Textures ----====----
|
||||||
int texture_count = pFbxScene->GetSrcObjectCount<FbxFileTexture>();
|
int texture_count = pFbxScene->GetSrcObjectCount<FbxFileTexture>();
|
||||||
|
|
||||||
@@ -162,13 +162,8 @@ std::vector<KRResource *> KRResource::LoadFbx(KRContext &context, const std::str
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for(unordered_map<std::string, KRTexture *>::iterator texture_itr = context.getTextureManager()->getTextures().begin(); texture_itr != context.getTextureManager()->getTextures().end(); texture_itr++) {
|
std::vector<KRResource *> resources2 = context.getResources();
|
||||||
resources.push_back((*texture_itr).second);
|
resources.insert(resources.begin(), resources2.begin(), resources2.end());
|
||||||
}
|
|
||||||
|
|
||||||
for(unordered_map<std::string, KRMesh *>::iterator mesh_itr = context.getModelManager()->getModels().begin(); mesh_itr != context.getModelManager()->getModels().end(); mesh_itr++) {
|
|
||||||
resources.push_back((*mesh_itr).second);
|
|
||||||
}
|
|
||||||
|
|
||||||
DestroySdkObjects(lSdkManager);
|
DestroySdkObjects(lSdkManager);
|
||||||
|
|
||||||
@@ -1044,6 +1039,7 @@ void LoadMaterial(KRContext &context, std::vector<KRResource *> &resources, FbxS
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
bool bFound = false;
|
bool bFound = false;
|
||||||
for(vector<KRResource *>::iterator resource_itr = resources.begin(); resource_itr != resources.end(); resource_itr++) {
|
for(vector<KRResource *>::iterator resource_itr = resources.begin(); resource_itr != resources.end(); resource_itr++) {
|
||||||
KRResource *pResource = (*resource_itr);
|
KRResource *pResource = (*resource_itr);
|
||||||
@@ -1056,7 +1052,16 @@ void LoadMaterial(KRContext &context, std::vector<KRResource *> &resources, FbxS
|
|||||||
} else {
|
} else {
|
||||||
resources.push_back(new_material);
|
resources.push_back(new_material);
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
// Only save unique materials
|
||||||
|
KRMaterial *found_material = context.getMaterialManager()->getMaterial(new_material->getName());
|
||||||
|
if(found_material == NULL) {
|
||||||
|
context.getMaterialManager()->add(new_material);
|
||||||
|
} else {
|
||||||
|
delete new_material;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void LoadMesh(KRContext &context, std::vector<KRResource *> &resources, FbxGeometryConverter *pGeometryConverter, KFbxMesh* pSourceMesh) {
|
void LoadMesh(KRContext &context, std::vector<KRResource *> &resources, FbxGeometryConverter *pGeometryConverter, KFbxMesh* pSourceMesh) {
|
||||||
@@ -1162,8 +1167,18 @@ void LoadMesh(KRContext &context, std::vector<KRResource *> &resources, FbxGeome
|
|||||||
|
|
||||||
int dest_vertex_id = 0;
|
int dest_vertex_id = 0;
|
||||||
|
|
||||||
|
bool need_tangents = false;
|
||||||
|
|
||||||
for(int iMaterial=0; iMaterial < material_count; iMaterial++) {
|
for(int iMaterial=0; iMaterial < material_count; iMaterial++) {
|
||||||
KFbxSurfaceMaterial *pMaterial = pSourceMesh->GetNode()->GetMaterial(iMaterial);
|
KFbxSurfaceMaterial *pMaterial = pSourceMesh->GetNode()->GetMaterial(iMaterial);
|
||||||
|
|
||||||
|
KRMaterial *material = context.getMaterialManager()->getMaterial(pMaterial->GetName());
|
||||||
|
if(material) {
|
||||||
|
if(material->needsVertexTangents()) {
|
||||||
|
need_tangents = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int source_vertex_id = 0;
|
int source_vertex_id = 0;
|
||||||
int mat_vertex_count = 0;
|
int mat_vertex_count = 0;
|
||||||
int mat_vertex_start = dest_vertex_id;
|
int mat_vertex_start = dest_vertex_id;
|
||||||
@@ -1294,7 +1309,7 @@ void LoadMesh(KRContext &context, std::vector<KRResource *> &resources, FbxGeome
|
|||||||
KRMesh *new_mesh = new KRMesh(context, pSourceMesh->GetNode()->GetName());
|
KRMesh *new_mesh = new KRMesh(context, pSourceMesh->GetNode()->GetName());
|
||||||
std::vector<__uint16_t> vertex_indexes;
|
std::vector<__uint16_t> vertex_indexes;
|
||||||
std::vector<std::pair<int, int> > vertex_index_bases;
|
std::vector<std::pair<int, int> > vertex_index_bases;
|
||||||
new_mesh->LoadData(vertex_indexes, vertex_index_bases, vertices, uva, uvb, normals, tangents, submesh_starts, submesh_lengths, material_names, bone_names, bone_indexes, bone_weights,KRMesh::KRENGINE_MODEL_FORMAT_TRIANGLES, true, false); // FINDME, HACK! "false" set for importing tangents so that we can merge more vertices in the index buffer. This should be configurable by the end-user so if normal maps are required and no tangents are included in the model, they can be calculated
|
new_mesh->LoadData(vertex_indexes, vertex_index_bases, vertices, uva, uvb, normals, tangents, submesh_starts, submesh_lengths, material_names, bone_names, bone_indexes, bone_weights,KRMesh::KRENGINE_MODEL_FORMAT_TRIANGLES, true, need_tangents);
|
||||||
|
|
||||||
context.getModelManager()->addModel(new_mesh);
|
context.getModelManager()->addModel(new_mesh);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -46,6 +46,11 @@ KRUnknownManager::~KRUnknownManager()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unordered_map<std::string, unordered_map<std::string, KRUnknown *> > &KRUnknownManager::getUnknowns()
|
||||||
|
{
|
||||||
|
return m_unknowns;
|
||||||
|
}
|
||||||
|
|
||||||
void KRUnknownManager::add(KRUnknown *unknown)
|
void KRUnknownManager::add(KRUnknown *unknown)
|
||||||
{
|
{
|
||||||
std::string lower_name = unknown->getName();
|
std::string lower_name = unknown->getName();
|
||||||
|
|||||||
@@ -51,6 +51,8 @@ public:
|
|||||||
|
|
||||||
const unordered_map<std::string, KRUnknown *> &get(const std::string &extension);
|
const unordered_map<std::string, KRUnknown *> &get(const std::string &extension);
|
||||||
|
|
||||||
|
unordered_map<std::string, unordered_map<std::string, KRUnknown *> > &getUnknowns();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
unordered_map<std::string, unordered_map<std::string, KRUnknown *> > m_unknowns;
|
unordered_map<std::string, unordered_map<std::string, KRUnknown *> > m_unknowns;
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user