FBX: Enable the Collection exporter feature #105273
@ -315,6 +315,11 @@ class ExportFBX(bpy.types.Operator, ExportHelper):
|
|||||||
description="Export only objects from the active collection (and its children)",
|
description="Export only objects from the active collection (and its children)",
|
||||||
default=False,
|
default=False,
|
||||||
)
|
)
|
||||||
|
collection: StringProperty(
|
||||||
|
name="Source Collection",
|
||||||
|
description="Export only objects from this collection (and its children)",
|
||||||
|
default="",
|
||||||
|
)
|
||||||
global_scale: FloatProperty(
|
global_scale: FloatProperty(
|
||||||
name="Scale",
|
name="Scale",
|
||||||
description="Scale all data (Some importers do not support scaled armatures!)",
|
description="Scale all data (Some importers do not support scaled armatures!)",
|
||||||
@ -557,8 +562,11 @@ class ExportFBX(bpy.types.Operator, ExportHelper):
|
|||||||
layout.use_property_split = True
|
layout.use_property_split = True
|
||||||
layout.use_property_decorate = False # No animation.
|
layout.use_property_decorate = False # No animation.
|
||||||
|
|
||||||
export_main(layout, self)
|
# Are we inside the File browser
|
||||||
export_panel_include(layout, self)
|
is_file_browser = context.space_data.type == 'FILE_BROWSER'
|
||||||
|
|
||||||
|
export_main(layout, self, is_file_browser)
|
||||||
deadpin marked this conversation as resolved
Outdated
|
|||||||
|
export_panel_include(layout, self, is_file_browser)
|
||||||
export_panel_transform(layout, self)
|
export_panel_transform(layout, self)
|
||||||
export_panel_geometry(layout, self)
|
export_panel_geometry(layout, self)
|
||||||
export_panel_armature(layout, self)
|
export_panel_armature(layout, self)
|
||||||
@ -589,27 +597,29 @@ class ExportFBX(bpy.types.Operator, ExportHelper):
|
|||||||
return export_fbx_bin.save(self, context, **keywords)
|
return export_fbx_bin.save(self, context, **keywords)
|
||||||
|
|
||||||
|
|
||||||
def export_main(layout, operator):
|
def export_main(layout, operator, is_file_browser):
|
||||||
row = layout.row(align=True)
|
row = layout.row(align=True)
|
||||||
row.prop(operator, "path_mode")
|
row.prop(operator, "path_mode")
|
||||||
sub = row.row(align=True)
|
sub = row.row(align=True)
|
||||||
sub.enabled = (operator.path_mode == 'COPY')
|
sub.enabled = (operator.path_mode == 'COPY')
|
||||||
sub.prop(operator, "embed_textures", text="", icon='PACKAGE' if operator.embed_textures else 'UGLYPACKAGE')
|
sub.prop(operator, "embed_textures", text="", icon='PACKAGE' if operator.embed_textures else 'UGLYPACKAGE')
|
||||||
row = layout.row(align=True)
|
if is_file_browser:
|
||||||
row.prop(operator, "batch_mode")
|
row = layout.row(align=True)
|
||||||
sub = row.row(align=True)
|
row.prop(operator, "batch_mode")
|
||||||
sub.prop(operator, "use_batch_own_dir", text="", icon='NEWFOLDER')
|
sub = row.row(align=True)
|
||||||
|
sub.prop(operator, "use_batch_own_dir", text="", icon='NEWFOLDER')
|
||||||
|
|
||||||
|
|
||||||
def export_panel_include(layout, operator):
|
def export_panel_include(layout, operator, is_file_browser):
|
||||||
header, body = layout.panel("FBX_export_include", default_closed=False)
|
header, body = layout.panel("FBX_export_include", default_closed=False)
|
||||||
header.label(text="Include")
|
header.label(text="Include")
|
||||||
if body:
|
if body:
|
||||||
sublayout = body.column(heading="Limit to")
|
sublayout = body.column(heading="Limit to")
|
||||||
sublayout.enabled = (operator.batch_mode == 'OFF')
|
sublayout.enabled = (operator.batch_mode == 'OFF')
|
||||||
sublayout.prop(operator, "use_selection")
|
if is_file_browser:
|
||||||
sublayout.prop(operator, "use_visible")
|
sublayout.prop(operator, "use_selection")
|
||||||
sublayout.prop(operator, "use_active_collection")
|
sublayout.prop(operator, "use_visible")
|
||||||
|
sublayout.prop(operator, "use_active_collection")
|
||||||
|
|
||||||
body.column().prop(operator, "object_types")
|
body.column().prop(operator, "object_types")
|
||||||
body.prop(operator, "use_custom_props")
|
body.prop(operator, "use_custom_props")
|
||||||
@ -681,6 +691,7 @@ class IO_FH_fbx(bpy.types.FileHandler):
|
|||||||
bl_idname = "IO_FH_fbx"
|
bl_idname = "IO_FH_fbx"
|
||||||
bl_label = "FBX"
|
bl_label = "FBX"
|
||||||
bl_import_operator = "import_scene.fbx"
|
bl_import_operator = "import_scene.fbx"
|
||||||
|
bl_export_operator = "export_scene.fbx"
|
||||||
bl_file_extensions = ".fbx"
|
bl_file_extensions = ".fbx"
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
|
@ -3586,6 +3586,7 @@ def save(operator, context,
|
|||||||
use_selection=False,
|
use_selection=False,
|
||||||
use_visible=False,
|
use_visible=False,
|
||||||
use_active_collection=False,
|
use_active_collection=False,
|
||||||
|
collection="",
|
||||||
batch_mode='OFF',
|
batch_mode='OFF',
|
||||||
use_batch_own_dir=False,
|
use_batch_own_dir=False,
|
||||||
**kwargs
|
**kwargs
|
||||||
@ -3606,13 +3607,23 @@ def save(operator, context,
|
|||||||
|
|
||||||
if batch_mode == 'OFF':
|
if batch_mode == 'OFF':
|
||||||
kwargs_mod = kwargs.copy()
|
kwargs_mod = kwargs.copy()
|
||||||
|
|
||||||
|
source_collection = None
|
||||||
if use_active_collection:
|
if use_active_collection:
|
||||||
if use_selection:
|
source_collection = context.view_layer.active_layer_collection.collection
|
||||||
ctx_objects = tuple(obj
|
elif collection:
|
||||||
for obj in context.view_layer.active_layer_collection.collection.all_objects
|
local_collection = bpy.data.collections.get((collection, None))
|
||||||
if obj.select_get())
|
if local_collection:
|
||||||
Thomas Barlow
commented
Might want to consider whether performing a Collection export from a Collection linked from another file should be supported because a linked Collection can have the same name as a Collection local to the current file (or presumably another Collection linked from another different file). Currently, exporting from a linked Collection appears to work, but doesn't seem too useful because the Collection's children, export settings and export file path cannot be changed due to being linked from another file. I don't know if there is a guarantee that If exporting from a linked Collection should not be supported, Otherwise, to get specific Collections, which could have the same name, linked from different libraries would require I don't know enough about how library linked data-blocks are used and supported by different parts of Blender to say if any changes are needed here. Might want to consider whether performing a Collection export from a Collection linked from another file should be supported because a linked Collection can have the same name as a Collection local to the current file (or presumably another Collection linked from another different file).
Currently, exporting from a linked Collection appears to work, but doesn't seem too useful because the Collection's children, export settings and export file path cannot be changed due to being linked from another file.
I don't know if there is a guarantee that `bpy.data.collections[collection]` will always return a Collection from the current file in preference to a linked Collection with the same name, but it seems like that might be the case from a quick test using the Python Console. So, exporting from a linked Collection with the same name as a local Collection would export the local Collection instead.
If exporting from a linked Collection should not be supported, `bpy.data.collections[(collection, None)]` can be used to only get a Collection local to the current file.
Otherwise, to get specific Collections, which could have the same name, linked from different libraries would require `bpy.data.collections[(collection, library_filepath)]` where `library_filepath` is the value of `my_collection.library.filepath` or `None` (when `my_collection.library is None` due to the Collection being local to the current file).
I don't know enough about how library linked data-blocks are used and supported by different parts of Blender to say if any changes are needed here.
Jesse Yurkovich
commented
Hmm, how did you arrive in this state? If you link in a Collection from foo.blend which has an exporter set you shouldn't see anything in the UI as it's not intended to be exportable in the current file. Are you seeing otherwise?
I'll make the change to use the > Currently, exporting from a linked Collection appears to work, but doesn't seem too useful because the Collection's children, export settings and export file path cannot be changed due to being linked from another file.
Hmm, how did you arrive in this state? If you link in a Collection from foo.blend which has an exporter set you shouldn't see anything in the UI as it's not intended to be exportable in the current file. Are you seeing otherwise?
> I don't know if there is a guarantee that `bpy.data.collections[collection]` will always return a Collection from the current file in preference to a linked Collection with the same name, but it seems like that might be the case from a quick test using the Python Console. So, exporting from a linked Collection with the same name as a local Collection would export the local Collection instead.
> If exporting from a linked Collection should not be supported, `bpy.data.collections[(collection, None)]` can be used to only get a Collection local to the current file.
I'll make the change to use the `None` argument to make it more explicit.
|
|||||||
|
source_collection = local_collection
|
||||||
else:
|
else:
|
||||||
ctx_objects = context.view_layer.active_layer_collection.collection.all_objects
|
operator.report({'ERROR'}, "Collection '%s' was not found" % collection)
|
||||||
|
return {'CANCELLED'}
|
||||||
|
|
||||||
|
if source_collection:
|
||||||
|
if use_selection:
|
||||||
|
ctx_objects = tuple(obj for obj in source_collection.all_objects if obj.select_get())
|
||||||
|
else:
|
||||||
|
ctx_objects = source_collection.all_objects
|
||||||
else:
|
else:
|
||||||
if use_selection:
|
if use_selection:
|
||||||
ctx_objects = context.selected_objects
|
ctx_objects = context.selected_objects
|
||||||
|
The
batch_mode
anduse_batch_own_dir
properties drawn inexport_main()
should also only be drawn whenis_file_browser
because the new code inexport_fbx_bin.py
is only run whenbatch_mode == 'OFF'
(the default value).Changing the
batch_mode
to anything else I don't think makes sense for a Collection exporter.