From f74a249e242503eb66c63138e6f1e9b509e3ba98 Mon Sep 17 00:00:00 2001 From: Drew Hoener Date: Sun, 15 Oct 2023 01:13:36 -0400 Subject: [PATCH 1/3] Added Oasis Clothes UI Element --- UIInfoSuite2/Infrastructure/LanguageKeys.cs | 2 + UIInfoSuite2/Options/ModOptions.cs | 2 + UIInfoSuite2/Options/ModOptionsPageHandler.cs | 13 +- UIInfoSuite2/UIElements/ShowOasisClothes.cs | 189 ++++++++++++++++++ UIInfoSuite2/i18n/default.json | 5 + 5 files changed, 207 insertions(+), 4 deletions(-) create mode 100644 UIInfoSuite2/UIElements/ShowOasisClothes.cs diff --git a/UIInfoSuite2/Infrastructure/LanguageKeys.cs b/UIInfoSuite2/Infrastructure/LanguageKeys.cs index d6e8f04e..8e421aad 100644 --- a/UIInfoSuite2/Infrastructure/LanguageKeys.cs +++ b/UIInfoSuite2/Infrastructure/LanguageKeys.cs @@ -33,5 +33,7 @@ public static class LanguageKeys public const string CanFindSalmonberry = "CanFindSalmonberry"; public const string CanFindBlackberry = "CanFindBlackberry"; public const string CanFindHazelnut = "CanFindHazelnut"; + public const string SandyClothingItemAll = "SandyClothingItemAll"; + public const string SandyClothingItemRare = "SandyClothingItemRare"; } } diff --git a/UIInfoSuite2/Options/ModOptions.cs b/UIInfoSuite2/Options/ModOptions.cs index a4c3c8bc..6f0f6ce4 100644 --- a/UIInfoSuite2/Options/ModOptions.cs +++ b/UIInfoSuite2/Options/ModOptions.cs @@ -31,6 +31,8 @@ internal record ModOptions public bool ShowSeasonalBerryHazelnut { get; set; } = false; public bool ShowTodaysGifts { get; set; } = true; public bool HideBirthdayIfFullFriendShip { get; set; } = true; + public bool ShowOasisClothes { get; set; } = true; + public bool ShowOasisClothesAll { get; set; } = true; public Dictionary ShowLocationOfFriends { get; set; } = new(); } } diff --git a/UIInfoSuite2/Options/ModOptionsPageHandler.cs b/UIInfoSuite2/Options/ModOptionsPageHandler.cs index d5ea6879..3790220f 100644 --- a/UIInfoSuite2/Options/ModOptionsPageHandler.cs +++ b/UIInfoSuite2/Options/ModOptionsPageHandler.cs @@ -15,7 +15,7 @@ internal class ModOptionsPageHandler : IDisposable { private readonly IModHelper _helper; private readonly bool _showPersonalConfigButton; - + private List _optionsElements = new(); private readonly List _elementsToDispose; @@ -23,7 +23,7 @@ internal class ModOptionsPageHandler : IDisposable private ModOptionsPageButton _modOptionsPageButton; private int _modOptionsTabPageNumber; - private PerScreen _lastMenu = new(); + private PerScreen _lastMenu = new(); private List _instancesWithOptionsPageOpen = new(); private bool _windowResizing = false; @@ -56,6 +56,7 @@ public ModOptionsPageHandler(IModHelper helper, ModOptions options, bool showPer var showRobinBuildingStatusIcon = new ShowRobinBuildingStatusIcon(helper); var showSeasonalBerry = new ShowSeasonalBerry(helper); var showTodaysGift = new ShowTodaysGifts(helper); + var showOasisClothes = new ShowOasisClothes(helper); _elementsToDispose = new List() { @@ -74,7 +75,8 @@ public ModOptionsPageHandler(IModHelper helper, ModOptions options, bool showPer showQueenOfSauceIcon, showToolUpgradeStatus, showRobinBuildingStatusIcon, - showSeasonalBerry + showSeasonalBerry, + showOasisClothes }; int whichOption = 1; @@ -113,6 +115,9 @@ public ModOptionsPageHandler(IModHelper helper, ModOptions options, bool showPer _optionsElements.Add(seasonalBerryIcon); _optionsElements.Add(new ModOptionsCheckbox(_helper.SafeGetString(nameof(options.ShowSeasonalBerryHazelnut)), whichOption++, showSeasonalBerry.ToggleHazelnutOption, () => options.ShowSeasonalBerryHazelnut, v => options.ShowSeasonalBerryHazelnut = v, seasonalBerryIcon)); _optionsElements.Add(new ModOptionsCheckbox(_helper.SafeGetString(nameof(options.ShowTodaysGifts)), whichOption++, showTodaysGift.ToggleOption, () => options.ShowTodaysGifts, v => options.ShowTodaysGifts = v)); + var showOasisClothesIcon = new ModOptionsCheckbox(_helper.SafeGetString(nameof(options.ShowOasisClothes)), whichOption++, showOasisClothes.ToggleOption, () => options.ShowOasisClothes, v => options.ShowOasisClothes = v); + _optionsElements.Add(showOasisClothesIcon); + _optionsElements.Add(new ModOptionsCheckbox(_helper.SafeGetString(nameof(options.ShowOasisClothesAll)), whichOption++, showOasisClothes.ToggleShowAllClothes, () => options.ShowOasisClothesAll, v => options.ShowOasisClothesAll = v, showOasisClothesIcon)); } @@ -160,7 +165,7 @@ private void EarlyOnMenuChanged(IClickableMenu? oldMenu, IClickableMenu? newMenu _modOptionsPage = new ModOptionsPage(_optionsElements, _helper.Events); if (_modOptionsPageButton == null) _modOptionsPageButton = new ModOptionsPageButton(_helper.Events); - + _modOptionsPageButton.OnLeftClicked += OnButtonLeftClicked; List tabPages = newGameMenu.pages; _modOptionsTabPageNumber = tabPages.Count; diff --git a/UIInfoSuite2/UIElements/ShowOasisClothes.cs b/UIInfoSuite2/UIElements/ShowOasisClothes.cs new file mode 100644 index 00000000..aa491574 --- /dev/null +++ b/UIInfoSuite2/UIElements/ShowOasisClothes.cs @@ -0,0 +1,189 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Reflection; +using Microsoft.Xna.Framework; +using StardewModdingAPI; +using StardewModdingAPI.Events; +using StardewModdingAPI.Utilities; +using StardewValley; +using StardewValley.Menus; +using StardewValley.Objects; +using UIInfoSuite2.Infrastructure; +using UIInfoSuite2.Infrastructure.Extensions; + +namespace UIInfoSuite2.UIElements +{ + internal class ShowOasisClothes : IDisposable + { + #region Properties + + private int[] _valuableIds = + { + 20, 23, 24, 41, 42, 44, 46, 47, 50, 55, 57, 61, 77, 81, 83, 85, 88, 91, 109, 110, 111, 119, 120, 121, 122 + }; + + private Clothing? _clothingItem; + + private readonly PerScreen _shouldRenderItem = new(); + private readonly PerScreen _icon = new(); + private readonly IModHelper _helper; + + private bool Enabled { get; set; } + private bool ShowAllClothes { get; set; } + + #endregion + + #region Life cycle + + public ShowOasisClothes(IModHelper helper) + { + _helper = helper; + ToggleOption(true); + } + + public void Dispose() + { + ToggleOption(false); + } + + public void ToggleOption(bool enabled) + { + Enabled = enabled; + + _helper.Events.Display.RenderingHud -= OnRenderingHud; + _helper.Events.Display.RenderedHud -= OnRenderedHud; + _helper.Events.Display.MenuChanged -= OnMenuChanged; + _helper.Events.GameLoop.DayStarted -= OnDayStarted; + _helper.Events.GameLoop.SaveLoaded -= OnSaveLoaded; + + if (enabled) + { + _helper.Events.GameLoop.DayStarted += OnDayStarted; + _helper.Events.Display.RenderingHud += OnRenderingHud; + _helper.Events.Display.RenderedHud += OnRenderedHud; + _helper.Events.Display.MenuChanged += OnMenuChanged; + _helper.Events.GameLoop.SaveLoaded += OnSaveLoaded; + } + + UpdateOasisItem(); + } + + public void ToggleShowAllClothes(bool showAllClothes) + { + ShowAllClothes = showAllClothes; + ToggleOption(Enabled); + } + + #endregion + + #region Event subscriptions + + private void OnDayStarted(object sender, DayStartedEventArgs e) + { + UpdateOasisItem(); + } + + private void OnSaveLoaded(object sender, SaveLoadedEventArgs e) + { + UpdateOasisItem(); + } + + private void OnMenuChanged(object sender, MenuChangedEventArgs e) + { + // Stop rendering if we visit Sandy + if (e.NewMenu is not ShopMenu || Game1.currentLocation.Name != "SandyHouse") return; + _shouldRenderItem.Value = false; + } + + private void OnRenderingHud(object sender, RenderingHudEventArgs e) + { + if (Game1.eventUp || !_shouldRenderItem.Value) return; + + Point iconPosition = IconHandler.Handler.GetNewIconPosition(); + + _icon.Value = new ClickableTextureComponent( + new Rectangle(iconPosition.X, iconPosition.Y, 40, 40), + null, + Rectangle.Empty, + 1); + _icon.Value.draw(Game1.spriteBatch); + + _clothingItem?.drawInMenu( + Game1.spriteBatch, + new Vector2(iconPosition.X - 12, iconPosition.Y - 12), + 1.25f + ); + } + + private void OnRenderedHud(object sender, RenderedHudEventArgs e) + { + if (_clothingItem == null || !_shouldRenderItem.Value || Game1.IsFakedBlackScreen() || + !(_icon.Value?.containsPoint(Game1.getMouseX(), Game1.getMouseY()) ?? false)) return; + var formattedStr = GetHoverString(); + IClickableMenu.drawHoverText(Game1.spriteBatch, formattedStr, Game1.dialogueFont); + } + + #endregion + + #region Logic + + private string GetHoverString() + { + return ShowAllClothes + ? string.Format(_helper.SafeGetString(LanguageKeys.SandyClothingItemAll), _clothingItem?.displayName) + : _helper.SafeGetString(LanguageKeys.SandyClothingItemRare); + } + + private static bool HasVisitedDesert() + { + return Game1.player.eventsSeen.Contains(67); + } + + private void UpdateOasisItem() + { + _clothingItem = GetClothingItem(); + _shouldRenderItem.Value = false; + // Early escape if we don't have an item for some reason + if (_clothingItem == null || !Enabled) return; + + // Check to make sure the store is open, and the desert is accessible + if (!HasVisitedDesert()) + return; + + var isExclusive = _valuableIds.Contains(_clothingItem.ParentSheetIndex - 1000); + if (isExclusive || ShowAllClothes) + { + _shouldRenderItem.Value = true; + } + } + + private static Clothing? GetClothingItem() + { + var oasisStock = GetOasisStock(); + return oasisStock?.Keys.FirstOrDefault(elem => elem is Clothing) as Clothing; + } + + private static Dictionary? GetOasisStock() + { + var oasis = Game1.getLocationFromName("SandyHouse"); + if (oasis == null) + { + return null; + } + + var getShopStockMethod = + typeof(GameLocation).GetMethod("sandyShopStock", BindingFlags.Instance | BindingFlags.NonPublic); + if (getShopStockMethod == null) + { + return null; + } + + var ret = getShopStockMethod.Invoke(oasis, null); + + return ret as Dictionary; + } + + #endregion + } +} diff --git a/UIInfoSuite2/i18n/default.json b/UIInfoSuite2/i18n/default.json index b22db25c..f4965b54 100644 --- a/UIInfoSuite2/i18n/default.json +++ b/UIInfoSuite2/i18n/default.json @@ -40,6 +40,9 @@ "LuckStatus4": "The spirits feel absolutely neutral today", "LuckStatus5": "Luck will not be on your side today", "LuckStatus6": "Maybe you should stay home today...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", //Settings - General "ShowLevelUpAnimation": "Show level up animation", "ShowExperienceBar": "Show experience bar", @@ -69,6 +72,8 @@ "ShowExactValue": "Show exact value", "ShowSeasonalBerry": "Show seasonal forageables", "ShowSeasonalBerryHazelnut": "Show hazelnuts on trees", + "ShowOasisClothes": "Show Oasis's rare clothing items", + "ShowOasisClothesAll": "Show all clothing items", //Others "LevelUp": "Level Up" } From 0472b1f79c8b215a772447f73d5754336ceeabde Mon Sep 17 00:00:00 2001 From: Drew Hoener Date: Wed, 18 Oct 2023 13:18:17 -0400 Subject: [PATCH 2/3] Updated all translation files with placeholders --- UIInfoSuite2/i18n/de.json | 5 +++++ UIInfoSuite2/i18n/es.json | 5 +++++ UIInfoSuite2/i18n/fr.json | 5 +++++ UIInfoSuite2/i18n/hu.json | 5 +++++ UIInfoSuite2/i18n/it.json | 5 +++++ UIInfoSuite2/i18n/ja.json | 5 +++++ UIInfoSuite2/i18n/ko.json | 5 +++++ UIInfoSuite2/i18n/pl.json | 5 +++++ UIInfoSuite2/i18n/pt.json | 5 +++++ UIInfoSuite2/i18n/ru.json | 5 +++++ UIInfoSuite2/i18n/th.json | 5 +++++ UIInfoSuite2/i18n/tr.json | 5 +++++ UIInfoSuite2/i18n/uk.json | 5 +++++ UIInfoSuite2/i18n/zh.json | 5 +++++ 14 files changed, 70 insertions(+) diff --git a/UIInfoSuite2/i18n/de.json b/UIInfoSuite2/i18n/de.json index d0743051..ff5e1c2d 100644 --- a/UIInfoSuite2/i18n/de.json +++ b/UIInfoSuite2/i18n/de.json @@ -39,6 +39,9 @@ "LuckStatus4": "Fortuna's Laune ist heute absolut neutral", "LuckStatus5": "Das Glück ist heute nicht auf deiner Seite", "LuckStatus6": "Vielleicht solltest du heute zu Hause bleiben", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Zeige Aufstiegsanimation", "ShowExperienceBar": "Zeige Erfahrungsleiste", @@ -68,6 +71,8 @@ "ShowExactValue": "Zeige exakten Wert", "ShowSeasonalBerry": "Zeige saisonale Früchte", "ShowSeasonalBerryHazelnut": "Zeige Haselnüsse auf Bäumen", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Level aufgestiegen" } diff --git a/UIInfoSuite2/i18n/es.json b/UIInfoSuite2/i18n/es.json index ef7adcfe..c9d64302 100644 --- a/UIInfoSuite2/i18n/es.json +++ b/UIInfoSuite2/i18n/es.json @@ -39,6 +39,9 @@ "LuckStatus4": "Los espíritus se sienten absolutamente neutrales hoy", "LuckStatus5": "La suerte no estará de tu lado hoy", "LuckStatus6": "Tal vez deberías quedarte en casa hoy...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Mostrar animación de subida de nivel", "ShowExperienceBar": "Mostrar barra de experiencia", @@ -68,6 +71,8 @@ "ShowExactValue": "Mostrar valor exacto", "ShowSeasonalBerry": "Mostrar recolectables de temporada", "ShowSeasonalBerryHazelnut": "Mostrar avellanas en los árboles", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Subida de nivel" } diff --git a/UIInfoSuite2/i18n/fr.json b/UIInfoSuite2/i18n/fr.json index 940f9b4b..1f0cbb12 100644 --- a/UIInfoSuite2/i18n/fr.json +++ b/UIInfoSuite2/i18n/fr.json @@ -39,6 +39,9 @@ "LuckStatus4": "Les esprits sont plutôt neutre aujourd'hui", "LuckStatus5": "La chance n'est pas avec toi aujourd'hui", "LuckStatus6": "Tu ferais mieux de rester à la maison aujourd'hui", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Montrer l'animation de gain de niveau", "ShowExperienceBar": "Montrer la barre d'exp.", @@ -68,6 +71,8 @@ "ShowExactValue": "Montrer la valeur exacte", "ShowSeasonalBerry": "Montrer les cultures de saison", "ShowSeasonalBerryHazelnut": "Montrer les noisettes sur les arbres", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Gain de niveau" } diff --git a/UIInfoSuite2/i18n/hu.json b/UIInfoSuite2/i18n/hu.json index c73ad1a4..7690dae6 100644 --- a/UIInfoSuite2/i18n/hu.json +++ b/UIInfoSuite2/i18n/hu.json @@ -39,6 +39,9 @@ "LuckStatus4": "Ma a szellemek teljesen semlegesnek érzik magukat!", "LuckStatus5": "Ma a szerencse nem a te oldaladon áll!", "LuckStatus6": "Talán ma otthon kellene maradnod!", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Szintlépés animáció megjelenítés", "ShowExperienceBar": "Tapasztalatpont mérő megjelenítés", @@ -68,6 +71,8 @@ "ShowExactValue": "Pontos érték megjelenítés", "ShowSeasonalBerry": "Szezonális takarmánynövény megjelenítés", "ShowSeasonalBerryHazelnut": "Mogyoró megjelenítés a fákon", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Szintlépés" } diff --git a/UIInfoSuite2/i18n/it.json b/UIInfoSuite2/i18n/it.json index 1c2b3b0f..c9074b41 100644 --- a/UIInfoSuite2/i18n/it.json +++ b/UIInfoSuite2/i18n/it.json @@ -39,6 +39,9 @@ "LuckStatus4": "Gli spiriti sono neutrali oggi", "LuckStatus5": "La fortuna non sarà dalla tua parte oggi", "LuckStatus6": "Forse dovresti restare a casa oggi...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Mostra animazione di nuovo livello", "ShowExperienceBar": "Mostra barra dell'esperienza", @@ -68,6 +71,8 @@ "ShowExactValue": "Mostra valore esatto", "ShowSeasonalBerry": "Mostra foraggiabili di stagione", "ShowSeasonalBerryHazelnut": "Mostra Nocciole sugli alberi", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Nuovo livello" } diff --git a/UIInfoSuite2/i18n/ja.json b/UIInfoSuite2/i18n/ja.json index 95462435..1676acf2 100644 --- a/UIInfoSuite2/i18n/ja.json +++ b/UIInfoSuite2/i18n/ja.json @@ -39,6 +39,9 @@ "LuckStatus4": "今日の運勢はどっちつかず", "LuckStatus5": "今日は運が味方してくれそうにない...", "LuckStatus6": "今日は家で安静にしたほうが良いだろう...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "レベルアップアニメーションを表示する", "ShowExperienceBar": "経験値バーを表示する", @@ -68,6 +71,8 @@ "ShowExactValue": "詳細な値を表示する", "ShowSeasonalBerry": "季節の採取を表示する", "ShowSeasonalBerryHazelnut": "ヘーゼルナッツを表示する", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "レベルアップ" } diff --git a/UIInfoSuite2/i18n/ko.json b/UIInfoSuite2/i18n/ko.json index b95637a7..fe614c2f 100644 --- a/UIInfoSuite2/i18n/ko.json +++ b/UIInfoSuite2/i18n/ko.json @@ -39,6 +39,9 @@ "LuckStatus4": "오늘은 정령들의 기분이 완벽히 중립적이다", "LuckStatus5": "오늘은 운이 따라주지 않는 것 같다", "LuckStatus6": "오늘은 집에 있는 편이 좋을 것 같다...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "레벨 업 애니메이션 표시", "ShowExperienceBar": "경험치 바 표시", @@ -68,6 +71,8 @@ "ShowExactValue": "정확한 수치 표시", "ShowSeasonalBerry": "Show seasonal forageables", // TODO "ShowSeasonalBerryHazelnut": "Show hazelnuts on trees", // TODO + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "레벨 업" } diff --git a/UIInfoSuite2/i18n/pl.json b/UIInfoSuite2/i18n/pl.json index 40b814a8..53063445 100644 --- a/UIInfoSuite2/i18n/pl.json +++ b/UIInfoSuite2/i18n/pl.json @@ -39,6 +39,9 @@ "LuckStatus4": "Duchy wydają się dziś zupełnie neutralne", "LuckStatus5": "Szczęście nie będzie dziś po twojej stronie", "LuckStatus6": "Może lepiej zostań dziś w domu...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Pokaż animację awansu", "ShowExperienceBar": "Pokaż pasek doświadczenia", @@ -68,6 +71,8 @@ "ShowExactValue": "Pokaż dokładną wartość", "ShowSeasonalBerry": "Pokaż sezonowe dary lasu do zebrania", "ShowSeasonalBerryHazelnut": "Pokaż ikonę orzechów laskowych", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Awans" } diff --git a/UIInfoSuite2/i18n/pt.json b/UIInfoSuite2/i18n/pt.json index 7c6617db..b6e56cb4 100644 --- a/UIInfoSuite2/i18n/pt.json +++ b/UIInfoSuite2/i18n/pt.json @@ -39,6 +39,9 @@ "LuckStatus4": "Os espíritos estão neutros", "LuckStatus5": "Os espíritos estão meio aborrecidos", "LuckStatus6": "Os espíritos estão muito aborrecidos", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Mostrar animação de Level Up", "ShowExperienceBar": "Mostrar barra de experiência", @@ -68,6 +71,8 @@ "ShowExactValue": "Mostra o valor exato", "ShowSeasonalBerry": "Mostrar coletáveis sazonais", "ShowSeasonalBerryHazelnut": "Mostrar avelãs nas árvores", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Level Up" } diff --git a/UIInfoSuite2/i18n/ru.json b/UIInfoSuite2/i18n/ru.json index 1aee3be8..c981c67e 100644 --- a/UIInfoSuite2/i18n/ru.json +++ b/UIInfoSuite2/i18n/ru.json @@ -39,6 +39,9 @@ "LuckStatus4": "Сегодня духи абсолютно нейтральны", "LuckStatus5": "Удача сегодня не на вашей стороне", "LuckStatus6": "Может быть, вам стоит сегодня остаться дома...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Показывать анимацию уровня", "ShowExperienceBar": "Показывать панель опыта", @@ -68,6 +71,8 @@ "ShowExactValue": "Показывать точное значение", "ShowSeasonalBerry": "Показывать сезонные растения", "ShowSeasonalBerryHazelnut": "Показывать фундук на деревьях", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Уровень повышен" } diff --git a/UIInfoSuite2/i18n/th.json b/UIInfoSuite2/i18n/th.json index 83bed7cf..b0797107 100644 --- a/UIInfoSuite2/i18n/th.json +++ b/UIInfoSuite2/i18n/th.json @@ -39,6 +39,9 @@ "LuckStatus4": "วันนี้เหล่าวิญญาณรู้สึกวางตัวเป็นกลาง", "LuckStatus5": "วันนี้โชคไม่เข้าข้างคุณ", "LuckStatus6": "บางทีวันนี้คุณควรจะอยู่บ้าน...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "แสดงอะนิเมชั่นการเลื่อนขั้น", "ShowExperienceBar": "แสดงแถบค่าประสบการณ์", @@ -68,6 +71,8 @@ "ShowExactValue": "แสดงมูลค่าจริง", "ShowSeasonalBerry": "แสดงของป่าตามฤดูกาล", "ShowSeasonalBerryHazelnut": "แสดง Hazelnuts บนต้นไม้", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "เลื่อนขั้น" } diff --git a/UIInfoSuite2/i18n/tr.json b/UIInfoSuite2/i18n/tr.json index 90edb4a8..595ca4ce 100644 --- a/UIInfoSuite2/i18n/tr.json +++ b/UIInfoSuite2/i18n/tr.json @@ -39,6 +39,9 @@ "LuckStatus4": "Ruhlar bugün tarafsız hissediyor", "LuckStatus5": "Şans bugün yanında değil", "LuckStatus6": "Belki de bugün evde kalmalısın...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Seviye atlama animasyonunu göster", "ShowExperienceBar": "Deneyim çubuğu görünebilsin", @@ -68,6 +71,8 @@ "ShowExactValue": "Tam değeri göster", "ShowSeasonalBerry": "Mevsimsel yemişleri göster", "ShowSeasonalBerryHazelnut": "Ağaçlardaki fındıkları göster", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Seviye atlama" } diff --git a/UIInfoSuite2/i18n/uk.json b/UIInfoSuite2/i18n/uk.json index 9357578f..94a50a20 100644 --- a/UIInfoSuite2/i18n/uk.json +++ b/UIInfoSuite2/i18n/uk.json @@ -39,6 +39,9 @@ "LuckStatus4": "Духи сьогодні абсолютно нейтральні.", "LuckStatus5": "Сьогодні удача не буде на вашому боці.", "LuckStatus6": "Можливо, сьогодні вам слід залишися вдома...", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "Показ. анім. переходу до нового рівня", "ShowExperienceBar": "Показувати шкалу досвіду", @@ -68,6 +71,8 @@ "ShowExactValue": "Показувати точне значення", "ShowSeasonalBerry": "Показувати сезонні лісові ягоди", "ShowSeasonalBerryHazelnut": "Показ., чи є фундук на деревах", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "Новий рівень" } diff --git a/UIInfoSuite2/i18n/zh.json b/UIInfoSuite2/i18n/zh.json index 49e7f772..bbdf8b5c 100644 --- a/UIInfoSuite2/i18n/zh.json +++ b/UIInfoSuite2/i18n/zh.json @@ -39,6 +39,9 @@ "LuckStatus4": "今天精灵们十分冷漠", "LuckStatus5": "今天运气不会站在你这边", "LuckStatus6": "也许你今天应该呆在家里……", + // Display icons - Merchants + "SandyClothingItemRare": "Sandy has rare clothing for sale", // TODO + "SandyClothingItemAll": "Sandy's Clothing Item: {0}", // TODO //Settings - General "ShowLevelUpAnimation": "显示升级动画", "ShowExperienceBar": "显示经验条", @@ -68,6 +71,8 @@ "ShowExactValue": "显示精确的值", "ShowSeasonalBerry": "显示季节采摘物", "ShowSeasonalBerryHazelnut": "显示树上的榛子", + "ShowOasisClothes": "Show Oasis's rare clothing items", // TODO + "ShowOasisClothesAll": "Show all clothing items", // TODO //Others "LevelUp": "升级" } From 0cf569d642dd4527ddd4b3de6d74ccf44796e4d6 Mon Sep 17 00:00:00 2001 From: Annosz Date: Thu, 17 Oct 2024 18:57:20 +0200 Subject: [PATCH 3/3] Event ID is string --- UIInfoSuite2/UIElements/ShowOasisClothes.cs | 344 ++++++++++---------- 1 file changed, 172 insertions(+), 172 deletions(-) diff --git a/UIInfoSuite2/UIElements/ShowOasisClothes.cs b/UIInfoSuite2/UIElements/ShowOasisClothes.cs index aa491574..0ff5c350 100644 --- a/UIInfoSuite2/UIElements/ShowOasisClothes.cs +++ b/UIInfoSuite2/UIElements/ShowOasisClothes.cs @@ -1,189 +1,189 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Reflection; -using Microsoft.Xna.Framework; +using Microsoft.Xna.Framework; using StardewModdingAPI; using StardewModdingAPI.Events; using StardewModdingAPI.Utilities; using StardewValley; using StardewValley.Menus; using StardewValley.Objects; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Reflection; using UIInfoSuite2.Infrastructure; using UIInfoSuite2.Infrastructure.Extensions; namespace UIInfoSuite2.UIElements { - internal class ShowOasisClothes : IDisposable - { - #region Properties + internal class ShowOasisClothes : IDisposable + { + #region Properties - private int[] _valuableIds = - { + private int[] _valuableIds = + { 20, 23, 24, 41, 42, 44, 46, 47, 50, 55, 57, 61, 77, 81, 83, 85, 88, 91, 109, 110, 111, 119, 120, 121, 122 }; - private Clothing? _clothingItem; - - private readonly PerScreen _shouldRenderItem = new(); - private readonly PerScreen _icon = new(); - private readonly IModHelper _helper; - - private bool Enabled { get; set; } - private bool ShowAllClothes { get; set; } - - #endregion - - #region Life cycle - - public ShowOasisClothes(IModHelper helper) - { - _helper = helper; - ToggleOption(true); - } - - public void Dispose() - { - ToggleOption(false); - } - - public void ToggleOption(bool enabled) - { - Enabled = enabled; - - _helper.Events.Display.RenderingHud -= OnRenderingHud; - _helper.Events.Display.RenderedHud -= OnRenderedHud; - _helper.Events.Display.MenuChanged -= OnMenuChanged; - _helper.Events.GameLoop.DayStarted -= OnDayStarted; - _helper.Events.GameLoop.SaveLoaded -= OnSaveLoaded; - - if (enabled) - { - _helper.Events.GameLoop.DayStarted += OnDayStarted; - _helper.Events.Display.RenderingHud += OnRenderingHud; - _helper.Events.Display.RenderedHud += OnRenderedHud; - _helper.Events.Display.MenuChanged += OnMenuChanged; - _helper.Events.GameLoop.SaveLoaded += OnSaveLoaded; - } - - UpdateOasisItem(); - } - - public void ToggleShowAllClothes(bool showAllClothes) - { - ShowAllClothes = showAllClothes; - ToggleOption(Enabled); - } - - #endregion - - #region Event subscriptions - - private void OnDayStarted(object sender, DayStartedEventArgs e) - { - UpdateOasisItem(); - } - - private void OnSaveLoaded(object sender, SaveLoadedEventArgs e) - { - UpdateOasisItem(); - } - - private void OnMenuChanged(object sender, MenuChangedEventArgs e) - { - // Stop rendering if we visit Sandy - if (e.NewMenu is not ShopMenu || Game1.currentLocation.Name != "SandyHouse") return; - _shouldRenderItem.Value = false; - } - - private void OnRenderingHud(object sender, RenderingHudEventArgs e) - { - if (Game1.eventUp || !_shouldRenderItem.Value) return; - - Point iconPosition = IconHandler.Handler.GetNewIconPosition(); - - _icon.Value = new ClickableTextureComponent( - new Rectangle(iconPosition.X, iconPosition.Y, 40, 40), - null, - Rectangle.Empty, - 1); - _icon.Value.draw(Game1.spriteBatch); - - _clothingItem?.drawInMenu( - Game1.spriteBatch, - new Vector2(iconPosition.X - 12, iconPosition.Y - 12), - 1.25f - ); - } - - private void OnRenderedHud(object sender, RenderedHudEventArgs e) - { - if (_clothingItem == null || !_shouldRenderItem.Value || Game1.IsFakedBlackScreen() || - !(_icon.Value?.containsPoint(Game1.getMouseX(), Game1.getMouseY()) ?? false)) return; - var formattedStr = GetHoverString(); - IClickableMenu.drawHoverText(Game1.spriteBatch, formattedStr, Game1.dialogueFont); - } - - #endregion - - #region Logic - - private string GetHoverString() - { - return ShowAllClothes - ? string.Format(_helper.SafeGetString(LanguageKeys.SandyClothingItemAll), _clothingItem?.displayName) - : _helper.SafeGetString(LanguageKeys.SandyClothingItemRare); - } - - private static bool HasVisitedDesert() - { - return Game1.player.eventsSeen.Contains(67); - } - - private void UpdateOasisItem() - { - _clothingItem = GetClothingItem(); - _shouldRenderItem.Value = false; - // Early escape if we don't have an item for some reason - if (_clothingItem == null || !Enabled) return; - - // Check to make sure the store is open, and the desert is accessible - if (!HasVisitedDesert()) - return; - - var isExclusive = _valuableIds.Contains(_clothingItem.ParentSheetIndex - 1000); - if (isExclusive || ShowAllClothes) - { - _shouldRenderItem.Value = true; - } - } - - private static Clothing? GetClothingItem() - { - var oasisStock = GetOasisStock(); - return oasisStock?.Keys.FirstOrDefault(elem => elem is Clothing) as Clothing; - } - - private static Dictionary? GetOasisStock() - { - var oasis = Game1.getLocationFromName("SandyHouse"); - if (oasis == null) - { - return null; - } - - var getShopStockMethod = - typeof(GameLocation).GetMethod("sandyShopStock", BindingFlags.Instance | BindingFlags.NonPublic); - if (getShopStockMethod == null) - { - return null; - } - - var ret = getShopStockMethod.Invoke(oasis, null); - - return ret as Dictionary; - } - - #endregion + private Clothing? _clothingItem; + + private readonly PerScreen _shouldRenderItem = new(); + private readonly PerScreen _icon = new(); + private readonly IModHelper _helper; + + private bool Enabled { get; set; } + private bool ShowAllClothes { get; set; } + + #endregion + + #region Life cycle + + public ShowOasisClothes(IModHelper helper) + { + _helper = helper; + ToggleOption(true); + } + + public void Dispose() + { + ToggleOption(false); + } + + public void ToggleOption(bool enabled) + { + Enabled = enabled; + + _helper.Events.Display.RenderingHud -= OnRenderingHud; + _helper.Events.Display.RenderedHud -= OnRenderedHud; + _helper.Events.Display.MenuChanged -= OnMenuChanged; + _helper.Events.GameLoop.DayStarted -= OnDayStarted; + _helper.Events.GameLoop.SaveLoaded -= OnSaveLoaded; + + if (enabled) + { + _helper.Events.GameLoop.DayStarted += OnDayStarted; + _helper.Events.Display.RenderingHud += OnRenderingHud; + _helper.Events.Display.RenderedHud += OnRenderedHud; + _helper.Events.Display.MenuChanged += OnMenuChanged; + _helper.Events.GameLoop.SaveLoaded += OnSaveLoaded; + } + + UpdateOasisItem(); + } + + public void ToggleShowAllClothes(bool showAllClothes) + { + ShowAllClothes = showAllClothes; + ToggleOption(Enabled); + } + + #endregion + + #region Event subscriptions + + private void OnDayStarted(object sender, DayStartedEventArgs e) + { + UpdateOasisItem(); + } + + private void OnSaveLoaded(object sender, SaveLoadedEventArgs e) + { + UpdateOasisItem(); + } + + private void OnMenuChanged(object sender, MenuChangedEventArgs e) + { + // Stop rendering if we visit Sandy + if (e.NewMenu is not ShopMenu || Game1.currentLocation.Name != "SandyHouse") return; + _shouldRenderItem.Value = false; + } + + private void OnRenderingHud(object sender, RenderingHudEventArgs e) + { + if (Game1.eventUp || !_shouldRenderItem.Value) return; + + Point iconPosition = IconHandler.Handler.GetNewIconPosition(); + + _icon.Value = new ClickableTextureComponent( + new Rectangle(iconPosition.X, iconPosition.Y, 40, 40), + null, + Rectangle.Empty, + 1); + _icon.Value.draw(Game1.spriteBatch); + + _clothingItem?.drawInMenu( + Game1.spriteBatch, + new Vector2(iconPosition.X - 12, iconPosition.Y - 12), + 1.25f + ); } + + private void OnRenderedHud(object sender, RenderedHudEventArgs e) + { + if (_clothingItem == null || !_shouldRenderItem.Value || Game1.IsFakedBlackScreen() || + !(_icon.Value?.containsPoint(Game1.getMouseX(), Game1.getMouseY()) ?? false)) return; + var formattedStr = GetHoverString(); + IClickableMenu.drawHoverText(Game1.spriteBatch, formattedStr, Game1.dialogueFont); + } + + #endregion + + #region Logic + + private string GetHoverString() + { + return ShowAllClothes + ? string.Format(_helper.SafeGetString(LanguageKeys.SandyClothingItemAll), _clothingItem?.displayName) + : _helper.SafeGetString(LanguageKeys.SandyClothingItemRare); + } + + private static bool HasVisitedDesert() + { + return Game1.player.eventsSeen.Contains("67"); + } + + private void UpdateOasisItem() + { + _clothingItem = GetClothingItem(); + _shouldRenderItem.Value = false; + // Early escape if we don't have an item for some reason + if (_clothingItem == null || !Enabled) return; + + // Check to make sure the store is open, and the desert is accessible + if (!HasVisitedDesert()) + return; + + var isExclusive = _valuableIds.Contains(_clothingItem.ParentSheetIndex - 1000); + if (isExclusive || ShowAllClothes) + { + _shouldRenderItem.Value = true; + } + } + + private static Clothing? GetClothingItem() + { + var oasisStock = GetOasisStock(); + return oasisStock?.Keys.FirstOrDefault(elem => elem is Clothing) as Clothing; + } + + private static Dictionary? GetOasisStock() + { + var oasis = Game1.getLocationFromName("SandyHouse"); + if (oasis == null) + { + return null; + } + + var getShopStockMethod = + typeof(GameLocation).GetMethod("sandyShopStock", BindingFlags.Instance | BindingFlags.NonPublic); + if (getShopStockMethod == null) + { + return null; + } + + var ret = getShopStockMethod.Invoke(oasis, null); + + return ret as Dictionary; + } + + #endregion + } }