CelesteNet icon indicating copy to clipboard operation
CelesteNet copied to clipboard

Fix ghost life cycle edge cases

Open Popax21 opened this issue 2 years ago • 1 comments

This fixes a few edge cases related to ghost life cycles, which can cause ghosts to become invisible, frozen, or not rendered.

Popax21 avatar May 24 '22 18:05 Popax21

There seems to be a conflict between the loop for LastFrames in OnPlayerAdded being moved into scene.OnEndOfFrame += () ... https://github.com/0x0ade/CelesteNet/blob/f80b8f0186eb17e46594388f72d6d477515a1040/CelesteNet.Client/Components/CelesteNetMainComponent.cs#L815 and the fact that newly created Ghosts also do level.OnEndOfFrame += () => ghost.Active = true; with the result that a lot of spawned Ghosts are permanently disabled, presumably after being created inside this aforementioned loop. This is because you can't add to OnEndOfFrame from within itself, because Scene.AfterUpdate sets its OnEndOfFrame = null right after executing it, removing any newly added event handlers.

One fix that seems to work is to keep the new OnEndOfFrame but remove the one in CreateGhost, leaving new Ghosts disabled: https://github.com/0x0ade/CelesteNet/blob/f80b8f0186eb17e46594388f72d6d477515a1040/CelesteNet.Client/Components/CelesteNetMainComponent.cs#L578 and then doing this within CelesteNetMainComponent.Update:

            foreach (Ghost g in Ghosts.Values)
                if (g != null)
                    g.Active = true;

I don't know if this would need a flag on the Ghosts to only activate them once or if doing it unconditionally is fine.

RedFlames avatar Sep 22 '22 17:09 RedFlames