using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Cryptography;
using System.Security.Permissions;
using System.Text;
using BepInEx;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using Newtonsoft.Json;
using OMSLib.Modules;
using TMPro;
using Unity.Netcode;
using UnityEngine;
using UnityEngine.Localization;
using UnityEngine.Localization.Settings;
using UnityEngine.Localization.Tables;
using UnityEngine.UI;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")]
[assembly: IgnoresAccessChecksTo("Assembly-CSharp")]
[assembly: IgnoresAccessChecksTo("Unity.Localization")]
[assembly: IgnoresAccessChecksTo("Unity.Netcode.Runtime")]
[assembly: AssemblyCompany("ViViKo.OMSLib")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyDescription("Modding tools for Old Market Simulator")]
[assembly: AssemblyFileVersion("1.2.0.0")]
[assembly: AssemblyInformationalVersion("1.2.0")]
[assembly: AssemblyProduct("OMSLib")]
[assembly: AssemblyTitle("ViViKo.OMSLib")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.2.0.0")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
namespace Microsoft.CodeAnalysis
{
[CompilerGenerated]
[Microsoft.CodeAnalysis.Embedded]
internal sealed class EmbeddedAttribute : Attribute
{
}
}
namespace System.Runtime.CompilerServices
{
[CompilerGenerated]
[Microsoft.CodeAnalysis.Embedded]
[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
internal sealed class RefSafetyRulesAttribute : Attribute
{
public readonly int Version;
public RefSafetyRulesAttribute(int P_0)
{
Version = P_0;
}
}
}
namespace OMSLib
{
[BepInPlugin("ViViKo.OMSLib", "OMSLib", "1.2.0")]
public class OMSLib : BaseUnityPlugin
{
private readonly Harmony harmony = new Harmony("ViViKo.OMSLib");
public static OMSLib Instance;
internal static ManualLogSource Logger { get; private set; }
private void Awake()
{
Instance = this;
Logger = ((BaseUnityPlugin)this).Logger;
harmony.PatchAll();
ContentLoader.Init();
Logger.LogInfo((object)"Plugin OMSLib v1.2.0 is loaded!");
}
}
public static class PluginInfo
{
public const string PLUGIN_GUID = "ViViKo.OMSLib";
public const string PLUGIN_NAME = "OMSLib";
public const string PLUGIN_VERSION = "1.2.0";
}
}
namespace OMSLib.Patches
{
[HarmonyPatch(typeof(GameManager))]
public class GameManagerPatch
{
[HarmonyPatch("Awake")]
[HarmonyPostfix]
private static void AwakePatch(GameManager __instance)
{
__instance.isModded = true;
Items.Init();
Recipes.Init();
Events.Init();
Employees.Init();
Expansions.Init();
Licenses.Init();
Seasons.Init();
NetworkPrefabs.Init();
}
}
[HarmonyPatch(typeof(MenuManager))]
public class MenuManagerPatch
{
public static Slider fovSlider;
[HarmonyPatch("CheckMenu")]
[HarmonyPostfix]
private static void CheckMenuPatch(MenuManager __instance)
{
((TMP_Text)__instance.textVersion).text = "<color=red>Modded</color> V" + Application.version;
}
}
}
namespace OMSLib.Modules
{
public class Assets
{
public static Shader defaultLit;
public static AssetBundle LoadFromFile(string path)
{
AssetBundle val = AssetBundle.LoadFromFile(path);
if ((Object)(object)val == (Object)null)
{
return null;
}
FixShaders(val);
return val;
}
public static void FixShaders(GameObject gameObject)
{
Renderer[] componentsInChildren = gameObject.GetComponentsInChildren<Renderer>();
for (int i = 0; i < componentsInChildren.Length; i++)
{
Material[] materials = componentsInChildren[i].materials;
foreach (Material val in materials)
{
if (((Object)val.shader).name.Equals("Universal Render Pipeline/Lit") || ((Object)val.shader).name.Equals("Standard"))
{
val.shader = defaultLit;
}
}
}
}
public static void FixShaders(AssetBundle bundle)
{
//IL_0043: Unknown result type (might be due to invalid IL or missing references)
//IL_004d: Expected O, but got Unknown
if ((Object)(object)defaultLit == (Object)null)
{
defaultLit = Shader.Find("Universal Render Pipeline/Lit");
}
Object[] array = bundle.LoadAllAssets();
foreach (Object val in array)
{
if (((object)val).GetType() == typeof(GameObject))
{
Assets.FixShaders((GameObject)val);
}
}
}
}
internal class ContentLoader
{
private struct CustomRecipe
{
public List<Recipes.RecipeIngredient> ingredients;
public Recipes.RecipeIngredient output;
public Recipes.RecipeType machine;
public int requiredDays;
}
private struct CustomItem
{
public Dictionary<string, string> translations;
public string itemName;
}
private struct CustomLicense
{
public Dictionary<string, string> translations;
public string title;
public int price;
}
private static List<CustomRecipe> recipes = new List<CustomRecipe>();
private static List<CustomItem> items = new List<CustomItem>();
private static List<CustomLicense> licenses = new List<CustomLicense>();
public static Dictionary<string, Dictionary<string, string>> translations = new Dictionary<string, Dictionary<string, string>>();
private static void ParseRecipe(string name, string jsonString)
{
CustomRecipe customRecipe = JsonConvert.DeserializeObject<CustomRecipe>(jsonString);
Recipes.RegisterRecipe(customRecipe.ingredients, customRecipe.output.itemName, customRecipe.output.amount, customRecipe.requiredDays, customRecipe.machine);
}
private static void ParseItem(string name, string jsonString)
{
CustomItem item = JsonConvert.DeserializeObject<CustomItem>(jsonString);
items.Add(item);
translations.Add(item.itemName, item.translations);
}
private static void ParseLicense(string name, string jsonString)
{
CustomLicense item = JsonConvert.DeserializeObject<CustomLicense>(jsonString);
licenses.Add(item);
translations.Add(item.title, item.translations);
}
public static void Init()
{
LocalizationSettings.SelectedLocaleChanged += OnSelectedLocaleChanged;
List<string> list = Directory.GetDirectories(Paths.PluginPath, "omscontent", SearchOption.AllDirectories).ToList();
List<string> list2 = new List<string>();
foreach (string item in list)
{
if (item != "")
{
list2.AddRange(Directory.GetFiles(item, "*.*.json"));
}
}
foreach (string item2 in list2)
{
string fileNameWithoutExtension = Path.GetFileNameWithoutExtension(item2);
string jsonString = File.ReadAllText(item2);
string text = item2.Split('.')[^2];
if (text.ToLower() == "recipe")
{
ParseRecipe(fileNameWithoutExtension, jsonString);
}
else if (text.ToLower() == "item")
{
ParseItem(fileNameWithoutExtension, jsonString);
}
else if (text.ToLower() == "license")
{
ParseLicense(fileNameWithoutExtension, jsonString);
}
}
UpdateTranslations();
}
public static void UpdateTranslations()
{
//IL_0010: Unknown result type (might be due to invalid IL or missing references)
//IL_0053: Unknown result type (might be due to invalid IL or missing references)
//IL_0058: Unknown result type (might be due to invalid IL or missing references)
Locale selectedLocale = LocalizationSettings.SelectedLocale;
StringTable table = ((LocalizedDatabase<StringTable, StringTableEntry>)(object)LocalizationSettings.StringDatabase).GetTable(TableReference.op_Implicit("Translations"), (Locale)null);
foreach (KeyValuePair<string, Dictionary<string, string>> translation in translations)
{
string valueOrDefault = translation.Value.GetValueOrDefault("en", translation.Key);
Dictionary<string, string> value = translation.Value;
LocaleIdentifier identifier = selectedLocale.Identifier;
string valueOrDefault2 = value.GetValueOrDefault(((LocaleIdentifier)(ref identifier)).Code, valueOrDefault);
((DetailedLocalizationTable<StringTableEntry>)(object)table).AddEntry(translation.Key, valueOrDefault2);
}
}
private static void OnSelectedLocaleChanged(Locale locale)
{
if ((Object)(object)locale != (Object)null)
{
UpdateTranslations();
}
}
}
public class Employees
{
public class LibEmployee
{
public EmployeeSO employee;
public string name;
public string modName;
public LibEmployee(EmployeeSO employee, string modName)
{
this.employee = employee;
this.modName = modName;
long id = BitConverter.ToInt32(MD5.Create().ComputeHash(Encoding.UTF8.GetBytes(this.modName + this.employee.title)), 0);
if (Object.op_Implicit((Object)(object)this.employee.prefab.GetComponent<NetworkObject>()))
{
NetworkPrefabs.RegisterNetworkPrefab(this.employee.prefab);
}
this.employee.id = id;
}
}
public static List<LibEmployee> libEmployees = new List<LibEmployee>();
public static void RegisterEmployee(EmployeeSO employeeso)
{
LibEmployee libEmployee = libEmployees.FirstOrDefault((LibEmployee x) => x.employee.title == employeeso.title);
if (libEmployee == null)
{
string name = Assembly.GetCallingAssembly().GetName().Name;
libEmployee = new LibEmployee(employeeso, name);
libEmployees.Add(libEmployee);
}
}
public static void Init()
{
foreach (LibEmployee libEmployee in libEmployees)
{
GameManager.Instance.employeeDatabase.Add(libEmployee.employee);
OMSLib.Logger.LogInfo((object)$"{libEmployee.modName} registered employee: {libEmployee.employee.title} {libEmployee.employee.id}");
}
}
}
public class Events
{
public class LibEvent
{
public EventSO _event;
public string name;
public string modName;
public LibEvent(EventSO _event, string modName)
{
this._event = _event;
this.modName = modName;
}
}
public static List<LibEvent> libEvents = new List<LibEvent>();
public static void RegisterEvent(EventSO eventso)
{
}
public static void Init()
{
foreach (LibEvent libEvent in libEvents)
{
GameManager.Instance.events.Add(libEvent._event);
OMSLib.Logger.LogInfo((object)(libEvent.modName + " registered event: " + libEvent._event.title));
}
}
}
public class Expansions
{
public class LibExpansion
{
public ExpansionSO expansion;
public string name;
public string modName;
public LibExpansion(ExpansionSO expansion, string modName)
{
this.expansion = expansion;
this.modName = modName;
long id = BitConverter.ToInt32(MD5.Create().ComputeHash(Encoding.UTF8.GetBytes(this.modName + this.expansion.title)), 0);
this.expansion.id = id;
}
}
public static List<LibExpansion> libExpansions = new List<LibExpansion>();
public static void RegisterExpansion(ExpansionSO expansionso)
{
}
public static void Init()
{
foreach (LibExpansion libExpansion in libExpansions)
{
GameManager.Instance.expansionDatabase.Add(libExpansion.expansion);
OMSLib.Logger.LogInfo((object)$"{libExpansion.modName} registered expansion: {libExpansion.expansion.title} {libExpansion.expansion.id}");
}
}
}
public class Items
{
public class LibItem
{
public ItemSO item;
public string name;
public string modName;
public bool initiated;
public LibItem(ItemSO item, string modName)
{
this.item = item;
this.modName = modName;
byte[] value = MD5.Create().ComputeHash(Encoding.UTF8.GetBytes(this.modName + this.item.itemName));
long id = BitConverter.ToInt32(value, 0);
if (Object.op_Implicit((Object)(object)this.item.prefab.GetComponent<NetworkObject>()))
{
this.item.prefab.GetComponent<NetworkObject>().GlobalObjectIdHash = BitConverter.ToUInt32(value, 0);
NetworkPrefabs.RegisterNetworkPrefab(this.item.prefab);
}
this.item.id = id;
}
}
public enum ItemType
{
Item,
FishJunk,
Fish,
FishTrap,
AdvancedFish,
AdvancedFishJunk
}
public static List<LibItem> libItems = new List<LibItem>();
public static List<LibItem> fishJunkItems = new List<LibItem>();
public static List<LibItem> fishItems = new List<LibItem>();
public static List<LibItem> advancedFishJunkItems = new List<LibItem>();
public static List<LibItem> advancedFishItems = new List<LibItem>();
public static List<LibItem> fishTrapItems = new List<LibItem>();
public static Dictionary<string, string> translations = new Dictionary<string, string>();
public static void RegisterItem(ItemSO itemso, ItemType[] addTo = null)
{
LibItem libItem = libItems.FirstOrDefault((LibItem x) => x.item.itemName == itemso.itemName);
if (libItem != null)
{
return;
}
string name = Assembly.GetCallingAssembly().GetName().Name;
libItem = new LibItem(itemso, name);
libItems.Add(libItem);
if (addTo != null)
{
if (addTo.Contains(ItemType.Fish))
{
fishItems.Add(libItem);
}
if (addTo.Contains(ItemType.FishJunk))
{
fishJunkItems.Add(libItem);
}
if (addTo.Contains(ItemType.AdvancedFish))
{
fishItems.Add(libItem);
}
if (addTo.Contains(ItemType.AdvancedFishJunk))
{
fishJunkItems.Add(libItem);
}
if (addTo.Contains(ItemType.FishTrap))
{
fishTrapItems.Add(libItem);
}
}
}
public static void Init()
{
foreach (LibItem libItem in libItems)
{
if (!GameManager.Instance.itemDatabase.Contains(libItem.item))
{
GameManager.Instance.itemDatabase.Add(libItem.item);
}
OMSLib.Logger.LogInfo((object)$"{libItem.modName} registered item: {libItem.item.itemName} {libItem.item.id}");
}
FishingRod component = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == "fishing_rod").prefab.GetComponent<FishingRod>();
FishingRod component2 = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == "advanced_fishing_rod").prefab.GetComponent<FishingRod>();
foreach (LibItem fishJunkItem in fishJunkItems)
{
if (!component.commonItems.Contains(fishJunkItem.item))
{
component.commonItems.Add(fishJunkItem.item);
}
if (!component2.commonItems.Contains(fishJunkItem.item))
{
component2.commonItems.Add(fishJunkItem.item);
}
OMSLib.Logger.LogInfo((object)$"{fishJunkItem.modName} registered fishing junk item: {fishJunkItem.item.itemName} {fishJunkItem.item.id}");
}
foreach (LibItem fishItem in fishItems)
{
List<ProductSO> commonFishes = component.commonFishes;
ItemSO item2 = fishItem.item;
if (!commonFishes.Contains((ProductSO)(object)((item2 is ProductSO) ? item2 : null)))
{
List<ProductSO> commonFishes2 = component.commonFishes;
ItemSO item3 = fishItem.item;
commonFishes2.Add((ProductSO)(object)((item3 is ProductSO) ? item3 : null));
}
List<ProductSO> commonFishes3 = component2.commonFishes;
ItemSO item4 = fishItem.item;
if (!commonFishes3.Contains((ProductSO)(object)((item4 is ProductSO) ? item4 : null)))
{
List<ProductSO> commonFishes4 = component2.commonFishes;
ItemSO item5 = fishItem.item;
commonFishes4.Add((ProductSO)(object)((item5 is ProductSO) ? item5 : null));
}
OMSLib.Logger.LogInfo((object)$"{fishItem.modName} registered fishing item: {fishItem.item.itemName} {fishItem.item.id}");
}
foreach (LibItem advancedFishJunkItem in advancedFishJunkItems)
{
if (!component2.commonItems.Contains(advancedFishJunkItem.item))
{
component2.commonItems.Add(advancedFishJunkItem.item);
}
OMSLib.Logger.LogInfo((object)$"{advancedFishJunkItem.modName} registered advanced fishing junk item: {advancedFishJunkItem.item.itemName} {advancedFishJunkItem.item.id}");
}
foreach (LibItem advancedFishItem in advancedFishItems)
{
List<ProductSO> commonFishes5 = component2.commonFishes;
ItemSO item6 = advancedFishItem.item;
if (!commonFishes5.Contains((ProductSO)(object)((item6 is ProductSO) ? item6 : null)))
{
List<ProductSO> commonFishes6 = component2.commonFishes;
ItemSO item7 = advancedFishItem.item;
commonFishes6.Add((ProductSO)(object)((item7 is ProductSO) ? item7 : null));
}
OMSLib.Logger.LogInfo((object)$"{advancedFishItem.modName} registered advanced fishing item: {advancedFishItem.item.itemName} {advancedFishItem.item.id}");
}
BlockFishTrap component3 = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == "fish_trap").prefab.GetComponent<BlockFishTrap>();
foreach (LibItem fishTrapItem in fishTrapItems)
{
List<ProductSO> commonFishes7 = component3.commonFishes;
ItemSO item8 = fishTrapItem.item;
if (!commonFishes7.Contains((ProductSO)(object)((item8 is ProductSO) ? item8 : null)))
{
List<ProductSO> commonFishes8 = component3.commonFishes;
ItemSO item9 = fishTrapItem.item;
commonFishes8.Add((ProductSO)(object)((item9 is ProductSO) ? item9 : null));
}
OMSLib.Logger.LogInfo((object)$"{fishTrapItem.modName} registered fish trap item: {fishTrapItem.item.itemName} {fishTrapItem.item.id}");
}
}
}
public class Licenses
{
public class LibLicense
{
public LicenseSO license;
public string name;
public string modName;
public LibLicense(LicenseSO license, string modName)
{
this.license = license;
this.modName = modName;
long id = BitConverter.ToInt32(MD5.Create().ComputeHash(Encoding.UTF8.GetBytes(this.modName + this.license.title)), 0);
this.license.id = id;
}
}
public static List<LibLicense> libLicenses = new List<LibLicense>();
public static void RegisterLicense(LicenseSO licenseso)
{
}
public static void Init()
{
foreach (LibLicense libLicense in libLicenses)
{
GameManager.Instance.licenseDatabase.Add(libLicense.license);
OMSLib.Logger.LogInfo((object)$"{libLicense.modName} registered license: {libLicense.license.title} {libLicense.license.id}");
}
}
}
public class NetworkPrefabs
{
private static List<GameObject> networkPrefabs = new List<GameObject>();
public static void Init()
{
foreach (GameObject networkPrefab in networkPrefabs)
{
if (!NetworkManager.Singleton.NetworkConfig.Prefabs.Contains(networkPrefab))
{
NetworkManager.Singleton.AddNetworkPrefab(networkPrefab);
}
}
}
public static void RegisterNetworkPrefab(GameObject prefab)
{
if (!networkPrefabs.Contains(prefab))
{
networkPrefabs.Add(prefab);
}
}
}
public class Recipes
{
public class LibRecipe
{
public RecipeSO recipe;
public string modName;
public RecipeType type;
public List<RecipeIngredient> ingredients;
public string output;
public bool initiated;
}
public class RecipeIngredient
{
public string itemName;
public int amount;
}
public enum RecipeType
{
AlcoholMachine,
Oven,
MeatCutter,
JamMachine
}
public static List<LibRecipe> libRecipes = new List<LibRecipe>();
public static void RegisterRecipe(List<RecipeIngredient> ingredients, string output, int amount = 1, int requiredDays = 0, RecipeType type = RecipeType.AlcoholMachine)
{
RecipeSO val = ScriptableObject.CreateInstance<RecipeSO>();
((Object)val).name = output;
val.ingredients = new List<Ingredient>();
val.amount = amount;
val.requiredDays = requiredDays;
string name = Assembly.GetCallingAssembly().GetName().Name;
LibRecipe item = new LibRecipe
{
recipe = val,
ingredients = ingredients,
output = output,
type = type,
modName = name
};
libRecipes.Add(item);
}
public static void Init()
{
//IL_018c: Unknown result type (might be due to invalid IL or missing references)
//IL_0191: Unknown result type (might be due to invalid IL or missing references)
//IL_0199: Unknown result type (might be due to invalid IL or missing references)
//IL_01ad: Expected O, but got Unknown
GameObject prefab = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == "alcohol_machine").prefab;
BlockAlcoholMachine component = prefab.GetComponent<BlockAlcoholMachine>();
RecipePaper componentInChildren = prefab.GetComponentInChildren<RecipePaper>();
GameObject prefab2 = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == "oven").prefab;
BlockOven component2 = prefab2.GetComponent<BlockOven>();
RecipePaper componentInChildren2 = prefab2.GetComponentInChildren<RecipePaper>();
GameObject prefab3 = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == "meat_cutter").prefab;
BlockMeatCutter component3 = prefab3.GetComponent<BlockMeatCutter>();
RecipePaper componentInChildren3 = prefab3.GetComponentInChildren<RecipePaper>();
GameObject prefab4 = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == "jam_machine").prefab;
BlockJamMachine component4 = prefab4.GetComponent<BlockJamMachine>();
prefab4.GetComponentInChildren<RecipePaper>();
foreach (LibRecipe libRecipe in libRecipes)
{
if (libRecipe.initiated)
{
continue;
}
foreach (RecipeIngredient recipeIngredient in libRecipe.ingredients)
{
ItemSO val = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == recipeIngredient.itemName);
if (!((Object)(object)val == (Object)null))
{
Ingredient item2 = new Ingredient
{
itemSO = val,
amount = recipeIngredient.amount
};
libRecipe.recipe.ingredients.Add(item2);
}
}
ItemSO val2 = GameManager.Instance.itemDatabase.Find((ItemSO item) => item.itemName == libRecipe.output);
if (!((Object)(object)val2 == (Object)null))
{
libRecipe.recipe.output = val2;
if (libRecipe.type == RecipeType.AlcoholMachine)
{
component.recipes.Add(libRecipe.recipe);
}
else if (libRecipe.type == RecipeType.Oven)
{
component2.recipes.Add(libRecipe.recipe);
}
else if (libRecipe.type == RecipeType.MeatCutter)
{
component3.recipes.Add(libRecipe.recipe);
}
else if (libRecipe.type == RecipeType.JamMachine)
{
component4.recipes.Add(libRecipe.recipe);
}
OMSLib.Logger.LogInfo((object)$"{libRecipe.modName} registered {libRecipe.type} recipe: {((Object)libRecipe.recipe).name}");
libRecipe.initiated = true;
}
}
componentInChildren.recipes = component.recipes;
componentInChildren2.recipes = component2.recipes;
componentInChildren3.recipes = component3.recipes;
}
}
public class Seasons
{
public class LibSeason
{
public SeasonSO season;
public string name;
public string modName;
public LibSeason(SeasonSO season, string modName)
{
this.season = season;
this.modName = modName;
}
}
public static List<LibSeason> libSeasons = new List<LibSeason>();
public static void RegisterSeason(SeasonSO seasonso)
{
LibSeason libSeason = libSeasons.FirstOrDefault((LibSeason x) => x.season.title == seasonso.title);
if (libSeason == null)
{
string name = new StackTrace().GetFrame(2).GetMethod().ReflectedType.Assembly.GetName().Name;
libSeason = new LibSeason(seasonso, name);
libSeasons.Add(libSeason);
}
}
public static void Init()
{
foreach (LibSeason libSeason in libSeasons)
{
GameManager.Instance.seasons.Add(libSeason.season);
OMSLib.Logger.LogInfo((object)(libSeason.modName + " registered season: " + libSeason.season.title));
}
}
}
}
namespace System.Runtime.CompilerServices
{
[AttributeUsage(AttributeTargets.Assembly, AllowMultiple = true)]
internal sealed class IgnoresAccessChecksToAttribute : Attribute
{
public IgnoresAccessChecksToAttribute(string assemblyName)
{
}
}
}