Exemplo n.º 1
0
        private PlayerDeadBody Player_Die(On.Celeste.Player.orig_Die orig, Player self, Microsoft.Xna.Framework.Vector2 direction, bool evenIfInvincible, bool registerDeathInStats)
        {
            PlayerDeadBody result = orig(self, direction, evenIfInvincible, registerDeathInStats);

            if (result == null)
            {
                return(null);
            }

            if (Settings.RecordDeaths)
            {
                Vector2 newlocation = self.Position;
                newlocation.Y -= 16;
                deaths.Add(newlocation);
            }

            deathspopupdelays.Clear();

            deaths.ForEach((_) =>
            {
                deathspopupdelays.Add(GetRandom.NextFloat(0.25f));
            });

            if (Settings.RecordDeaths)
            {
                deathspopupdelays[deaths.Count - 1] = 0f;
            }

            deathTimer = 0f;

            return(result);
        }
Exemplo n.º 2
0
        private static PlayerDeadBody PlayerDie(On.Celeste.Player.orig_Die orig, Player self, Vector2 direction, bool evenIfInvincible, bool registerDeathInStats)
        {
            Session session = (self.Scene as Level).Session;

            PlayerDeadBody playerDeadBody = orig(self, direction, evenIfInvincible, registerDeathInStats);

            if (playerDeadBody != null)
            {
                Strawberry goldenStrawb = null;
                foreach (Follower follower in self.Leader.Followers)
                {
                    if (follower.Entity is Strawberry && (follower.Entity as Strawberry).Golden && !(follower.Entity as Strawberry).Winged)
                    {
                        goldenStrawb = (follower.Entity as Strawberry);
                    }
                }
                Vector2?specialBoxLevel = (FactoryHelperModule.Instance._Session as FactoryHelperSession).SpecialBoxPosition;
                if (goldenStrawb == null && specialBoxLevel != null)
                {
                    playerDeadBody.DeathAction = delegate
                    {
                        Engine.Scene = new LevelExit(LevelExit.Mode.Restart, session);
                    };
                }
            }
            return(playerDeadBody);
        }
Exemplo n.º 3
0
        new public PlayerDeadBody Die(Vector2 direction, bool evenIfInvincible = false, bool registerDeathInStats = true)
        {
            PlayerDeadBody orig = orig_Die(direction, evenIfInvincible, registerDeathInStats);

            Everest.Events.Player.Die(this);
            return(orig);
        }
Exemplo n.º 4
0
        public PlayerDeadBody OnDie(On.Celeste.Player.orig_Die orig, Player player, Vector2 direction, bool evenIfInvincible, bool registerDeathInStats)
        {
            PlayerDeadBody corpse = orig(player, direction, evenIfInvincible, registerDeathInStats);

            if (GhostRecorder == null || GhostRecorder.Data == null)
            {
                return(corpse);
            }

            // This is hacky, but it works:
            // Check the stack trace for Celeste.Level+* <Pause>*
            // and throw away the data when we're just retrying.
            foreach (StackFrame frame in new StackTrace().GetFrames())
            {
                MethodBase method = frame?.GetMethod();
                if (method == null || method.DeclaringType == null)
                {
                    continue;
                }
                if (!method.DeclaringType.FullName.StartsWith("Celeste.Level+") ||
                    !method.Name.StartsWith("<Pause>"))
                {
                    continue;
                }

                GhostRecorder.Data = null;
                return(corpse);
            }

            GhostRecorder.Data.Dead = true;

            return(corpse);
        }
Exemplo n.º 5
0
 private void PlayerDeadBodyOnEnd(On.Celeste.PlayerDeadBody.orig_End orig, PlayerDeadBody self)
 {
     orig(self);
     if (Enabled)
     {
         Died = true;
     }
 }
        private Celeste.PlayerDeadBody OnPlayerDie(On.Celeste.Player.orig_Die orig, Celeste.Player self, Vector2 direction, bool evenIfInvincible, bool registerDeathInStats)
        {
            PlayerDeadBody result = orig(self, direction, evenIfInvincible, registerDeathInStats);

            if (Settings.Enabled && result != null)
            {
                ApplyRules(self.Scene, "Die");
            }
            return(result);
        }
Exemplo n.º 7
0
        private static PlayerDeadBody OnPlayerDie(On.Celeste.Player.orig_Die orig, Player self, Vector2 direction, bool evenIfInvincible, bool registerDeathInStats)
        {
            PlayerDeadBody result = orig(self, direction, evenIfInvincible, registerDeathInStats);

            if (result != null && self.Scene is Level level && overworldWrapper != null)
            {
                // the player died, so we should close the "in-game overworld" before weird stuff happens.
                Close(level, true, true);
            }
            return(result);
        }
Exemplo n.º 8
0
        private PlayerDeadBody PlayerOnDie(On.Celeste.Player.orig_Die orig, Player self, Vector2 direction,
                                           bool evenIfInvincible, bool registerDeathInStats)
        {
            PlayerDeadBody playerDeadBody = orig(self, direction, evenIfInvincible, registerDeathInStats);

            if (playerDeadBody != null && Enabled)
            {
                causeOfDeath  = GetCauseOfDeath();
                deathPosition = self.Position;
            }

            return(playerDeadBody);
        }
Exemplo n.º 9
0
        private PlayerDeadBody onPlayerDie(On.Celeste.Player.orig_Die orig, Player self, Vector2 direction, bool evenIfInvincible, bool registerDeathInStats)
        {
            if (!Settings.AllStrawberriesAreGoldens)
            {
                return(orig(self, direction, evenIfInvincible, registerDeathInStats));
            }

            // get the first following strawberry before it is detached by the orig method
            Strawberry firstStrawberry = null;

            foreach (Follower follower in self.Leader.Followers)
            {
                if (follower.Entity is Strawberry)
                {
                    firstStrawberry = (follower.Entity as Strawberry);
                    break;
                }
            }

            Level level = self.SceneAs <Level>();

            // call the orig method
            PlayerDeadBody deadBody = orig(self, direction, evenIfInvincible, registerDeathInStats);

            if (deadBody != null && !deadBody.HasGolden && firstStrawberry != null)
            {
                // the player is dead, doesn't have the actual golden but has a strawberry.
                // we have to do magic to make the game believe they had the golden.
                // (actually, we just do what vanilla does, but with a regular berry instead.)
                deadBody.HasGolden   = true;
                deadBody.DeathAction = () => {
                    LevelExit exit = new LevelExit(LevelExit.Mode.GoldenBerryRestart, level.Session)
                    {
                        GoldenStrawberryEntryLevel = firstStrawberry.ID.Level
                    };

                    // if the berry saved the player's inventory on collection, pass it over to the scene.
                    DynData <Strawberry> firstStrawberryData = new DynData <Strawberry>(firstStrawberry);
                    if (firstStrawberryData.Data.ContainsKey("playerInventoryOnCollection"))
                    {
                        new DynData <LevelExit>(exit)["playerInventoryToRestore"] = firstStrawberryData.Get <PlayerInventory>("playerInventoryOnCollection");
                    }

                    Engine.Scene = exit;
                };
            }

            // proceed
            return(deadBody);
        }
 private void AutoLoadStateWhenDeath(On.Celeste.PlayerDeadBody.orig_End orig, PlayerDeadBody self)
 {
     if (SpeedrunToolModule.Settings.Enabled &&
         SpeedrunToolModule.Settings.AutoLoadAfterDeath &&
         IsSaved &&
         !(bool)self.GetFieldValue("finished") &&
         Engine.Scene is Level level
         )
     {
         level.OnEndOfFrame += () => LoadState();
         self.RemoveSelf();
     }
     else
     {
         orig(self);
     }
 }
Exemplo n.º 11
0
        private void onLightingRender(On.Celeste.LightingRenderer.orig_BeforeRender orig, LightingRenderer self, Scene scene)
        {
            float origSpotlightAlpha = 0f;

            Player         player     = scene?.Tracker.GetEntity <Player>();
            PlayerDeadBody deadPlayer = null;

            if (player == null)
            {
                deadPlayer = scene?.Entities?.OfType <PlayerDeadBody>().FirstOrDefault();
            }

            if (Settings.DisableMadelineSpotlight)
            {
                // save the lighting alpha, then replace it.
                if (player != null)
                {
                    origSpotlightAlpha = player.Light.Alpha;
                    player.Light.Alpha = 0f;
                }
                else if (deadPlayer != null)
                {
                    VertexLight light = new DynData <PlayerDeadBody>(deadPlayer).Get <VertexLight>("light");
                    origSpotlightAlpha = light.Alpha;
                    light.Alpha        = 0f;
                }
            }

            orig(self, scene);

            if (Settings.DisableMadelineSpotlight)
            {
                // restore the spotlight
                if (player != null)
                {
                    player.Light.Alpha = origSpotlightAlpha;
                }
                else if (deadPlayer != null)
                {
                    VertexLight light = new DynData <PlayerDeadBody>(deadPlayer).Get <VertexLight>("light");
                    light.Alpha = origSpotlightAlpha;
                }
            }
        }
Exemplo n.º 12
0
        new public PlayerDeadBody Die(Vector2 direction, bool evenIfInvincible = false, bool registerDeathInStats = true)
        {
            Level level = Scene as Level;

            // 2 catches spawn-blade-kill GBJs.
            // 4 catches spawn-OOB-kill GBJs.
            if (framesAlive < 6 && level != null)
            {
                diedInGBJ++;
                if (diedInGBJ != 0 && (diedInGBJ % 2) == 0 && level.Session.Area.GetLevelSet() != "Celeste" && !CoreModule.Settings.DisableAntiSoftlock)
                {
                    level.Pause();
                    return(null);
                }
            }

            PlayerDeadBody orig = orig_Die(direction, evenIfInvincible, registerDeathInStats);

            Everest.Events.Player.Die(this);
            return(orig);
        }
Exemplo n.º 13
0
        // Everest 的 Bug,另外的 Mod Hook 了 PlayerDeadBody.End 方法后 Level.DoScreenWipe Hook 的方法 wipeIn 为 false 时就不触发了
        // 所以改成了 Hook AreaData.DoScreenWipe 方法
        private void QuickLoadWhenDeath(On.Celeste.AreaData.orig_DoScreenWipe orig, AreaData self, Scene scene,
                                        bool wipeIn, Action onComplete)
        {
            if (SpeedrunToolModule.Settings.Enabled && SpeedrunToolModule.Settings.AutoLoadAfterDeath && IsSaved &&
                !wipeIn && scene is Level level &&
                onComplete != null && (onComplete == level.Reload || currentPlayerDeadBody?.HasGolden == true))
            {
                Action complete = onComplete;
                currentPlayerDeadBody = null;
                onComplete            = () => {
                    if (IsSaved)
                    {
                        LoadState();
                    }
                    else
                    {
                        complete();
                    }
                };
            }

            orig(self, scene, wipeIn, onComplete);
        }
Exemplo n.º 14
0
        private static PlayerDeadBody Player_OnDie(On.Celeste.Player.orig_Die orig, Player self, Vector2 direction, bool evenIfInvincible = false, bool registerDeathsInStats = true)
        {
            IEnumerable <Player> players = self.Scene.Tracker.GetEntities <Player>().Cast <Player>();
            int            playerCount   = players.Count();
            int            deadPlayers   = players.Where(p => p.Dead).Count();
            PlayerDeadBody body          = self.Scene.Entities.FindFirst <PlayerDeadBody>();

            // Kill all other players with "fake deaths" if we are the first player to die
            if (deadPlayers == 0)
            {
                if (!SaveData.Instance.Assists.Invincible || evenIfInvincible)
                {
                    foreach (Player player in players)
                    {
                        if (player != self)
                        {
                            foreach (Follower follower in player.Leader.Followers)
                            {
                                self.Leader.Followers.Add(follower);
                            }

                            if (!player.Dead)
                            {
                                player.Scene.Add(new CustomPlayerDeadBody(player, Vector2.Zero, false, true));
                            }

                            player.Scene.Remove(player);
                        }
                    }

                    return(orig(self, direction, evenIfInvincible, registerDeathsInStats));
                }
            }

            return(null);
        }
Exemplo n.º 15
0
        private static PlayerDeadBody onPlayerDie(On.Celeste.Player.orig_Die orig, Player self, Vector2 direction, bool evenIfInvincible, bool registerDeathInStats)
        {
            bool       hasSilver  = false;
            SpeedBerry speedBerry = null;

            // check if the player is actually going to die first.
            if (!self.Dead && (evenIfInvincible || !SaveData.Instance.Assists.Invincible) && self.StateMachine.State != Player.StReflectionFall)
            {
                hasSilver = self.Leader.Followers.Any(follower => follower.Entity is SilverBerry);
                Follower speedBerryFollower = self.Leader.Followers.Find(follower => follower.Entity is SpeedBerry);
                if (speedBerryFollower != null)
                {
                    speedBerry = (SpeedBerry)speedBerryFollower.Entity;
                    // Don't restart the player to the starting room if there's still time left on the speed berry
                    if (!speedBerry.TimeRanOut)
                    {
                        DynData <Strawberry> data = new DynData <Strawberry>(speedBerry);
                        data["Golden"] = false;
                        // set the starting position to the spawn point
                        Level level = self.SceneAs <Level>();
                        data["start"] = level.GetSpawnPoint(new Vector2(level.Bounds.Left, level.Bounds.Top)) + new Vector2(8, -16);
                    }
                }
            }

            PlayerDeadBody body = orig(self, direction, evenIfInvincible, registerDeathInStats);

            if (body != null)
            {
                DynData <PlayerDeadBody> data = new DynData <PlayerDeadBody>(body);
                data["hasSilver"]     = hasSilver;
                data["hasSpeedBerry"] = (speedBerry != null);
                storedSpeedBerry      = speedBerry;
            }
            return(body);
        }
Exemplo n.º 16
0
 private PlayerDeadBody PlayerOnDie(On.Celeste.Player.orig_Die orig, Player self, Vector2 direction,
                                    bool evenIfInvincible, bool registerDeathInStats)
 {
     currentPlayerDeadBody = orig(self, direction, evenIfInvincible, registerDeathInStats);
     return(currentPlayerDeadBody);
 }
Exemplo n.º 17
0
        public override void Update()
        {
            base.Update();
            if (fadeOut)
            {
                tiles.Alpha  = Calc.Approach(tiles.Alpha, 0f, 3f * Engine.DeltaTime);
                cutout.Alpha = tiles.Alpha;
                if (tiles.Alpha <= 0f)
                {
                    tiles.Alpha = 0;
                }
            }
            else if (fadeIn)
            {
                tiles.Alpha  = Calc.Approach(tiles.Alpha, 1f, 3f * Engine.DeltaTime);
                cutout.Alpha = tiles.Alpha;
                if (tiles.Alpha >= 1f)
                {
                    tiles.Alpha = 1;
                }
            }

            if (MasterOfGroup)
            {
                Player player = null;
                foreach (CaveWall entity in Group)
                {
                    player = entity.CollideFirst <Player>();
                    if (player != null)
                    {
                        break;
                    }
                }
                // The wall shouldn't fade out when a player dies in it
                PlayerDeadBody playerDeadBody = null;
                bool           bodyCollided   = false;
                if ((playerDeadBody = SceneAs <Level>().Entities.FindFirst <PlayerDeadBody>()) != null)
                {
                    foreach (CaveWall entity in Group)
                    {
                        bodyCollided = playerDeadBody.Position.X >= entity.Left && playerDeadBody.Position.X <= entity.Right && playerDeadBody.Position.Y >= entity.Top && playerDeadBody.Position.Y <= entity.Bottom;
                        if (bodyCollided)
                        {
                            break;
                        }
                    }
                }

                if ((player != null && player.StateMachine.State != 9) || bodyCollided)
                {
                    fadeOut = true;
                    foreach (CaveWall entity in Group)
                    {
                        entity.fadeOut = true;
                    }
                }
                else if (fadeOut)
                {
                    fadeOut = false;
                    fadeIn  = true;
                    foreach (CaveWall entity in Group)
                    {
                        entity.fadeOut = false;
                        entity.fadeIn  = true;
                    }
                }
            }
        }
Exemplo n.º 18
0
        private void PlayerDeadBody_Render(On.Celeste.PlayerDeadBody.orig_Render orig, PlayerDeadBody self)
        {
            if (Settings.DisplayDeaths)
            {
                Level level = self.Scene as Level;
                int   i     = 0;

                deaths.ForEach((location) =>
                {
                    if (level.IsInBounds(location) && deathTimer >= deathspopupdelays[i])
                    {
                        float alpha = deathTimer - deathspopupdelays[i];

                        if (i == deaths.Count - 1)
                        {
                            alpha *= 2;
                        }
                        if (alpha > 1f)
                        {
                            alpha = 1f;
                        }

                        deathsprite.DrawCentered(location, Color.White, alpha);
                    }

                    i++;
                });
            }

            orig(self);
        }
Exemplo n.º 19
0
 private void PlayerDeadBody_Update(On.Celeste.PlayerDeadBody.orig_Update orig, PlayerDeadBody self)
 {
     deathTimer += Engine.DeltaTime;
     orig(self);
 }
        private void PlayerDeadBodyRenderHook(On.Celeste.PlayerDeadBody.orig_Render orig, PlayerDeadBody self)
        {
            DynData <PlayerDeadBody> deadBody = new DynData <PlayerDeadBody>(self);
            int dashCount = deadBody.Get <Player>("player").Dashes;

            if (UniqueSkinSelected())
            {
                string colorGradePath = skinConfigs[Settings.SelectedSkinMod].GetUniquePath() + "dash";

                while (dashCount > 2 && !GFX.ColorGrades.Has(colorGradePath + dashCount))
                {
                    dashCount--;
                }
                if (GFX.ColorGrades.Has(colorGradePath + dashCount))
                {
                    Effect fxColorGrading = GFX.FxColorGrading;
                    fxColorGrading.CurrentTechnique            = fxColorGrading.Techniques["ColorGradeSingle"];
                    Engine.Graphics.GraphicsDevice.Textures[1] = GFX.ColorGrades[colorGradePath + dashCount].Texture.Texture_Safe;
                    Draw.SpriteBatch.End();
                    Draw.SpriteBatch.Begin(SpriteSortMode.Deferred, BlendState.AlphaBlend, SamplerState.PointWrap, DepthStencilState.None, RasterizerState.CullNone, fxColorGrading, (self.Scene as Level).GameplayRenderer.Camera.Matrix);
                    orig(self);
                    Draw.SpriteBatch.End();
                    Draw.SpriteBatch.Begin(SpriteSortMode.Deferred, BlendState.AlphaBlend, SamplerState.PointWrap, DepthStencilState.None, RasterizerState.CullNone, null, (self.Scene as Level).GameplayRenderer.Camera.Matrix);
                    return;
                }
            }
            orig(self);
        }