diff --git a/blender-for-unrealengine/bfu_import_module/__init__.py b/blender-for-unrealengine/bfu_import_module/__init__.py
index 6e6e1994..a7355cce 100644
--- a/blender-for-unrealengine/bfu_import_module/__init__.py
+++ b/blender-for-unrealengine/bfu_import_module/__init__.py
@@ -18,22 +18,27 @@
import importlib
+from . import bps
+from . import import_module_utils
+from . import import_module_unreal_utils
from . import asset_import
from . import sequencer_import
+if "bps" in locals():
+ importlib.reload(bps)
+if "import_module_utils" in locals():
+ importlib.reload(import_module_utils)
+if "import_module_unreal_utils" in locals():
+ importlib.reload(import_module_unreal_utils)
if "asset_import" in locals():
importlib.reload(asset_import)
if "sequencer_import" in locals():
importlib.reload(sequencer_import)
-
-
-print("Import module loaded.")
-
def run_asset_import(assets_data):
- pass
- asset_import.ImportAllAssets(assets_data)
+ if asset_import.ready_for_asset_import():
+ return asset_import.ImportAllAssets(assets_data)
def run_sequencer_import(sequence_data):
- pass
- sequencer_import.CreateSequencer(sequence_data)
\ No newline at end of file
+ if sequencer_import.ready_for_sequence_import():
+ return sequencer_import.CreateSequencer(sequence_data)
\ No newline at end of file
diff --git a/blender-for-unrealengine/bfu_import_module/asset_import.py b/blender-for-unrealengine/bfu_import_module/asset_import.py
index 9469a76c..b94ba569 100644
--- a/blender-for-unrealengine/bfu_import_module/asset_import.py
+++ b/blender-for-unrealengine/bfu_import_module/asset_import.py
@@ -1,15 +1,26 @@
-# This script was generated with the addons Blender for UnrealEngine : https://github.com/xavier150/Blender-For-UnrealEngine-Addons
-# It will import into Unreal Engine all the assets of type StaticMesh, SkeletalMesh, Animation and Pose
-# The script must be used in Unreal Engine Editor with Python plugins : https://docs.unrealengine.com/en-US/Engine/Editor/ScriptingAndAutomation/Python
-# Use this command in Unreal cmd consol: py "[ScriptLocation]\ImportSequencerScript.py"
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
-
-import sys
import os.path
-import json
-import string
-from unittest import result
+from . import bps
+from . import import_module_utils
+from . import import_module_unreal_utils
try: # TO DO: Found a better way to check that.
import unreal
@@ -17,503 +28,463 @@
import unreal_engine as unreal
-def CheckTasks():
- if is_unreal_version_greater_or_equal(4,20): # TO DO: EditorAssetLibrary was added in witch version exactly?
+
+def ready_for_asset_import():
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(4,20): # TO DO: EditorAssetLibrary was added in witch version exactly?
if not hasattr(unreal, 'EditorAssetLibrary'):
- print('--------------------------------------------------')
- print('WARNING: Editor Scripting Utilities should be activated.')
- print('Edit > Plugin > Scripting > Editor Scripting Utilities.')
+ message = 'WARNING: Editor Scripting Utilities should be activated.' + "\n"
+ message += 'Edit > Plugin > Scripting > Editor Scripting Utilities.'
+ import_module_unreal_utils.show_warning_message("Editor Scripting Utilities not activated.", message)
return False
return True
-def JsonLoad(json_file):
- # Changed in Python 3.9: The keyword argument encoding has been removed.
- if sys.version_info >= (3, 9):
- return json.load(json_file)
- else:
- return json.load(json_file, encoding="utf8")
-def JsonLoadFile(json_file_path):
- if sys.version_info[0] < 3:
- with open(json_file_path, "r") as json_file:
- return JsonLoad(json_file)
- else:
- with open(json_file_path, "r", encoding="utf8") as json_file:
- return JsonLoad(json_file)
+def ImportAsset(asset_data):
-def get_unreal_version():
- version_info = unreal.SystemLibrary.get_engine_version().split('-')[0]
- version_numbers = version_info.split('.')
- major = int(version_numbers[0])
- minor = int(version_numbers[1])
- patch = int(version_numbers[2])
- return major, minor, patch
+ if asset_data["asset_type"] == "StaticMesh" or asset_data["asset_type"] == "SkeletalMesh":
+ if "lod" in asset_data:
+ if asset_data["lod"] > 0: # Lod should not be imported here so return if lod is not 0.
+ return
-def is_unreal_version_greater_or_equal(target_major, target_minor=0, target_patch=0):
- major, minor, patch = get_unreal_version()
-
- if major > target_major or (major == target_major and minor >= target_minor) or (major == target_major and minor == target_minor and patch >= target_patch):
- return True
+ if asset_data["asset_type"] == "Alembic":
+ FileType = "ABC"
else:
- return False
+ FileType = "FBX"
+ def GetAdditionalData():
+ if "additional_tracks_path" in asset_data:
+ if asset_data["additional_tracks_path"] is not None:
+ return import_module_utils.JsonLoadFile(asset_data["additional_tracks_path"])
+ return None
-def ImportAllAssets(assets_data):
+ additional_data = GetAdditionalData()
- # Prepare process import
- json_data_file = 'ImportAssetData.json'
- dir_path = os.path.dirname(os.path.realpath(__file__))
- assets_data
- bfu_unreal_import_location = assets_data['bfu_unreal_import_location']
- ImportedList = []
- ImportFailList = []
+ if asset_data["asset_type"] == "Animation" or asset_data["asset_type"] == "SkeletalMesh":
+ find_asset = unreal.find_asset(asset_data["animation_skeleton_path"])
+ if isinstance(find_asset, unreal.Skeleton):
+ OriginSkeleton = find_asset
+ elif isinstance(find_asset, unreal.SkeletalMesh):
+ OriginSkeleton = find_asset.skeleton
+ else:
+ OriginSkeleton = None
+ if OriginSkeleton:
+ pass
+ #print("Setting skeleton asset: " + OriginSkeleton.get_full_name())
+ else:
+ message = "Could not find skeleton at the path: " + asset_data["animation_skeleton_path"]
+ import_module_unreal_utils.show_warning_message("Skeleton not found.", message)
- def ValidUnrealAssetsName(filename):
- # Normalizes string, removes non-alpha characters
- # Asset name in Unreal use
+ # docs.unrealengine.com/4.26/en-US/PythonAPI/class/AssetImportTask.html
+ task = unreal.AssetImportTask()
- filename = filename.replace('.', '_')
- filename = filename.replace('(', '_')
- filename = filename.replace(')', '_')
- filename = filename.replace(' ', '_')
- valid_chars = "-_%s%s" % (string.ascii_letters, string.digits)
- filename = ''.join(c for c in filename if c in valid_chars)
- return filename
+ def GetStaticMeshImportData():
+ if asset_data["asset_type"] == "StaticMesh":
+ return task.get_editor_property('options').static_mesh_import_data
+ return None
- def GetAssetByType(type):
- target_assets = []
- for asset in assets_data["assets"]:
- if asset["asset_type"] == type:
- target_assets.append(asset)
- return target_assets
+ def GetSkeletalMeshImportData():
+ if asset_data["asset_type"] == "SkeletalMesh":
+ return task.get_editor_property('options').skeletal_mesh_import_data
+ return None
- def ImportAsset(asset_data):
-
- counter = str(len(ImportedList)+1) + "/" + str(len(assets_data["assets"]))
- print("Import asset " + counter + ": ", asset_data["asset_name"])
-
- if asset_data["asset_type"] == "StaticMesh" or asset_data["asset_type"] == "SkeletalMesh":
- if "lod" in asset_data:
- if asset_data["lod"] > 0: # Lod should not be imported here so return if lod is not 0.
- return
+ def GetAnimationImportData():
+ if asset_data["asset_type"] == "Animation":
+ return task.get_editor_property('options').anim_sequence_import_data
+ return None
+ def GetAlembicImportData():
if asset_data["asset_type"] == "Alembic":
- FileType = "ABC"
- else:
- FileType = "FBX"
-
- def GetAdditionalData():
- if "additional_tracks_path" in asset_data:
- if asset_data["additional_tracks_path"] is not None:
- return JsonLoadFile(asset_data["additional_tracks_path"])
- return None
+ return task.get_editor_property('options')
+ return None
- additional_data = GetAdditionalData()
+ def GetMeshImportData():
+ if asset_data["asset_type"] == "StaticMesh":
+ return GetStaticMeshImportData()
+ if asset_data["asset_type"] == "SkeletalMesh":
+ return GetSkeletalMeshImportData()
+ return None
- def ImportTask():
- # New import task
- # Property
+ if asset_data["asset_type"] == "Alembic":
+ task.filename = asset_data["abc_path"]
+ else:
+ task.filename = asset_data["fbx_path"]
+ task.destination_path = os.path.normpath(asset_data["full_import_path"]).replace('\\', '/')
+ task.automated = True
+ # task.automated = False #Debug for show dialog
+ task.save = True
+ task.replace_existing = True
+
+ if asset_data["asset_type"] == "Alembic":
+ task.set_editor_property('options', unreal.AbcImportSettings())
+ else:
+ task.set_editor_property('options', unreal.FbxImportUI())
+
+ # Alembic
+ if GetAlembicImportData():
+ GetAlembicImportData().static_mesh_settings.set_editor_property("merge_meshes", True)
+ GetAlembicImportData().set_editor_property("import_type", unreal.AlembicImportType.SKELETAL)
+ GetAlembicImportData().conversion_settings.set_editor_property("flip_u", False)
+ GetAlembicImportData().conversion_settings.set_editor_property("flip_v", True)
+ scale = asset_data["scene_unit_scale"] * asset_data["asset_global_scale"]
+ ue_scale = unreal.Vector(scale * 100, scale * -100, scale * 100) # Unit scale * object scale * 100
+ rotation = unreal.Vector(90, 0, 0)
+ GetAlembicImportData().conversion_settings.set_editor_property("scale", ue_scale)
+ GetAlembicImportData().conversion_settings.set_editor_property("rotation", rotation)
+
+ # Vertex color
+ vertex_override_color = None
+ vertex_color_import_option = None
+ if additional_data:
+
+ vertex_color_import_option = unreal.VertexColorImportOption.REPLACE # Default
+ if "vertex_color_import_option" in additional_data:
+ if additional_data["vertex_color_import_option"] == "IGNORE":
+ vertex_color_import_option = unreal.VertexColorImportOption.IGNORE
+ elif additional_data["vertex_color_import_option"] == "OVERRIDE":
+ vertex_color_import_option = unreal.VertexColorImportOption.OVERRIDE
+ elif additional_data["vertex_color_import_option"] == "REPLACE":
+ vertex_color_import_option = unreal.VertexColorImportOption.REPLACE
+
+ if "vertex_override_color" in additional_data:
+ vertex_override_color = unreal.LinearColor(
+ additional_data["vertex_override_color"][0],
+ additional_data["vertex_override_color"][1],
+ additional_data["vertex_override_color"][2]
+ )
+
+ # #################################[Change]
+
+ # unreal.FbxImportUI
+ # https://docs.unrealengine.com/4.26/en-US/PythonAPI/class/FbxImportUI.html
+
+ # Import transform
+ anim_sequence_import_data = GetAnimationImportData()
+ if anim_sequence_import_data:
+ anim_sequence_import_data.import_translation = unreal.Vector(0, 0, 0)
+
+ # Vertex color
+ if vertex_color_import_option and GetMeshImportData():
+ GetMeshImportData().set_editor_property('vertex_color_import_option', vertex_color_import_option)
+
+ if vertex_override_color and GetMeshImportData():
+ GetMeshImportData().set_editor_property('vertex_override_color', vertex_override_color.to_rgbe())
+
+ if asset_data["asset_type"] == "Alembic":
+ task.get_editor_property('options').set_editor_property('import_type', unreal.AlembicImportType.SKELETAL)
- if asset_data["asset_type"] == "Animation" or asset_data["asset_type"] == "SkeletalMesh":
- find_asset = unreal.find_asset(asset_data["animation_skeleton_path"])
- if isinstance(find_asset, unreal.Skeleton):
- OriginSkeleton = find_asset
- elif isinstance(find_asset, unreal.SkeletalMesh):
- OriginSkeleton = find_asset.skeleton
- else:
- OriginSkeleton = None
- if OriginSkeleton:
- print("Setting skeleton asset: " + OriginSkeleton.get_full_name())
+ else:
+ if asset_data["asset_type"] == "Animation" or asset_data["asset_type"] == "SkeletalMesh":
+ if OriginSkeleton:
+ task.get_editor_property('options').set_editor_property('Skeleton', OriginSkeleton)
+ else:
+ if asset_data["asset_type"] == "Animation":
+ fail_reason = 'Skeleton ' + asset_data["animation_skeleton_path"] + ' Not found for ' + asset_data["asset_name"] + ' asset.'
+ return fail_reason
else:
- print("Could not find skeleton at the path: " + asset_data["animation_skeleton_path"])
+ print("Skeleton is not set, a new skeleton asset will be created...")
- # docs.unrealengine.com/4.26/en-US/PythonAPI/class/AssetImportTask.html
- task = unreal.AssetImportTask()
- def GetStaticMeshImportData():
- if asset_data["asset_type"] == "StaticMesh":
- return task.get_editor_property('options').static_mesh_import_data
- return None
+ if asset_data["asset_type"] == "StaticMesh":
+ task.get_editor_property('options').set_editor_property('original_import_type', unreal.FBXImportType.FBXIT_STATIC_MESH)
+ elif asset_data["asset_type"] == "Animation":
+ task.get_editor_property('options').set_editor_property('original_import_type', unreal.FBXImportType.FBXIT_ANIMATION)
+ else:
+ task.get_editor_property('options').set_editor_property('original_import_type', unreal.FBXImportType.FBXIT_SKELETAL_MESH)
- def GetSkeletalMeshImportData():
- if asset_data["asset_type"] == "SkeletalMesh":
- return task.get_editor_property('options').skeletal_mesh_import_data
- return None
+ if asset_data["asset_type"] == "Animation":
+ task.get_editor_property('options').set_editor_property('import_materials', False)
+ else:
+ task.get_editor_property('options').set_editor_property('import_materials', True)
- def GetAnimationImportData():
- if asset_data["asset_type"] == "Animation":
- return task.get_editor_property('options').anim_sequence_import_data
- return None
+ task.get_editor_property('options').set_editor_property('import_textures', False)
- def GetAlembicImportData():
- if asset_data["asset_type"] == "Alembic":
- return task.get_editor_property('options')
- return None
+ if asset_data["asset_type"] == "Animation":
- def GetMeshImportData():
- if asset_data["asset_type"] == "StaticMesh":
- return GetStaticMeshImportData()
- if asset_data["asset_type"] == "SkeletalMesh":
- return GetSkeletalMeshImportData()
+ task.get_editor_property('options').set_editor_property('import_animations', True)
+ task.get_editor_property('options').set_editor_property('import_mesh', False)
+ task.get_editor_property('options').set_editor_property('create_physics_asset',False)
+ else:
+ task.get_editor_property('options').set_editor_property('import_animations', False)
+ task.get_editor_property('options').set_editor_property('import_mesh', True)
+ if "create_physics_asset" in asset_data:
+ task.get_editor_property('options').set_editor_property('create_physics_asset', asset_data["create_physics_asset"])
- return None
+ # unreal.FbxMeshImportData
- if asset_data["asset_type"] == "Alembic":
- task.filename = asset_data["abc_path"]
- else:
- task.filename = asset_data["fbx_path"]
- task.destination_path = os.path.normpath(asset_data["full_import_path"]).replace('\\', '/')
- task.automated = True
- # task.automated = False #Debug for show dialog
- task.save = True
- task.replace_existing = True
-
- if asset_data["asset_type"] == "Alembic":
- task.set_editor_property('options', unreal.AbcImportSettings())
+ if asset_data["asset_type"] == "StaticMesh" or asset_data["asset_type"] == "SkeletalMesh":
+ if "material_search_location" in asset_data:
+ # unreal.FbxTextureImportData
+ if asset_data["material_search_location"] == "Local":
+ task.get_editor_property('options').texture_import_data.set_editor_property('material_search_location', unreal.MaterialSearchLocation.LOCAL)
+ if asset_data["material_search_location"] == "UnderParent":
+ task.get_editor_property('options').texture_import_data.set_editor_property('material_search_location', unreal.MaterialSearchLocation.UNDER_PARENT)
+ if asset_data["material_search_location"] == "UnderRoot":
+ task.get_editor_property('options').texture_import_data.set_editor_property('material_search_location', unreal.MaterialSearchLocation.UNDER_ROOT)
+ if asset_data["material_search_location"] == "AllAssets":
+ task.get_editor_property('options').texture_import_data.set_editor_property('material_search_location', unreal.MaterialSearchLocation.ALL_ASSETS)
+
+ if asset_data["asset_type"] == "StaticMesh":
+ # unreal.FbxStaticMeshImportData
+ task.get_editor_property('options').static_mesh_import_data.set_editor_property('combine_meshes', True)
+ if "auto_generate_collision" in asset_data:
+ task.get_editor_property('options').static_mesh_import_data.set_editor_property('auto_generate_collision', asset_data["auto_generate_collision"])
+ if "static_mesh_lod_group" in asset_data:
+ if asset_data["static_mesh_lod_group"]:
+ task.get_editor_property('options').static_mesh_import_data.set_editor_property('static_mesh_lod_group', asset_data["static_mesh_lod_group"])
+ if "generate_lightmap_u_vs" in asset_data:
+ task.get_editor_property('options').static_mesh_import_data.set_editor_property('generate_lightmap_u_vs', asset_data["generate_lightmap_u_vs"])
+
+ if asset_data["asset_type"] == "SkeletalMesh" or asset_data["asset_type"] == "Animation":
+ # unreal.FbxSkeletalMeshImportData
+ task.get_editor_property('options').skeletal_mesh_import_data.set_editor_property('import_morph_targets', True)
+ task.get_editor_property('options').skeletal_mesh_import_data.set_editor_property('convert_scene', True)
+ task.get_editor_property('options').skeletal_mesh_import_data.set_editor_property('normal_import_method', unreal.FBXNormalImportMethod.FBXNIM_IMPORT_NORMALS_AND_TANGENTS)
+
+ # ###############[ pre import ]################
+
+ # Check is the file alredy exit
+ if additional_data:
+ if "preview_import_path" in additional_data:
+ task_asset_full_path = task.destination_path+"/"+additional_data["preview_import_path"]+"."+additional_data["preview_import_path"]
+ find_asset = unreal.find_asset(task_asset_full_path)
+ if find_asset:
+
+ # Vertex color
+
+ asset_import_data = find_asset.get_editor_property('asset_import_data')
+ if vertex_color_import_option:
+ asset_import_data.set_editor_property('vertex_color_import_option', vertex_color_import_option)
+
+ if vertex_override_color:
+ asset_import_data.set_editor_property('vertex_override_color', vertex_override_color.to_rgbe())
+
+ # ###############[ import asset ]################
+
+ if asset_data["asset_type"] == "Animation":
+ # For animation the script will import a skeletal mesh and remove after.
+ # If the skeletal mesh alredy exist try to remove.
+
+
+ AssetName = asset_data["asset_name"]
+ AssetName = import_module_unreal_utils.ValidUnrealAssetsName(AssetName)
+ AssetPath = "SkeletalMesh'"+asset_data["full_import_path"]+"/"+AssetName+"."+AssetName+"'"
+
+ if unreal.EditorAssetLibrary.does_asset_exist(AssetPath):
+ oldAsset = unreal.EditorAssetLibrary.find_asset_data(AssetPath)
+ if oldAsset.asset_class == "SkeletalMesh":
+ unreal.EditorAssetLibrary.delete_asset(AssetPath)
+
+ unreal.AssetToolsHelpers.get_asset_tools().import_asset_tasks([task])
+
+ if len(task.imported_object_paths) > 0:
+ asset = unreal.find_asset(task.imported_object_paths[0])
+ else:
+ asset = None
+
+ if asset is None:
+ fail_reason = 'Error zero imported object for: ' + asset_data["asset_name"]
+ return fail_reason
+
+ if asset_data["asset_type"] == "Animation":
+ # For animation remove the extra mesh
+ p = task.imported_object_paths[0]
+ if type(unreal.find_asset(p)) is not unreal.AnimSequence:
+ animAssetName = p.split('.')[0]+'_anim.'+p.split('.')[1]+'_anim'
+ animAssetNameDesiredPath = p.split('.')[0]+'.'+p.split('.')[1]
+ animAsset = unreal.find_asset(animAssetName)
+ if animAsset is not None:
+ unreal.EditorAssetLibrary.delete_asset(p)
+ unreal.EditorAssetLibrary.rename_asset(animAssetName, animAssetNameDesiredPath)
+ asset = animAsset
else:
- task.set_editor_property('options', unreal.FbxImportUI())
-
- # Alembic
- if GetAlembicImportData():
- GetAlembicImportData().static_mesh_settings.set_editor_property("merge_meshes", True)
- GetAlembicImportData().set_editor_property("import_type", unreal.AlembicImportType.SKELETAL)
- GetAlembicImportData().conversion_settings.set_editor_property("flip_u", False)
- GetAlembicImportData().conversion_settings.set_editor_property("flip_v", True)
- scale = asset_data["scene_unit_scale"] * asset_data["asset_global_scale"]
- ue_scale = unreal.Vector(scale * 100, scale * -100, scale * 100) # Unit scale * object scale * 100
- rotation = unreal.Vector(90, 0, 0)
- GetAlembicImportData().conversion_settings.set_editor_property("scale", ue_scale)
- GetAlembicImportData().conversion_settings.set_editor_property("rotation", rotation)
-
- # Vertex color
- vertex_override_color = None
- vertex_color_import_option = None
- if additional_data:
-
- vertex_color_import_option = unreal.VertexColorImportOption.REPLACE # Default
- if "vertex_color_import_option" in additional_data:
- if additional_data["vertex_color_import_option"] == "IGNORE":
- vertex_color_import_option = unreal.VertexColorImportOption.IGNORE
- elif additional_data["vertex_color_import_option"] == "OVERRIDE":
- vertex_color_import_option = unreal.VertexColorImportOption.OVERRIDE
- elif additional_data["vertex_color_import_option"] == "REPLACE":
- vertex_color_import_option = unreal.VertexColorImportOption.REPLACE
-
- if "vertex_override_color" in additional_data:
- vertex_override_color = unreal.LinearColor(
- additional_data["vertex_override_color"][0],
- additional_data["vertex_override_color"][1],
- additional_data["vertex_override_color"][2]
- )
-
- # #################################[Change]
-
- # unreal.FbxImportUI
- # https://docs.unrealengine.com/4.26/en-US/PythonAPI/class/FbxImportUI.html
-
- # Import transform
- anim_sequence_import_data = GetAnimationImportData()
- if anim_sequence_import_data:
- anim_sequence_import_data.import_translation = unreal.Vector(0, 0, 0)
-
- # Vertex color
- if vertex_color_import_option and GetMeshImportData():
- GetMeshImportData().set_editor_property('vertex_color_import_option', vertex_color_import_option)
-
- if vertex_override_color and GetMeshImportData():
- GetMeshImportData().set_editor_property('vertex_override_color', vertex_override_color.to_rgbe())
-
- if asset_data["asset_type"] == "Alembic":
- task.get_editor_property('options').set_editor_property('import_type', unreal.AlembicImportType.SKELETAL)
+ fail_reason = 'animAsset ' + asset_data["asset_name"] + ' not found for after inport: ' + animAssetName
+ return fail_reason
+
+ # ###############[ Post treatment ]################
+ asset_import_data = asset.get_editor_property('asset_import_data')
+ if asset_data["asset_type"] == "StaticMesh":
+ if "static_mesh_lod_group" in asset_data:
+ if asset_data["static_mesh_lod_group"]:
+ asset.set_editor_property('lod_group', asset_data["static_mesh_lod_group"])
+ if "use_custom_light_map_resolution" in asset_data:
+ if asset_data["use_custom_light_map_resolution"]:
+ if "light_map_resolution" in asset_data:
+ asset.set_editor_property('light_map_resolution', asset_data["light_map_resolution"])
+ build_settings = unreal.EditorStaticMeshLibrary.get_lod_build_settings(asset, 0)
+ build_settings.min_lightmap_resolution = asset_data["light_map_resolution"]
+ unreal.EditorStaticMeshLibrary.set_lod_build_settings(asset, 0, build_settings)
+
+ if "collision_trace_flag" in asset_data:
+ collision_data = asset.get_editor_property('body_setup')
+ if collision_data:
+ if asset_data["collision_trace_flag"] == "CTF_UseDefault":
+ collision_data.set_editor_property('collision_trace_flag', unreal.CollisionTraceFlag.CTF_USE_DEFAULT)
+ elif asset_data["collision_trace_flag"] == "CTF_UseSimpleAndComplex":
+ collision_data.set_editor_property('collision_trace_flag', unreal.CollisionTraceFlag.CTF_USE_SIMPLE_AND_COMPLEX)
+ elif asset_data["collision_trace_flag"] == "CTF_UseSimpleAsComplex":
+ collision_data.set_editor_property('collision_trace_flag', unreal.CollisionTraceFlag.CTF_USE_SIMPLE_AS_COMPLEX)
+ elif asset_data["collision_trace_flag"] == "CTF_UseComplexAsSimple":
+ collision_data.set_editor_property('collision_trace_flag', unreal.CollisionTraceFlag.CTF_USE_COMPLEX_AS_SIMPLE)
+
+
+ if asset_data["asset_type"] == "StaticMesh":
+ if "generate_lightmap_u_vs" in asset_data:
+ asset_import_data.set_editor_property('generate_lightmap_u_vs', asset_data["generate_lightmap_u_vs"]) # Import data
+ unreal.EditorStaticMeshLibrary.set_generate_lightmap_uv(asset, asset_data["generate_lightmap_u_vs"]) # Build settings at lod
+
+ if asset_data["asset_type"] == "SkeletalMesh":
+ asset_import_data.set_editor_property('normal_import_method', unreal.FBXNormalImportMethod.FBXNIM_IMPORT_NORMALS_AND_TANGENTS)
+ if OriginSkeleton is None:
+ #Unreal create a new skeleton when no skeleton was selected, so addon rename it.
+ p = task.imported_object_paths[0]
+ old_skeleton_name = p.split('.')[0]+'_Skeleton.'+p.split('.')[1]+'_Skeleton'
+ new_skeleton_name = asset_data["animation_skeleton_path"]
+ unreal.EditorAssetLibrary.rename_asset(old_skeleton_name, new_skeleton_name)
+
+ if "enable_skeletal_mesh_per_poly_collision" in asset_data:
+ asset.set_editor_property('enable_per_poly_collision', asset_data["enable_skeletal_mesh_per_poly_collision"])
+
+
+ # Socket
+ if asset_data["asset_type"] == "SkeletalMesh":
+ # Import the SkeletalMesh socket(s)
+ sockets_to_add = additional_data["Sockets"]
+ for socket in sockets_to_add:
+ old_socket = asset.find_socket(socket["SocketName"])
+ if old_socket:
+ # Edit socket
+ pass
+ # old_socket.relative_location = socket["Location"]
+ # old_socket.relative_rotation = socket["Rotation"]
+ # old_socket.relative_scale = socket["Scale"]
else:
- if asset_data["asset_type"] == "Animation" or asset_data["asset_type"] == "SkeletalMesh":
- if OriginSkeleton:
- task.get_editor_property('options').set_editor_property('Skeleton', OriginSkeleton)
- else:
- if asset_data["asset_type"] == "Animation":
- ImportFailList.append('Skeleton ' + asset_data["animation_skeleton_path"] + ' Not found for ' + asset_data["asset_name"] + ' asset.')
- return
+ # Create socket
+ pass
+ # new_socket = unreal.SkeletalMeshSocket(asset)
+ # new_socket.socket_name = socket["SocketName"]
+ # new_socket.bone_name = socket["BoneName"]
+ # new_socket.relative_location = socket["Location"]
+ # new_socket.relative_rotation = socket["Rotation"]
+ # new_socket.relative_scale = socket["Scale"]
+ # NEED UNREAL ENGINE IMPLEMENTATION IN PYTHON API.
+ # skeleton.add_socket(new_socket)
+
+ # Lod
+ if asset_data["asset_type"] == "StaticMesh" or asset_data["asset_type"] == "SkeletalMesh":
+ if asset_data["asset_type"] == "StaticMesh":
+ unreal.EditorStaticMeshLibrary.remove_lods(asset) # Import the StaticMesh lod(s)
+
+ if asset_data["asset_type"] == "SkeletalMesh" or asset_data["asset_type"] == "StaticMesh":
+
+ def ImportStaticLod(lod_name, lod_number):
+ if "LevelOfDetail" in additional_data:
+ if lod_name in additional_data["LevelOfDetail"]:
+ lodTask = unreal.AssetImportTask()
+ lodTask.filename = additional_data["LevelOfDetail"][lod_name]
+ destination_path = os.path.normpath(asset_data["full_import_path"]).replace('\\', '/')
+ lodTask.destination_path = destination_path
+ lodTask.automated = True
+ lodTask.replace_existing = True
+
+ # Set vertex color import settings to replicate base StaticMesh's behaviour
+ if asset_data["asset_type"] == "Alembic":
+ lodTask.set_editor_property('options', unreal.AbcImportSettings())
else:
- print("Skeleton is not set, a new skeleton asset will be created...")
+ lodTask.set_editor_property('options', unreal.FbxImportUI())
+ lodTask.get_editor_property('options').static_mesh_import_data.set_editor_property('vertex_color_import_option', vertex_color_import_option)
+ lodTask.get_editor_property('options').static_mesh_import_data.set_editor_property('vertex_override_color', vertex_override_color.to_rgbe())
- if asset_data["asset_type"] == "StaticMesh":
- task.get_editor_property('options').set_editor_property('original_import_type', unreal.FBXImportType.FBXIT_STATIC_MESH)
- elif asset_data["asset_type"] == "Animation":
- task.get_editor_property('options').set_editor_property('original_import_type', unreal.FBXImportType.FBXIT_ANIMATION)
- else:
- task.get_editor_property('options').set_editor_property('original_import_type', unreal.FBXImportType.FBXIT_SKELETAL_MESH)
+ unreal.AssetToolsHelpers.get_asset_tools().import_asset_tasks([lodTask])
+ if len(lodTask.imported_object_paths) > 0:
+ lodAsset = unreal.find_asset(lodTask.imported_object_paths[0])
+ slot_replaced = unreal.EditorStaticMeshLibrary.set_lod_from_static_mesh(asset, lod_number, lodAsset, 0, True)
+ unreal.EditorAssetLibrary.delete_asset(lodTask.imported_object_paths[0])
- if asset_data["asset_type"] == "Animation":
- task.get_editor_property('options').set_editor_property('import_materials', False)
- else:
- task.get_editor_property('options').set_editor_property('import_materials', True)
+ def ImportSkeletalLod(lod_name, lod_number):
+ if "LevelOfDetail" in additional_data:
+ if lod_name in additional_data["LevelOfDetail"]:
+ # Unreal python no longer support Skeletal mesh LODS import.
+ pass
- task.get_editor_property('options').set_editor_property('import_textures', False)
+ if asset_data["asset_type"] == "StaticMesh":
+ ImportStaticLod("lod_1", 1)
+ ImportStaticLod("lod_2", 2)
+ ImportStaticLod("lod_3", 3)
+ ImportStaticLod("lod_4", 4)
+ ImportStaticLod("lod_5", 5)
- if asset_data["asset_type"] == "Animation":
+ elif asset_data["asset_type"] == "SkeletalMesh":
+ ImportSkeletalLod("lod_1", 1)
+ ImportSkeletalLod("lod_2", 2)
+ ImportSkeletalLod("lod_3", 3)
+ ImportSkeletalLod("lod_4", 4)
+ ImportSkeletalLod("lod_5", 5)
- task.get_editor_property('options').set_editor_property('import_animations', True)
- task.get_editor_property('options').set_editor_property('import_mesh', False)
- task.get_editor_property('options').set_editor_property('create_physics_asset',False)
- else:
- task.get_editor_property('options').set_editor_property('import_animations', False)
- task.get_editor_property('options').set_editor_property('import_mesh', True)
- if "create_physics_asset" in asset_data:
- task.get_editor_property('options').set_editor_property('create_physics_asset', asset_data["create_physics_asset"])
-
- # unreal.FbxMeshImportData
-
- if asset_data["asset_type"] == "StaticMesh" or asset_data["asset_type"] == "SkeletalMesh":
- if "material_search_location" in asset_data:
- # unreal.FbxTextureImportData
- if asset_data["material_search_location"] == "Local":
- task.get_editor_property('options').texture_import_data.set_editor_property('material_search_location', unreal.MaterialSearchLocation.LOCAL)
- if asset_data["material_search_location"] == "UnderParent":
- task.get_editor_property('options').texture_import_data.set_editor_property('material_search_location', unreal.MaterialSearchLocation.UNDER_PARENT)
- if asset_data["material_search_location"] == "UnderRoot":
- task.get_editor_property('options').texture_import_data.set_editor_property('material_search_location', unreal.MaterialSearchLocation.UNDER_ROOT)
- if asset_data["material_search_location"] == "AllAssets":
- task.get_editor_property('options').texture_import_data.set_editor_property('material_search_location', unreal.MaterialSearchLocation.ALL_ASSETS)
-
- if asset_data["asset_type"] == "StaticMesh":
- # unreal.FbxStaticMeshImportData
- task.get_editor_property('options').static_mesh_import_data.set_editor_property('combine_meshes', True)
- if "auto_generate_collision" in asset_data:
- task.get_editor_property('options').static_mesh_import_data.set_editor_property('auto_generate_collision', asset_data["auto_generate_collision"])
- if "static_mesh_lod_group" in asset_data:
- if asset_data["static_mesh_lod_group"]:
- task.get_editor_property('options').static_mesh_import_data.set_editor_property('static_mesh_lod_group', asset_data["static_mesh_lod_group"])
- if "generate_lightmap_u_vs" in asset_data:
- task.get_editor_property('options').static_mesh_import_data.set_editor_property('generate_lightmap_u_vs', asset_data["generate_lightmap_u_vs"])
-
- if asset_data["asset_type"] == "SkeletalMesh" or asset_data["asset_type"] == "Animation":
- # unreal.FbxSkeletalMeshImportData
- task.get_editor_property('options').skeletal_mesh_import_data.set_editor_property('import_morph_targets', True)
- task.get_editor_property('options').skeletal_mesh_import_data.set_editor_property('convert_scene', True)
- task.get_editor_property('options').skeletal_mesh_import_data.set_editor_property('normal_import_method', unreal.FBXNormalImportMethod.FBXNIM_IMPORT_NORMALS_AND_TANGENTS)
-
- # ###############[ pre import ]################
-
- # Check is the file alredy exit
- if additional_data:
- if "preview_import_path" in additional_data:
- task_asset_full_path = task.destination_path+"/"+additional_data["preview_import_path"]+"."+additional_data["preview_import_path"]
- find_asset = unreal.find_asset(task_asset_full_path)
- if find_asset:
-
- # Vertex color
-
- asset_import_data = find_asset.get_editor_property('asset_import_data')
- if vertex_color_import_option:
- asset_import_data.set_editor_property('vertex_color_import_option', vertex_color_import_option)
-
- if vertex_override_color:
- asset_import_data.set_editor_property('vertex_override_color', vertex_override_color.to_rgbe())
-
- # ###############[ import asset ]################
-
- print("Import task")
- if asset_data["asset_type"] == "Animation":
- # For animation the script will import a skeletal mesh and remove after.
- # If the skeletal mesh alredy exist try to remove.
-
-
- AssetName = asset_data["asset_name"]
- AssetName = ValidUnrealAssetsName(AssetName)
- AssetPath = "SkeletalMesh'"+asset_data["full_import_path"]+"/"+AssetName+"."+AssetName+"'"
-
- if unreal.EditorAssetLibrary.does_asset_exist(AssetPath):
- oldAsset = unreal.EditorAssetLibrary.find_asset_data(AssetPath)
- if oldAsset.asset_class == "SkeletalMesh":
- unreal.EditorAssetLibrary.delete_asset(AssetPath)
-
- unreal.AssetToolsHelpers.get_asset_tools().import_asset_tasks([task])
-
- if len(task.imported_object_paths) > 0:
- asset = unreal.find_asset(task.imported_object_paths[0])
- else:
- asset = None
+ # Vertex color
+ if vertex_override_color:
+ asset_import_data.set_editor_property('vertex_override_color', vertex_override_color.to_rgbe())
- if asset is None:
- ImportFailList.append('Error zero imported object for: ' + asset_data["asset_name"])
- return
+ if vertex_color_import_option:
+ asset_import_data.set_editor_property('vertex_color_import_option', vertex_color_import_option)
- if asset_data["asset_type"] == "Animation":
- # For animation remove the extra mesh
- p = task.imported_object_paths[0]
- if type(unreal.find_asset(p)) is not unreal.AnimSequence:
- animAssetName = p.split('.')[0]+'_anim.'+p.split('.')[1]+'_anim'
- animAssetNameDesiredPath = p.split('.')[0]+'.'+p.split('.')[1]
- animAsset = unreal.find_asset(animAssetName)
- if animAsset is not None:
- unreal.EditorAssetLibrary.delete_asset(p)
- unreal.EditorAssetLibrary.rename_asset(animAssetName, animAssetNameDesiredPath)
- asset = animAsset
- else:
- ImportFailList.append('animAsset ' + asset_data["asset_name"] + ' not found for after inport: ' + animAssetName)
- return
-
- # ###############[ Post treatment ]################
- asset_import_data = asset.get_editor_property('asset_import_data')
- if asset_data["asset_type"] == "StaticMesh":
- if "static_mesh_lod_group" in asset_data:
- if asset_data["static_mesh_lod_group"]:
- asset.set_editor_property('lod_group', asset_data["static_mesh_lod_group"])
- if "use_custom_light_map_resolution" in asset_data:
- if asset_data["use_custom_light_map_resolution"]:
- if "light_map_resolution" in asset_data:
- asset.set_editor_property('light_map_resolution', asset_data["light_map_resolution"])
- build_settings = unreal.EditorStaticMeshLibrary.get_lod_build_settings(asset, 0)
- build_settings.min_lightmap_resolution = asset_data["light_map_resolution"]
- unreal.EditorStaticMeshLibrary.set_lod_build_settings(asset, 0, build_settings)
-
- if "collision_trace_flag" in asset_data:
- collision_data = asset.get_editor_property('body_setup')
- if collision_data:
- if asset_data["collision_trace_flag"] == "CTF_UseDefault":
- collision_data.set_editor_property('collision_trace_flag', unreal.CollisionTraceFlag.CTF_USE_DEFAULT)
- elif asset_data["collision_trace_flag"] == "CTF_UseSimpleAndComplex":
- collision_data.set_editor_property('collision_trace_flag', unreal.CollisionTraceFlag.CTF_USE_SIMPLE_AND_COMPLEX)
- elif asset_data["collision_trace_flag"] == "CTF_UseSimpleAsComplex":
- collision_data.set_editor_property('collision_trace_flag', unreal.CollisionTraceFlag.CTF_USE_SIMPLE_AS_COMPLEX)
- elif asset_data["collision_trace_flag"] == "CTF_UseComplexAsSimple":
- collision_data.set_editor_property('collision_trace_flag', unreal.CollisionTraceFlag.CTF_USE_COMPLEX_AS_SIMPLE)
+ # #################################[EndChange]
+ if asset_data["asset_type"] == "StaticMesh" or asset_data["asset_type"] == "SkeletalMesh":
+ unreal.EditorAssetLibrary.save_loaded_asset(asset)
+ return "SUCCESS", asset, asset_data["asset_type"]
- if asset_data["asset_type"] == "StaticMesh":
- if "generate_lightmap_u_vs" in asset_data:
- asset_import_data.set_editor_property('generate_lightmap_u_vs', asset_data["generate_lightmap_u_vs"]) # Import data
- unreal.EditorStaticMeshLibrary.set_generate_lightmap_uv(asset, asset_data["generate_lightmap_u_vs"]) # Build settings at lod
-
- if asset_data["asset_type"] == "SkeletalMesh":
- asset_import_data.set_editor_property('normal_import_method', unreal.FBXNormalImportMethod.FBXNIM_IMPORT_NORMALS_AND_TANGENTS)
- if OriginSkeleton is None:
- #Unreal create a new skeleton when no skeleton was selected, so addon rename it.
- p = task.imported_object_paths[0]
- old_skeleton_name = p.split('.')[0]+'_Skeleton.'+p.split('.')[1]+'_Skeleton'
- new_skeleton_name = asset_data["animation_skeleton_path"]
- unreal.EditorAssetLibrary.rename_asset(old_skeleton_name, new_skeleton_name)
-
- if "enable_skeletal_mesh_per_poly_collision" in asset_data:
- asset.set_editor_property('enable_per_poly_collision', asset_data["enable_skeletal_mesh_per_poly_collision"])
-
-
- # Socket
- if asset_data["asset_type"] == "SkeletalMesh":
- # Import the SkeletalMesh socket(s)
- sockets_to_add = additional_data["Sockets"]
- for socket in sockets_to_add:
- old_socket = asset.find_socket(socket["SocketName"])
- if old_socket:
- # Edit socket
- pass
- # old_socket.relative_location = socket["Location"]
- # old_socket.relative_rotation = socket["Rotation"]
- # old_socket.relative_scale = socket["Scale"]
- else:
- # Create socket
- pass
- # new_socket = unreal.SkeletalMeshSocket(asset)
- # new_socket.socket_name = socket["SocketName"]
- # new_socket.bone_name = socket["BoneName"]
- # new_socket.relative_location = socket["Location"]
- # new_socket.relative_rotation = socket["Rotation"]
- # new_socket.relative_scale = socket["Scale"]
- # NEED UNREAL ENGINE IMPLEMENTATION IN PYTHON API.
- # skeleton.add_socket(new_socket)
-
- # Lod
- if asset_data["asset_type"] == "StaticMesh" or asset_data["asset_type"] == "SkeletalMesh":
- if asset_data["asset_type"] == "StaticMesh":
- unreal.EditorStaticMeshLibrary.remove_lods(asset) # Import the StaticMesh lod(s)
-
- if asset_data["asset_type"] == "SkeletalMesh" or asset_data["asset_type"] == "StaticMesh":
-
- def ImportStaticLod(lod_name, lod_number):
- if "LevelOfDetail" in additional_data:
- if lod_name in additional_data["LevelOfDetail"]:
- lodTask = unreal.AssetImportTask()
- lodTask.filename = additional_data["LevelOfDetail"][lod_name]
- destination_path = os.path.normpath(asset_data["full_import_path"]).replace('\\', '/')
- lodTask.destination_path = destination_path
- lodTask.automated = True
- lodTask.replace_existing = True
-
- # Set vertex color import settings to replicate base StaticMesh's behaviour
- if asset_data["asset_type"] == "Alembic":
- lodTask.set_editor_property('options', unreal.AbcImportSettings())
- else:
- lodTask.set_editor_property('options', unreal.FbxImportUI())
-
- lodTask.get_editor_property('options').static_mesh_import_data.set_editor_property('vertex_color_import_option', vertex_color_import_option)
- lodTask.get_editor_property('options').static_mesh_import_data.set_editor_property('vertex_override_color', vertex_override_color.to_rgbe())
-
- print(destination_path, additional_data["LevelOfDetail"][lod_name])
- unreal.AssetToolsHelpers.get_asset_tools().import_asset_tasks([lodTask])
- if len(lodTask.imported_object_paths) > 0:
- lodAsset = unreal.find_asset(lodTask.imported_object_paths[0])
- slot_replaced = unreal.EditorStaticMeshLibrary.set_lod_from_static_mesh(asset, lod_number, lodAsset, 0, True)
- unreal.EditorAssetLibrary.delete_asset(lodTask.imported_object_paths[0])
-
- def ImportSkeletalLod(lod_name, lod_number):
- if "LevelOfDetail" in additional_data:
- if lod_name in additional_data["LevelOfDetail"]:
- # Unreal python no longer support Skeletal mesh LODS import.
- pass
-
- if asset_data["asset_type"] == "StaticMesh":
- ImportStaticLod("lod_1", 1)
- ImportStaticLod("lod_2", 2)
- ImportStaticLod("lod_3", 3)
- ImportStaticLod("lod_4", 4)
- ImportStaticLod("lod_5", 5)
-
- elif asset_data["asset_type"] == "SkeletalMesh":
- ImportSkeletalLod("lod_1", 1)
- ImportSkeletalLod("lod_2", 2)
- ImportSkeletalLod("lod_3", 3)
- ImportSkeletalLod("lod_4", 4)
- ImportSkeletalLod("lod_5", 5)
-
- # Vertex color
- if vertex_override_color:
- asset_import_data.set_editor_property('vertex_override_color', vertex_override_color.to_rgbe())
-
- if vertex_color_import_option:
- asset_import_data.set_editor_property('vertex_color_import_option', vertex_color_import_option)
-
- # #################################[EndChange]
- if asset_data["asset_type"] == "StaticMesh" or asset_data["asset_type"] == "SkeletalMesh":
- unreal.EditorAssetLibrary.save_loaded_asset(asset)
+def ImportAllAssets(assets_data):
+
+
+
+
+ bfu_unreal_import_location = assets_data['bfu_unreal_import_location']
+ ImportedList = []
+ ImportFailList = []
+
+ def GetAssetByType(type):
+ target_assets = []
+ for asset in assets_data["assets"]:
+ if asset["asset_type"] == type:
+ target_assets.append(asset)
+ return target_assets
+
+ def PrepareImportAsset(asset_data):
+ counter = str(len(ImportedList)+1) + "/" + str(len(assets_data["assets"]))
+ print("Import asset " + counter + ": ", asset_data["asset_name"])
+
+ result, asset, asset_type = ImportAsset(asset_data)
+ if result == "SUCCESS":
ImportedList.append([asset, asset_data["asset_type"]])
+ else:
+ ImportFailList.append(result)
- ImportTask()
- # Process import
+ # Process import
print('========================= Import started ! =========================')
- print(assets_data["assets"])
+ counter = bps.utils.CounterTimer()
# Import assets with a specific order
- for asset in GetAssetByType("Alembic"):
- ImportAsset(asset)
- for asset in GetAssetByType("StaticMesh"):
- ImportAsset(asset)
- for asset in GetAssetByType("SkeletalMesh"):
- ImportAsset(asset)
- for asset in GetAssetByType("Animation"):
- ImportAsset(asset)
+ for asset_data in GetAssetByType("Alembic"):
+ PrepareImportAsset(asset_data)
+ for asset_data in GetAssetByType("StaticMesh"):
+ PrepareImportAsset(asset_data)
+ for asset_data in GetAssetByType("SkeletalMesh"):
+ PrepareImportAsset(asset_data)
+ for asset_data in GetAssetByType("Animation"):
+ PrepareImportAsset(asset_data)
print('========================= Full import completed ! =========================')
@@ -532,11 +503,16 @@ def ImportSkeletalLod(lod_name, lod_number):
else:
Animation_ImportedList.append(asset[0])
- print('Imported StaticMesh: '+str(len(StaticMesh_ImportedList)))
- print('Imported SkeletalMesh: '+str(len(SkeletalMesh_ImportedList)))
- print('Imported Alembic: '+str(len(Alembic_ImportedList)))
- print('Imported Animation: '+str(len(Animation_ImportedList)))
- print('Import failled: '+str(len(ImportFailList)))
+ import_log = []
+ import_log.append('Imported StaticMesh: '+str(len(StaticMesh_ImportedList)))
+ import_log.append('Imported SkeletalMesh: '+str(len(SkeletalMesh_ImportedList)))
+ import_log.append('Imported Alembic: '+str(len(Alembic_ImportedList)))
+ import_log.append('Imported Animation: '+str(len(Animation_ImportedList)))
+ import_log.append('Import failled: '+str(len(ImportFailList)))
+
+ for import_row in import_log:
+ print(import_row)
+
for error in ImportFailList:
print(error)
@@ -548,7 +524,21 @@ def ImportSkeletalLod(lod_name, lod_number):
print('=========================')
if len(ImportFailList) > 0:
- return 'Some asset(s) could not be imported.'
+ message = 'Some asset(s) could not be imported.' + "\n"
else:
- return 'Assets imported with success !'
+ message = 'All assets imported with success!' + "\n"
+
+ message += "Import finished in " + counter.get_str_time() + "\n"
+ message += "\n"
+ for import_row in import_log:
+ message += import_row + "\n"
+ if len(ImportFailList) > 0:
+ message += "\n"
+ for error in ImportFailList:
+ message += error + "\n"
+
+ title = "Import finished!"
+ import_module_unreal_utils.show_simple_message(title, message)
+
+ return True
diff --git a/blender-for-unrealengine/bfu_import_module/asset_import_script.py b/blender-for-unrealengine/bfu_import_module/asset_import_script.py
index 058827c7..ac0073cc 100644
--- a/blender-for-unrealengine/bfu_import_module/asset_import_script.py
+++ b/blender-for-unrealengine/bfu_import_module/asset_import_script.py
@@ -58,14 +58,11 @@ def RunImportScriptWithJsonData():
import_assets_data = JsonLoadFile(os.path.join(dir_path, json_data_file))
- import_module_path = import_assets_data["info"]["import_modiule_path"] # Module to run
- print("Module path to import:", import_module_path)
-
+ import_module_path = import_assets_data["info"]["import_modiule_path"] # Module to run
imported_module, module_name = load_module(import_module_path)
unload_module(module_name)
imported_module.run_asset_import(import_assets_data)
-print("Start importing assets.")
-RunImportScriptWithJsonData()
-print("Importing assets finished.")
+if __name__ == "__main__":
+ RunImportScriptWithJsonData()
diff --git a/blender-for-unrealengine/bfu_import_module/bps/__init__.py b/blender-for-unrealengine/bfu_import_module/bps/__init__.py
new file mode 100644
index 00000000..b0dbec29
--- /dev/null
+++ b/blender-for-unrealengine/bfu_import_module/bps/__init__.py
@@ -0,0 +1,39 @@
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
+
+# ----------------------------------------------
+# BPS -> BleuRaven Python Script
+# BleuRaven.fr
+# XavierLoux.com
+# ----------------------------------------------
+
+import importlib
+
+from . import advprint
+from . import utils
+from . import math
+from . import color_set
+
+if "advprint" in locals():
+ importlib.reload(advprint)
+if "utils" in locals():
+ importlib.reload(utils)
+if "math" in locals():
+ importlib.reload(math)
+if "math" in locals():
+ importlib.reload(color_set)
\ No newline at end of file
diff --git a/blender-for-unrealengine/bfu_import_module/bps/advprint.py b/blender-for-unrealengine/bfu_import_module/bps/advprint.py
new file mode 100644
index 00000000..75ac6f27
--- /dev/null
+++ b/blender-for-unrealengine/bfu_import_module/bps/advprint.py
@@ -0,0 +1,127 @@
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
+
+# ----------------------------------------------
+# BPS -> BleuRaven Python Script
+# BleuRaven.fr
+# XavierLoux.com
+# ----------------------------------------------
+
+
+import sys
+import time
+
+
+class ProgressionBarClass():
+
+ def _get_name(self):
+ return self.__name
+
+ def _set_name(self, value):
+ if not isinstance(value, str):
+ raise TypeError("name must be set to an String")
+ self.__name = value
+
+ name = property(_get_name, _set_name)
+
+ def _get_length(self):
+ return self.__length
+
+ def _set_length(self, value):
+ if not isinstance(value, int):
+ raise TypeError("length must be set to an Integer")
+ self.__length = value
+
+ length = property(_get_length, _set_length)
+
+ previous_step = 0.0
+
+ def _get_total_step(self):
+ return self.__total_step
+
+ def _set_total_step(self, value):
+ if not (isinstance(value, int) or isinstance(value, float)):
+ raise TypeError("total_step must be set to an Integer or Float")
+
+ self.__total_step = value
+
+ total_step = property(_get_total_step, _set_total_step)
+
+ # Visual
+ show_block = True
+ show_steps = True
+ show_percentage = True
+
+ def __init__(self):
+ self.__name = "My progression bar"
+ self.__length = 20 # modify this to change the length
+ self.__previous_step = 0.0
+ self.__total_step = 1.0 # from 0 to 1
+ self.__counter_start = time.perf_counter()
+
+ def update_progress(self, progress):
+ job_title = self.__name
+ length = self.__length
+ total_step = self.__total_step
+ self.__previous_step = progress # Update the previous step.
+
+ is_done = False
+ if progress >= total_step:
+ is_done = True
+
+ # Write message.
+ msg = "\r{0}:".format(job_title)
+
+ if self.show_block:
+ block = int(round(length*progress/total_step))
+ msg += " [{0}]".format("#"*block + "-"*(length-block))
+
+ if self.show_steps:
+ msg += " {0}/{1}".format(progress, total_step)
+
+ if is_done:
+ msg += " DONE IN {0}s\r\n".format(round(time.perf_counter()-self.__counter_start, 3))
+
+ else:
+ if self.show_percentage:
+ msg += " {0}%".format(round((progress*100)/total_step, 2))
+
+ sys.stdout.write(msg)
+ sys.stdout.flush()
+
+
+def print_separation(number=60, char="-"):
+ """
+ Prints a separation line consisting of '#' characters.
+
+ Args:
+ number (int, optional): The number of '#' characters in the line. Defaults to 60.
+ """
+ print("# {0} #".format(char * number))
+
+
+def print_title(text, number=60):
+ """
+ Prints a title surrounded by a line of '#' characters.
+
+ Args:
+ text (str): The text of the title.
+ number (int, optional): The total number of characters in the line. Defaults to 60.
+ """
+ remain_number = len(text) - number - 2
+ print("# {0} {1} {2} #".format("-" * remain_number, text, "-" * remain_number))
diff --git a/blender-for-unrealengine/bfu_import_module/bps/color_set.py b/blender-for-unrealengine/bfu_import_module/bps/color_set.py
new file mode 100644
index 00000000..8d39ebe4
--- /dev/null
+++ b/blender-for-unrealengine/bfu_import_module/bps/color_set.py
@@ -0,0 +1,156 @@
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
+
+# ----------------------------------------------
+# BPS -> BleuRaven Python Script
+# BleuRaven.fr
+# XavierLoux.com
+# ----------------------------------------------
+
+# This use ANSI color codes.
+# You can found it all here -> https://gist.github.com/JBlond/2fea43a3049b38287e5e9cefc87b2124
+# This file use the code of rene-d -> https://gist.github.com/rene-d/9e584a7dd2935d0f461904b9f2950007
+
+
+
+# SGR color constants
+# rene-d 2018
+
+class Colors:
+ """ ANSI color codes """
+
+ # Color
+ BLACK = "\033[0;30m"
+ RED = "\033[0;31m"
+ GREEN = "\033[0;32m"
+ BROWN = "\033[0;33m"
+ BLUE = "\033[0;34m"
+ PURPLE = "\033[0;35m"
+ CYAN = "\033[0;36m"
+ LIGHT_GRAY = "\033[0;37m"
+ DARK_GRAY = "\033[1;30m"
+ LIGHT_RED = "\033[1;31m"
+ LIGHT_GREEN = "\033[1;32m"
+ YELLOW = "\033[1;33m"
+ LIGHT_BLUE = "\033[1;34m"
+ LIGHT_PURPLE = "\033[1;35m"
+ LIGHT_CYAN = "\033[1;36m"
+ LIGHT_WHITE = "\033[1;37m"
+
+ #Style
+ BOLD = "\033[1m"
+ FAINT = "\033[2m"
+ ITALIC = "\033[3m"
+ UNDERLINE = "\033[4m"
+ BLINK = "\033[5m"
+ NEGATIVE = "\033[7m"
+ CROSSED = "\033[9m"
+ END = "\033[0m"
+
+
+@staticmethod
+def black(string):
+ return Colors.BLACK + string + Colors.END
+
+@staticmethod
+def red(string):
+ return Colors.RED + string + Colors.END
+
+@staticmethod
+def green(string):
+ return Colors.GREEN + string + Colors.END
+
+@staticmethod
+def brown(string):
+ return Colors.BROWN + string + Colors.END
+
+@staticmethod
+def blue(string):
+ return Colors.BLUE + string + Colors.END
+
+@staticmethod
+def purple(string):
+ return Colors.PURPLE + string + Colors.END
+
+@staticmethod
+def cyan(string):
+ return Colors.CYAN + string + Colors.END
+
+@staticmethod
+def light_gray(string):
+ return Colors.LIGHT_GRAY + string + Colors.END
+
+@staticmethod
+def dark_gray(string):
+ return Colors.DARK_GRAY + string + Colors.END
+
+@staticmethod
+def light_red(string):
+ return Colors.LIGHT_RED + string + Colors.END
+
+@staticmethod
+def light_green(string):
+ return Colors.LIGHT_GREEN + string + Colors.END
+
+@staticmethod
+def yellow(string):
+ return Colors.YELLOW + string + Colors.END
+
+@staticmethod
+def light_blue(string):
+ return Colors.LIGHT_BLUE + string + Colors.END
+
+@staticmethod
+def light_purple(string):
+ return Colors.LIGHT_PURPLE + string + Colors.END
+
+@staticmethod
+def light_cyan(string):
+ return Colors.LIGHT_CYAN + string + Colors.END
+
+@staticmethod
+def light_white(string):
+ return Colors.LIGHT_WHITE + string + Colors.END
+
+@staticmethod
+def bold(string):
+ return Colors.BOLD + string + Colors.END
+
+@staticmethod
+def faint(string):
+ return Colors.FAINT + string + Colors.END
+
+@staticmethod
+def italic(string):
+ return Colors.ITALIC + string + Colors.END
+
+@staticmethod
+def underline(string):
+ return Colors.UNDERLINE + string + Colors.END
+
+@staticmethod
+def blink(string):
+ return Colors.BLINK + string + Colors.END
+
+@staticmethod
+def negative(string):
+ return Colors.NEGATIVE + string + Colors.END
+
+@staticmethod
+def crossed(string):
+ return Colors.CROSSED + string + Colors.END
\ No newline at end of file
diff --git a/blender-for-unrealengine/bfu_import_module/bps/math.py b/blender-for-unrealengine/bfu_import_module/bps/math.py
new file mode 100644
index 00000000..d036605a
--- /dev/null
+++ b/blender-for-unrealengine/bfu_import_module/bps/math.py
@@ -0,0 +1,85 @@
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
+
+# ----------------------------------------------
+# BPS -> BleuRaven Python Script
+# BleuRaven.fr
+# XavierLoux.com
+# ----------------------------------------------
+
+
+def next_power_of_two(n):
+ """
+ Computes the next power of two that is greater than or equal to n.
+
+ Args:
+ n (int): The input number.
+
+ Returns:
+ int: The next power of two greater than or equal to n.
+ """
+ # decrement n (to handle cases when n itself
+ # is a power of 2)
+ n = n - 1
+
+ # do till only one bit is left
+ while n & n - 1:
+ n = n & n - 1 # unset rightmost bit
+
+ # n is now a power of two (less than n)
+ return n << 1
+
+
+def previous_power_of_two(n):
+ """
+ Computes the previous power of two that is less than or equal to n.
+
+ Args:
+ n (int): The input number.
+
+ Returns:
+ int: The previous power of two less than or equal to n.
+ """
+ # do till only one bit is left
+ while (n & n - 1):
+ n = n & n - 1 # unset rightmost bit
+
+ # n is now a power of two (less than or equal to n)
+ return n
+
+
+def nearest_power_of_two(value):
+ """
+ Computes the nearest power of two to the given value.
+
+ Args:
+ value (int): The input value.
+
+ Returns:
+ int: The nearest power of two.
+ """
+ if value < 2:
+ return 2
+
+ a = previous_power_of_two(value)
+ b = next_power_of_two(value)
+
+ if value - a < b - value:
+ return a
+ else:
+ return b
diff --git a/blender-for-unrealengine/bfu_import_module/bps/utils.py b/blender-for-unrealengine/bfu_import_module/bps/utils.py
new file mode 100644
index 00000000..9eccd267
--- /dev/null
+++ b/blender-for-unrealengine/bfu_import_module/bps/utils.py
@@ -0,0 +1,62 @@
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
+
+# ----------------------------------------------
+# BPS -> BleuRaven Python Script
+# BleuRaven.fr
+# XavierLoux.com
+# ----------------------------------------------
+
+import time
+
+
+class CounterTimer():
+ """
+ A simple timer.
+ """
+
+ def __init__(self):
+ self.start = time.perf_counter()
+
+ def reset_time(self):
+ """
+ Reset the timer.
+ """
+ self.start = time.perf_counter()
+
+ def get_time(self):
+ """
+ Get the elapsed time since the timer started. (Class create)
+ """
+ return time.perf_counter() - self.start
+
+ def get_str_time(self):
+ """
+ Get the elapsed str time since the timer started. (Class create)
+ """
+ elapsed_time = self.get_time()
+ if elapsed_time < 60:
+ return f"{elapsed_time:.2f} secondes"
+ elif elapsed_time < 3600:
+ minutes, seconds = divmod(elapsed_time, 60)
+ return f"{int(minutes)} minutes et {seconds:.2f} secondes"
+ else:
+ hours, remainder = divmod(elapsed_time, 3600)
+ minutes, seconds = divmod(remainder, 60)
+ return f"{int(hours)} heures, {int(minutes)} minutes et {seconds:.2f} secondes"
+
diff --git a/blender-for-unrealengine/bfu_import_module/import_module_unreal_utils.py b/blender-for-unrealengine/bfu_import_module/import_module_unreal_utils.py
new file mode 100644
index 00000000..2b620715
--- /dev/null
+++ b/blender-for-unrealengine/bfu_import_module/import_module_unreal_utils.py
@@ -0,0 +1,60 @@
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
+
+import string
+
+try: # TO DO: Found a better way to check that.
+ import unreal
+except ImportError:
+ import unreal_engine as unreal
+
+def get_unreal_version():
+ version_info = unreal.SystemLibrary.get_engine_version().split('-')[0]
+ version_numbers = version_info.split('.')
+ major = int(version_numbers[0])
+ minor = int(version_numbers[1])
+ patch = int(version_numbers[2])
+ return major, minor, patch
+
+def is_unreal_version_greater_or_equal(target_major, target_minor=0, target_patch=0):
+ major, minor, patch = get_unreal_version()
+
+ if major > target_major or (major == target_major and minor >= target_minor) or (major == target_major and minor == target_minor and patch >= target_patch):
+ return True
+ else:
+ return False
+
+def ValidUnrealAssetsName(filename):
+ # Normalizes string, removes non-alpha characters
+ # Asset name in Unreal use
+
+ filename = filename.replace('.', '_')
+ filename = filename.replace('(', '_')
+ filename = filename.replace(')', '_')
+ filename = filename.replace(' ', '_')
+ valid_chars = "-_%s%s" % (string.ascii_letters, string.digits)
+ filename = ''.join(c for c in filename if c in valid_chars)
+ return filename
+
+def show_simple_message(title, message):
+ return unreal.EditorDialog.show_message(title, message, unreal.AppMsgType.OK)
+
+def show_warning_message(title, message):
+ print('--------------------------------------------------')
+ print(message)
+ return unreal.EditorDialog.show_message(title, message, unreal.AppMsgType.OK)
\ No newline at end of file
diff --git a/blender-for-unrealengine/bfu_import_module/import_module_utils.py b/blender-for-unrealengine/bfu_import_module/import_module_utils.py
new file mode 100644
index 00000000..6c5d3df3
--- /dev/null
+++ b/blender-for-unrealengine/bfu_import_module/import_module_utils.py
@@ -0,0 +1,37 @@
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
+
+import sys
+import json
+
+def JsonLoad(json_file):
+ # Changed in Python 3.9: The keyword argument encoding has been removed.
+ if sys.version_info >= (3, 9):
+ return json.load(json_file)
+ else:
+ return json.load(json_file, encoding="utf8")
+
+
+def JsonLoadFile(json_file_path):
+ if sys.version_info[0] < 3:
+ with open(json_file_path, "r") as json_file:
+ return JsonLoad(json_file)
+ else:
+ with open(json_file_path, "r", encoding="utf8") as json_file:
+ return JsonLoad(json_file)
+
diff --git a/blender-for-unrealengine/bfu_import_module/sequencer_import.py b/blender-for-unrealengine/bfu_import_module/sequencer_import.py
index 77cb1133..0f39a489 100644
--- a/blender-for-unrealengine/bfu_import_module/sequencer_import.py
+++ b/blender-for-unrealengine/bfu_import_module/sequencer_import.py
@@ -1,11 +1,25 @@
-# This script was generated with the addons Blender for UnrealEngine : https://github.com/xavier150/Blender-For-UnrealEngine-Addons
-# It will import into Unreal Engine all the assets of type StaticMesh, SkeletalMesh, Animation and Pose
-# The script must be used in Unreal Engine Editor with Python plugins : https://docs.unrealengine.com/en-US/Engine/Editor/ScriptingAndAutomation/Python
-# Use this command in Unreal cmd consol: py "[ScriptLocation]\ImportSequencerScript.py"
+# ====================== BEGIN GPL LICENSE BLOCK ============================
+#
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see .
+# All rights reserved.
+#
+# ======================= END GPL LICENSE BLOCK =============================
-import sys
import os.path
-import json
+from . import bps
+from . import import_module_utils
+from . import import_module_unreal_utils
try: # TO DO: Found a better way to check that.
import unreal
@@ -13,61 +27,25 @@
import unreal_engine as unreal
-def CheckTasks():
- if is_unreal_version_greater_or_equal(4,20): # TO DO: EditorAssetLibrary was added in witch version exactly?
+
+
+def ready_for_sequence_import():
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(4,20): # TO DO: EditorAssetLibrary was added in witch version exactly?
if not hasattr(unreal, 'EditorAssetLibrary'):
- print('--------------------------------------------------')
- print('WARNING: Editor Scripting Utilities should be activated.')
- print('Edit > Plugin > Scripting > Editor Scripting Utilities.')
+ message = 'WARNING: Editor Scripting Utilities should be activated.' + "\n"
+ message += 'Edit > Plugin > Scripting > Editor Scripting Utilities.'
+ import_module_unreal_utils.show_warning_message("Editor Scripting Utilities not activated.", message)
return False
if not hasattr(unreal.MovieSceneSequence, 'set_display_rate'):
- print('--------------------------------------------------')
- print('WARNING: Editor Scripting Utilities should be activated.')
- print('Edit > Plugin > Scripting > Sequencer Scripting.')
+ message = 'WARNING: Editor Scripting Utilities should be activated.' + "\n"
+ message += 'Edit > Plugin > Scripting > Sequencer Scripting.'
+ import_module_unreal_utils.show_warning_message("Editor Scripting Utilities not activated.", message)
return False
return True
-
-def JsonLoad(json_file):
- # Changed in Python 3.9: The keyword argument encoding has been removed.
- if sys.version_info >= (3, 9):
- return json.load(json_file)
- else:
- return json.load(json_file, encoding="utf8")
-
-
-def JsonLoadFile(json_file_path):
- if sys.version_info[0] < 3:
- with open(json_file_path, "r") as json_file:
- return JsonLoad(json_file)
- else:
- with open(json_file_path, "r", encoding="utf8") as json_file:
- return JsonLoad(json_file)
-
-
-def get_unreal_version():
- version_info = unreal.SystemLibrary.get_engine_version().split('-')[0]
- version_numbers = version_info.split('.')
- major = int(version_numbers[0])
- minor = int(version_numbers[1])
- patch = int(version_numbers[2])
- return major, minor, patch
-
-def is_unreal_version_greater_or_equal(target_major, target_minor=0, target_patch=0):
- major, minor, patch = get_unreal_version()
-
- if major > target_major or (major == target_major and minor >= target_minor) or (major == target_major and minor == target_minor and patch >= target_patch):
- return True
- else:
- return False
-
def CreateSequencer(sequence_data):
- # Prepare process import
- json_data_file = 'ImportSequencerData.json'
- dir_path = os.path.dirname(os.path.realpath(__file__))
-
spawnable_camera = sequence_data['spawnable_camera']
startFrame = sequence_data['startFrame']
endFrame = sequence_data['endFrame']+1
@@ -85,7 +63,7 @@ def AddSequencerSectionTransformKeysByIniFile(sequencer_section, track_dict):
frame = unreal.FrameNumber(int(key))
- if is_unreal_version_greater_or_equal(5,0):
+ if import_module_utils.is_unreal_version_greater_or_equal(5,0):
sequencer_section.get_all_channels()[0].add_key(frame, value["location_x"])
sequencer_section.get_all_channels()[1].add_key(frame, value["location_y"])
sequencer_section.get_all_channels()[2].add_key(frame, value["location_z"])
@@ -110,7 +88,7 @@ def AddSequencerSectionFloatKeysByIniFile(sequencer_section, track_dict):
for key in track_dict.keys():
frame = unreal.FrameNumber(int(key))
value = track_dict[key]
- if is_unreal_version_greater_or_equal(5,0):
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(5,0):
sequencer_section.get_all_channels()[0].add_key(frame, value)
else:
sequencer_section.get_channels()[0].add_key(frame, value)
@@ -119,7 +97,7 @@ def AddSequencerSectionBoolKeysByIniFile(sequencer_section, track_dict):
for key in track_dict.keys():
frame = unreal.FrameNumber(int(key))
value = track_dict[key]
- if is_unreal_version_greater_or_equal(5,0):
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(5,0):
sequencer_section.get_all_channels()[0].add_key(frame, value)
else:
sequencer_section.get_channels()[0].add_key(frame, value)
@@ -145,13 +123,13 @@ def AddSequencerSectionBoolKeysByIniFile(sequencer_section, track_dict):
# Set playback range
seq.set_playback_end_seconds((endFrame-secureCrop)/float(frameRateNumerator))
seq.set_playback_start_seconds(startFrame/float(frameRateNumerator)) # set_playback_end_seconds
- if is_unreal_version_greater_or_equal(5,2):
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(5,2):
camera_cut_track = seq.add_track(unreal.MovieSceneCameraCutTrack)
else:
camera_cut_track = seq.add_master_track(unreal.MovieSceneCameraCutTrack)
camera_cut_track.set_editor_property('display_name', 'Imported Camera Cuts')
- if is_unreal_version_greater_or_equal(4,26):
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(4,26):
camera_cut_track.set_color_tint(unreal.Color(b=200, g=0, r=0, a=0))
else:
pass
@@ -160,7 +138,7 @@ def AddSequencerSectionBoolKeysByIniFile(sequencer_section, track_dict):
# import camera
print("Start camera import " + str(x+1) + "/" + str(len(sequence_data["cameras"])) + " :" + camera_data["name"])
# Import camera tracks transform
- camera_tracks = JsonLoadFile(camera_data["additional_tracks_path"])
+ camera_tracks = import_module_utils.JsonLoadFile(camera_data["additional_tracks_path"])
# Create spawnable camera and add camera in sequencer
cine_camera_actor = unreal.EditorLevelLibrary().spawn_actor_from_class(unreal.CineCameraActor, unreal.Vector(0, 0, 0), unreal.Rotator(0, 0, 0))
@@ -209,7 +187,7 @@ def AddSequencerSectionBoolKeysByIniFile(sequencer_section, track_dict):
TrackFocusDistance = camera_component_binding.add_track(unreal.MovieSceneFloatTrack)
- if is_unreal_version_greater_or_equal(4,24):
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(4,24):
TrackFocusDistance.set_property_name_and_path('FocusSettings.ManualFocusDistance', 'FocusSettings.ManualFocusDistance')
TrackFocusDistance.set_editor_property('display_name', 'Manual Focus Distance (Focus Settings)')
else:
@@ -253,7 +231,7 @@ def AddSequencerSectionBoolKeysByIniFile(sequencer_section, track_dict):
else:
current_camera_binding = camera_binding
- if is_unreal_version_greater_or_equal(4,26):
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(4,26):
current_camera_binding.set_display_name(camera_data["name"])
else:
pass
@@ -292,11 +270,11 @@ def AddSequencerSectionBoolKeysByIniFile(sequencer_section, track_dict):
for camera in ImportedCamera:
if camera[0] == section["camera_name"]:
camera_binding_id = unreal.MovieSceneObjectBindingID()
- if is_unreal_version_greater_or_equal(5,3):
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(5,3):
camera_binding_id = seq.get_binding_id(camera[1])
- elif is_unreal_version_greater_or_equal(4,27):
+ elif import_module_unreal_utils.is_unreal_version_greater_or_equal(4,27):
camera_binding_id = seq.get_portable_binding_id(seq, camera[1])
- elif is_unreal_version_greater_or_equal(4,26):
+ elif import_module_unreal_utils.is_unreal_version_greater_or_equal(4,26):
camera_binding_id = seq.make_binding_id(camera[1], unreal.MovieSceneObjectBindingSpace.LOCAL)
else:
camera_binding_id = seq.make_binding_id(camera[1])
@@ -314,10 +292,10 @@ def AddSequencerSectionBoolKeysByIniFile(sequencer_section, track_dict):
print('=========================')
# Select and open seq in content browser
- if is_unreal_version_greater_or_equal(5,0):
+ if import_module_unreal_utils.is_unreal_version_greater_or_equal(5,0):
pass #TO DO make crate the engine
#unreal.AssetEditorSubsystem.open_editor_for_assets(unreal.AssetEditorSubsystem(), [unreal.load_asset(seq.get_path_name())])
- elif is_unreal_version_greater_or_equal(4,26):
+ elif import_module_unreal_utils.is_unreal_version_greater_or_equal(4,26):
unreal.AssetEditorSubsystem.open_editor_for_assets(unreal.AssetEditorSubsystem(), [unreal.load_asset(seq.get_path_name())])
else:
unreal.AssetToolsHelpers.get_asset_tools().open_editor_for_assets([unreal.load_asset(seq.get_path_name())])
diff --git a/blender-for-unrealengine/bfu_import_module/sequencer_import_script.py b/blender-for-unrealengine/bfu_import_module/sequencer_import_script.py
index be7e5452..2f594607 100644
--- a/blender-for-unrealengine/bfu_import_module/sequencer_import_script.py
+++ b/blender-for-unrealengine/bfu_import_module/sequencer_import_script.py
@@ -58,14 +58,11 @@ def RunImportScriptWithJsonData():
sequence_data = JsonLoadFile(os.path.join(dir_path, json_data_file))
- import_module_path = sequence_data["info"]["import_modiule_path"] # Module to run
- print("Module path to import:", import_module_path)
-
+ import_module_path = sequence_data["info"]["import_modiule_path"] # Module to run
imported_module, module_name = load_module(import_module_path)
unload_module(module_name)
imported_module.run_sequencer_import(sequence_data)
-print("Start importing assets.")
-RunImportScriptWithJsonData()
-print("Importing assets finished.")
+if __name__ == "__main__":
+ RunImportScriptWithJsonData()