From a8a4da067976e4c2ffdfd0e80fe042d975ff657a Mon Sep 17 00:00:00 2001 From: David Markowitz Date: Sat, 21 Oct 2023 18:15:57 -0700 Subject: [PATCH] Component work Further component ripping finish switch rip Fix bad names Get it running Fix issues Components: order is complete, need epilogue code now. finished port of thingy Update ComponentFactories.py Update DoObjectPreLoad.py --- ComponentDefinitions.py | 264 ++++++++++++ ComponentFactories.py | 408 ++++++++++++++++++ DoObjectPreLoad.py | 306 +++++++++++++ .../ComponentDefinitions.cpython-310.pyc | Bin 0 -> 7344 bytes .../ComponentFactories.cpython-310.pyc | Bin 0 -> 15221 bytes 5 files changed, 978 insertions(+) create mode 100644 ComponentDefinitions.py create mode 100644 ComponentFactories.py create mode 100644 DoObjectPreLoad.py create mode 100644 __pycache__/ComponentDefinitions.cpython-310.pyc create mode 100644 __pycache__/ComponentFactories.cpython-310.pyc diff --git a/ComponentDefinitions.py b/ComponentDefinitions.py new file mode 100644 index 00000000..7dc16bba --- /dev/null +++ b/ComponentDefinitions.py @@ -0,0 +1,264 @@ +components = { + 'COMPONENT_TYPE_CONTROLLABLE_PHYSICS': 1, + 'COMPONENT_TYPE_RENDER': 2, + 'COMPONENT_TYPE_SIMPLE_PHYSICS': 3, + 'COMPONENT_TYPE_CHARACTER': 4, + 'COMPONENT_TYPE_SCRIPT': 5, + 'COMPONENT_TYPE_BOUNCER': 6, + 'COMPONENT_TYPE_DESTROYABLE': 7, + 'COMPONENT_TYPE_GHOST': 8, + 'COMPONENT_TYPE_SKILL': 9, + 'COMPONENT_TYPE_SPAWNER': 10, + 'COMPONENT_TYPE_ITEM': 11, + 'COMPONENT_TYPE_MODULAR_BUILD': 12, + 'COMPONENT_TYPE_BUILD_CONTROLLER': 13, + 'COMPONENT_TYPE_REBUILD_ACTIVATOR': 14, + 'COMPONENT_TYPE_ICON_ONLY': 15, + 'COMPONENT_TYPE_VENDOR': 16, + 'COMPONENT_TYPE_INVENTORY': 17, + 'COMPONENT_TYPE_PROJECTILE_PHYSICS': 18, + 'COMPONENT_TYPE_SHOOTING_GALLERY': 19, + 'COMPONENT_TYPE_RIGID_BODY_PHANTOM_PHYSICS': 20, + 'COMPONENT_TYPE_DROP_EFFECT': 21, + 'COMPONENT_TYPE_CHEST': 22, + 'COMPONENT_TYPE_COLLECTIBLE': 23, + 'COMPONENT_TYPE_BLUEPRINT': 24, + 'COMPONENT_TYPE_MOVING_PLATFORM': 25, + 'COMPONENT_TYPE_PET': 26, + 'COMPONENT_TYPE_PLATFORM_BOUNDARY': 27, + 'COMPONENT_TYPE_MODULE': 28, + 'COMPONENT_TYPE_ARCADE': 29, + 'COMPONENT_TYPE_HAVOK_VEHICLE_PHYSICS': 30, + 'COMPONENT_TYPE_MOVEMENT_AI': 31, + 'COMPONENT_TYPE_EXHIBIT': 32, + 'COMPONENT_TYPE_OVERHEAD_ICON': 33, + 'COMPONENT_TYPE_PET_CONTROL': 34, + 'COMPONENT_TYPE_MINIFIG': 35, + 'COMPONENT_TYPE_PROPERTY': 36, + 'COMPONENT_TYPE_PET_CREATOR': 37, + 'COMPONENT_TYPE_MODEL_BUILDER': 38, + 'COMPONENT_TYPE_SCRIPTED_ACTIVITY': 39, + 'COMPONENT_TYPE_PHANTOM_PHYSICS': 40, + 'COMPONENT_TYPE_SPRING_PAD': 41, + 'COMPONENT_TYPE_MODEL': 42, + 'COMPONENT_TYPE_PROPERTY_ENTRANCE': 43, + 'COMPONENT_TYPE_FX': 44, + 'COMPONENT_TYPE_PROPERTY_MANAGEMENT': 45, + 'COMPONENT_TYPE_VEHICLE_PHYSICS': 46, + 'COMPONENT_TYPE_PHYSICS_SYSTEM': 47, + 'COMPONENT_TYPE_REBUILD': 48, + 'COMPONENT_TYPE_SWITCH': 49, + 'COMPONENT_TYPE_ZONE_CONTROL': 50, + 'COMPONENT_TYPE_CHANGELING': 51, + 'COMPONENT_TYPE_CHOICE_BUILD': 52, + 'COMPONENT_TYPE_PACKAGE': 53, + 'COMPONENT_TYPE_SOUND_REPEATER': 54, + 'COMPONENT_TYPE_SOUND_AMBIENT_2D': 55, + 'COMPONENT_TYPE_SOUND_AMBIENT_3D': 56, + 'COMPONENT_TYPE_PRECONDITION': 57, + 'COMPONENT_TYPE_PLAYER_FLAG': 58, + 'COMPONENT_TYPE_CUSTOM_BUILD_ASSEMBLY': 59, + 'COMPONENT_TYPE_BASE_COMBAT_AI': 60, + 'COMPONENT_TYPE_MODULE_ASSEMBLY': 61, + 'COMPONENT_TYPE_SHOWCASE_MODEL_HANDLER': 62, + 'COMPONENT_TYPE_RACING_MODULE': 63, + 'COMPONENT_TYPE_GENERIC_ACTIVATOR': 64, + 'COMPONENT_TYPE_PROPERTY_VENDOR': 65, + 'COMPONENT_TYPE_HF_LIGHT_DIRECTION_GADGET': 66, + 'COMPONENT_TYPE_ROCKET_LAUNCH': 67, + 'COMPONENT_TYPE_ROCKET_LANDING_COMPONENT': 68, + 'COMPONENT_TYPE_TRIGGER': 69, + 'COMPONENT_TYPE_DROPPED_LOOT': 70, + 'COMPONENT_TYPE_RACING_CONTROL': 71, + 'COMPONENT_TYPE_FACTION_TRIGGER': 72, + 'COMPONENT_TYPE_MISSION_OFFER': 73, + 'COMPONENT_TYPE_RACING_STATS': 74, + 'COMPONENT_TYPE_LUP_EXHIBIT': 75, + 'COMPONENT_TYPE_BBB': 76, + 'COMPONENT_TYPE_SOUND_TRIGGER': 77, + 'COMPONENT_TYPE_PROXIMITY_MONITOR': 78, + 'COMPONENT_TYPE_RACING_SOUND_TRIGGER': 79, + 'COMPONENT_TYPE_CHAT': 80, + 'COMPONENT_TYPE_FRIENDS_LIST': 81, + 'COMPONENT_TYPE_GUILD': 82, + 'COMPONENT_TYPE_LOCAL_SYSTEM': 83, + 'COMPONENT_TYPE_MISSION': 84, + 'COMPONENT_TYPE_MUTUABLE_MODEL_BEHAVIORS': 85, + 'COMPONENT_TYPE_PATHFINDING_CONTROL': 86, + 'COMPONENT_TYPE_PLAYER_PET_TAMING': 87, + 'COMPONENT_TYPE_PROPERTY_EDITOR': 88, + 'COMPONENT_TYPE_SKINNED_RENDER': 89, + 'COMPONENT_TYPE_SLASH_COMMAND': 90, + 'COMPONENT_TYPE_STATUS_EFFECT': 91, + 'COMPONENT_TYPE_TEAMS': 92, + 'COMPONENT_TYPE_TEXT_EFFECT': 93, + 'COMPONENT_TYPE_TRADE': 94, + 'COMPONENT_TYPE_USER_CONTROL': 95, + 'COMPONENT_TYPE_IGNORE_LIST': 96, + 'COMPONENT_TYPE_ROCKET_LAUNCH_LUP': 97, + 'COMPONENT_TYPE_BUFF': 98, + 'COMPONENT_TYPE_INTERACTION_MANAGER': 99, + 'COMPONENT_TYPE_DONATION_VENDOR': 100, + 'COMPONENT_TYPE_COMBAT_MEDIATOR': 101, + 'COMPONENT_TYPE_ACHIEVEMENT_VENDOR': 102, + 'COMPONENT_TYPE_GATE_RUSH': 103, + 'COMPONENT_TYPE_RAIL_ACTIVATOR': 104, + 'COMPONENT_TYPE_ROLLER': 105, + 'COMPONENT_TYPE_PLAYER_FORCED_MOVEMENT': 106, + 'COMPONENT_TYPE_CRAFTING': 107, + 'COMPONENT_TYPE_POSSESSABLE': 108, + 'COMPONENT_TYPE_LEVEL_PROGRESSION': 109, + 'COMPONENT_TYPE_POSSESSOR': 110, + 'COMPONENT_TYPE_MOUNT_CONTROL': 111, + 'UNKNOWN_112': 112, + 'COMPONENT_TYPE_PROPERTY_PLAQUE': 113, + 'COMPONENT_TYPE_BUILD_BORDER': 114, + 'UNKNOWN_115': 115, + 'COMPONENT_TYPE_CULLING_PLANE': 116, + 'INVALID': 4294967295 +} + +component_initialization_order = [ + 'COMPONENT_TYPE_POSSESSABLE', + 'COMPONENT_TYPE_BLUEPRINT', + 'COMPONENT_TYPE_MODULE_ASSEMBLY', + 'COMPONENT_TYPE_CONTROLLABLE_PHYSICS', + 'COMPONENT_TYPE_PROJECTILE_PHYSICS', + 'COMPONENT_TYPE_PHYSICS_SYSTEM', + 'COMPONENT_TYPE_VEHICLE_PHYSICS', + 'COMPONENT_TYPE_HAVOK_VEHICLE_PHYSICS', + 'COMPONENT_TYPE_RIGID_BODY_PHANTOM_PHYSICS', + 'COMPONENT_TYPE_SIMPLE_PHYSICS', + 'COMPONENT_TYPE_PHANTOM_PHYSICS', + 'COMPONENT_TYPE_DESTROYABLE', + 'COMPONENT_TYPE_MINIFIG', + 'COMPONENT_TYPE_CHARACTER', + 'COMPONENT_TYPE_PLAYER_FORCED_MOVEMENT', + 'COMPONENT_TYPE_POSSESSOR', + 'COMPONENT_TYPE_MOUNT_CONTROL', + 'COMPONENT_TYPE_PET', + 'COMPONENT_TYPE_INVENTORY', + 'COMPONENT_TYPE_PROXIMITY_MONITOR', + 'COMPONENT_TYPE_MOVEMENT_AI', + 'COMPONENT_TYPE_SCRIPT', + 'COMPONENT_TYPE_SKILL', + 'COMPONENT_TYPE_BASE_COMBAT_AI', + 'COMPONENT_TYPE_SPAWNER', + 'COMPONENT_TYPE_ITEM', + 'COMPONENT_TYPE_REBUILD', + 'COMPONENT_TYPE_BUILD_BORDER', + 'COMPONENT_TYPE_MODULE', + 'COMPONENT_TYPE_BUILD_CONTROLLER', + 'COMPONENT_TYPE_REBUILD_ACTIVATOR', + 'COMPONENT_TYPE_MODULAR_BUILD', + 'COMPONENT_TYPE_MISSION_OFFER', + 'COMPONENT_TYPE_VENDOR', + 'COMPONENT_TYPE_DONATION_VENDOR', + 'COMPONENT_TYPE_ACHIEVEMENT_VENDOR', + 'COMPONENT_TYPE_SHOOTING_GALLERY', + 'COMPONENT_TYPE_ROLLER', + 'COMPONENT_TYPE_SCRIPTED_ACTIVITY', + 'COMPONENT_TYPE_COLLECTIBLE', + 'COMPONENT_TYPE_MOVING_PLATFORM', + 'COMPONENT_TYPE_CHANGELING', + 'COMPONENT_TYPE_CHOICE_BUILD', + 'COMPONENT_TYPE_PACKAGE', + 'COMPONENT_TYPE_PLATFORM_BOUNDARY', + 'COMPONENT_TYPE_HF_LIGHT_DIRECTION_GADGET', + 'COMPONENT_TYPE_CULLING_PLANE', + 'COMPONENT_TYPE_EXHIBIT', + 'COMPONENT_TYPE_LUP_EXHIBIT', + 'COMPONENT_TYPE_PROPERTY', + 'COMPONENT_TYPE_PROPERTY_PLAQUE', + 'COMPONENT_TYPE_MODEL', + 'COMPONENT_TYPE_PROPERTY_ENTRANCE', + 'COMPONENT_TYPE_ROCKET_LAUNCH_LUP', + 'COMPONENT_TYPE_PROPERTY_MANAGEMENT', + 'COMPONENT_TYPE_RAIL_ACTIVATOR', + 'COMPONENT_TYPE_BOUNCER', + 'COMPONENT_TYPE_SPRING_PAD', + 'COMPONENT_TYPE_SWITCH', + 'COMPONENT_TYPE_ZONE_CONTROL', + 'COMPONENT_TYPE_MODEL_BUILDER', + 'COMPONENT_TYPE_SOUND_REPEATER', + 'COMPONENT_TYPE_CHEST', + 'COMPONENT_TYPE_SHOWCASE_MODEL_HANDLER', + 'COMPONENT_TYPE_ARCADE', + 'COMPONENT_TYPE_RENDER', + 'COMPONENT_TYPE_SOUND_AMBIENT_2D', + 'COMPONENT_TYPE_SOUND_AMBIENT_3D', + 'COMPONENT_TYPE_SOUND_TRIGGER', + 'COMPONENT_TYPE_RACING_SOUND_TRIGGER', + 'COMPONENT_TYPE_CUSTOM_BUILD_ASSEMBLY', + 'COMPONENT_TYPE_GENERIC_ACTIVATOR', + 'COMPONENT_TYPE_PROPERTY_VENDOR', + 'COMPONENT_TYPE_ROCKET_LAUNCH', + 'COMPONENT_TYPE_ROCKET_LANDING_COMPONENT', + 'COMPONENT_TYPE_FACTION_TRIGGER', + 'COMPONENT_TYPE_RACING_CONTROL', + 'COMPONENT_TYPE_GATE_RUSH', + 'COMPONENT_TYPE_BBB', + 'COMPONENT_TYPE_CRAFTING' +] +component_order_as_ints = {} + +component_int_to_name = {} + +for component in component_initialization_order: + component_order_as_ints[components[component]] = component + +for component in components: + component_int_to_name[components[component]] = component + +class GameObject: + type = "" + +class ObjectLoadState: + createdGameObject = GameObject() + components = [] + hasPhysicsComponent = False + hasDestroyable = False + hasPathfindingComponent = False + hasProximityMonitorComponent = False + hasScriptComponent = False + hasDroppedLootComponent = False + hasModelbehaviors = False + somethingOrNothing = False + physicsComponentId = -1 + +# Begin custom attributes + serializedOrder = [] + hasMissionOffer = False + +class NiPoint3: + x = 0.0 + y = 0.0 + z = 0.0 + +class NiQuaternion: + w = 0.0 + x = 0.0 + y = 0.0 + z = 0.0 + +class LoadObject: + objId = 0 + owner = 0 + lotToSpawn = 0 + isLocalPlayer = False + hasDropEffect = False + bIsSmashable = False + dynamicPhysics = False + spawnPosition = NiPoint3() + spawnRotation = NiQuaternion() + scale = 0.0 + legoBrickID = 0 + legoColorID = 0 + configData = {} + isHFPaletteObject = False + objType = 0 + useSimplePhysics = False + bDelayedLoad = False + +# Don't know the name yet of this + field8_0x20 = True diff --git a/ComponentFactories.py b/ComponentFactories.py new file mode 100644 index 00000000..980d44ee --- /dev/null +++ b/ComponentFactories.py @@ -0,0 +1,408 @@ +import ComponentDefinitions as cd + +def ApplyComponentWhitelist(): + # Dont care to actually do this, just want the call for now. + pass + +def ControllablePhysFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if not objectLoadState.hasModelbehaviors: + if not loadObject.hasDropEffect: + if not loadObject.useSimplePhysics: + objectLoadState.components.append('CONTROLLABLE_PHYSICS') + else: + objectLoadState.components.append('SIMPLE_PHYSICS') + else: + loadObject.physicsComponentId = componentId + +def RenderFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if loadObject.lotToSpawn == 176: + return + gmlevel = loadObject.configData.get('gmlevel', 0) + if gmlevel > 0 and gmlevel < 6: + componentId = 9940 # Override the componentId of the render component to be 9940, the Mythran Render Component + renderDisabled = loadObject.configData.get('renderDisabled', False) + if renderDisabled: + return + if objectLoadState.createdGameObject.type == 'BlockingVolume': + return + rejectedLots = [5937, 5938, 9741, 9742, 9862, 9863] + if loadObject.lotToSpawn in rejectedLots: + return + if loadObject.lotToSpawn == 6368: + FxFactory(loadObject, objectLoadState, componentId) + return + FxFactory(loadObject, objectLoadState, componentId) + defaultWrapperAsset = "" + hasNifAsset = False + hasKfmAsset = False + allowRenderWrapping = False + nifName = loadObject.configData.get('nif_name', '') + if nifName == '': + print('TODO query cdc for this data in the Render component') + nifName = 'mesh/something.nif' # if empty get nifname as the render_asset column of the RenderComponent table from the database + if nifName[-1] == 'f': + hasNifAsset = True + elif nifName[-1] == 'm': + hasKfmAsset = True + if defaultWrapperAsset != '': + if defaultWrapperAsset[-1] == 'm': + allowRenderWrapping = not loadObject.configData.get('preventRenderWrapping', False) + if allowRenderWrapping or hasKfmAsset or (not defaultWrapperAsset == 'PrimitiveModels' and not hasNifAsset and not loadObject.configData.get('CreateNULLRender', False)): + objectLoadState.components.append('SKINNED_RENDER') + else: + objectLoadState.components.append('RENDER') + +def FxFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('FX') + +def SimplePhysFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if not objectLoadState.hasModelbehaviors: + objectLoadState.physicsComponentId = componentId + return + if not loadObject.hasDropEffect: + return + markedAsPhantom = loadObject.configData.get('markedAsPhantom', False) + if markedAsPhantom: + objectLoadState.components.append('PHANTOM_PHYSICS') + else: + objectLoadState.components.append('SIMPLE_PHYSICS') + objectLoadState.hasPhysicsComponent = True + +def CharacterFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('POSSESSOR') + objectLoadState.components.append('MOUNT_CONTROL') + objectLoadState.components.append('PET_CREATOR') + objectLoadState.components.append('LEVEL_PROGRESSION') + objectLoadState.components.append('PLAYER_FORCED_MOVEMENT') + objectLoadState.components.append('CHARACTER') + +def ScriptFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int, add_pathfinding_control: bool): + custom_script_client = loadObject.configData.get('custom_script_client', '') + custom_script_server = loadObject.configData.get('custom_script_server', '') + if componentId == 0 and custom_script_client == '' and custom_script_server == '': + return + objectLoadState.components.append('SCRIPT') + + if not objectLoadState.hasProximityMonitorComponent: + objectLoadState.components.append('PROXIMITY_MONITOR') + objectLoadState.hasProximityMonitorComponent = True + + if not objectLoadState.hasPathfindingComponent and add_pathfinding_control: + objectLoadState.components.append('PATHFINDING_CONTROL') + objectLoadState.hasPathfindingComponent = True + +def BouncerFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('BOUNCER') + +def DestroyableFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('STATUS_EFFECT') + objectLoadState.components.append('BUFF') + objectLoadState.components.append('DESTROYABLE') + objectLoadState.hasDestroyable = True + +def SkillFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SKILL') + +def SpawnerFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SPAWNER') + # If game state is happy flower + spawntemplate = loadObject.configData.get('spawntemplate', '') + + print('TODO query cdc for this data in the Spawner component') + render_asset = loadObject.configData.get('render_asset', 'test.nif') # Get this from RenderComponent table + render_id = loadObject.configData.get('render_id', '') # Get this from RenderComponent table + + if render_asset[-1] == 'f': + objectLoadState.components.append('SKINNED_RENDER') + else: + objectLoadState.components.append('RENDER') + +def ItemFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('ITEM') + +def ModularBuildFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('MODULAR_BUILD') + +def BuildControllerFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('BUILD_CONTROLLER') + +def VendorFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if not objectLoadState.hasProximityMonitorComponent: + objectLoadState.components.append('PROXIMITY_MONITOR') + objectLoadState.hasProximityMonitorComponent = True + objectLoadState.components.append('VENDOR') + +def InventoryFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('INVENTORY') + +def ProjectilePhysicsFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if not loadObject.hasDropEffect: + objectLoadState.components.append('PROJECTILE_PHYSICS') + objectLoadState.hasPhysicsComponent = True + +def ShootingGalleryFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SHOOTING_GALLERY') + +def RigibBodyPhantomPhysicsFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('RIGID_BODY_PHANTOM_PHYSICS') + objectLoadState.hasPhysicsComponent = True + +def ChestFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('CHEST') + +def CollectibleFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('COLLECTIBLE') + if not objectLoadState.hasDestroyable: + objectLoadState.components.append('DESTROYABLE') + objectLoadState.hasDestroyable = True + +def BlueprintFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('BLUEPRINT') + +def MovingPlatformFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('MOVING_PLATFORM') + +def PetFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + inInventory = loadObject.configData.get('inInventory', False) + if inInventory: + return + + if not objectLoadState.hasPathfindingComponent: + objectLoadState.components.append('PATHFINDING_CONTROL') + objectLoadState.hasPathfindingComponent = True + objectLoadState.components.append('PET') + +def PlatformBoundaryFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('PLATFORM_BOUNDARY') + +def ModuleFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('MODULE') + +def ArcadeFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('ARCADE') + +def HavokVehiclePhysicsFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + use_simple_physics = loadObject.configData.get('use_simple_physics', False) + if use_simple_physics: + objectLoadState.components.append('SIMPLE_PHYSICS') + objectLoadState.hasPhysicsComponent = True + else: + objectWorldState = loadObject.configData.get('objectWorldState', '') + if objectWorldState == 0 or objectWorldState != 2: + objectLoadState.components.append('HAVOK_VEHICLE_PHYSICS') + objectLoadState.hasPhysicsComponent = True + +def MovementAiFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('MOVEMENT_AI') + +def ExhibitFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + # Sorry aron, doesnt do anything :( + pass + +def MinifigFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('MINIFIG') + +def PropertyFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('PROPERTY') + +def ModelBuilderFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('MODEL_BUILDER') + +def ScriptedActivityFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SCRIPTED_ACTIVITY') + +def PhantomPhysicsFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if not loadObject.hasDropEffect: + objectLoadState.components.append('PHANTOM_PHYSICS') + objectLoadState.hasPhysicsComponent = True + +def SpringPadFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SPRING_PAD') + +def ModelFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + modelType = loadObject.configData.get('modelType', 0) + if not objectLoadState.hasModelbehaviors: + if not objectLoadState.hasPhysicsComponent: + objectLoadState.components.append('SIMPLE_PHYSICS') + objectLoadState.hasPhysicsComponent = True + elif not objectLoadState.hasPhysicsComponent: + if modelType == 0: + objectLoadState.components.append('CONTROLLABLE_PHYSICS') + else: + objectLoadState.components.append('SIMPLE_PHYSICS') + objectLoadState.hasPhysicsComponent = True + if modelType != 0 and not objectLoadState.hasPathfindingComponent: + objectLoadState.components.append('PATHFINDING_CONTROL') + objectLoadState.hasPathfindingComponent = True + + hasPropertyObjectID = loadObject.configData.get('propertyObjectID', 0) != 0 + inInventory = loadObject.configData.get('inInventory', False) + if hasPropertyObjectID and inInventory: + objectLoadState.components.append('MODEL_BEHAVIORS') + else: + objectLoadState.components.append('MUTABLE_MODEL_BEHAVIORS') + +def PropertyEntranceFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('PROPERTY_ENTRANCE') + +def PropertyManagementFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('PROPERTY_MANAGEMENT') + +def VehiclePhysicsFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('VEHICLE_PHYSICS') + objectLoadState.hasPhysicsComponent = True + +def PhysicsSystemFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if not objectLoadState.hasModelbehaviors: + if not loadObject.hasDropEffect: + objectLoadState.components.append('PHYSICS_SYSTEM') + objectLoadState.hasPhysicsComponent = True + +def RebuildFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('REBUILD') + if not objectLoadState.hasDestroyable: + objectLoadState.components.append('DESTROYABLE') + objectLoadState.hasDestroyable = True + loadObject.bIsSmashable = True + +def BaseCombatAiFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int, add_pathfinding_control: bool): + if not objectLoadState.hasProximityMonitorComponent: + objectLoadState.components.append('PROXIMITY_MONITOR') + objectLoadState.hasProximityMonitorComponent = True + + if not objectLoadState.hasPathfindingComponent and add_pathfinding_control: + objectLoadState.components.append('PATHFINDING_CONTROL') + objectLoadState.hasPathfindingComponent = True + + objectLoadState.components.append('BASE_COMBAT_AI') + +def ProximityMonitorFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + print('TODO query cdc for this data in prox mon') + # There must be a row for this component in the ProximityMonitorComponent table to get this component + LoadOnClient = loadObject.configData.get('LoadOnClient', False) # Get this from ProximityMonitorComponent table if you know there is a column for it + if LoadOnClient: + objectLoadState.components.append('PROXIMITY_MONITOR') + objectLoadState.hasProximityMonitorComponent = True + +def DonationVendorFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if not objectLoadState.hasProximityMonitorComponent: + objectLoadState.components.append('PROXIMITY_MONITOR') + objectLoadState.hasProximityMonitorComponent = True + objectLoadState.components.append('DONATION_VENDOR') + +def AchievmentVendorFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if not objectLoadState.hasProximityMonitorComponent: + objectLoadState.components.append('PROXIMITY_MONITOR') + objectLoadState.hasProximityMonitorComponent = True + + objectLoadState.components.append('ACHIEVEMENT_VENDOR') + +def CraftingFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + # Game verson must be above 999 for this to work! + gameVersion = 1000 + if gameVersion > 999: + objectLoadState.components.append('CRAFTING') + +# Technically Possessable and Possessor are the exact same thing +def PossessableFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('POSSESSABLE') + +def PossessorFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('POSSESSOR') + +def PropertyPlaqueFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('PROPERTY_PLAQUE') + +def BuildBorderFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('BUILD_BORDER') + +def CullingPlaneFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('CULLING_PLANE') + +def GateRushFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('GATE_RUSH') + +def RailActivatorFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('RAIL_ACTIVATOR') + +def RollerFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('ROLLER') + +def PlayerForcedMovementFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('PLAYER_FORCED_MOVEMENT') + +def RacingSoundTriggerFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('RACING_SOUND_TRIGGER') + +def RocketLaunchLupFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('ROCKET_LAUNCH_LUP') + + +def ModuleAssemblyFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('MODULE_ASSEMBLY') + +def ShowcaseModelHandlerFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SHOWCASE_MODEL_HANDLER') + +def GenericActivatorFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('GENERIC_ACTIVATOR') + +def PropertyVendorFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('PROPERTY_VENDOR') + +def RocketLaunchFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('ROCKET_LAUNCH') + +def RocketLandingComponentFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('ROCKET_LANDING_COMPONENT') + +def RacingControlFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('RACING_CONTROL') + +def FactionTriggerFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('FACTION_TRIGGER') + +def MissionOfferFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('MISSION_OFFER') + objectLoadState.hasMissionOffer = True + +def RacingStatsFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('RACING_STATS') + +def LupExhibitFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('LUP_EXHIBIT') + +def BBBFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('BBB') + +def SoundTriggerFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SOUND_TRIGGER') + +def SwitchFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SWITCH') + +def ZoneControlFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('ZONE_CONTROL') + +def ChanglingFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('CHANGELING') + +def ChoiceBuildFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('CHOICE_BUILD') + +def PackageFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + # Literally returns nothing + pass + +def SoundRepeaterFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SOUND_REPEATER') + +def SoundAmbient2DFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + if loadObject.isLocalPlayer: + objectLoadState.components.append('SOUND_AMBIENT_2D') + +def SoundAmbient3DFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('SOUND_AMBIENT_3D') + +def CustomBuildAssemblyFactory(loadObject: cd.LoadObject, objectLoadState: cd.ObjectLoadState, componentId: int): + objectLoadState.components.append('CUSTOM_BUILD_ASSEMBLY') diff --git a/DoObjectPreLoad.py b/DoObjectPreLoad.py new file mode 100644 index 00000000..fc71220c --- /dev/null +++ b/DoObjectPreLoad.py @@ -0,0 +1,306 @@ +import ComponentDefinitions as cd +import ComponentFactories as cf + +# If we have any of these components, we need pathfinding control +def CheckIfNeedsPathfindingControl(components_to_load: dict): + add_pathfinding_control = cd.components['COMPONENT_TYPE_CONTROLLABLE_PHYSICS'] in components_to_load + add_pathfinding_control |= cd.components['COMPONENT_TYPE_PROJECTILE_PHYSICS'] in components_to_load + add_pathfinding_control |= cd.components['COMPONENT_TYPE_HAVOK_VEHICLE_PHYSICS'] in components_to_load + add_pathfinding_control |= cd.components['COMPONENT_TYPE_VEHICLE_PHYSICS'] in components_to_load + return add_pathfinding_control + +def DoObjectPreLoad(components_to_load: dict): + isHfActive = False + cf.ApplyComponentWhitelist() + objectLoadState = cd.ObjectLoadState() + loadObject = cd.LoadObject() + + for componentType in cd.component_order_as_ints.keys(): + try: + componentId = components_to_load[componentType] + except KeyError: + continue + try: + match cd.component_int_to_name[componentType]: + case 'COMPONENT_TYPE_CONTROLLABLE_PHYSICS': + if objectLoadState.hasDroppedLootComponent: continue + cf.ControllablePhysFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_RENDER': + cf.RenderFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SIMPLE_PHYSICS': + if objectLoadState.hasDroppedLootComponent: continue + cf.SimplePhysFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_CHARACTER': + cf.CharacterFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SCRIPT': + cf.ScriptFactory(loadObject, objectLoadState, componentId, CheckIfNeedsPathfindingControl(components_to_load)) + + case 'COMPONENT_TYPE_BOUNCER': + cf.BouncerFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_DESTROYABLE': + cf.DestroyableFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SKILL': + cf.SkillFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SPAWNER': + cf.SpawnerFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_ITEM': + cf.ItemFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_MODULAR_BUILD': + cf.ModularBuildFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_BUILD_CONTROLLER': + cf.BuildControllerFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_VENDOR': + cf.VendorFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_INVENTORY': + cf.InventoryFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PROJECTILE_PHYSICS': + if objectLoadState.hasDroppedLootComponent: continue + cf.ProjectilePhysicsFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SHOOTING_GALLERY': + cf.ShootingGalleryFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_RIGID_BODY_PHANTOM_PHYSICS': + cf.RigibBodyPhantomPhysicsFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_CHEST': + cf.ChestFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_COLLECTIBLE': + cf.CollectibleFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_BLUEPRINT': + cf.BlueprintFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_MOVING_PLATFORM': + cf.MovingPlatformFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PET': + cf.PetFactory(loadObject, objectLoadState, componentId) + print('Deleting COMPONENT_TYPE_MODEL and COMPONENT_TYPE_ITEM due to COMPONENT_TYPE_PET being loaded') + toDel = cd.components['COMPONENT_TYPE_MODEL'] + del components_to_load[toDel] + toDel = cd.components['COMPONENT_TYPE_ITEM'] + del components_to_load[toDel] + + case 'COMPONENT_TYPE_PLATFORM_BOUNDARY': + cf.PlatformBoundaryFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_MODULE': + cf.ModuleFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_ARCADE': + cf.ArcadeFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_HAVOK_VEHICLE_PHYSICS': + cf.HavokVehiclePhysicsFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_MOVEMENT_AI': + cf.MovementAiFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_EXHIBIT': + cf.ExhibitFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_MINIFIG': + cf.MinifigFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PROPERTY': + cf.PropertyFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_MODEL_BUILDER': + cf.ModelBuilderFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SCRIPTED_ACTIVITY': + cf.ScriptedActivityFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PHANTOM_PHYSICS': + if objectLoadState.hasDroppedLootComponent: continue + cf.PhantomPhysicsFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SPRING_PAD': + cf.SpringPadFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_MODEL': + cf.ModelFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PROPERTY_ENTRANCE': + cf.PropertyEntranceFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PROPERTY_MANAGEMENT': + cf.PropertyManagementFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_VEHICLE_PHYSICS': + cf.VehiclePhysicsFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PHYSICS_SYSTEM': + cf.PhysicsSystemFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_REBUILD': + cf.RebuildFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SWITCH': + cf.SwitchFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_ZONE_CONTROL': + cf.ZoneControlFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_CHANGELING': + cf.ChanglingFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_CHOICE_BUILD': + cf.ChoiceBuildFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PACKAGE': + cf.PackageFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SOUND_REPEATER': + cf.SoundRepeaterFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SOUND_AMBIENT_2D': + cf.SoundAmbient2DFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SOUND_AMBIENT_3D': + cf.SoundAmbient3DFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_CUSTOM_BUILD_ASSEMBLY': + cf.CustomBuildAssemblyFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_BASE_COMBAT_AI': + cf.BaseCombatAiFactory(loadObject, objectLoadState, componentId, CheckIfNeedsPathfindingControl(components_to_load)) + + case 'COMPONENT_TYPE_MODULE_ASSEMBLY': + cf.ModuleAssemblyFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SHOWCASE_MODEL_HANDLER': + cf.ShowcaseModelHandlerFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_GENERIC_ACTIVATOR': + cf.GenericActivatorFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PROPERTY_VENDOR': + cf.PropertyVendorFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_ROCKET_LAUNCH': + cf.RocketLaunchFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_ROCKET_LANDING_COMPONENT': + cf.RocketLandingComponentFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_RACING_CONTROL': + cf.RacingControlFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_FACTION_TRIGGER': + cf.FactionTriggerFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_MISSION_OFFER': + cf.MissionOfferFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_RACING_STATS': + cf.RacingStatsFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_LUP_EXHIBIT': + cf.LupExhibitFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_BBB': + cf.BBBFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_SOUND_TRIGGER': + cf.SoundTriggerFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PROXIMITY_MONITOR': + cf.ProximityMonitorFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_RACING_SOUND_TRIGGER': + cf.RacingSoundTriggerFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_ROCKET_LAUNCH_LUP': + cf.RocketLaunchLupFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_DONATION_VENDOR': + cf.DonationVendorFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_ACHIEVEMENT_VENDOR': + cf.AchievmentVendorFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_GATE_RUSH': + cf.GateRushFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_RAIL_ACTIVATOR': + cf.RailActivatorFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_ROLLER': + cf.RollerFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PLAYER_FORCED_MOVEMENT': + cf.PlayerForcedMovementFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_CRAFTING': + cf.CraftingFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_POSSESSABLE': + cf.PossessableFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_POSSESSOR': + cf.PossessorFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_PROPERTY_PLAQUE': + cf.PropertyPlaqueFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_BUILD_BORDER': + cf.BuildBorderFactory(loadObject, objectLoadState, componentId) + + case 'COMPONENT_TYPE_CULLING_PLANE': + cf.CullingPlaneFactory(loadObject, objectLoadState, componentId) + + except KeyError: + print(f'Unknown component: {componentType}') + + if not 'is_smashable' in loadObject.configData and loadObject.bIsSmashable: + loadObject.configData['is_smashable'] = True + + is_smashable = loadObject.configData['is_smashable'] + if is_smashable and not objectLoadState.hasDestroyable and loadObject.lotToSpawn != 176: + objectLoadState.components.append('DESTROYABLE') + + if objectLoadState.hasMissionOffer and not objectLoadState.hasProximityMonitorComponent: + objectLoadState.components.append('PROXIMITY_MONITOR') + objectLoadState.hasProximityMonitorComponent = True + + if loadObject.field8_0x20 and loadObject.owner != 0: + objectLoadState.components.append('OVERHEAD_ICON') + + trigger_id = loadObject.configData.get('trigger_id', 0) + if trigger_id != 0: + objectLoadState.components.append('TRIGGER') + + return objectLoadState + +components_to_load = {} + +# Testing code to load all components +for i in range(110): + components_to_load[i] = i + +objectLoadState = DoObjectPreLoad(components_to_load) + +# Convert the components to ints +components_to_int = [] +for component in objectLoadState.components: + components_to_int.append([cd.components[f'COMPONENT_TYPE_{component}'], component]) + +# Print out the components in a more readable format +for comp in components_to_int: + print(comp[0], comp[1]) diff --git a/__pycache__/ComponentDefinitions.cpython-310.pyc b/__pycache__/ComponentDefinitions.cpython-310.pyc new file mode 100644 index 0000000000000000000000000000000000000000..12bcc76f12aefe91687dea841fe565346e04024c GIT binary patch literal 7344 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 R`ZWLj;&=ahvWJuI{{tM|?Cbyl literal 0 HcmV?d00001