1. Hello,

    I'm getting a little issue from my INdev-plugin while create new teleporter after using one of them.
    I'm assigning 3 tp to each arena using a command:
    The problem appear only if i use on of existing tp and after that trying to create/change a tp

    After some search it seem to be related to missing registry key for timezone, but which one?
    I'm under my local windows 10 pro edition and my oxide is uptodate
    1522165287.png
    If someone has a tip for this, maybe @Wulf
    Here is the exception :
    Code:
    15:38 [Error] Failed to call hook 'cmdTeleport' on plugin 'PVPArena v1.0.0' (TimeZoneNotFoundException: Exception of type 'System.TimeZoneNotFoundException' was thrown.)
      at System.TimeZoneInfo.get_Local () [0x00000] in <filename unknown>:0
      at Newtonsoft.Json.Utilities.DateTimeUtils.GetUtcOffset (DateTime d) [0x00000] in <filename unknown>:0
      at Newtonsoft.Json.Utilities.DateTimeUtils.WriteDateTimeString (System.Char[] chars, Int32 start, DateTime value, Nullable`1 offset, DateTimeKind kind, DateFormatHandling format) [0x00000] in <filename unknown>:0
      at Newtonsoft.Json.JsonTextWriter.WriteValue (DateTime value) [0x00000] in <filename unknown>:0
      at Newtonsoft.Json.JsonWriter.WriteValue (Newtonsoft.Json.JsonWriter writer, PrimitiveTypeCode typeCode, System.Object value) [0x00000] in <filename unknown>:0
      at Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializePrimitive (Newtonsoft.Json.JsonWriter writer, System.Object value, Newtonsoft.Json.Serialization.JsonPrimitiveContract contract, Newtonsoft.Json.Serialization.JsonProperty member, Newtonsoft.Json.Serialization.JsonContainerContract containerContract, Newtonsoft.Json.Serialization.JsonProperty containerProperty) [0x00000] in <filename unknown>:0
      at Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeValue (Newtonsoft.Json.JsonWriter writer, System.Object value, Newtonsoft.Json.Serialization.JsonContract valueContract, Newtonsoft.Json.Serialization.JsonProperty member, Newtonsoft.Json.Serialization.JsonContainerContract containerContract, Newtonsoft.Json.Serialization.JsonProperty containerProperty) [0x00000] in <filename unknown>:0
      at Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeObject (Newtonsoft.Json.JsonWriter writer, System.Object value, Newtonsoft.Json.Serialization.JsonObjectContract contract, Newtonsoft.Json.Serialization.JsonProperty member, Newtonsoft.Json.Serialization.JsonContainerContract collectionContract, Newtonsoft.Json.Serialization.JsonProperty containerProperty) [0x00000] in <filename unknown>:0
    
    and here is the class and save data function:
    Code:
    private List<Arena> arenas = new List<Arena>();private class Arena
    {
        public string ID { get; set; }
        public TeleporterInfo Lobby { get; set; }
        public TeleporterInfo TeamA { get; set; }
        public TeleporterInfo TeamB { get; set; }
        public List<TDMPlayer> ListPlayer { get; set; }    public Arena(string ID)
        {
            this.ID = ID;
            ListPlayer = new List<TDMPlayer>();
        }
    }
    class TDMPlayer : MonoBehaviour
    {
        public BasePlayer player;
        public Team team;
        public int kills;    void Awake()
        {
            player = GetComponent<BasePlayer>();
            enabled = false;
            team = Team.NONE;
            kills = 0;
        }
    }private class TeleporterPlayerHandler : MonoBehaviour
    {
        public Timer timer;
        public BasePlayer player => gameObject.GetComponent<BasePlayer>();    public void Teleport(TeleporterEntity teleporter)
        {
            TeleporterPoint otherPoint = teleporter.point.PointType == PortalPointType.Entrance
                ? teleporter.info.Exit
                : teleporter.info.Entrance;        if (teleporter.info.ID.Contains("lobby"))
            {
                string[] name = teleporter.info.ID.Split('_');
                if (Instance.arenas.FindIndex(x => x.ID == name[0]) != -1)
                {
                    List<TDMPlayer> p = new List<TDMPlayer>();
                    if (player.gameObject.GetComponent<TDMPlayer>() != null)
                    {
                        Destroy(player.gameObject.GetComponent<TDMPlayer>());
                    }                player.gameObject.AddComponent<TDMPlayer>();
                    var pl = player.GetComponent<TDMPlayer>();
                    pl.team = Team.NONE;                foreach (var arena in Instance.arenas)
                    {
                        arena.ListPlayer?.RemoveAll(x => x.player.UserIDString == player.UserIDString);
                    }                p.Add(pl);
                    if (Instance.arenas[Instance.arenas.FindIndex(x => x.ID == name[0])].ListPlayer == null)
                        Instance.arenas[Instance.arenas.FindIndex(x => x.ID == name[0])].ListPlayer = p;
                    else
                        Instance.arenas[Instance.arenas.FindIndex(x => x.ID == name[0])].ListPlayer.Add(pl);
                }
            }
            else
            {
                string[] name = teleporter.info.ID.Split('_');
                if (Instance.arenas.FindIndex(x => x.ID == name[0]) != -1)
                {
                    List<TDMPlayer> p = new List<TDMPlayer>();
                    TDMPlayer pl;
                    if (player.gameObject.GetComponent<TDMPlayer>())
                    {
                        Destroy(player.gameObject.GetComponent<TDMPlayer>());
                    }                player.gameObject.AddComponent<TDMPlayer>();
                    if (name[1].Contains("team"))
                    {
                        pl = player.GetComponent<TDMPlayer>();
                        pl.team = name[1] == "teama" ? Team.A : Team.B;
                    }
                    else
                    {
                        pl = player.GetComponent<TDMPlayer>();
                        pl.team = Team.NONE;
                    }                foreach (var arena in Instance.arenas)
                    {
                        arena.ListPlayer?.RemoveAll(x => x.player.UserIDString == player.UserIDString);
                    }                p.Add(pl);
                    if (Instance.arenas[Instance.arenas.FindIndex(x => x.ID == name[0])].ListPlayer == null)
                        Instance.arenas[Instance.arenas.FindIndex(x => x.ID == name[0])].ListPlayer = p;
                    else
                        Instance.arenas[Instance.arenas.FindIndex(x => x.ID == name[0])].ListPlayer.Add(pl);
                }
            }        Instance.Teleport(player, otherPoint.Location.Vector3);
        }
    }
            private void SaveData()
            {
                Interface.Oxide.DataFileSystem.WriteObject($"{DataFileName}/CombatTag_Arena", arenas);
                Interface.Oxide.DataFileSystem.WriteObject($"{DataFileName}/CombatTag_Portals", portals);
            }
    Here my command
    Code:
            [ChatCommand("arena")]
            private void cmdTeleport(BasePlayer player, string cmd, string[] args)
            {
                if (!HasPerm(player.userID, "admin"))
                {
                    SendReply(player, GetMsg("No Permission"));
                    return;
                }            if (args.Length == 0)
                {
                    SendReply(player, "Syntax: /arena <create|lobby|teama|teamb|remove|list> <ID>");
                    return;
                }            string ID;
                Arena arena = null;            TeleporterInfo teleporter;
                switch (args[0].ToLower())
                {
                    case "create":                    if (args.Length != 2)
                        {
                            SendReply(player, "Syntax: /arena create <name>");
                            return;
                        }                    ID = args[1];                    if (arenas != null && arenas.Count != 0)
                        {
                            if (arenas.FindIndex(x => x.ID == ID) != -1)
                            {
                                arena = arenas[arenas.FindIndex(x => x.ID == ID)];
                            }
                            else
                            {
                                arena = new Arena(ID);
                                arenas.Add(arena);
                            }                    }
                        else
                        {
                            arena = new Arena(ID);
                            arenas.Add(arena);
                        }                    string msg = GetMsg("Arena Created").Replace("{ID}", args[1]);
                        msg = msg.Replace("{syntax}", "/arena lobby entrance " + args[1]);
                        SendReply(player, msg);
                        SaveData();
                        break;                case "lobby":                    if (args.Length != 3)
                        {
                            SendReply(player, "Syntax: /arena lobby <entrance|exit> <ID>");
                            return;
                        }                    ID = args[2];
                        if (arenas != null && arenas.Count != 0)
                        {
                            if (arenas.FindIndex(x => x.ID == ID) != -1)
                            {
                                arena = arenas[arenas.FindIndex(x => x.ID == ID)];
                            }
                            else
                            {
                                arena = new Arena(ID);
                                arenas.Add(arena);
                            }                    }
                        else
                        {
                            arena = new Arena(ID);
                            arenas.Add(arena);
                        }                    switch (args[1].ToLower())
                        {
                            case "entrance":
                                teleporter = TeleporterInfo.Find(ID + "_lobby");
                                if (teleporter == null)
                                {
                                    teleporter = new TeleporterInfo(ID + "_lobby");
                                    portals.Add(teleporter);
                                }                            teleporter.Entrance.Location.Vector3 = player.transform.position;
                                arena.Lobby = teleporter;
                                teleporter.Refresh();                            break;
                            case "exit":
                                teleporter = TeleporterInfo.Find(ID + "_lobby");
                                if (teleporter == null)
                                {
                                    teleporter = new TeleporterInfo(ID + "_lobby");
                                    portals.Add(teleporter);
                                }                            teleporter.Exit.Location.Vector3 = player.transform.position;
                                arena.Lobby = teleporter;
                                teleporter.Refresh();                            break;
                        }                    SaveData();
                        break;
                    case "teama":                    if (args.Length != 3)
                        {
                            SendReply(player, "Syntax: /arena teama <entrance|exit> <ID>");
                            return;
                        }                    ID = args[2];
                        if (arenas != null && arenas.Count != 0)
                        {
                            if (arenas.FindIndex(x => x.ID == ID) != -1)
                            {
                                arena = arenas[arenas.FindIndex(x => x.ID == ID)];
                            }
                            else
                            {
                                arena = new Arena(ID);
                                arenas.Add(arena);
                            }                    }
                        else
                        {
                            arena = new Arena(ID);
                            arenas.Add(arena);
                        }                    switch (args[1].ToLower())
                        {
                            case "entrance":
                                teleporter = TeleporterInfo.Find(ID + "_teama");
                                if (teleporter == null)
                                {
                                    teleporter = new TeleporterInfo(ID + "_teama");
                                    portals.Add(teleporter);
                                }                            teleporter.Entrance.Location.Vector3 = player.transform.position;
                                arena.TeamA = teleporter;
                                teleporter.Refresh();                            break;
                            case "exit":
                                teleporter = TeleporterInfo.Find(ID + "_teama");
                                if (teleporter == null)
                                {
                                    teleporter = new TeleporterInfo(ID + "_teama");
                                    portals.Add(teleporter);
                                }                            teleporter.Exit.Location.Vector3 = player.transform.position;
                                arena.TeamA = teleporter;
                                teleporter.Refresh();                            break;
                        }                    SaveData();
                        break;                case "teamb":                    if (args.Length != 3)
                        {
                            SendReply(player, "Syntax: /arena teamb <entrance|exit> <ID>");
                            return;
                        }                    ID = args[2];
                        if (arenas != null && arenas.Count != 0)
                        {
                            if (arenas.FindIndex(x => x.ID == ID) != -1)
                            {
                                arena = arenas[arenas.FindIndex(x => x.ID == ID)];
                            }
                            else
                            {
                                arena = new Arena(ID);
                                arenas.Add(arena);
                            }                    }
                        else
                        {
                            arena = new Arena(ID);
                            arenas.Add(arena);
                        }                    switch (args[1].ToLower())
                        {
                            case "entrance":
                                teleporter = TeleporterInfo.Find(ID + "_teamb");
                                if (teleporter == null)
                                {
                                    teleporter = new TeleporterInfo(ID + "_teamb");
                                    portals.Add(teleporter);
                                }                            teleporter.Entrance.Location.Vector3 = player.transform.position;
                                arena.TeamB = teleporter;
                                teleporter.Refresh();                            break;
                            case "exit":
                                teleporter = TeleporterInfo.Find(ID + "_teamb");
                                if (teleporter == null)
                                {
                                    teleporter = new TeleporterInfo(ID + "_teamb");
                                    portals.Add(teleporter);
                                }                            teleporter.Exit.Location.Vector3 = player.transform.position;
                                arena.TeamB = teleporter;
                                teleporter.Refresh();                            break;
                        }                    SaveData();
                        break;                case "remove":                    if (args.Length != 2)
                        {
                            SendReply(player, "Syntax: /arena remove <ID>");
                            return;
                        }                    ID = args[1];
                        if (arenas != null && arenas.Count != 0)
                        {
                            if (arenas.FindIndex(x => x.ID == ID) != -1)
                            {
                                arena = arenas[arenas.FindIndex(x => x.ID == ID)];
                            }
                        }                    if (arena == null)
                        {
                            SendReply(player, "This arena did not exist);
                            return;
                        }                    arenas.Remove(arena);                    SaveData();                    break;                case "detail":                    if (args.Length != 2)
                        {
                            SendReply(player, "Syntax: /arena detail <ID>");
                            return;
                        }                    ID = args[1];
                        if (arenas != null && arenas.Count != 0)
                        {
                            if (arenas.FindIndex(x => x.ID == ID) != -1)
                            {
                                arena = arenas[arenas.FindIndex(x => x.ID == ID)];
                                Puts(arena.ID + "\n");
                            }
                        }                    break;
                    case "save":
                        SaveData();
                        break;
                    default:                    SendReply(player, "Syntax: /arena <create|lobby|teama|teamb|remove|list> <ID>");                    break;
                }
            }
    
     
  2. Wulf

    Wulf Community Admin

    I believe it's Mono or Newtonsoft.Json issue, can't recall which. Basically has to do with DateTime.Now or ToLocalTime() last I recall; using DateTime.UtcNow or similar should work fine.
     
  3. Solved by removing public List<TDMPlayer> ListPlayer { get; set; } from my Arena class
    @Wulf can't find anymore the button to mark thread as solved