예제 #1
0
        /// <summary>Safely strikes lightning.</summary>
        /// <param name="position">The position to strike lightning</param>
        /// <param name="effects">Whether visual/sound effects should be created</param>
        internal static void StrikeLightningSafelyAt(Vector2 position, bool effects)
        {
            Farm farm = Game1.getFarm();

            Farm.LightningStrikeEvent lightningStrikeEvent;

            if (farm.objects.TryGetValue(position, out StardewValley.Object obj) && obj.bigCraftable.Value && obj.ParentSheetIndex == 9 && obj.heldObject.Value == null)
            {
                obj.heldObject.Value  = new StardewValley.Object(787, 1, false, -1, 0);
                obj.MinutesUntilReady = Utility.CalculateMinutesUntilMorning(Game1.timeOfDay);
                obj.shakeTimer        = 1000;

                lightningStrikeEvent = new Farm.LightningStrikeEvent
                {
                    bigFlash     = true,
                    createBolt   = true,
                    boltPosition = position * 64f + new Vector2(32f, 0.0f)
                };
            }
            else
            {
                lightningStrikeEvent = new Farm.LightningStrikeEvent()
                {
                    smallFlash = true
                };
            }

            if (effects)
            {
                farm.lightningStrikeEvent.Fire(lightningStrikeEvent);
            }
        }
예제 #2
0
        public void LightningStrike(Farmer who, MeleeWeapon weapon, Dictionary <string, string> parameters)
        {
            int minDamage = weapon.minDamage;
            int maxDamage = weapon.maxDamage;

            if (parameters.ContainsKey("damageMult"))
            {
                minDamage = (int)Math.Round(weapon.minDamage * float.Parse(parameters["damageMult"]));
                maxDamage = (int)Math.Round(weapon.maxDamage * float.Parse(parameters["damageMult"]));
            }
            else if (parameters.ContainsKey("minDamage") && parameters.ContainsKey("maxDamage"))
            {
                minDamage = int.Parse(parameters["minDamage"]);
                maxDamage = int.Parse(parameters["maxDamage"]);
            }

            int radius = int.Parse(parameters["radius"]);

            Vector2      playerLocation  = who.position;
            GameLocation currentLocation = who.currentLocation;

            Farm.LightningStrikeEvent lightningEvent = new Farm.LightningStrikeEvent();
            lightningEvent.bigFlash   = true;
            lightningEvent.createBolt = true;

            Vector2 offset = Vector2.Zero;

            if (parameters.ContainsKey("offsetX") && parameters.ContainsKey("offsetY"))
            {
                float x = float.Parse(parameters["offsetX"]);
                float y = float.Parse(parameters["offsetY"]);
                offset = TranslateVector(new Vector2(x, y), who.FacingDirection);
            }
            lightningEvent.boltPosition = playerLocation + new Vector2(32f, 32f) + offset;
            Game1.flashAlpha            = (float)(0.5 + Game1.random.NextDouble());

            if (parameters.ContainsKey("sound"))
            {
                Game1.playSound(parameters["sound"]);
            }

            Utility.drawLightningBolt(lightningEvent.boltPosition, currentLocation);

            currentLocation.damageMonster(new Rectangle((int)Math.Round(playerLocation.X - radius), (int)Math.Round(playerLocation.Y - radius), radius * 2, radius * 2), minDamage, maxDamage, false, who);
        }
예제 #3
0
        private void lightningStrike(Vector2 playerLocation)
        {
            Farm.LightningStrikeEvent lightningEvent = new Farm.LightningStrikeEvent();
            lightningEvent.bigFlash     = true;
            lightningEvent.createBolt   = true;
            lightningEvent.boltPosition = playerLocation + new Vector2(32f, 32f);
            Game1.flashAlpha            = (float)(0.5 + Game1.random.NextDouble());
            Game1.playSound("thunder");
            Utility.drawLightningBolt(lightningEvent.boltPosition, currentLocation);

            List <Farmer> farmers = new List <Farmer>();

            FarmerCollection.Enumerator enumerator = currentLocation.farmers.GetEnumerator();
            while (enumerator.MoveNext())
            {
                if (enumerator.Current.currentLocation == currentLocation && enumerator.Current.GetBoundingBox().Intersects(new Rectangle((int)Math.Round(playerLocation.X - 32), (int)Math.Round(playerLocation.Y - 32), 64, 64)))
                {
                    enumerator.Current.takeDamage((int)Math.Round(20 * difficulty), true, null);
                }
            }
        }
예제 #4
0
        public static void Utility_performLightningUpdate_Transpiler_ModifyStrikeEvent(Farm.LightningStrikeEvent @event)
        {
            switch (Instance.Config.BigLightningBehavior)
            {
            case BigLightningBehavior.Never:
                @event.smallFlash = true;
                @event.bigFlash   = false;
                break;

            case BigLightningBehavior.WhenSupposedToStrike:
                break;

            case BigLightningBehavior.WhenActuallyStrikes:
                if (@event.bigFlash && (Instance.DidPreventLast || Instance.LastTargetType is null))
                {
                    @event.smallFlash = true;
                    @event.bigFlash   = false;
                }
                break;

            case BigLightningBehavior.Always:
                @event.smallFlash = false;
                @event.bigFlash   = true;
                break;
            }
        }
        public void PerformLightningStrike()
        {
            Double diceRoll = ClimatesOfFerngill.Dice.NextDouble();

            if (diceRoll < 0.4 - Game1.player.team.AverageDailyLuck())
            {
                if (ClimatesOfFerngill.WeatherOpt.Verbose)
                {
                    ClimatesOfFerngill.Logger.Log($"Condition 1 with {diceRoll}. There will be a strike attempt.");
                }

                Farm.LightningStrikeEvent lightningStrikeEvent = new Farm.LightningStrikeEvent
                {
                    bigFlash = true
                };
                Farm           locationFromName = Game1.getLocationFromName("Farm") as Farm;
                List <Vector2> source           = new List <Vector2>();
                foreach (KeyValuePair <Vector2, SObject> keyValuePair in locationFromName.objects.Pairs)
                {
                    if (keyValuePair.Value.bigCraftable.Value && keyValuePair.Value.ParentSheetIndex == 9)
                    {
                        source.Add(keyValuePair.Key);
                    }
                }
                if (source.Count > 0)
                {
                    for (int index1 = 0; index1 < 2; ++index1)
                    {
                        Vector2 index2 = source.ElementAt(ClimatesOfFerngill.Dice.Next(source.Count));
                        if (locationFromName.objects[index2].heldObject.Value == null)
                        {
                            locationFromName.objects[index2].heldObject.Value  = new SObject(787, 1, false, -1, 0);
                            locationFromName.objects[index2].MinutesUntilReady = 3000 - Game1.timeOfDay;
                            locationFromName.objects[index2].shakeTimer        = 1000;
                            lightningStrikeEvent.createBolt   = true;
                            lightningStrikeEvent.boltPosition = index2 * 64f + new Vector2(32f, 0.0f);
                            locationFromName.lightningStrikeEvent.Fire(lightningStrikeEvent);
                            return;
                        }
                    }
                }
                //make strikes more likely. Very more likely.
                if (ClimatesOfFerngill.Dice.NextDouble() >= 0.8 - Game1.player.team.AverageDailyLuck())
                {
                    return;
                }

                try
                {
                    KeyValuePair <Vector2, TerrainFeature> keyValuePair = locationFromName.terrainFeatures.Pairs.ElementAt(ClimatesOfFerngill.Dice.Next(locationFromName.terrainFeatures.Count()));
                    if (!(keyValuePair.Value is FruitTree))
                    {
                        int num = !(keyValuePair.Value is HoeDirt) || (keyValuePair.Value as HoeDirt).crop == null ? 0 : (!(bool)(keyValuePair.Value as HoeDirt).crop.dead.Value ? 1 : 0);
                        if (ClimatesOfFerngill.UseSafeLightningApi && !(ClimatesOfFerngill.SafeLightningAPI is null))
                        {
                            ClimatesOfFerngill.SafeLightningAPI.StrikeLightningSafely(keyValuePair.Key);
                        }
                        else if (keyValuePair.Value.performToolAction((Tool)null, 50, keyValuePair.Key, (GameLocation)locationFromName))
                        {
                            lightningStrikeEvent.destroyedTerrainFeature = true;
                            lightningStrikeEvent.createBolt = true;
                            locationFromName.terrainFeatures.Remove(keyValuePair.Key);
                            lightningStrikeEvent.boltPosition = keyValuePair.Key * 64f + new Vector2(32f, (float)sbyte.MinValue);
                        }
                        if (num != 0)
                        {
                            if (keyValuePair.Value is HoeDirt)
                            {
                                if ((keyValuePair.Value as HoeDirt).crop != null)
                                {
                                    if ((bool)((keyValuePair.Value as HoeDirt).crop.dead.Value))
                                    {
                                        lightningStrikeEvent.createBolt   = true;
                                        lightningStrikeEvent.boltPosition = keyValuePair.Key * 64f + new Vector2(32f, 0.0f);
                                    }
                                }
                            }
                        }
                    }
                    else if (keyValuePair.Value is FruitTree)
                    {
                        (keyValuePair.Value as FruitTree).struckByLightningCountdown.Value = 4;
                        (keyValuePair.Value as FruitTree).shake(keyValuePair.Key, true, (GameLocation)locationFromName);
                        lightningStrikeEvent.createBolt   = true;
                        lightningStrikeEvent.boltPosition = keyValuePair.Key * 64f + new Vector2(32f, (float)sbyte.MinValue);
                    }
                }
                catch (Exception)
                {
                }
                locationFromName.lightningStrikeEvent.Fire(lightningStrikeEvent);
            }
            else
            {
                if (ClimatesOfFerngill.Dice.NextDouble() >= 0.1)
                {
                    return;
                }
                (Game1.getLocationFromName("Farm") as Farm).lightningStrikeEvent.Fire(new Farm.LightningStrikeEvent()
                {
                    smallFlash = true
                });
            }
        }
예제 #6
0
        public bool tickUpdate(GameTime time)
        {
            Game1.UpdateGameClock(time);
            _farm.UpdateWhenCurrentLocation(time);
            _farm.updateEvenIfFarmerIsntHere(time);
            Game1.UpdateOther(time);

            if (_terminate)
            {
                return(true);
            }

            _timer += time.ElapsedGameTime.Milliseconds;

            _yOffset = 6f * (float)Math.Sin(Game1.currentGameTime.TotalGameTime.TotalMilliseconds / (Math.PI * 384f));

            // PHASE 1 -- INPUT
            if (_timer > 3333 && _monologue1 && !_monologue1plus)
            {
                if (_awaitingInput && !Game1.dialogueUp)
                {
                    Log.D("Phase 1 end");

                    _awaitingInput  = false;
                    _monologue1     = false;
                    _monologue1plus = true;
                    _timer          = 3333;
                }
                else if (!Game1.dialogueUp)
                {
                    Log.W("Phase 1: Monologue 1");

                    Game1.drawObjectDialogue(i18n.Get("talk.story.plant.mono1"));
                    _awaitingInput = true;
                }
            }

            // PHASE 1 AND A BIT -- INPUT
            if (_timer > 5000 && _monologue1plus && !_afterMonologue1)
            {
                if (_awaitingInput && !Game1.dialogueUp)
                {
                    Log.D("Phase 1 end");

                    _awaitingInput   = false;
                    _monologue1plus  = false;
                    _afterMonologue1 = true;
                    _timer           = 5000;
                }
                else if (!Game1.dialogueUp)
                {
                    Log.W("Phase 1 and a bit: Monologue 1 plus");

                    Game1.drawObjectDialogue(i18n.Get("talk.story.plant.mono1plus"));
                    _awaitingInput = true;
                }
            }

            // PHASE 2 -- TIMER
            // After first monologue, fade out of black, then start panning upward from our start point
            if (_timer > 6250 && _afterMonologue1 && !_awaitingInput)
            {
                Log.W("Phase 2: Wait and pan");

                _isBlack          = false;
                Game1.nonWarpFade = true;
                Game1.fadeClear();
                if (Game1.musicPlayerVolume > 0f)
                {
                    Game1.changeMusicTrack("none");
                    Game1.playSound(ModConsts.ContentPrefix + "dark_despair");
                }

                _timer           = 6250;
                _afterMonologue1 = false;
                _panning         = true;
            }

            // Pan viewport upward to our target
            if (_panning)
            {
                if (_cameraSpeedMult < 0.175f)
                {
                    _cameraSpeedMult += 0.0006f;
                }
                Game1.viewport.Y -= (int)Math.Ceiling(Math.Max(0.01f, time.ElapsedGameTime.Milliseconds * (0.175f - _cameraSpeedMult)));
                if (Game1.viewport.Y <= (_targetLocation.Y + 2) * 64f - Game1.viewport.Height / 2f)
                {
                    Log.D($"Reached target at {_targetLocation.ToString()}");

                    _panning    = false;
                    _monologue2 = true;
                    _timer      = 9001;
                }
            }

            // Fade in the crystal ball
            if (_timer > 8400 && _panning && !_crystalGlareFadeIn && _fire == 0)
            {
                _crystalGlareFadeIn = true;
            }
            else if (_crystalGlareFadeIn && _crystalGlareOpacity >= 1f)
            {
                _crystalGlareFadeIn = false;
            }
            else if (_crystalGlareFadeIn)
            {
                _crystalGlareOpacity += (_crystalGlareOpacity < 0.3f
                                        ? 0.03f
                                        : (_crystalGlareOpacity < 0.6f
                                                ? 0.045f
                                                : 0.06f)) / time.ElapsedGameTime.Milliseconds;
            }

            if (_timer > 9500 && _panning && !_crystalBallFadeIn && _fire == 0)
            {
                _crystalBallFadeIn = true;
            }
            else if (_crystalBallFadeIn && _crystalBallOpacity >= 1f)
            {
                _crystalBallFadeIn = false;
            }
            else if (_crystalBallFadeIn)
            {
                _crystalBallOpacity += (_crystalBallOpacity < 0.3f
                                        ? 0.035f
                                        : (_crystalBallOpacity < 0.6f
                                                ? 0.05f
                                                : 0.065f)) / time.ElapsedGameTime.Milliseconds;
            }

            // PHASE 3 -- INPUT
            // After panning to the target, start the fireworks
            if (_timer > 10500 && !_panning && _monologue2)
            {
                if (_awaitingInput && !Game1.dialogueUp)
                {
                    Log.D("Phase 3 end");

                    _awaitingInput   = false;
                    _monologue2      = false;
                    _afterMonologue2 = true;
                }
                else if (!Game1.dialogueUp)
                {
                    Log.W("Phase 3: Monologue 2");

                    Game1.drawObjectDialogue(i18n.Get("talk.story.plant.mono2"));
                    _timer         = 10500;
                    _awaitingInput = true;
                }
            }

            // PHASE 3 AND A BIT -- TIMER
            if (_timer > 11250 && _afterMonologue2)
            {
                _afterMonologue2 = false;
                _fire            = 1;
            }

            // Fade out the crystal ball
            if (_fire >= 1 && _crystalBallOpacity > 0f)
            {
                _crystalBallOpacity -= (_crystalBallOpacity < 0.3f
                                        ? 0.03f
                                        : (_crystalBallOpacity < 0.6f
                                                ? 0.045f
                                                : 0.06f)) / time.ElapsedGameTime.Milliseconds;
            }

            // PHASE 4 -- TIMER
            // Start the fireworks after dialogue is closed
            if (_crystalBallOpacity < 0.7f && _fire == 1)
            {
                Log.W("Phase 4: Fireworks");
                Log.W("Zap 1");

                _fire     = 2;
                var where = new Vector2(_targetLocation.X - 3, _targetLocation.Y - 1);
                var lightningStrike = new Farm.LightningStrikeEvent
                {
                    createBolt   = true,
                    boltPosition = where * 64f
                };
                _farm.lightningStrikeEvent.Fire(lightningStrike);
                Game1.playSound("thunder");
            }
            if (_crystalBallOpacity < 0.55f && _fire == 2)
            {
                Log.W("Zap 2");

                _fire     = 3;
                var where = new Vector2(_targetLocation.X + 1, _targetLocation.Y + 2);
                var lightningStrike = new Farm.LightningStrikeEvent
                {
                    createBolt   = true,
                    boltPosition = where * 64f
                };
                _farm.lightningStrikeEvent.Fire(lightningStrike);
                Game1.playSound("thunder");
            }
            if (_crystalBallOpacity < 0.15f && _fire == 3)
            {
                Log.W("Zap 3");

                _fire     = 4;
                _timer    = 11250;
                var where = new Vector2(_targetLocation.X + 1, _targetLocation.Y + 2);
                var lightningStrike = new Farm.LightningStrikeEvent
                {
                    createBolt   = true,
                    boltPosition = where * 64f,
                    bigFlash     = true
                };
                _farm.lightningStrikeEvent.Fire(lightningStrike);

                Game1.currentLightSources.Add(new LightSource(
                                                  1,
                                                  _targetLocation,
                                                  1f,
                                                  Color.Black,
                                                  942069));
            }

            // Wait a moment before sticking the banana
            if (!(_crystalBallOpacity > 0) && _fire == 4 && _timer > 11250)
            {
                _fire = 5;
            }

            // PHASE 5 -- TIMER
            // Throw down that banana
            if (!(_crystalBallOpacity > 0f) && _fire == 5)
            {
                Log.W("Phase 5: Plant");

                _fire = 6;

                var assetKey = Helper.Content.GetActualAssetKey(
                    Path.Combine(ModConsts.SpritesPath, $"{ModConsts.ExtraSpritesFile}.png"));
                ModEntry.Multiplayer.broadcastSprites(_farm,
                                                      new TemporaryAnimatedSprite(
                                                          assetKey,
                                                          new Rectangle(
                                                              0,
                                                              48,
                                                              16, 32),
                                                          900f,
                                                          4,
                                                          1,
                                                          _targetLocation * 64f,
                                                          false,
                                                          false)
                {
                    scale         = 4f,
                    pulse         = true,
                    pulseAmount   = 1.5f,
                    pulseTime     = 512f,
                    holdLastFrame = true
                });
            }

            // Fade out the crystal glare
            if (_fire >= 4)
            {
                _crystalGlareOpacity -= (_crystalGlareOpacity < 0.3f
                                        ? 0.04f
                                        : (_crystalGlareOpacity < 0.6f
                                                ? 0.05f
                                                : 0.06f)) / time.ElapsedGameTime.Milliseconds;
            }

            // PHASE 0 -- TIMER
            // Fade to black outro
            if (_timer > 18000 && !Game1.fadeToBlack && _fire == 6)
            {
                if (!Game1.dialogueUp && _awaitingInput)
                {
                    _timer = 22000;
                }

                Log.W("Phase 0: Fade out");

                Game1.globalFadeToBlack(AfterLastFade);
                Game1.changeMusicTrack("none");
                Game1.freezeControls = false;
                _fire          = 7;
                _awaitingInput = true;
            }

            // End the rain
            if (_timer > 25000 && !Game1.dialogueUp && !_terminate && _fire == 7)
            {
                Log.D("End of RainInTheNight");

                // Mark for no repeat views once we've sat through all this
                ModEntry.Instance.SaveData.Story[ModData.Chapter.Plant] = ModData.Progress.Stage1;
                _terminate = true;
            }

            return(false);
        }
        private static void PerformLightningUpdate()
        {
            Random random = new Random((int)Game1.uniqueIDForThisGame + (int)Game1.stats.DaysPlayed + Game1.timeOfDay);

            if (random.NextDouble() < 0.125 + Game1.player.team.AverageDailyLuck((GameLocation)null) + Game1.player.team.AverageLuckLevel((GameLocation)null) / 100.0)
            {
                Farm.LightningStrikeEvent lightningStrikeEvent = new Farm.LightningStrikeEvent();
                lightningStrikeEvent.bigFlash = true;
                Farm           locationFromName = Game1.getLocationFromName("Farm") as Farm;
                List <Vector2> source           = new List <Vector2>();
                foreach (KeyValuePair <Vector2, Object> pair in locationFromName.objects.Pairs)
                {
                    if ((bool)((NetFieldBase <bool, NetBool>)pair.Value.bigCraftable) && pair.Value.ParentSheetIndex == 9)
                    {
                        source.Add(pair.Key);
                    }
                }
                if (source.Count > 0)
                {
                    for (int index1 = 0; index1 < 2; ++index1)
                    {
                        Vector2 index2 = source.ElementAt <Vector2>(random.Next(source.Count));
                        if (locationFromName.objects[index2].heldObject.Value == null)
                        {
                            locationFromName.objects[index2].heldObject.Value        = new Object(787, 1, false, -1, 0);
                            locationFromName.objects[index2].minutesUntilReady.Value = Utility.CalculateMinutesUntilMorning(Game1.timeOfDay);
                            locationFromName.objects[index2].shakeTimer = 1000;
                            lightningStrikeEvent.createBolt             = true;
                            lightningStrikeEvent.boltPosition           = index2 * 64f + new Vector2(32f, 0.0f);
                            locationFromName.lightningStrikeEvent.Fire(lightningStrikeEvent);
                            return;
                        }
                    }
                }
                if (random.NextDouble() < 0.25 - Game1.player.team.AverageDailyLuck((GameLocation)null) - Game1.player.team.AverageLuckLevel((GameLocation)null) / 100.0)
                {
                    try
                    {
                        KeyValuePair <Vector2, TerrainFeature> keyValuePair = locationFromName.terrainFeatures.Pairs.ElementAt(random.Next(locationFromName.terrainFeatures.Count()));
                        if (!(keyValuePair.Value is FruitTree))
                        {
                            int num = !(keyValuePair.Value is HoeDirt) || (keyValuePair.Value as HoeDirt).crop == null ? 0 : (!(bool)((NetFieldBase <bool, NetBool>)(keyValuePair.Value as HoeDirt).crop.dead) ? 1 : 0);
                            if (keyValuePair.Value.performToolAction((Tool)null, 50, keyValuePair.Key, (GameLocation)locationFromName))
                            {
                                //lightningStrikeEvent.destroyedTerrainFeature = true;
                                lightningStrikeEvent.createBolt = true;
                                //locationFromName.terrainFeatures.Remove(keyValuePair.Key);
                                lightningStrikeEvent.boltPosition = keyValuePair.Key * 64f + new Vector2(32f, (float)sbyte.MinValue);
                            }
                            if (num != 0)
                            {
                                if (keyValuePair.Value is HoeDirt)
                                {
                                    if ((keyValuePair.Value as HoeDirt).crop != null)
                                    {
                                        if ((bool)((NetFieldBase <bool, NetBool>)(keyValuePair.Value as HoeDirt).crop.dead))
                                        {
                                            lightningStrikeEvent.createBolt   = true;
                                            lightningStrikeEvent.boltPosition = keyValuePair.Key * 64f + new Vector2(32f, 0.0f);
                                        }
                                    }
                                }
                            }
                        }
                        else if (keyValuePair.Value is FruitTree)
                        {
                            //(keyValuePair.Value as FruitTree).struckByLightningCountdown.Value = 4;
                            //(keyValuePair.Value as FruitTree).shake(keyValuePair.Key, true, (GameLocation)locationFromName);
                            lightningStrikeEvent.createBolt   = true;
                            lightningStrikeEvent.boltPosition = keyValuePair.Key * 64f + new Vector2(32f, (float)sbyte.MinValue);
                        }
                    }
                    catch (Exception ex)
                    {
                    }
                }
                locationFromName.lightningStrikeEvent.Fire(lightningStrikeEvent);
            }
            else
            {
                if (random.NextDouble() >= 0.1)
                {
                    return;
                }
                (Game1.getLocationFromName("Farm") as Farm).lightningStrikeEvent.Fire(new Farm.LightningStrikeEvent()
                {
                    smallFlash = true
                });
            }
        }