diff --git a/.gitignore b/.gitignore index 66a3158..5966056 100644 --- a/.gitignore +++ b/.gitignore @@ -15,6 +15,123 @@ /BepInEx/bin/Debug/net6.0 .HOWTO-sync-MelonLoader-from-origin-main.txt /MelonLoader/bin/ReleaseMulti/net6.0 -BepInEx/Patches/GameObjects/changes.txt -/Assembly-CSharp -/MelonLoader/bin/Debug/net6.0 +MelonLoader/bin/Debug/net6.0/WebSocketDotNet.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.XRModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.WindModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.VRModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.VideoModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.VFXModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.VehiclesModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityWebRequestWWWModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityWebRequestTextureModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityWebRequestModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityWebRequestAudioModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityWebRequestAssetBundleModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityTestProtocolModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityCurlModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityConnectModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityAnalyticsModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UnityAnalyticsCommonModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UmbraModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UIModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UIElementsModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.UI.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.TLSModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.TilemapModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.TextRenderingModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.TextCoreTextEngineModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.TextCoreFontEngineModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.TerrainPhysicsModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.TerrainModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.SubsystemsModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.SubstanceModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.StreamingModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.SpriteShapeModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.SpriteMaskModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.SharedInternalsModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.ScreenCaptureModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.RuntimeInitializeOnLoadManagerInitializerModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.PropertiesModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.ProfilerModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.PhysicsModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.Physics2DModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.PerformanceReportingModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.ParticleSystemModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.LocalizationModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.JSONSerializeModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.InputModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.InputLegacyModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.IMGUIModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.ImageConversionModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.HotReloadModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.GridModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.GIModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.GameCenterModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.DSPGraphModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.DirectorModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.CrashReportingModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.CoreModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.ContentLoadModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.ClothModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.AudioModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.AssetBundleModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.ARModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.AnimationModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.AndroidJNIModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.AIModule.dll +MelonLoader/bin/Debug/net6.0/UnityEngine.AccessibilityModule.dll +MelonLoader/bin/Debug/net6.0/Unity.VisualScripting.Core.dll +MelonLoader/bin/Debug/net6.0/Unity.TextMeshPro.dll +MelonLoader/bin/Debug/net6.0/Unity.RenderPipelines.Universal.Runtime.dll +MelonLoader/bin/Debug/net6.0/Unity.RenderPipelines.Core.Runtime.dll +MelonLoader/bin/Debug/net6.0/Unity.RenderPipeline.Universal.ShaderLibrary.dll +MelonLoader/bin/Debug/net6.0/Unity.Mathematics.dll +MelonLoader/bin/Debug/net6.0/Unity.InternalAPIEngineBridge.001.dll +MelonLoader/bin/Debug/net6.0/Unity.Collections.LowLevel.ILSupport.dll +MelonLoader/bin/Debug/net6.0/Unity.Collections.dll +MelonLoader/bin/Debug/net6.0/Unity.Burst.Unsafe.dll +MelonLoader/bin/Debug/net6.0/Unity.Burst.dll +MelonLoader/bin/Debug/net6.0/Unity.2D.SpriteShape.Runtime.dll +MelonLoader/bin/Debug/net6.0/Unity.2D.Common.Runtime.dll +MelonLoader/bin/Debug/net6.0/Unity.2D.Animation.Runtime.dll +MelonLoader/bin/Debug/net6.0/Tomlet.dll +MelonLoader/bin/Debug/net6.0/PvZ_Fusion_Translator.pdb +MelonLoader/bin/Debug/net6.0/PvZ_Fusion_Translator.dll +MelonLoader/bin/Debug/net6.0/PvZ_Fusion_Translator.deps.json +MelonLoader/bin/Debug/net6.0/MonoMod.Utils.dll +MelonLoader/bin/Debug/net6.0/MonoMod.RuntimeDetour.dll +MelonLoader/bin/Debug/net6.0/MonoMod.ILHelpers.dll +MelonLoader/bin/Debug/net6.0/MonoMod.Backports.dll +MelonLoader/bin/Debug/net6.0/Mono.Cecil.Rocks.dll +MelonLoader/bin/Debug/net6.0/Mono.Cecil.Pdb.dll +MelonLoader/bin/Debug/net6.0/Mono.Cecil.Mdb.dll +MelonLoader/bin/Debug/net6.0/Mono.Cecil.dll +MelonLoader/bin/Debug/net6.0/Microsoft.Extensions.Logging.Abstractions.dll +MelonLoader/bin/Debug/net6.0/Microsoft.Diagnostics.Runtime.dll +MelonLoader/bin/Debug/net6.0/Microsoft.Diagnostics.NETCore.Client.dll +MelonLoader/bin/Debug/net6.0/MelonLoader.xml +MelonLoader/bin/Debug/net6.0/MelonLoader.pdb +MelonLoader/bin/Debug/net6.0/MelonLoader.dll +MelonLoader/bin/Debug/net6.0/Il2CppSystem.Xml.dll +MelonLoader/bin/Debug/net6.0/Il2CppSystem.dll +MelonLoader/bin/Debug/net6.0/Il2CppSystem.Core.dll +MelonLoader/bin/Debug/net6.0/Il2CppSystem.Configuration.dll +MelonLoader/bin/Debug/net6.0/Il2Cppmscorlib.dll +MelonLoader/bin/Debug/net6.0/Il2CppMono.Security.dll +MelonLoader/bin/Debug/net6.0/Il2CppInterop.Runtime.dll +MelonLoader/bin/Debug/net6.0/Il2CppInterop.HarmonySupport.dll +MelonLoader/bin/Debug/net6.0/Il2CppInterop.Generator.dll +MelonLoader/bin/Debug/net6.0/Il2CppInterop.Common.dll +MelonLoader/bin/Debug/net6.0/Il2Cpp__Generated.dll +MelonLoader/bin/Debug/net6.0/bHapticsLib.dll +MelonLoader/bin/Debug/net6.0/AudioImportLib.dll +MelonLoader/bin/Debug/net6.0/AssetsTools.NET.dll +MelonLoader/bin/Debug/net6.0/AssetRipper.Primitives.dll +MelonLoader/bin/Debug/net6.0/Assembly-CSharp.dll +MelonLoader/bin/Debug/net6.0/AsmResolver.PE.File.dll +MelonLoader/bin/Debug/net6.0/AsmResolver.PE.dll +MelonLoader/bin/Debug/net6.0/AsmResolver.DotNet.dll +MelonLoader/bin/Debug/net6.0/AsmResolver.dll +MelonLoader/bin/Debug/net6.0/0Harmony.dll +/MelonLoader/bin diff --git a/MelonLoader/AssetStore/WarningStore.cs b/MelonLoader/AssetStore/WarningStore.cs index 7850a2f..7f753f1 100644 --- a/MelonLoader/AssetStore/WarningStore.cs +++ b/MelonLoader/AssetStore/WarningStore.cs @@ -1,234 +1,234 @@ -using System.Runtime.CompilerServices; -using Il2Cpp; -using Il2CppTMPro; -using MelonLoader; -using UnityEngine; -using UnityEngine.TextCore.Text; -using static MelonLoader.MelonLogger; +//using System.Runtime.CompilerServices; +//using Il2Cpp; +//using Il2CppTMPro; +//using MelonLoader; +//using UnityEngine; +//using UnityEngine.TextCore.Text; +//using static MelonLoader.MelonLogger; -namespace PvZ_Fusion_Translator.AssetStore -{ - public static class WarningStore - { - #if MULTI_LANGUAGE - private static Dictionary warningMessages = new() - { - { "English", ("The only valid source of this translation is from this community:\n" + - "discord.gg/DPAC5ZVJ8T. If you got this anywhere else like \n" + - "Plants Hybrid and superhybrid.online, they stole it.\n" + - "Stray away from other sources as they may contain viruses.\n" + - "Please visit our community for future updates.", - "Okay! Got it.") }, - { "French", ("La seule source valide pour cette traduction provient de cette\n" + - "communauté :discord.gg/DPAC5ZVJ8T. Si vous l'avez obtenue \n" + - "ailleurs, comme Plants Hybrid ou superhybrid.online, ils l'ont volée.\n" + - "Évitez les autres sources, car elles peuvent contenir des virus.\n" + - "Veuillez visiter notre communauté pour les mises à jour futures.", - "D'accord !") }, - { "Italian", ("L'unica fonte valida di questa traduzione è questa community:\n" + - "discord.gg/DPAC5ZVJ8T. Se l'hai ottenuta altrove, come \n" + - "Plants Hybrid e superhybrid.online, l'hanno rubata.\n" + - "Evita altre fonti, potrebbero contenere virus.\n" + - "Visita la nostra community per aggiornamenti futuri.", - "Va bene! Ho capito.") }, - { "German", ("Die einzige gültige Quelle für diese Übersetzung stammt aus\n" + - "dieser Community: discord.gg/DPAC5ZVJ8T. Wenn Sie diese \n" + - "irgendwo anders gefunden haben, z. B. bei Plants Hybrid oder \n" + - "superhybrid.online, dann haben sie sie gestohlen.\n" + - "Meiden Sie andere Quellen, da diese Viren enthalten könnten.\n" + - "Bitte besuchen Sie unsere Community für zukünftige Updates.", - "Okay, verstanden!") }, - { "Spanish", ("La única fuente válida de esta traducción proviene de esta\n" + - "comunidad: discord.gg/DPAC5ZVJ8T. Si la obtuvo en cualquier\n" + - "otro lugar como Plants Hybrid o superhybrid.online, la robaron.\n" + - "Manténgase alejado de otras fuentes, ya que podrían contener virus.\n" + - "Por favor, visite nuestra comunidad para futuras actualizaciones.", - "¡Entendido!") }, - { "Portuguese", ("O lugar original e seguro dessa tradução vem daqui:\n" + - "discord.gg/DPAC5ZVJ8T. Se você baixou ela de qualquer \n" + - "lugar como Plants Hybrid ou superhybrid.online, eles\n" + - "roubaram. Evite baixar deles, pode conter vírus.\n" + - "Por favor, visite nossa comunidade para atualizações futuras.", - "Okay, entendido.") }, - { "Filipino", ("Ang tanging opisyal na source ng pagsasaling ito ay mula\n" + - "lamang dito: discord.gg/DPAC5ZVJ8T. Kung nakuha nmo ito kahit \n" + - "saan pa tulad ng Plants Hybrid at superhybrid.online, ito ay ninakaw. \n" + - "Lumayo sa ibang source dahil posibleng may kasamang virus.\n" + - "Paki-bisita ang aming komunidad para sa mga darating na update." , - "Naiintindihan!") }, - { "Vietnamese", ("Nguồn duy nhất hợp lệ của bản dịch này là từ cộng\n" + - "đồng này: discord.gg/DPAC5ZVJ8T. Nếu bạn nhận \n" + - "được nó ở bất cứ nơi nào khác như Plants Hybrid \n" + - "hoặc superhybrid.online, họ đã ăn cắp nó.\n" + - "Tránh xa các nguồn khác vì chúng có thể chứa \n" + - "virus. Hãy ghé thăm cộng đồng của chúng tôi để \n" + - "cập nhật trong tương lai.", - "Đồng ý!") }, - { "Indonesian", ("Satu-satunya sumber resmi dari terjemahan ini adalah \n" + - "komunitas kami: discord.gg/DPAC5ZVJ8T. Jika Anda \n" + - "mendapatkannya dari sumber lain seperti Plants Hybrid \n" + - "dan superhybrid.online, mereka mencurinya. \n" + - "Jauhi sumber lain karena mungkin ada virus.\n" + - "Silakan kunjungi komunitas kami untuk pembaruan berikutnya.", - "Oke! Mengerti.") }, - { "Russian", ("Единственный проверенный источник этого перевода —\n" + - "сообщество discord.gg/DPAC5ZVJ8T.\n" + - "Или же его замена https://t.me/nekoshkindom\n" + - "Если вы скачали этот мод где-либо ещё, возможно он содержит вирусы.\n" + - "Программист перевода: LancerX0.\n" + - "Переводчик: Nekosha.", "Хорошо!") }, - { "Japanese", ("この翻訳の唯一の有効なソースは、このコミュニティからです:\n" + - "discord.gg/DPAC5ZVJ8T.Plants Hybridやsuperhybrid.online、\n" + - "YoutubeのBlue Flyが作っているもの、他のどこかでこれを入手した場合、\n" + - "彼らはそれを盗んだことになります。ウイルスが含まれている可能性があるので、\n" + - "他のソースからは離れてください。今後のアップデートについては、\n私たちのコミュニティをご覧ください。", - "了解しました!") }, - { "Korean", ("이 번역은 Bloom(discord.gg/DPAC5ZVJ8T)에서만\n" + - "제공됩니다. Bloom 디스코드 이외의 다른서드 파티 사이트, \n" + - "예를 들어 Plants Hybrid 및 superhybrid.online, 또는\n" + - "유튜브 Blue Fly등에서 제공하는 파일은 무단으로 재배포된 것이며,\n" + - "이런 사이트들에는 바이러스가 포함되어 있을 가능성이 높습니다. \n향후 업데이트를 위해 저희 디스코드를 방문해 주세요.", - "확인") }, - { "Javanese" , ("Sumber mung sing sah kanggo terjemahan iki saka komunitas iki:\n" + - "discord.gg/DPAC5ZVJ8T. Yen sampeyan nemokake iki ing papan\n" + - "liya kaya Plants Hybrid lan superhybrid.online, iku dicolong.\n" + - "Aja nyedhaki sumber liya amarga bisa ngandhut virus. Mangga\n" + - "ngunjungi komunitas kita kanggo nganyari ing mangsa ngarep.", - "Oke! Ngertos.") }, - { "Polish" , ("Jedynym wiarygodnym źródłem tego tłumaczenia jest ta społeczność:\n" + - "discord.gg/DPAC5ZVJ8T. Jeśli znalazłeś to gdziekolwiek indziej, np. \n" + - "Plants Hybrid i superhybrid.online, ukradli to.\n" + - "Omijaj inne źródła, ponieważ mogą zawierać wirusy.\n" + - "Odwiedź naszą społeczność, aby uzyskać przyszłe aktualizacje.", - "Okay! Rozumiem.") }, - { "Hungarian" , ("Ennek a fordításnak az egyetlen érvényes forrása ebből a közösségből származik:\n" + - "discord.gg/DPAC5ZVJ8T. Ha ezt valahol máshol szerezted, például \n" + - "Plants Hybrid és superhybrid.online oldalakon, akkor ők lopták.\n" + - "Kerüld a többi forrást, mert vírusokat tartalmazhatnak.\n" + - "Kérjük, látogass el közösségünkbe a jövőbeli frissítésekért.", - "Oké! Értem.") }, - { "Arabic" , ("The only valid source of this translation is from this community:\n" + - "discord.gg/DPAC5ZVJ8T. If you got this anywhere else like \n" + - "Plants Hybrid and superhybrid.online, they stole it.\n" + - "Stray away from other sources as they may contain viruses.\n" + - "Please visit our community for future updates.", - "Okay! Got it.") }, - // { "OTHER" , ("A única fonte válida dessa tradução é desta\ncomunidade: discord.gg/DPAC5ZVJ8T. Se você obteve \nisso em qualquer lugar como Plants Hybrid\ne superhybrid.online,ou Blue Fly do Youtube,\nelses roubaram. Fique longe de sites falsos. Por favor,\nvisite nossa comunidade para futuras atualizações.", "¡Okei! Entendido.") } - // { "OTHER" , ("Ang translation na ito ay galing dito lamang:\ndiscord.gg/DPAC5ZVJ8T. Pag nakuha niyo ito sa iba pa\nkagaya ng Plants Hybrid o superhybrid.online, anumang\nginawagawa ng Blue Fly mula sa Youtube, o anumang\nSub2Unlock links, scam sila. MAG INGAT dahil\nkasi baka may virus 'jan. Join kayo sa discord namin!\nFilipino Translation by ColinPogi" , "Tayo magsi-laro!") } - }; - #else - public static string warningMessage = "La única fuente válida de esta traducción proviene de esta\ncomunidad: discord.gg/DPAC5ZVJ8T. Si la obtuvo en cualquier\notro lugar como Plants Hybrid o superhybrid.online, la robaron.\nManténgase alejado de otras fuentes, ya que podrían contener virus.\nPor favor, visite nuestra comunidad para futuras actualizaciones."; - public static string okayButton = "¡Entendido!"; - #endif +//namespace PvZ_Fusion_Translator.AssetStore +//{ +// public static class WarningStore +// { +// #if MULTI_LANGUAGE +// private static Dictionary warningMessages = new() +// { +// { "English", ("The only valid source of this translation is from this community:\n" + +// "discord.gg/DPAC5ZVJ8T. If you got this anywhere else like \n" + +// "Plants Hybrid and superhybrid.online, they stole it.\n" + +// "Stray away from other sources as they may contain viruses.\n" + +// "Please visit our community for future updates.", +// "Okay! Got it.") }, +// { "French", ("La seule source valide pour cette traduction provient de cette\n" + +// "communauté :discord.gg/DPAC5ZVJ8T. Si vous l'avez obtenue \n" + +// "ailleurs, comme Plants Hybrid ou superhybrid.online, ils l'ont volée.\n" + +// "Évitez les autres sources, car elles peuvent contenir des virus.\n" + +// "Veuillez visiter notre communauté pour les mises à jour futures.", +// "D'accord !") }, +// { "Italian", ("L'unica fonte valida di questa traduzione è questa community:\n" + +// "discord.gg/DPAC5ZVJ8T. Se l'hai ottenuta altrove, come \n" + +// "Plants Hybrid e superhybrid.online, l'hanno rubata.\n" + +// "Evita altre fonti, potrebbero contenere virus.\n" + +// "Visita la nostra community per aggiornamenti futuri.", +// "Va bene! Ho capito.") }, +// { "German", ("Die einzige gültige Quelle für diese Übersetzung stammt aus\n" + +// "dieser Community: discord.gg/DPAC5ZVJ8T. Wenn Sie diese \n" + +// "irgendwo anders gefunden haben, z. B. bei Plants Hybrid oder \n" + +// "superhybrid.online, dann haben sie sie gestohlen.\n" + +// "Meiden Sie andere Quellen, da diese Viren enthalten könnten.\n" + +// "Bitte besuchen Sie unsere Community für zukünftige Updates.", +// "Okay, verstanden!") }, +// { "Spanish", ("La única fuente válida de esta traducción proviene de esta\n" + +// "comunidad: discord.gg/DPAC5ZVJ8T. Si la obtuvo en cualquier\n" + +// "otro lugar como Plants Hybrid o superhybrid.online, la robaron.\n" + +// "Manténgase alejado de otras fuentes, ya que podrían contener virus.\n" + +// "Por favor, visite nuestra comunidad para futuras actualizaciones.", +// "¡Entendido!") }, +// { "Portuguese", ("O lugar original e seguro dessa tradução vem daqui:\n" + +// "discord.gg/DPAC5ZVJ8T. Se você baixou ela de qualquer \n" + +// "lugar como Plants Hybrid ou superhybrid.online, eles\n" + +// "roubaram. Evite baixar deles, pode conter vírus.\n" + +// "Por favor, visite nossa comunidade para atualizações futuras.", +// "Okay, entendido.") }, +// { "Filipino", ("Ang tanging opisyal na source ng pagsasaling ito ay mula\n" + +// "lamang dito: discord.gg/DPAC5ZVJ8T. Kung nakuha nmo ito kahit \n" + +// "saan pa tulad ng Plants Hybrid at superhybrid.online, ito ay ninakaw. \n" + +// "Lumayo sa ibang source dahil posibleng may kasamang virus.\n" + +// "Paki-bisita ang aming komunidad para sa mga darating na update." , +// "Naiintindihan!") }, +// { "Vietnamese", ("Nguồn duy nhất hợp lệ của bản dịch này là từ cộng\n" + +// "đồng này: discord.gg/DPAC5ZVJ8T. Nếu bạn nhận \n" + +// "được nó ở bất cứ nơi nào khác như Plants Hybrid \n" + +// "hoặc superhybrid.online, họ đã ăn cắp nó.\n" + +// "Tránh xa các nguồn khác vì chúng có thể chứa \n" + +// "virus. Hãy ghé thăm cộng đồng của chúng tôi để \n" + +// "cập nhật trong tương lai.", +// "Đồng ý!") }, +// { "Indonesian", ("Satu-satunya sumber resmi dari terjemahan ini adalah \n" + +// "komunitas kami: discord.gg/DPAC5ZVJ8T. Jika Anda \n" + +// "mendapatkannya dari sumber lain seperti Plants Hybrid \n" + +// "dan superhybrid.online, mereka mencurinya. \n" + +// "Jauhi sumber lain karena mungkin ada virus.\n" + +// "Silakan kunjungi komunitas kami untuk pembaruan berikutnya.", +// "Oke! Mengerti.") }, +// { "Russian", ("Единственный проверенный источник этого перевода —\n" + +// "сообщество discord.gg/DPAC5ZVJ8T.\n" + +// "Или же его замена https://t.me/nekoshkindom\n" + +// "Если вы скачали этот мод где-либо ещё, возможно он содержит вирусы.\n" + +// "Программист перевода: LancerX0.\n" + +// "Переводчик: Nekosha.", "Хорошо!") }, +// { "Japanese", ("この翻訳の唯一の有効なソースは、このコミュニティからです:\n" + +// "discord.gg/DPAC5ZVJ8T.Plants Hybridやsuperhybrid.online、\n" + +// "YoutubeのBlue Flyが作っているもの、他のどこかでこれを入手した場合、\n" + +// "彼らはそれを盗んだことになります。ウイルスが含まれている可能性があるので、\n" + +// "他のソースからは離れてください。今後のアップデートについては、\n私たちのコミュニティをご覧ください。", +// "了解しました!") }, +// { "Korean", ("이 번역은 Bloom(discord.gg/DPAC5ZVJ8T)에서만\n" + +// "제공됩니다. Bloom 디스코드 이외의 다른서드 파티 사이트, \n" + +// "예를 들어 Plants Hybrid 및 superhybrid.online, 또는\n" + +// "유튜브 Blue Fly등에서 제공하는 파일은 무단으로 재배포된 것이며,\n" + +// "이런 사이트들에는 바이러스가 포함되어 있을 가능성이 높습니다. \n향후 업데이트를 위해 저희 디스코드를 방문해 주세요.", +// "확인") }, +// { "Javanese" , ("Sumber mung sing sah kanggo terjemahan iki saka komunitas iki:\n" + +// "discord.gg/DPAC5ZVJ8T. Yen sampeyan nemokake iki ing papan\n" + +// "liya kaya Plants Hybrid lan superhybrid.online, iku dicolong.\n" + +// "Aja nyedhaki sumber liya amarga bisa ngandhut virus. Mangga\n" + +// "ngunjungi komunitas kita kanggo nganyari ing mangsa ngarep.", +// "Oke! Ngertos.") }, +// { "Polish" , ("Jedynym wiarygodnym źródłem tego tłumaczenia jest ta społeczność:\n" + +// "discord.gg/DPAC5ZVJ8T. Jeśli znalazłeś to gdziekolwiek indziej, np. \n" + +// "Plants Hybrid i superhybrid.online, ukradli to.\n" + +// "Omijaj inne źródła, ponieważ mogą zawierać wirusy.\n" + +// "Odwiedź naszą społeczność, aby uzyskać przyszłe aktualizacje.", +// "Okay! Rozumiem.") }, +// { "Hungarian" , ("Ennek a fordításnak az egyetlen érvényes forrása ebből a közösségből származik:\n" + +// "discord.gg/DPAC5ZVJ8T. Ha ezt valahol máshol szerezted, például \n" + +// "Plants Hybrid és superhybrid.online oldalakon, akkor ők lopták.\n" + +// "Kerüld a többi forrást, mert vírusokat tartalmazhatnak.\n" + +// "Kérjük, látogass el közösségünkbe a jövőbeli frissítésekért.", +// "Oké! Értem.") }, +// { "Arabic" , ("The only valid source of this translation is from this community:\n" + +// "discord.gg/DPAC5ZVJ8T. If you got this anywhere else like \n" + +// "Plants Hybrid and superhybrid.online, they stole it.\n" + +// "Stray away from other sources as they may contain viruses.\n" + +// "Please visit our community for future updates.", +// "Okay! Got it.") }, +// // { "OTHER" , ("A única fonte válida dessa tradução é desta\ncomunidade: discord.gg/DPAC5ZVJ8T. Se você obteve \nisso em qualquer lugar como Plants Hybrid\ne superhybrid.online,ou Blue Fly do Youtube,\nelses roubaram. Fique longe de sites falsos. Por favor,\nvisite nossa comunidade para futuras atualizações.", "¡Okei! Entendido.") } +// // { "OTHER" , ("Ang translation na ito ay galing dito lamang:\ndiscord.gg/DPAC5ZVJ8T. Pag nakuha niyo ito sa iba pa\nkagaya ng Plants Hybrid o superhybrid.online, anumang\nginawagawa ng Blue Fly mula sa Youtube, o anumang\nSub2Unlock links, scam sila. MAG INGAT dahil\nkasi baka may virus 'jan. Join kayo sa discord namin!\nFilipino Translation by ColinPogi" , "Tayo magsi-laro!") } +// }; +// #else +// public static string warningMessage = "La única fuente válida de esta traducción proviene de esta\ncomunidad: discord.gg/DPAC5ZVJ8T. Si la obtuvo en cualquier\notro lugar como Plants Hybrid o superhybrid.online, la robaron.\nManténgase alejado de otras fuentes, ya que podrían contener virus.\nPor favor, visite nuestra comunidad para futuras actualizaciones."; +// public static string okayButton = "¡Entendido!"; +// #endif - #if MULTI_LANGUAGE - public static (string, string) GetWarningMessage(Utils.LanguageEnum language) - { - if (warningMessages.TryGetValue(language.ToString(), out var message)) - { +// #if MULTI_LANGUAGE +// public static (string, string) GetWarningMessage(Utils.LanguageEnum language) +// { +// if (warningMessages.TryGetValue(language.ToString(), out var message)) +// { - return message; - } - else - { - return warningMessages["English"]; // Default to English if language code is not found - } - } -#endif +// return message; +// } +// else +// { +// return warningMessages["English"]; // Default to English if language code is not found +// } +// } +//#endif - public static void WarningLoad(NoticeMenu noticeMenu) - { - if (noticeMenu == null || noticeMenu.transform == null) - { - MelonLogger.Warning("[WarningStore] NoticeMenu or transform is null - ABORTING"); - return; - } +// public static void WarningLoad(NoticeMenu noticeMenu) +// { +// if (noticeMenu == null || noticeMenu.transform == null) +// { +// MelonLogger.Warning("[WarningStore] NoticeMenu or transform is null - ABORTING"); +// return; +// } -#if MULTI_LANGUAGE - try - { - var (warningMessage, okayButton) = GetWarningMessage(Utils.Language); - TMP_FontAsset fontAsset = FontStore.LoadTMPFont(Utils.Language.ToString()); +//#if MULTI_LANGUAGE +// try +// { +// var (warningMessage, okayButton) = GetWarningMessage(Utils.Language); +// TMP_FontAsset fontAsset = FontStore.LoadTMPFont(Utils.Language.ToString()); - Transform warningTransform = noticeMenu.transform.Find("窗口"); - if (warningTransform == null) - { - MelonLogger.Warning("[WarningStore] '窗口' transform not found - ABORTING"); - return; - } +// Transform warningTransform = noticeMenu.transform.Find("窗口"); +// if (warningTransform == null) +// { +// MelonLogger.Warning("[WarningStore] '窗口' transform not found - ABORTING"); +// return; +// } - Transform warningTextTransform = warningTransform.Find("文字"); - Transform warningTextShadowTransform = warningTransform.Find("文字2"); +// Transform warningTextTransform = warningTransform.Find("文字"); +// Transform warningTextShadowTransform = warningTransform.Find("文字2"); - if (warningTextTransform == null || warningTextShadowTransform == null) - { - MelonLogger.Warning("[WarningStore] Could not find text components (文字/文字2)"); - return; - } +// if (warningTextTransform == null || warningTextShadowTransform == null) +// { +// MelonLogger.Warning("[WarningStore] Could not find text components (文字/文字2)"); +// return; +// } - TextMeshProUGUI warningText = warningTextTransform.GetComponent(); - TextMeshProUGUI shadowText = warningTextShadowTransform.GetComponent(); +// TextMeshProUGUI warningText = warningTextTransform.GetComponent(); +// TextMeshProUGUI shadowText = warningTextShadowTransform.GetComponent(); - if (warningText == null || shadowText == null) - { - MelonLogger.Warning("[WarningStore] TextMeshProUGUI components missing"); - return; - } +// if (warningText == null || shadowText == null) +// { +// MelonLogger.Warning("[WarningStore] TextMeshProUGUI components missing"); +// return; +// } - warningText.text = warningMessage; - shadowText.text = warningMessage; +// warningText.text = warningMessage; +// shadowText.text = warningMessage; - if (fontAsset != null) - { - warningText.font = fontAsset; - shadowText.font = fontAsset; - } - else - { - MelonLogger.Warning("[WarningStore] Font asset is null"); - } +// if (fontAsset != null) +// { +// warningText.font = fontAsset; +// shadowText.font = fontAsset; +// } +// else +// { +// MelonLogger.Warning("[WarningStore] Font asset is null"); +// } - MelonLogger.Msg("Warning message loaded successfully!"); - } - catch (Exception e) - { - MelonLogger.Error($"Critical error in WarningLoad: {e}"); - } -#endif - } -#if MULTI_LANGUAGE - public static bool isWarningMessageLoaded = false; +// MelonLogger.Msg("Warning message loaded successfully!"); +// } +// catch (Exception e) +// { +// MelonLogger.Error($"Critical error in WarningLoad: {e}"); +// } +//#endif +// } +//#if MULTI_LANGUAGE +// public static bool isWarningMessageLoaded = false; - public static void WarningReload(Utils.LanguageEnum language, NoticeMenu noticeMenu) - { - if (noticeMenu == null) - { - MelonLogger.Warning("[WarningStore] NoticeMenu is null in WarningReload"); - return; - } +// public static void WarningReload(Utils.LanguageEnum language, NoticeMenu noticeMenu) +// { +// if (noticeMenu == null) +// { +// MelonLogger.Warning("[WarningStore] NoticeMenu is null in WarningReload"); +// return; +// } - if (Utils.OldLanguage.ToString() == language.ToString() && Utils.OldLanguage.ToString() != "English") - { - return; - } +// if (Utils.OldLanguage.ToString() == language.ToString() && Utils.OldLanguage.ToString() != "English") +// { +// return; +// } - if (!isWarningMessageLoaded) - { - WarningLoad(noticeMenu); - isWarningMessageLoaded = true; - } - } -#else - public static bool isWarningMessageLoaded = false; +// if (!isWarningMessageLoaded) +// { +// WarningLoad(noticeMenu); +// isWarningMessageLoaded = true; +// } +// } +//#else +// public static bool isWarningMessageLoaded = false; - public static void WarningReload() - { - if (!WarningStore.isWarningMessageLoaded) - { - WarningStore.WarningLoad(); - WarningStore.isWarningMessageLoaded = true; - } - } -#endif - } -} \ No newline at end of file +// public static void WarningReload() +// { +// if (!WarningStore.isWarningMessageLoaded) +// { +// WarningStore.WarningLoad(); +// WarningStore.isWarningMessageLoaded = true; +// } +// } +//#endif +// } +//} \ No newline at end of file diff --git a/MelonLoader/Core.cs b/MelonLoader/Core.cs index 05812ca..3b8f9ca 100644 --- a/MelonLoader/Core.cs +++ b/MelonLoader/Core.cs @@ -5,6 +5,7 @@ using MelonLoader.Utils; using PvZ_Fusion_Translator.AssetStore; using PvZ_Fusion_Translator.Patches.Managers; using PvZ_Fusion_Translator.Patches.Modes.Odyssey; +using PvZ_Fusion_Translator.Patches.Modes.Super_Editor; using System.Runtime.CompilerServices; using System.Text.Json; using UnityEngine; @@ -82,10 +83,16 @@ namespace PvZ_Fusion_Translator Utils.OpenTrello(); } - if(TowerManager.Instance != null) + TowerManager_Patch.UpdateText(); + + if (CustomLevelMenu_Patch.requestTimer > 0) { - TowerManager_Patch.UpdateText(); - } + CustomLevelMenu_Patch.requestTimer -= Time.deltaTime; + if(CustomLevelMenu_Patch.requestTimer < 0) + { + CustomLevelMenu_Patch.requestTimer = 0; + } + } } public override void OnGUI() diff --git a/MelonLoader/FileLoader.cs b/MelonLoader/FileLoader.cs index f4ca6b2..7abd116 100644 --- a/MelonLoader/FileLoader.cs +++ b/MelonLoader/FileLoader.cs @@ -116,10 +116,6 @@ namespace PvZ_Fusion_Translator } #if MULTI_LANGUAGE - if (Utils.Language != Utils.LanguageEnum.English) - { - LoadLocalizedTextures(Utils.LanguageEnum.English); - } LoadLocalizedTextures(Utils.Language); LoadLocalizedSprites(Utils.Language); #else diff --git a/MelonLoader/ModFeatures.cs b/MelonLoader/ModFeatures.cs index 0bc356e..413d252 100644 --- a/MelonLoader/ModFeatures.cs +++ b/MelonLoader/ModFeatures.cs @@ -1,5 +1,6 @@ //#if DEBUG using PvZ_Fusion_Translator.AssetStore; +using PvZ_Fusion_Translator.Patches.Modes.Super_Editor; using UnityEngine; namespace PvZ_Fusion_Translator @@ -10,6 +11,7 @@ namespace PvZ_Fusion_Translator { ReloadStrings, ReloadTextures, + SwapLevelData } private class ModFeature @@ -42,6 +44,14 @@ namespace PvZ_Fusion_Translator Core.ShowToast("Textures Reloaded!"); return; } + + if(this.ModType == ModType.SwapLevelData) + { + CustomLevelMenu_Patch.SwapLevelData(); + string toast = (CustomLevelMenu_Patch.useLocal) ? "Using Local Data..." : "Using Online Data..."; + Core.ShowToast(toast); + return; + } } } @@ -49,6 +59,7 @@ namespace PvZ_Fusion_Translator { {ModType.ReloadStrings,new ModFeature("Reload Strings",ModType.ReloadStrings,KeyCode.Home, true)}, {ModType.ReloadTextures,new ModFeature("Reload Textures",ModType.ReloadTextures,KeyCode.End, true)}, + {ModType.SwapLevelData,new ModFeature("Swap Level Data Type",ModType.SwapLevelData,KeyCode.PageUp, true)}, }; diff --git a/MelonLoader/Patches/BaseTextObjects/InGameText_Patch.cs b/MelonLoader/Patches/BaseTextObjects/InGameText_Patch.cs index 6fa5ac4..26b5636 100644 --- a/MelonLoader/Patches/BaseTextObjects/InGameText_Patch.cs +++ b/MelonLoader/Patches/BaseTextObjects/InGameText_Patch.cs @@ -14,68 +14,224 @@ namespace PvZ_Fusion_Translator.Patches.BaseTextObjects [HarmonyPatch(typeof(InGameText))] public static class InGameText_Patch { + public static string currentText = ""; + [HarmonyPatch(nameof(InGameText.ShowText))] [HarmonyPostfix] public static void ShowText(InGameText __instance) { + TranslateInGameText(__instance); + } + + [HarmonyPatch(nameof(InGameText.DebugWarning))] + [HarmonyPostfix] + public static void DebugWarning(InGameText __instance) + { + TranslateInGameText(__instance); + } + + [HarmonyPatch(nameof(InGameText.Update))] + [HarmonyPostfix] + public static void Update(InGameText __instance) + { + TranslateInGameText(__instance); + } + + public static void TranslateInGameText(InGameText __instance) + { + if (__instance.textMesh == null) return; + TMP_FontAsset fontAsset = FontStore.LoadTMPFont(Utils.Language.ToString()); - foreach (TextMeshProUGUI txt in __instance.GetComponentsInChildren()) + currentText = __instance.textMesh.text; + + TextMeshProUGUI txt = __instance.textMesh; + string originalText = txt.text; + string travelMatch = TravelMgr_Patch.MatchTravelBuff(originalText); + int godsGachaCheck = CheckGodsGachaPopup(originalText); + string godsGachaMatch = ""; + string superEditorPlantMatch = CheckSuperEditorPopup(originalText); + + switch(godsGachaCheck) { - string originalText = txt.text; - string travelMatch = TravelMgr_Patch.MatchTravelBuff(originalText); - - if (txt.gameObject.name.Contains("shadow")) - { - continue; - } - - if (travelMatch != "") - { - txt.text = travelMatch; - if (txt.gameObject.name.Contains("main")) - { - originalText = txt.text; - Transform shadowText = txt.transform.parent.Find("Text_shadow"); - if (shadowText != null) - { - shadowText.GetComponent().text = Utils.RemoveColorTags(originalText); - } - } - } - else if((Regex.Match(txt.text, @"(]*>.*?)", RegexOptions.Singleline).Success) && !StringStore.translationString.ContainsKey(txt.text)) - { - txt.text = StringStore.TranslateColorText(txt.text, true); - if (txt.gameObject.name.Contains("main")) - { - originalText = txt.text; - Transform shadowText = txt.transform.parent.Find("Text_shadow"); - if (shadowText != null) - { - shadowText.GetComponent().text = Utils.RemoveColorTags(originalText); - } - } - } - else - { - txt.text = StringStore.TranslateText(txt.text, true); - if (txt.gameObject.name.Contains("main")) - { - originalText = txt.text; - Transform shadowText = txt.transform.parent.Find("Text_shadow"); - if (shadowText != null) - { - shadowText.GetComponent().text = Utils.RemoveColorTags(originalText); - } - } - } - txt.font = fontAsset; + case 1: + case 2: + case 3: + godsGachaMatch = TranslateGodsGachaPopup(originalText, godsGachaCheck); + break; + default: + break; } - if(__instance.TryGetComponent(out TextMeshProUGUI text)) + if(godsGachaMatch != "") { - text.text = StringStore.TranslateText(text.text); + txt.text = godsGachaMatch; + if (txt.gameObject.name.Contains("main")) + { + originalText = txt.text; + Transform shadowText = txt.transform.parent.Find("Text_shadow"); + if (shadowText != null) + { + shadowText.GetComponent().text = Utils.RemoveColorTags(originalText); + } + } } + else if (travelMatch != "") + { + txt.text = travelMatch; + if (txt.gameObject.name.Contains("main")) + { + originalText = txt.text; + Transform shadowText = txt.transform.parent.Find("Text_shadow"); + if (shadowText != null) + { + shadowText.GetComponent().text = Utils.RemoveColorTags(originalText); + } + } + } + else if(superEditorPlantMatch != "") + { + txt.text = superEditorPlantMatch; + } + else if((Regex.Match(txt.text, @"(]*>.*?)", RegexOptions.Singleline).Success) && !StringStore.translationString.ContainsKey(txt.text)) + { + txt.text = StringStore.TranslateColorText(txt.text, true); + if (txt.gameObject.name.Contains("main")) + { + originalText = txt.text; + Transform shadowText = txt.transform.parent.Find("Text_shadow"); + if (shadowText != null) + { + shadowText.GetComponent().text = Utils.RemoveColorTags(originalText); + } + } + } + else + { + txt.text = StringStore.TranslateText(txt.text, true); + if (txt.gameObject.name.Contains("main")) + { + originalText = txt.text; + Transform shadowText = txt.transform.parent.Find("Text_shadow"); + if (shadowText != null) + { + shadowText.GetComponent().text = Utils.RemoveColorTags(originalText); + } + } + } + txt.font = fontAsset; } - } + + public static string namePlantedPattern = "种植了:([^\\s]+)"; + public static string nameUpgradedPattern = "升级成功:([^\\s]+) -> ([^\\s]+)"; + public static string nameAlreadyPlantedPattern = "场上已经有一个([^\\s]+)了"; + + public static Dictionary fallbackFStrs = new Dictionary() + { + {"种植了:([^\\s]+)", "{0} planted!"}, + {"升级成功:([^\\s]+) -> ([^\\s]+)", "{0} successfully upgraded to {1}!"}, + {"场上已经有一个([^\\s]+)了", "{0} already exists on the lawn!"}, + {"已移除路线:([^\\s]+)", "Upgrade Path removed for {0}" }, + { @"([^\s]+)\((\d+)\)", "{0}({1})" } + }; + + public static int CheckGodsGachaPopup(string originalText) + { + int res = 0; + + if (Regex.IsMatch(originalText, namePlantedPattern)) + { + res = 1; + } + else if(Regex.IsMatch(originalText, nameUpgradedPattern)) + { + res = 2; + } + else if(Regex.IsMatch(originalText, nameAlreadyPlantedPattern)) + { + res = 3; + } + + return res; + } + + public static string TranslateGodsGachaPopup(string originalText, int type) + { + string res = originalText; + + switch(type) + { + case 1: + res = TranslatePlantNameParts(originalText, namePlantedPattern); + break; + case 2: + res = TranslatePlantNameParts(originalText, nameUpgradedPattern); + break; + case 3: + res = TranslatePlantNameParts(originalText, nameAlreadyPlantedPattern); + break; + default: + break; + } + + return res; + } + + public static string TranslatePlantNameParts(string originalText, string pattern) + { + string res = ""; + string fStr = ""; + Match match = Regex.Match(originalText, pattern); + if(match.Success) + { + GroupCollection groups = match.Groups; + fStr = StringStore.translationStringRegex.ContainsKey(pattern) ? StringStore.translationStringRegex[pattern] : fallbackFStrs[pattern]; + List dynamicParts = []; + for(int i = 1; i < groups.Count; i++) + { + string group = groups[i].Value; + string plantName = Utils.GetPlantNameFromAlmanac(group); + dynamicParts.Add(plantName); + } + res = string.Format(fStr, [.. dynamicParts]); + } + return res; + } + + public static string CheckSuperEditorPopup(string originalText) + { + string res = ""; + + if(Regex.IsMatch(originalText, "已移除路线:([^\\s]+)")) + { + res = TranslatePlantNameParts(originalText, "已移除路线:([^\\s]+)"); + } + else if(Regex.IsMatch(originalText, "当前全部基础植物:(.*)")) + { + string pattern = "当前全部基础植物:(.*)"; + Match match = Regex.Match(originalText, pattern); + if(match.Success) + { + GroupCollection groups = match.Groups; + string plantNameGroup = groups[1].Value; + string[] plantNames = plantNameGroup.Split(" "); + string plantRes = ""; + string shortPattern = @"([^\s]+)\((\d+)\)"; + foreach (string plantName in plantNames) + { + Match shortMatch = Regex.Match(plantName, shortPattern); + if(shortMatch.Success) + { + string fStr = StringStore.translationStringRegex.ContainsKey(shortPattern) ? StringStore.translationStringRegex[shortPattern] : fallbackFStrs[shortPattern]; + string shortRes = string.Format(fStr, [Utils.GetPlantNameFromAlmanac(shortMatch.Groups[1].Value), shortMatch.Groups[2].Value]); + plantRes += shortRes + " "; + } + } + res = StringStore.TranslateText("当前全部基础植物:" + plantRes); + } + } + + return res; + } + } } \ No newline at end of file diff --git a/MelonLoader/Patches/GameObjects/AlmanacZombieWindow_Patch.cs b/MelonLoader/Patches/GameObjects/AlmanacZombieWindow_Patch.cs index 3f8179e..64ea817 100644 --- a/MelonLoader/Patches/GameObjects/AlmanacZombieWindow_Patch.cs +++ b/MelonLoader/Patches/GameObjects/AlmanacZombieWindow_Patch.cs @@ -53,7 +53,7 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects ZombieDataManager.ZombieData zombieData = zombieDataDic[__instance.currentZombieType]; string spawnInfo = ""; - string spawnInfoFormat = StringStore.translationStringRegex["出怪等级: (\\d+)\n出怪权重: (\\d+)"]; + string spawnInfoFormat = StringStore.translationStringRegex.ContainsKey("出怪等级: (\\d+)\n出怪权重: (\\d+)") ? StringStore.translationStringRegex["出怪等级: (\\d+)\n出怪权重: (\\d+)"] : null; if(spawnInfoFormat != null) { spawnInfo = string.Format(spawnInfoFormat, [zombieData.summonLevel, zombieData.summonWeight]) + "\n\n"; diff --git a/MelonLoader/Patches/GameObjects/BaseMenu_Patch.cs b/MelonLoader/Patches/GameObjects/BaseMenu_Patch.cs index e4e8d50..b38c940 100644 --- a/MelonLoader/Patches/GameObjects/BaseMenu_Patch.cs +++ b/MelonLoader/Patches/GameObjects/BaseMenu_Patch.cs @@ -11,9 +11,29 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects public static class BaseMenu_Patch { [HarmonyPatch(nameof(BaseMenu.Awake))] - [HarmonyPostfix] - private static void Awake(BaseMenu __instance) + [HarmonyPrefix] + private static void Pre_Awake(BaseMenu __instance) { + if(__instance.name.Contains("NoticePauseMenu")) + { + NoticePauseMenu_Patch.Pre_Awake(__instance); + } + } + + [HarmonyPatch(nameof(BaseMenu.Awake))] + [HarmonyPostfix] + private static void Post_Awake(BaseMenu __instance) + { + if(__instance.name.Contains("NoticePauseMenu")) + { + NoticePauseMenu_Patch.Post_Awake(__instance); + } + + if(__instance.name.StartsWith("MainMenu(Clone)")) + { + MainMenu_Patch.AnimOver(__instance); + } + TranslateBaseMenu(__instance, "Level"); TranslateBaseMenu(__instance, "Levels"); TranslateBaseMenu(__instance, "CustomLevel"); diff --git a/MelonLoader/Patches/GameObjects/ButtonObjects/GodShootingLevelButton_Patch.cs b/MelonLoader/Patches/GameObjects/ButtonObjects/GodShootingLevelButton_Patch.cs new file mode 100644 index 0000000..6964c15 --- /dev/null +++ b/MelonLoader/Patches/GameObjects/ButtonObjects/GodShootingLevelButton_Patch.cs @@ -0,0 +1,27 @@ +using HarmonyLib; +using Il2Cpp; +using Il2CppTMPro; +using MelonLoader; +using PvZ_Fusion_Translator.AssetStore; +using UnityEngine; + +namespace PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects +{ + [HarmonyPatch(typeof(GodShootingLevelButton))] + public static class GodShootingLevelButton_Patch + { + [HarmonyPatch(nameof(GodShootingLevelButton.Awake))] + [HarmonyPostfix] + private static void Awake(GodShootingLevelButton __instance) + { + TMP_FontAsset fontAsset = FontStore.LoadTMPFont(Utils.Language.ToString()); + + foreach(TextMeshProUGUI txt in __instance.GetComponentsInChildren()) + { + string originalKey = StringStore.translationString.FirstOrDefault(x => x.Value == txt.text).Key; + txt.text = (StringStore.translationString.ContainsKey(originalKey + "_GS")) ? StringStore.TranslateText(originalKey + "_GS") : StringStore.TranslateText(txt.text); + txt.font = fontAsset; + } + } + } +} diff --git a/MelonLoader/Patches/GameObjects/ButtonObjects/OptLanguageBtn_Patch.cs b/MelonLoader/Patches/GameObjects/ButtonObjects/OptLanguageBtn_Patch.cs index 5fffd82..ab8dcd7 100644 --- a/MelonLoader/Patches/GameObjects/ButtonObjects/OptLanguageBtn_Patch.cs +++ b/MelonLoader/Patches/GameObjects/ButtonObjects/OptLanguageBtn_Patch.cs @@ -7,6 +7,7 @@ using PvZ_Fusion_Translator; using PvZ_Fusion_Translator.AssetStore; using UnityEngine; using UnityEngine.UIElements; +using static MelonLoader.MelonLogger; using Object = UnityEngine.Object; public class OptionButtonData @@ -58,6 +59,11 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects for (int i = 0; i < 6; i++) { var newButton = Object.Instantiate(templateButton, templateButton.transform.parent); + newButton.tag = "LangOpt"; + foreach(Transform child in newButton.GetComponentsInChildren()) + { + child.tag = "LangOpt"; + } newButton.optionType = 80 + i; float yPos = startY - i * ySpacing; @@ -90,6 +96,11 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects for (int i = 0; i < 2; i++) { var newButton = Object.Instantiate(templateButton, templateButton.transform.parent); + newButton.tag = "LangOpt"; + foreach(Transform child in newButton.GetComponentsInChildren()) + { + child.tag = "LangOpt"; + } newButton.optionType = 100 + i; float yPos = toggleStartY - i * ySpacing; @@ -125,7 +136,8 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects data.Language = lang; data.IsNextButton = false; btn.gameObject.SetActive(true); - UpdateButtonText(btn, lang.ToString()); + + UpdateButtonText(btn, Utils.LanguageNames[lang], FontStore.LoadTMPFont(lang.ToString())); } else { @@ -148,7 +160,7 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects data.Toggle = toggle; data.IsNextButton = false; btn.gameObject.SetActive(true); - UpdateButtonText(btn, toggle.ToString()); + UpdateButtonText(btn, StringStore.TranslateText(toggle.ToString()), FontStore.LoadTMPFont(Utils.Language.ToString())); } else { @@ -168,7 +180,7 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects UpdateButtonText(nextBtn, "Next"); } - public static void UpdateButtonText(OptionBtn button, string languageName) + public static void UpdateButtonText(OptionBtn button, string languageName, TMP_FontAsset fontAsset = null) { TMP_FontAsset defaultAsset = FontStore.LoadTMPFont("English"); @@ -192,7 +204,7 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects text.text = languageName; } text.fontSize = 16; - text.font = defaultAsset; + text.font = (fontAsset != null) ? fontAsset : defaultAsset; text.autoSizeTextContainer = false; } } @@ -257,17 +269,15 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects [HarmonyPatch(typeof(OptionBtn))] public static class OptLangBtn_Patch { - [HarmonyPatch(nameof(OptionBtn.Awake))] - [HarmonyPostfix] - private static void Awake(OptionBtn __instance) + public static void Awake(OptionBtn __instance) { if (!buttonsCreated || cachedTemplateButton == null) { buttonsCreated = false; togglesCreated = false; - CreateLanguageButtons(__instance); + CreateLanguageButtons(__instance); CreateToggleButtons(__instance); - } + } } [HarmonyPatch("OnMouseUpAsButton")] diff --git a/MelonLoader/Patches/GameObjects/ConfirmMenu_Patch.cs b/MelonLoader/Patches/GameObjects/ConfirmMenu_Patch.cs new file mode 100644 index 0000000..6dc92b7 --- /dev/null +++ b/MelonLoader/Patches/GameObjects/ConfirmMenu_Patch.cs @@ -0,0 +1,24 @@ +using HarmonyLib; +using Il2Cpp; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; +using UnityEngine; +using System.Text.RegularExpressions; + +namespace PvZ_Fusion_Translator.Patches.GameObjects +{ + [HarmonyPatch(typeof(ConfirmMenu))] + public static class ConfirmMenu_Patch + { + [HarmonyPatch(nameof(ConfirmMenu.SetTitle))] + [HarmonyPostfix] + private static void SetTitle(ConfirmMenu __instance) + { + foreach(TextMeshProUGUI title in __instance.title) + { + title.text = StringStore.TranslateText(title.text); + title.font = FontStore.LoadTMPFont(Utils.Language.ToString()); + } + } + } +} diff --git a/MelonLoader/Patches/GameObjects/GodShootingMenu_Patch.cs b/MelonLoader/Patches/GameObjects/GodShootingMenu_Patch.cs new file mode 100644 index 0000000..4932b4b --- /dev/null +++ b/MelonLoader/Patches/GameObjects/GodShootingMenu_Patch.cs @@ -0,0 +1,44 @@ +using HarmonyLib; +using Il2Cpp; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; +using UnityEngine; +using static MelonLoader.MelonLogger; + +namespace PvZ_Fusion_Translator.Patches.GameObjects +{ + [HarmonyPatch(typeof(GodShootingMenu))] + public static class GodShootingMenu_Patch + { + [HarmonyPatch(nameof(GodShootingMenu.Start))] + [HarmonyPostfix] + private static void Start(GodShootingMenu __instance) + { + foreach(TextMeshProUGUI text in __instance.transform.Find("Background").GetComponentsInChildren()) + { + text.autoSizeTextContainer = true; + text.text = StringStore.TranslateText(text.text); + } + + foreach(TextMeshProUGUI text in __instance.GetComponentsInChildren()) + { + text.text = StringStore.TranslateText(text.text); + } + } + + [HarmonyPatch(nameof(GodShootingMenu.ShowRoutes))] + [HarmonyPostfix] + private static void ShowRoutes(GodShootingMenu __instance) + { + foreach(var route in __instance.routes) + { + if (route.Value == null) continue; + + foreach(TextMeshProUGUI text in route.Value.GetComponentsInChildren()) + { + text.text = StringStore.TranslateText(text.text); + } + } + } + } +} diff --git a/MelonLoader/Patches/GameObjects/LoseMenu_Patch.cs b/MelonLoader/Patches/GameObjects/LoseMenu_Patch.cs new file mode 100644 index 0000000..2ba8b25 --- /dev/null +++ b/MelonLoader/Patches/GameObjects/LoseMenu_Patch.cs @@ -0,0 +1,26 @@ +using HarmonyLib; +using Il2Cpp; +using Il2CppTMPro; +using MelonLoader; +using PvZ_Fusion_Translator.AssetStore; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using UnityEngine; + +namespace PvZ_Fusion_Translator.Patches.GameObjects +{ + [HarmonyPatch(typeof(LoseMenu))] + public static class LoseMenu_Patch + { + public static void TranslateLoseMenu(BaseMenu __instance) + { + if(__instance.TryGetComponent(out LoseMenu loseMenu)) + { + loseMenu.title.text = StringStore.TranslateText(loseMenu.title.text); + } + } + } +} diff --git a/MelonLoader/Patches/GameObjects/MainMenu_Patch.cs b/MelonLoader/Patches/GameObjects/MainMenu_Patch.cs index 8c74b89..ee63097 100644 --- a/MelonLoader/Patches/GameObjects/MainMenu_Patch.cs +++ b/MelonLoader/Patches/GameObjects/MainMenu_Patch.cs @@ -1,24 +1,106 @@ using HarmonyLib; using Il2Cpp; +using Il2CppTMPro; using PvZ_Fusion_Translator.AssetStore; +using PvZ_Fusion_Translator.Patches.GameObjects.ButtonObjects; +using Unity.VisualScripting; using UnityEngine; +using UnityEngine.Events; +using UnityEngine.Rendering; +using UnityEngine.UIElements; namespace PvZ_Fusion_Translator.Patches.GameObjects { - [HarmonyPatch(typeof(MainMenu))] public class MainMenu_Patch { - private static bool _warningShown = false; - - [HarmonyPostfix] - [HarmonyPatch(nameof(MainMenu.AnimOver))] - private static void AnimOver(MainMenu __instance) + public static void AnimOver(BaseMenu __instance) { - if (_warningShown || NoticeMenu.Instance == null) - return; + Transform changelogObj = __instance.transform.Find("Grave/UpdateInfo"); + Transform langObj = UnityEngine.Object.Instantiate(changelogObj, changelogObj.position + new Vector3(0.0f, 0.855f), changelogObj.rotation, __instance.transform.Find("Grave")); + langObj.name = "Languages"; + UIButton langBtn = langObj.GetComponent(); - WarningStore.WarningReload(Utils.Language, NoticeMenu.Instance); - _warningShown = true; + foreach(TextMeshProUGUI text in langObj.GetComponentsInChildren()) + { + text.text = StringStore.TranslateText("Languages"); + } + + langBtn.clickEvent = new UnityEvent(); + langBtn.clickEvent.AddListener(new Action(() => OpenLanguageMenu(langBtn.gameObject))); + langBtn.clickEvent.AddListener(new Action(() => HideLangButton(langBtn.gameObject))); + } + + public static void OpenLanguageMenu(GameObject langBtn) + { + UIMgr.EnterOptionMenu(); + GameObject newOptionsMenu = GameAPP.canvasUp.Find("OptionMenu(Clone)").gameObject; + newOptionsMenu.name = "LanguageMenu"; + + List toKeep = new List() { "Background", "F", "Goback"}; + foreach(Transform child in newOptionsMenu.GetComponentsInChildren()) + { + if(!toKeep.Contains(child.name) && !toKeep.Contains(child.parent.name) && child.name != "LanguageMenu") + { + child.gameObject.SetActive(false); + } + } + + OptionBtn templateButton = newOptionsMenu.transform.Find("F").GetComponent(); + OptLanguageBtn_Patch.OptLangBtn_Patch.Awake(templateButton); + + UIButton goBackButton = newOptionsMenu.transform.Find("Goback").GetComponent(); + goBackButton.clickEvent.AddListener(new Action(() => ShowLangButton(langBtn.gameObject))); + + newOptionsMenu.transform.Find("F").gameObject.SetActive(false); + + foreach (TextMeshProUGUI text in newOptionsMenu.transform.Find("Background").GetComponentsInChildren()) + { + text.text = StringStore.TranslateText("Language Settings"); + } + + /*GameObject optionMenuAnchor = UnityEngine.Object.Instantiate(assetBundle.LoadAsset("OptionMenu").TryCast(), GameAPP.canvasUp); + optionMenuAnchor.transform.SetParent(newOptionsMenu.transform, false); + Transform messageAnchor = optionMenuAnchor.transform.Find("MessageAnchor"); + Transform plantAnchor = optionMenuAnchor.transform.Find("PlantAnchor"); + + System.Random random = new System.Random(); + var plantTypes = Enum.GetValues(typeof(PlantType)); + PlantType randomPlantChoice = (PlantType)plantTypes.GetValue(random.Next(plantTypes.Length)); + + if(!GameAPP.resourcesManager.plantPrefabs.ContainsKey(randomPlantChoice) || GameAPP.resourcesManager.plantPrefabs[randomPlantChoice] == null) + { + randomPlantChoice = (PlantType)plantTypes.GetValue(random.Next(plantTypes.Length)); + } + + if (GameAPP.resourcesManager.plantPrefabs[randomPlantChoice] != null) + { + GameObject plant = CreatePlant.SetPlantInAlmamac(plantAnchor.position, (int)randomPlantChoice); + plant.transform.SetParent(newOptionsMenu.transform); + SortingGroup sortingGroup = plant.AddComponent(); + sortingGroup.sortingLayerName = "UI"; + sortingGroup.sortingOrder = 20001; + //plant.transform.position = new Vector3(-7.21f, -3.66f); + UnityEngine.Object.Destroy(plant.GetComponent()); + }*/ + + /*GameObject messageObj = new GameObject(); + messageObj.name = "MultilangMessage"; + messageObj.transform.SetParent(newOptionsMenu.transform); + TextMeshProUGUI messageText = messageObj.AddComponent(); + messageObj.transform.localScale = Vector3.one; + messageText.autoSizeTextContainer = false; + messageText.font = FontStore.LoadTMPFont(Utils.LanguageEnum.English.ToString()); + messageText.text = "Hello this is multilanguage choose language over there ------>";*/ + } + + public static void HideLangButton(GameObject btn) + { + btn.GetComponent().enabled = false; + } + + public static void ShowLangButton(GameObject btn) + { + btn.GetComponent().enabled = true; } } } \ No newline at end of file diff --git a/MelonLoader/Patches/GameObjects/NoticePauseMenu_Patch.cs b/MelonLoader/Patches/GameObjects/NoticePauseMenu_Patch.cs index b434320..f8b196b 100644 --- a/MelonLoader/Patches/GameObjects/NoticePauseMenu_Patch.cs +++ b/MelonLoader/Patches/GameObjects/NoticePauseMenu_Patch.cs @@ -7,12 +7,9 @@ using UnityEngine.UI; namespace PvZ_Fusion_Translator.Patches.GameObjects { - [HarmonyPatch(typeof(NoticeMenu))] public class NoticePauseMenu_Patch { - [HarmonyPrefix] - [HarmonyPatch(nameof(NoticeMenu.Awake))] - private static void Pre_Awake(NoticeMenu __instance) + public static void Pre_Awake(BaseMenu __instance) { GameObject contentObject = __instance.transform.FindChild("Scroll View/Viewport/Content").gameObject; @@ -27,10 +24,8 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects File.WriteAllText(changelogDir, contentText.text); } } - - [HarmonyPostfix] - [HarmonyPatch(nameof(NoticeMenu.Awake))] - private static void Post_Awake(NoticeMenu __instance) + + public static void Post_Awake(BaseMenu __instance) { TMP_FontAsset fontAsset = FontStore.LoadTMPFont(Utils.Language.ToString()); string stringDir = FileLoader.GetAssetDir(FileLoader.AssetType.Strings, Utils.Language); diff --git a/MelonLoader/Patches/GameObjects/PVPRandomManager_Patch.cs b/MelonLoader/Patches/GameObjects/PVPRandomManager_Patch.cs new file mode 100644 index 0000000..a3d21b0 --- /dev/null +++ b/MelonLoader/Patches/GameObjects/PVPRandomManager_Patch.cs @@ -0,0 +1,33 @@ +using HarmonyLib; +using Il2Cpp; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; +using UnityEngine; +using static MelonLoader.MelonLogger; + +namespace PvZ_Fusion_Translator.Patches.GameObjects +{ + [HarmonyPatch(typeof(PVPRandomManager))] + public static class PVPRandomManager_Patch + { + [HarmonyPatch(nameof(PVPRandomManager.Start))] + [HarmonyPostfix] + private static void Start(PVPRandomManager __instance) + { + foreach(TextMeshPro text in __instance.texts) + { + text.text = StringStore.TranslateText(text.text); + } + } + + [HarmonyPatch(nameof(PVPRandomManager.Update))] + [HarmonyPostfix] + private static void ZombieEnterHouse(PVPRandomManager __instance) + { + foreach(TextMeshPro text in __instance.texts) + { + text.text = StringStore.TranslateText(text.text); + } + } + } +} diff --git a/MelonLoader/Patches/GameObjects/PlantDataMenu_Patch.cs b/MelonLoader/Patches/GameObjects/PlantDataMenu_Patch.cs new file mode 100644 index 0000000..0dafc50 --- /dev/null +++ b/MelonLoader/Patches/GameObjects/PlantDataMenu_Patch.cs @@ -0,0 +1,80 @@ +using HarmonyLib; +using Il2Cpp; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Text.RegularExpressions; +using System.Threading.Tasks; + +namespace PvZ_Fusion_Translator.Patches.GameObjects +{ + [HarmonyPatch(typeof(PlantDataMenu))] + public static class PlantDataMenu_Patch + { + [HarmonyPatch(nameof(PlantDataMenu.Start))] + [HarmonyPostfix] + public static void Post_Start(PlantDataMenu __instance) + { + TranslatePlantDataMenu(__instance); + } + + [HarmonyPatch(nameof(PlantDataMenu.Update))] + [HarmonyPostfix] + public static void Post_Update(PlantDataMenu __instance) + { + TranslatePlantDataMenu(__instance); + } + + public static void TranslatePlantDataMenu(PlantDataMenu __instance) + { + PlantType thePlantType = __instance.plant.thePlantType; + string plantName = Utils.GetPlantNameFromAlmanac(thePlantType); + + TMP_FontAsset fontAsset = FontStore.LoadTMPFont(Utils.Language.ToString()); + + foreach(TextMeshProUGUI text in __instance.nameText) + { + text.text = plantName; + text.font = fontAsset; + } + + foreach(TextMeshProUGUI text in __instance.infoText) + { + string toTranslate = text.text; + string startColorTag = ""; + + string colorPattern = @"(]+>)(.*?)()"; + Match match = Regex.Match(toTranslate, colorPattern); + if(match.Success) + { + startColorTag = match.Groups[1].Value; + toTranslate = match.Groups[2].Value; + } + + string[] parts = toTranslate.Split("\n"); + List translatedParts = new List(); + + foreach(string part in parts) + { + translatedParts.Add(StringStore.TranslateText(part)); + } + + string joinedTranslation = String.Join("\n", translatedParts); + + if(startColorTag != "") + { + text.text = startColorTag + joinedTranslation + ""; + } + else + { + text.text = joinedTranslation; + } + + text.font = fontAsset; + } + } + } +} diff --git a/MelonLoader/Patches/GameObjects/PlayerSaveMenu_Patch.cs b/MelonLoader/Patches/GameObjects/PlayerSaveMenu_Patch.cs new file mode 100644 index 0000000..f8e702d --- /dev/null +++ b/MelonLoader/Patches/GameObjects/PlayerSaveMenu_Patch.cs @@ -0,0 +1,36 @@ +using HarmonyLib; +using Il2Cpp; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; +using UnityEngine; +using System.Text.RegularExpressions; + +namespace PvZ_Fusion_Translator.Patches.GameObjects +{ + [HarmonyPatch(typeof(PlayerSaveMenu))] + public static class PlayerSaveMenu_Patch + { + [HarmonyPatch(nameof(PlayerSaveMenu.CreatePlayerData))] + [HarmonyPostfix] + public static void CreatePlayerData(PlayerSaveMenu __instance) + { + TranslateCreatePlayerSaveMenu(); + } + + [HarmonyPatch(nameof(PlayerSaveMenu.ResetName))] + [HarmonyPostfix] + public static void ResetName(PlayerSaveMenu __instance) + { + TranslateCreatePlayerSaveMenu(); + } + + public static void TranslateCreatePlayerSaveMenu() + { + Transform createPlayerSaveMenuTransform = GameAPP.canvasUp.Find("CreatePlayerSaveMenu(Clone)"); + if(createPlayerSaveMenuTransform.TryGetComponent(out CreatePlayerSaveMenu createPlayerSaveMenu)) + { + createPlayerSaveMenu.title.text = StringStore.TranslateText(createPlayerSaveMenu.title.text); + } + } + } +} diff --git a/MelonLoader/Patches/GameObjects/SeedLibrary_Patch.cs b/MelonLoader/Patches/GameObjects/SeedLibrary_Patch.cs index 230a392..ea01e81 100644 --- a/MelonLoader/Patches/GameObjects/SeedLibrary_Patch.cs +++ b/MelonLoader/Patches/GameObjects/SeedLibrary_Patch.cs @@ -15,11 +15,11 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects { TMP_FontAsset fontAsset = FontStore.LoadTMPFont(Utils.Language.ToString()); - foreach (TextMeshProUGUI txt in __instance.GetComponentsInChildren()) - { - txt.text = StringStore.TranslateText(txt.text); - txt.font = fontAsset; - } + //foreach (TextMeshProUGUI txt in __instance.GetComponentsInChildren()) + //{ + // txt.text = StringStore.TranslateText(txt.text); + // txt.font = fontAsset; + //} Transform safetyBoxButtonTransform = __instance.transform.FindChild("SafeBox").FindChild("StartSafeMode"); diff --git a/MelonLoader/Patches/GameObjects/WarningMenu_Patch.cs b/MelonLoader/Patches/GameObjects/WarningMenu_Patch.cs index b9b9b8b..f3103ff 100644 --- a/MelonLoader/Patches/GameObjects/WarningMenu_Patch.cs +++ b/MelonLoader/Patches/GameObjects/WarningMenu_Patch.cs @@ -41,8 +41,12 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects TextMeshProUGUI text = normalModeTransform.Find("text").GetComponent(); TextMeshProUGUI textShadow = normalModeTransform.Find("text (1)").GetComponent(); - text.text = Utils.RemoveColorTags(StringStore.TranslateText(text.text)); - textShadow.text = Utils.RemoveColorTags(textShadow.text); + text.text = StringStore.translationString.ContainsKey("普通模式_IV") ? StringStore.TranslateText("普通模式_IV") : Utils.RemoveColorTags(StringStore.TranslateText(text.text)); + text.alignment = TextAlignmentOptions.Center; + text.autoSizeTextContainer = true; + textShadow.text = Utils.RemoveColorTags(text.text); + textShadow.alignment = TextAlignmentOptions.Center; + textShadow.autoSizeTextContainer = true; } if (challengeModeTransform != null) @@ -50,8 +54,12 @@ namespace PvZ_Fusion_Translator.Patches.GameObjects TextMeshProUGUI text = challengeModeTransform.Find("text").GetComponent(); TextMeshProUGUI textShadow = challengeModeTransform.Find("text (1)").GetComponent(); - text.text = Utils.RemoveColorTags(StringStore.TranslateText(text.text)); - textShadow.text = Utils.RemoveColorTags(textShadow.text); + text.text = StringStore.translationString.ContainsKey("诅咒模式_IV") ? StringStore.TranslateText("诅咒模式_IV") : Utils.RemoveColorTags(StringStore.TranslateText(text.text)); + text.alignment = TextAlignmentOptions.Center; + text.autoSizeTextContainer = true; + textShadow.text = Utils.RemoveColorTags(text.text); + textShadow.alignment = TextAlignmentOptions.Center; + textShadow.autoSizeTextContainer = true; } if (__instance.tutor != null) diff --git a/MelonLoader/Patches/Managers/InGameUI_Patch.cs b/MelonLoader/Patches/Managers/InGameUI_Patch.cs index c5fd833..cd07a31 100644 --- a/MelonLoader/Patches/Managers/InGameUI_Patch.cs +++ b/MelonLoader/Patches/Managers/InGameUI_Patch.cs @@ -15,37 +15,30 @@ namespace PvZ_Fusion_Translator.Patches.Managers [HarmonyPostfix] private static void Start(InGameUI __instance) { - TextMeshProUGUI[] array = new TextMeshProUGUI[] + foreach(TextMeshProUGUI text in __instance.GetComponentsInChildren()) { - __instance.transform.GetChild(4).GetComponent(), - __instance.transform.GetChild(4).GetChild(0).GetComponent(), - __instance.transform.GetChild(5).GetComponent(), - __instance.transform.GetChild(5).GetChild(0).GetComponent(), - __instance.transform.GetChild(6).GetComponent(), - __instance.transform.GetChild(6).GetChild(0).GetComponent()}; - TextMeshProUGUI[] array2 = array; - for (int i = 0; i < array2.Length; i++) - { - string originalText = array2[i].text; - array2[i].text = array2[i].text.Replace("\n", " "); + if (text.text == null) continue; + + string originalText = text.text; + text.text = text.text.Replace("\n", " "); Regex checkFusionChallenge = new Regex("^超级([^\\s:]+)(:?挑战1?)"); - if (array2[i].text.Contains("配方:") && !checkFusionChallenge.IsMatch(array2[i].text)) + if (text.text.Contains("配方:") && !checkFusionChallenge.IsMatch(text.text)) { - string[] lines = array2[i].text.Split(":"); + string[] lines = text.text.Split(":"); lines[1] = Utils.GetPlantNameFromAlmanac(lines[1]); if (lines[1] == "") { Log.LogError("Couldn't find plant! (Fusion Showcase)"); lines[1] = StringStore.TranslateText(lines[1]); } - array2[i].text = StringStore.TranslateText("配方:") + lines[1]; - array2[i].autoSizeTextContainer = true; + text.text = StringStore.TranslateText("配方:") + lines[1]; + text.autoSizeTextContainer = true; } else { - array2[i].text = (StringStore.translationString.ContainsKey(array2[i].text + "_MG")) ? StringStore.TranslateText(array2[i].text + "_MG") : StringStore.TranslateText(array2[i].text); - array2[i].text = array2[i].text.Replace("\n", " "); + text.text = (StringStore.translationString.ContainsKey(text.text + "_MG")) ? StringStore.TranslateText(text.text + "_MG") : StringStore.TranslateText(text.text); + text.text = text.text.Replace("\n", " "); } } } diff --git a/MelonLoader/Patches/Managers/UIMgr_Patch.cs b/MelonLoader/Patches/Managers/UIMgr_Patch.cs index 3b49429..e3e1bad 100644 --- a/MelonLoader/Patches/Managers/UIMgr_Patch.cs +++ b/MelonLoader/Patches/Managers/UIMgr_Patch.cs @@ -1,22 +1,19 @@ using HarmonyLib; using Il2Cpp; using PvZ_Fusion_Translator.AssetStore; +using UnityEngine; namespace PvZ_Fusion_Translator.Patches.Managers { [HarmonyPatch(typeof(UIMgr))] public class UIMgr_Patch { - //[HarmonyPatch(nameof(UIMgr.EnterMainMenu))] - //[HarmonyPostfix] - //private static void EnterMainMenu(UIMgr __instance) - //{ - // // Log.LogInfo("Entered Main Menu"); - // #if MULTI_LANGUAGE - // WarningStore.WarningReload(Utils.Language); - // #else - // WarningStore.WarningReload(); - // #endif - //} + [HarmonyPatch(nameof(UIMgr.EnterLoseMenu))] + [HarmonyPostfix] + private static void EnterLoseMenu(UIMgr __instance) + { + LoseMenu loseMenu = GameObject.FindObjectOfType(); + loseMenu.title.text = StringStore.TranslateText(loseMenu.title.text); + } } } \ No newline at end of file diff --git a/MelonLoader/Patches/Modes/Odyssey/TravelRefresh_Patch.cs b/MelonLoader/Patches/Modes/Odyssey/TravelRefresh_Patch.cs index 56f73e4..5d58593 100644 --- a/MelonLoader/Patches/Modes/Odyssey/TravelRefresh_Patch.cs +++ b/MelonLoader/Patches/Modes/Odyssey/TravelRefresh_Patch.cs @@ -9,9 +9,9 @@ namespace PvZ_Fusion_Translator.Patches.Modes.Odyssey [HarmonyPatch(typeof(TravelRefresh))] public static class TravelRefresh_Patch { - [HarmonyPatch(nameof(TravelRefresh.Start))] + [HarmonyPatch(nameof(TravelRefresh.Awake))] [HarmonyPostfix] - private static void Start(TravelRefresh __instance) + private static void Awake(TravelRefresh __instance) { __instance.text = StringStore.TranslateText(__instance.text); __instance.text_shadow = StringStore.TranslateText(__instance.text_shadow); diff --git a/MelonLoader/Patches/Modes/Super Editor/CustomLevelMenu_Patch.cs b/MelonLoader/Patches/Modes/Super Editor/CustomLevelMenu_Patch.cs new file mode 100644 index 0000000..a0822cb --- /dev/null +++ b/MelonLoader/Patches/Modes/Super Editor/CustomLevelMenu_Patch.cs @@ -0,0 +1,162 @@ +using HarmonyLib; +using Il2Cpp; +using Il2CppTMPro; +using MelonLoader; +using Newtonsoft.Json; +using PvZ_Fusion_Translator.AssetStore; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Text.Encodings.Web; +using System.Text.Json; +using System.Threading.Tasks; +using System.Threading.Tasks; +using UnityEngine; + +namespace PvZ_Fusion_Translator.Patches.Modes.Super_Editor +{ + [HarmonyPatch(typeof(CustomLevelMenu))] + public static class CustomLevelMenu_Patch + { + public static Dictionary translatedLevelData = new Dictionary(); + public static float requestTimer = 0f; + public static bool useLocal = false; + + [HarmonyPatch(nameof(CustomLevelMenu.LoadOnlineFiles))] + [HarmonyPostfix] + public static void LoadOnlineFiles(CustomLevelMenu __instance) + { + translatedLevelData = new Dictionary(); + + if (!useLocal) + { + LoadOnlineData(); + } + else + { + LoadLocalData(); + } + } + + [HarmonyPatch(nameof(CustomLevelMenu.InitWindows))] + [HarmonyPostfix] + public static void InitWindows(CustomLevelMenu __instance) + { + TranslateLevelButtons(__instance); + } + + [HarmonyPatch(nameof(CustomLevelMenu.ReloadFiles))] + [HarmonyPostfix] + public static void ReloadFiles(CustomLevelMenu __instance) + { + TranslateLevelButtons(__instance); + } + + public static void TranslateLevelButtons(CustomLevelMenu __instance) + { + Dictionary dumpData = new Dictionary(); + + foreach(CustomButton_enterGame level in __instance.levels) + { + string levelId = level.levelData.levelId; + if(levelId != null) + { + if(translatedLevelData.ContainsKey(levelId)) + { + TranslatedLevelData levelData = translatedLevelData[levelId]; + level.levelName.text = levelData.name; + level.levelData.Name = levelData.name; + level.serializedLevel.boardConfig.startTip = levelData.startTip; + } + else + { + TranslatedLevelData dumpedLevelData = new TranslatedLevelData(level.levelData.Name, level.serializedLevel.boardConfig.startTip); + dumpData.Add(levelId, dumpedLevelData); + } + } + else + { + level.levelName.text = StringStore.TranslateText(level.levelData.Name); + } + } + + string dumpPath = Path.Combine(FileLoader.GetAssetDir(FileLoader.AssetType.Dumps), "custom_level_data.json"); + File.WriteAllText(dumpPath, System.Text.Json.JsonSerializer.Serialize(dumpData, new JsonSerializerOptions + { + WriteIndented = true, + Encoder = JavaScriptEncoder.UnsafeRelaxedJsonEscaping + })); + } + + public static async System.Threading.Tasks.Task> GetTranslatedLevelData() + { + var levelDataRequest = await new HttpClient().GetAsync($"https://raw.githubusercontent.com/Teyliu/PVZF-Translation/refs/heads/main/PvZ_Fusion_Translator/Localization/{Utils.Language.ToString()}/Strings/custom_level_data.json"); + if(levelDataRequest.StatusCode == System.Net.HttpStatusCode.OK) + { + string levelDataString = await levelDataRequest.Content.ReadAsStringAsync(); + Dictionary levelDataJson = JsonConvert.DeserializeObject>(levelDataString); + return levelDataJson; + } + else + { + new CancellationTokenSource().Cancel(); + return null; + } + } + + public static void LoadOnlineData() + { + if (requestTimer <= 0) + { + requestTimer = 5f; // 5 seconds in between request attempts to prevent any issues with github + + var translatedLevelDataRequest = System.Threading.Tasks.Task.Run(() => GetTranslatedLevelData()); + + if (translatedLevelDataRequest.Result != null) + { + translatedLevelData = translatedLevelDataRequest.Result; + Log.LogInfo($"Successfully loaded level data for {Utils.Language.ToString()}!"); + } + else + { + Log.LogError($"Couldn't find level data for {Utils.Language.ToString()}!"); + } + } + else + { + Log.LogInfo($"Please wait before requesting levels again! Current cooldown: {Math.Round(requestTimer, 3)}s"); + } + } + + public static void LoadLocalData() + { + string assetDir = Path.Combine(FileLoader.GetAssetDir(FileLoader.AssetType.Strings, Utils.Language), "custom_level_data.json"); + if (!File.Exists(assetDir)) + { + File.CreateText(assetDir); + File.WriteAllText(assetDir, "{}"); + } + string levelDataString = File.ReadAllText(assetDir); + Dictionary levelDataJson = JsonConvert.DeserializeObject>(levelDataString); + translatedLevelData = levelDataJson; + } + + public static void SwapLevelData() + { + useLocal = !useLocal; + } + } + + public class TranslatedLevelData + { + public string name { get; set; } + public string startTip { get; set; } + + public TranslatedLevelData(string name, string startTip) + { + this.name = name; + this.startTip = startTip; + } + } +} diff --git a/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_initZombies_Patch.cs b/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_initZombies_Patch.cs new file mode 100644 index 0000000..cc0df54 --- /dev/null +++ b/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_initZombies_Patch.cs @@ -0,0 +1,32 @@ +using MelonLoader; +using HarmonyLib; +using UnityEngine; +using Il2Cpp; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; + +namespace PvZ_Fusion_Translator.Patches.Modes.Super_Editor +{ + [HarmonyPatch(typeof(CustomMenuPage_initZombies))] + public static class CustomMenuPage_initZombies_Patch + { + [HarmonyPatch(nameof(CustomMenuPage_initZombies.SubWave))] + [HarmonyPostfix] + public static void SubWave(CustomMenuPage_initZombies __instance) + { + __instance.currentWaveText.text = StringStore.TranslateText(__instance.currentWaveText.text); + } + + [HarmonyPatch(nameof(CustomMenuPage_initZombies.AddWave))] + [HarmonyPostfix] + public static void AddWave(CustomMenuPage_initZombies __instance) + { + __instance.currentWaveText.text = StringStore.TranslateText(__instance.currentWaveText.text); + } + } +} diff --git a/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_page3_Patch.cs b/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_page3_Patch.cs new file mode 100644 index 0000000..7b0d4dd --- /dev/null +++ b/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_page3_Patch.cs @@ -0,0 +1,34 @@ +using MelonLoader; +using HarmonyLib; +using UnityEngine; +using Il2Cpp; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; + +namespace PvZ_Fusion_Translator.Patches.Modes.Super_Editor +{ + [HarmonyPatch(typeof(CustomMenu_page3))] + public static class CustomMenuPage_page3_Patch + { + [HarmonyPatch(nameof(CustomMenu_page3.UpdateCardsText))] + [HarmonyPostfix] + public static void UpdateCardsText(CustomMenu_page3 __instance) + { + string plantName = Utils.GetPlantNameFromAlmanac(__instance.nameText.text); + __instance.nameText.text = (plantName != "") ? (plantName) : StringStore.TranslateText(__instance.nameText.text); + } + + [HarmonyPatch(nameof(CustomMenu_page3.UpdateAdvancedInfo))] + [HarmonyPostfix] + public static void UpdateAdvancedInfo(CustomMenu_page3 __instance) + { + string plantName = Utils.GetPlantNameFromAlmanac(__instance.nameText.text); + __instance.nameText.text = (plantName != "") ? (plantName) : StringStore.TranslateText(__instance.nameText.text); + } + } +} diff --git a/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_shooting_Patch.cs b/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_shooting_Patch.cs new file mode 100644 index 0000000..a019938 --- /dev/null +++ b/MelonLoader/Patches/Modes/Super Editor/CustomMenuPage_shooting_Patch.cs @@ -0,0 +1,65 @@ +using MelonLoader; +using HarmonyLib; +using UnityEngine; +using Il2Cpp; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; + +namespace PvZ_Fusion_Translator.Patches.Modes.Super_Editor +{ + [HarmonyPatch(typeof(CustomMenuPage_shooting))] + public static class CustomMenuPage_shooting_Patch + { + [HarmonyPatch(nameof(CustomMenuPage_shooting.CreateRoute))] + [HarmonyPostfix] + public static void CreateRoute(CustomMenuPage_shooting __instance) + { + TranslateRoutes(__instance); + } + + [HarmonyPatch(nameof(CustomMenuPage_shooting.CreateStage))] + [HarmonyPostfix] + public static void CreateStage(CustomMenuPage_shooting __instance) + { + TranslateRoutes(__instance); + } + + [HarmonyPatch(nameof(CustomMenuPage_shooting.Awake))] + [HarmonyPostfix] + public static void Awake(CustomMenuPage_shooting __instance) + { + TranslateRoutes(__instance); + } + + [HarmonyPatch(nameof(CustomMenuPage_shooting.SearchRoute))] + [HarmonyPostfix] + public static void SearchRoute(CustomMenuPage_shooting __instance) + { + TranslateRoutes(__instance); + } + + [HarmonyPatch(nameof(CustomMenuPage_shooting.SearchAllRoute))] + [HarmonyPostfix] + public static void SearchAllRoute(CustomMenuPage_shooting __instance) + { + TranslateRoutes(__instance); + } + + public static void TranslateRoutes(CustomMenuPage_shooting __instance) + { + foreach(TextMeshProUGUI text in __instance.scollContent.GetComponentsInChildren()) + { + if (text.name == "PlantText") + { + string plantName = Utils.GetPlantNameFromAlmanac(text.text); + text.text = (plantName != "") ? plantName : StringStore.TranslateText(text.text); + } + } + } + } +} diff --git a/MelonLoader/Patches/Modes/Super Editor/CustomOnlineMenu_Patch.cs b/MelonLoader/Patches/Modes/Super Editor/CustomOnlineMenu_Patch.cs new file mode 100644 index 0000000..c01fd95 --- /dev/null +++ b/MelonLoader/Patches/Modes/Super Editor/CustomOnlineMenu_Patch.cs @@ -0,0 +1,39 @@ +using MelonLoader; +using HarmonyLib; +using UnityEngine; +using Il2Cpp; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Il2CppTMPro; +using PvZ_Fusion_Translator.AssetStore; + +namespace PvZ_Fusion_Translator.Patches.Modes.Super_Editor +{ + [HarmonyPatch(typeof(CustomOnlineMenu))] + public static class CustomOnlineMenu_Patch + { + [HarmonyPatch(nameof(CustomOnlineMenu.EditLevel))] + [HarmonyPostfix] + public static void EditLevel(CustomOnlineMenu __instance) + { + TranslateLevelName(__instance); + } + + [HarmonyPatch(nameof(CustomOnlineMenu.Start))] + [HarmonyPostfix] + public static void Start(CustomOnlineMenu __instance) + { + TranslateLevelName(__instance); + } + + public static void TranslateLevelName(CustomOnlineMenu __instance) + { + string translatedText = StringStore.TranslateText(__instance.title.text); + __instance.title.text = translatedText; + __instance.title2.text = translatedText; + } + } +} diff --git a/MelonLoader/PvZ Fusion Translator [MelonLoader].csproj b/MelonLoader/PvZ Fusion Translator [MelonLoader].csproj index 0b3becc..677f8f2 100644 --- a/MelonLoader/PvZ Fusion Translator [MelonLoader].csproj +++ b/MelonLoader/PvZ Fusion Translator [MelonLoader].csproj @@ -402,6 +402,13 @@ + + + + + + + @@ -500,6 +507,11 @@ + + + + + diff --git a/MelonLoader/Utils.cs b/MelonLoader/Utils.cs index 01b675e..db81a67 100644 --- a/MelonLoader/Utils.cs +++ b/MelonLoader/Utils.cs @@ -167,7 +167,7 @@ namespace PvZ_Fusion_Translator return thePlantName; } - public static string GetPlantNameFromAlmanac(string theOriginalPlantName) + public static string GetPlantNameFromAlmanac(string theOriginalPlantName, bool log = false) { string originalJson; string translatedJson; @@ -181,8 +181,11 @@ namespace PvZ_Fusion_Translator if ((!File.Exists(path)) || (!File.Exists(originalPath))) { - Log.LogError($"LawnStringsTranslate.json file not found at path: {path}"); - Log.LogError("Plant name could not be found!"); + if(log) + { + Log.LogError($"LawnStringsTranslate.json file not found at path: {path}"); + Log.LogError("Plant name could not be found!"); + } thePlantName = ""; } else @@ -208,7 +211,10 @@ namespace PvZ_Fusion_Translator if (!foundPlantName) { - Log.LogInfo("Couldn't find plant name!"); + if(log) + { + Log.LogInfo("Couldn't find plant name!"); + } thePlantName = ""; } } @@ -300,7 +306,7 @@ namespace PvZ_Fusion_Translator } } - public static Dictionary> recipeLinks = new Dictionary>(); + /*public static Dictionary> recipeLinks = new Dictionary>(); public static void RegisterRecipeLinks() { @@ -316,32 +322,32 @@ namespace PvZ_Fusion_Translator recipeLinks.Add(seedType, new()); - if(seedType > 0) + if (seedType > 0) { - foreach (PlantType checkType in Enum.GetValues(typeof(PlantType))) - { - if(checkType > 0) + foreach (PlantType checkType in Enum.GetValues(typeof(PlantType))) + { + if (checkType > 0) { - int[] checks = [mixData.GetValue(seedType, (int)checkType).Unbox(), mixData.GetValue((int)checkType, seedType).Unbox()]; + int[] checks = [mixData.GetValue(seedType, (int)checkType).Unbox(), mixData.GetValue((int)checkType, seedType).Unbox()]; - if (checks[0] != 0) - { - recipeLinks[seedType].Add(checks[0]); - } + if (checks[0] != 0) + { + recipeLinks[seedType].Add(checks[0]); + } - if (checks[1] != 0) - { - recipeLinks[seedType].Add(checks[1]); - } - } - } - } + if (checks[1] != 0) + { + recipeLinks[seedType].Add(checks[1]); + } + } + } + } if (recipeLinks[seedType].Count > 0) { Log.LogDebug($"Found {recipeLinks[seedType].Count} fusions for {seedType}!"); } - } - } + } + }*/ public static bool CheckForUntranslatedText(string text) { @@ -373,7 +379,7 @@ namespace PvZ_Fusion_Translator Log.LogError($"Invalid language string: {language}"); } - WarningStore.isWarningMessageLoaded = false; + //WarningStore.isWarningMessageLoaded = false; FontStore.Reload(); StringStore.Reload(); TextureStore.Reload(); @@ -396,31 +402,48 @@ namespace PvZ_Fusion_Translator { // first column English, + Chinese_cn, French, - Italian, - German, + //Italian, + //German, Spanish, - Portuguese, + // second column - Javanese, //Filipino, + //Portuguese, + //Javanese, + //Filipino, Vietnamese, - Indonesian, - Russian, //NOTE: legacy language + //Indonesian, + //Russian, //NOTE: legacy language Japanese, - Korean, + // third column - Ukrainian, + Korean, + Ukrainian, // Slovak, //Polish, - Turkish, + //Turkish, //Arabic, Romanian, LANG_END } + public static Dictionary LanguageNames = new Dictionary() + { + { LanguageEnum.English, "English"}, + { LanguageEnum.Chinese_cn, "简体中文"}, + { LanguageEnum.French, "Français"}, + { LanguageEnum.Spanish, "Español"}, + { LanguageEnum.Vietnamese, "Tiếng Việt"}, + { LanguageEnum.Japanese, "日本語"}, + { LanguageEnum.Korean, "한국어"}, + { LanguageEnum.Ukrainian, "українська"}, + { LanguageEnum.Romanian, "Română"} + }; + public enum ToggleEnum { Textures,