From 5993f997d103a1471db5786abbddae73bfa14591 Mon Sep 17 00:00:00 2001 From: Thomas Barlow Date: Fri, 2 Jun 2023 15:31:30 +0100 Subject: [PATCH] Fix #104665: FBX Export: Duplicate materials cause material indices to be offset The export of duplicate materials was changed to skip incrementing the material index for each duplicate in [0], however the connection was still being added for each duplicate. Because the connections to materials are what are indexed by the material indices, the material indices would no longer match up with the materials, resulting in incorrect exports. The original code before the change in [0] was actually exporting FBX files that worked in external software. The issue was instead in the FBX importer where it removed duplicate materials without updating the material indices. Changing the exporter in [0] appeared to fix the issue because the importer would cause the duplicate materials and material indices to realign. Reverting [0] would also have fixed the export issue, however, removing both the duplicate materials and their connections additionally avoids the importer issue when these exported files are imported back into Blender, and makes more sense because only one of each duplicate would have been used by the exported file in the first place. [0]: 5c9ecad1d29edd8ba9ebaaad8f71839bd5d88324 --- io_scene_fbx/export_fbx_bin.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/io_scene_fbx/export_fbx_bin.py b/io_scene_fbx/export_fbx_bin.py index 1cfa853e8..e5c724022 100644 --- a/io_scene_fbx/export_fbx_bin.py +++ b/io_scene_fbx/export_fbx_bin.py @@ -2899,20 +2899,23 @@ def fbx_data_from_scene(scene, depsgraph, settings): _objs_indices = {} for ma, (ma_key, ob_objs) in data_materials.items(): for ob_obj in ob_objs: - connections.append((b"OO", get_fbx_uuid_from_key(ma_key), ob_obj.fbx_uuid, None)) # Get index of this material for this object (or dupliobject). # Material indices for mesh faces are determined by their order in 'ma to ob' connections. # Only materials for meshes currently... # Note in case of dupliobjects a same me/ma idx will be generated several times... # Should not be an issue in practice, and it's needed in case we export duplis but not the original! if ob_obj.type not in BLENDER_OBJECT_TYPES_MESHLIKE: + connections.append((b"OO", get_fbx_uuid_from_key(ma_key), ob_obj.fbx_uuid, None)) continue _mesh_key, me, _free = data_meshes[ob_obj] material_indices = mesh_material_indices.setdefault(me, {}) if ma in material_indices: # Material has already been found for this mesh. # XXX If a mesh has multiple material slots with the same material, they are combined into one slot. + # Even if duplicate materials were exported without combining them into one slot, keeping duplicate + # materials separated does not appear to be common behaviour of external software when importing FBX. continue + connections.append((b"OO", get_fbx_uuid_from_key(ma_key), ob_obj.fbx_uuid, None)) idx = _objs_indices[ob_obj] = _objs_indices.get(ob_obj, -1) + 1 material_indices[ma] = idx del _objs_indices -- 2.30.2