So, some investigation found the answer to this pretty quickly, but it seems like a bug to me. Probably “legacy” behaviour.
Overriding IsTickableInEditor() to return false will not work because of this bit of code, I believe:
bool bTickIt = TickableObject->IsTickable() &&
(
(TickType != LEVELTICK_TimeOnly && !bIsPaused) ||
(bIsPaused && TickableObject->IsTickableWhenPaused()) ||
(GIsEditor && !IsPlayInEditor() && TickableObject->IsTickableInEditor())
);
in LevelTick.cpp. As you can see that OR makes it behave strangely.
The solution I came up with:
virtual bool IsTickable() const override { return (!GWorld->HasBegunPlay() && GIsEditor) ? false : true; }
If we’re in the editor, and NOT playing, don’t tick. Otherwise, tick.