Technically does not matter if code… or rether module is in project or a plugin, those models will be added to already existing modules in the engine. So you practically extending engine it self, plugins and project are only differently distributed. Engine is highly modular, and enigne code is divided in to modules same as one oyu making in the project, regardless if you put code in the project, plugin or add module directly in to engine it will work the same and have same possibilities. to put it to perspective this is actually new feature in UE4 not only for code but also content, in the past with UE3 (aka UDK) you actually need sperate engine installation to make a different game because there was no project system, you latterly extending the engine. Editor is also run on the engine it self and when you build module for editor build you also technicly extending the editor and you code runs litterly as a part in editor (thats why you can access UWorlds that are used for editing and preview windows and you actor classes are fully initiated when you place actors on the level), there no hard separation between engine, editor and you game components, all that creates one single program.
Obviously one way to do it is to edit engine source code, but UE4 allows you to override lot of it’s classes in engine modules with classes that in other modules. Including UEngine class:
Which is heart of the engine it self and editor do this too by having it’s own UEditorEngine, UUnrealEdEnigne class, the runtime game also have it’s own engine class UGameEnigne, so you need to override. And as much crazy it may sound… you do this in the config file, inside Engine.ini:
[/Script/Engine.Engine]
ConsoleClassName=/Script/Engine.Console
GameViewportClientClassName=/Script/Engine.GameViewportClient
......
AssetManagerClassName=/Script/Engine.AssetManager
bAllowMatureLanguage=false
GameEngine=/Script/Engine.GameEngine
EditorEngine=/Script/UnrealEd.EditorEngine
UnrealEdEngine=/Script/UnrealEd.UnrealEdEngine
And there you can Init function which is probably the eariest point of the engine you can hook up in to enigne from outside module:
Look up in engine source code:
https://github.com/EpicGames/UnrealEngine/blob/375ba9730e72bf85b383c07a5e4a7ba98774bcb9/Engine/Source/Runtime/Engine/Private/UnrealEngine.cpp#L1328
But there also other options, Each module have startup end shutdown code in it’s main class (it’s macroed in the game project C++ module by default but you can replace that with your code, same as you do in plugin), here some example code from one of engine plugins:
class FActorLayerUtilitiesEditorModule : public IModuleInterface
{
FName ActorLayerTypeName;
static TSharedRef<IPropertyTypeCustomization> MakeCustomization()
{
return MakeShared<FActorLayerPropertyTypeCustomization>();
}
virtual void StartupModule() override
{
ActorLayerTypeName = FActorLayer::StaticStruct()->GetFName();
FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked<FPropertyEditorModule>("PropertyEditor");
PropertyModule.RegisterCustomPropertyTypeLayout(ActorLayerTypeName, FOnGetPropertyTypeCustomizationInstance::CreateStatic(MakeCustomization));
}
virtual void ShutdownModule() override
{
FPropertyEditorModule* PropertyModule = FModuleManager::GetModulePtr<FPropertyEditorModule>("PropertyEditor");
if (PropertyModule && ActorLayerTypeName != NAME_None)
{
PropertyModule->UnregisterCustomPropertyTypeLayout(ActorLayerTypeName);
}
}
};
IMPLEMENT_MODULE(FActorLayerUtilitiesEditorModule, ActorLayerUtilitiesEditor)
Technically it’s entry point of your module and inside uproject or uplugin you can set how early module is loaded. Maybe you can do something from there.
Other solution since what you saying involves graphics you can create your own RHI as it is one that is reproducible for rendering, copy RHI module from engine source code (if i’m not mistaken you can do that, as long as you not redistribute it outside of your team) and there hook up to init code. Maybe there some hook up points in existing RHIs that allows to avoid doing the copy, i didn’t touch RHI much so i don’t know.
And at the end there always that option to simply modify engine directly.
And i never touched Havok so i don’t know what you really need, maybe there way to do this without doing anything invasive. As far as i know Havok do physics, so you can in it in module startup then hook it up to actors via component that would apply the physics of Havok to actor.