Иконка ресурса

FREE Medal : 1.0.8 1.0.8

Нет прав для скачивания
C#:
// Все права принадлежат дискорд сообществу https://discord.gg/VgNHPpNrz6
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Text.RegularExpressions;
using Newtonsoft.Json;
using Oxide.Core;
using Oxide.Core.Libraries;
using Oxide.Core.Plugins;
using Oxide.Game.Rust.Cui;
using UnityEngine;

namespace Oxide.Plugins
{
    [Info("Medal", "Kira", "1.0.8")]
    [Description("Uniq medal for Rust server")]
    public class Medal : RustPlugin
    {
        #region [Vars]

#pragma warning disable CS0649
        [PluginReference] private Plugin ImageLibrary;
#pragma warning restore CS0649
        private static Medal _;
        private MedalCore medal;
        private WipeCore wipe;
        private StoredData _dataBase = new StoredData();
        private bool IsWipe;
        private const string GenericPrefab = "assets/prefabs/deployable/vendingmachine/vending_mapmarker.prefab";
        private const string UIMain = "UI.Medal";

        #endregion

        #region [Configuration] / [Конфигурация]

        private static ConfigData _config;

        public class ConfigData
        {
            [JsonProperty(PropertyName = "Medal [Configuration]")]
            public MedalConfig MedalCfg = new MedalConfig();

            public class MedalConfig
            {
                [JsonProperty(PropertyName = "Название медали")]
                public string MarkerName;

                [JsonProperty(PropertyName = "SkinID медали")]
                public ulong SkinID;

                [JsonProperty(PropertyName = "Задний фон уведомления о победителе (URL)")]
                public string Image;

                [JsonProperty(PropertyName = "Цвет текста (HEX)")]
                public string Color;

                [JsonProperty(PropertyName = "Размер текста (HEX)")]
                public int Size;

                [JsonProperty(PropertyName = "Частота обновления (От данной настрокий зависит нагрузка)")]
                public float UpdateTime;

                [JsonProperty(PropertyName = "Вайп (День недели от 1 до 7)")]
                public DayOfWeek WipeDay;

                [JsonProperty(PropertyName = "Вайп (Время дня от 0 до 24)")]
                public int WipeHour;

                [JsonProperty(PropertyName = "Автовайп (Вкл/Выкл)")]
                public bool AutoWipe;

                [JsonProperty(PropertyName = "Discord WebHook")]
                public string DiscordHook;
            }
        }

        private static ConfigData GetDefaultConfig()
        {
            return new ConfigData
            {
                MedalCfg = new ConfigData.MedalConfig
                {
                    MarkerName = "Medal",
                    SkinID = 1,
                    Image = "https://i.imgur.com/TaPCCcP.png",
                    Size = 15,
                    Color = "#3b3d45",
                    UpdateTime = 60,
                    WipeDay = DayOfWeek.Tuesday,
                    WipeHour = 20,
                    AutoWipe = true
                }
            };
        }

        protected override void LoadConfig()
        {
            base.LoadConfig();

            try
            {
                _config = Config.ReadObject<ConfigData>();
            }
            catch
            {
                LoadDefaultConfig();
            }

            SaveConfig();
        }

        protected override void LoadDefaultConfig()
        {
            PrintError("The config file is corrupted (or does not exist), a new one was created!");
            _config = GetDefaultConfig();
        }

        protected override void SaveConfig()
        {
            Config.WriteObject(_config);
        }

        #endregion

        #region [Lang]

        protected override void LoadDefaultMessages()
        {
            var ru = new Dictionary<string, string>
            {
                ["WINNER"] = "Вы выиграли",
                ["MEDAL_PICKUP"] = "Медаль была найдена !!",
                ["MEDAL_PUT_IN_CUP"] = "Медаль положена в шкаф на базе!!!",
                ["MEDAL_PICKUP_CUP"] = "Медаль изъята из шкафа базы"
            };

            var en = new Dictionary<string, string>
            {
                ["WINNER"] = "You WIN",
                ["MEDAL_PICKUP"] = "Медаль была найдена !!",
                ["MEDAL_PUT_IN_CUP"] = "Медаль положена в шкаф на базе!!!",
                ["MEDAL_PICKUP_CUP"] = "Медаль изъята из шкафа базы"
            };
            lang.RegisterMessages(ru, this, "ru");
            lang.RegisterMessages(en, this);
        }

        #endregion

        #region [MonoBehaviour]

        public class WipeCore : MonoBehaviour
        {
            private void Awake()
            {
                InvokeRepeating(nameof(Timer), 1f, 1f);
            }

            public void Timer()
            {
                if (DateTime.Now.DayOfWeek != _config.MedalCfg.WipeDay) return;
                if (DateTime.Now.Hour != _config.MedalCfg.WipeHour) return;
                if (_.IsWipe) return;
                _.IsWipe = true;
                _.Wipe();
            }
        }

        public class MedalCore : MonoBehaviour
        {
            public BaseEntity Container;
            public BuildingPrivlidge Cupboard;
            private VendingMachineMapMarker Marker;
            private Dictionary<ulong, int> Players = new Dictionary<ulong, int>();
            public Vector3 Position = _._dataBase.CurrentPos;
            public ulong Owner;
            public int Time;

            private void Start()
            {
                if (_._dataBase.MedalList != null | _._dataBase.MedalList.Count > 1) Players = _._dataBase.MedalList;
                if (_._dataBase.CurrentOwner != 0)
                {
                    var ent = (BaseEntity) BaseNetworkable.serverEntities.entityList[_._dataBase.CurrentOwner];
                    SwitchOwner(ent);
                }

                InvokeRepeating(nameof(Timer), _config.MedalCfg.UpdateTime, _config.MedalCfg.UpdateTime);
            }

            private void CreateMarker()
            {
                Marker = GameManager.server.CreateEntity(GenericPrefab, Position).GetComponent<VendingMachineMapMarker>();
                Marker.markerShopName = _config.MedalCfg.MarkerName;
                Marker.enableSaving = false;
                Marker.Spawn();
            }

            public void CheckInList(ulong player)  
            {
                if (player == 0) return;
                if (Players.ContainsKey(player)) return;
                // if (Players.Count < 1)
                //     foreach (var obj in BasePlayer.activePlayerList)
                //         obj.ChatMessage(_.lang.GetMessage("MEDAL_PICKUP", _, obj.UserIDString));
                Players.Add(player, Time);
            }

            private void UpdateMarker()
            {
                if (Container == null) return;
                Marker.transform.position = Container.GetNetworkPosition();
                Marker.SendNetworkUpdate();
            }

            public void SwitchOwner(BaseEntity ent)
            {
                if (ent == null) return;
                Owner = ent.ToPlayer() != null ? ((BasePlayer) ent).userID : ent.OwnerID;
                if (Owner == 0) return;
                Position = _._dataBase.CurrentPos;
                // var admin = BasePlayer.FindByID(Owner);
                // if (admin != null)
                //     if (admin.IsAdmin)
                //         return;
                CheckInList(Owner);
                if (Marker == null) CreateMarker();
                Container = ent;
                Time = Players[Owner];
                _._dataBase.CurrentOwner = ent.net.ID;
                _._dataBase.CurrentPos = ent.GetNetworkPosition();

                _.SaveData();
            }

            public void Timer()
            {
                if (Owner == 0) return;
                if (Container == null) return;
                CheckInList(Owner);
                UpdateMarker();
                if (!(Container is BuildingPrivlidge)) return;
                Time++;
                Cupboard = Container as BuildingPrivlidge;
                foreach (var player in Cupboard.authorizedPlayers)
                {
                    CheckInList(player.userid);
                    Players[player.userid] = Time;
                }
            }

            private void OnDestroy()
            {
                _._dataBase.MedalList = Players;
                if (Marker != null) Marker.Kill();
            }
        }

        #endregion

        #region [DrawUI] / [Отрисовка UI]

        private void DrawUI_Alert(BasePlayer player)
        {
            var ui = new CuiElementContainer
            {
                {
                    new CuiPanel
                    {
                        CursorEnabled = true,
                        Image =
                        {
                            Color = "0 0 0 0"
                        },
                        RectTransform =
                        {
                            AnchorMin = "0 0",
                            AnchorMax = "1 1"
                        }
                    },
                    "Overlay", UIMain
                },
                new CuiElement
                {
                    Name = $"{UIMain}.Background",
                    Parent = UIMain,
                    Components =
                    {
                        new CuiRawImageComponent
                        {
                            Png = GetImage($"{UIMain}.Background")
                        },
                        new CuiRectTransformComponent
                        {
                            AnchorMin = "0.3666667 0.3814815",
                            AnchorMax = "0.6333333 0.6185185"
                        }
                    }
                }
            };


            ui.Add(new CuiLabel
            {
                Text =
                {
                    Align = TextAnchor.MiddleCenter,
                    Color = HexToRustFormat(_config.MedalCfg.Color),
                    FadeIn = 1f,
                    FontSize = _config.MedalCfg.Size,
                    Text = lang.GetMessage("WINNER", this, player.UserIDString)
                },
                RectTransform =
                {
                    AnchorMin = "0 0",
                    AnchorMax = "1 1"
                }
            }, $"{UIMain}.Background");

            ui.Add(new CuiButton
            {
                Button =
                {
                    Close = UIMain,
                    Color = "0 0 0 0"
                },
                Text = {Text = " "},
                RectTransform =
                {
                    AnchorMin = "0 0",
                    AnchorMax = "1 1"
                }
            }, UIMain);

            CuiHelper.DestroyUi(player, UIMain);
            CuiHelper.AddUi(player, ui);
        }

        #endregion

        #region [Hooks]

        // ReSharper disable once UnusedMember.Local
        private void OnServerSave()
        {
            timer.Once(5f, SaveData);
        }

        // ReSharper disable once UnusedMember.Local
        private void OnServerInitialized()
        {
            LoadData();
            ImageLibrary.Call("AddImage", _config.MedalCfg.Image, $"{UIMain}.Background");
            _ = this;
            medal = ServerMgr.Instance.gameObject.AddComponent<MedalCore>();
            if (_config.MedalCfg.AutoWipe) wipe = ServerMgr.Instance.gameObject.AddComponent<WipeCore>();
        }

        // ReSharper disable once UnusedMember.Local  
        private void Unload()
        {
            SaveData();
            if (medal != null) UnityEngine.Object.Destroy(medal);
            if (wipe != null) UnityEngine.Object.Destroy(wipe);
        }

        // ReSharper disable once UnusedMember.Local
        private void OnItemAddedToContainer(ItemContainer container, Item item)
        {
            if (item.skin != _config.MedalCfg.SkinID) return;
            if (container.entityOwner == null) medal.SwitchOwner(container.playerOwner);
            if (container.playerOwner != null) return;
            medal.SwitchOwner(container.entityOwner);
            if (!(container.entityOwner is BuildingPrivlidge)) return;
            foreach (var player in BasePlayer.activePlayerList)
                player.ChatMessage(lang.GetMessage("MEDAL_PUT_IN_CUP", this, player.UserIDString));
            
        }

        // ReSharper disable once UnusedMember.Local
        private object CanMoveItem(Item item)
        {
            if (item.skin != _config.MedalCfg.SkinID) return null;
            if (item.GetRootContainer() == null) return null;
            if (!(item.GetRootContainer().entityOwner is BuildingPrivlidge)) return null;
            foreach (var player in BasePlayer.activePlayerList)
                player.ChatMessage(lang.GetMessage("MEDAL_PICKUP_CUP", this, player.UserIDString));
            return null;
        }

        // ReSharper disable once UnusedMember.Local
        private void OnItemDropped(Item item, BaseEntity entity)
        {
            if (item.skin != _config.MedalCfg.SkinID) return;
            if (entity == null) return;
            medal.SwitchOwner(entity);
        }

        private string GetImage(string name)
        {
            return (string) ImageLibrary.Call("GetImage", name);
        }

        #endregion

        #region [Commands]

        [ChatCommand("medal")]
        // ReSharper disable once UnusedMember.Local
        private void GiveMedal(BasePlayer player)
        {
            if (!player.IsAdmin) return;
            var item = ItemManager.CreateByName("dogtagneutral");
            item.skin = _config.MedalCfg.SkinID;
            player.GiveItem(item);
        }

        #endregion

        #region [DataBase] / [База данных]

        private void Wipe()
        {
            if (_dataBase.MedalList.Count > 0) return;
            var winner = _dataBase.MedalList.OrderBy(x => x.Value).ToList();
            if (winner.Count < 1) return;
            var id = winner[0].Key;
            _dataBase.MedalList.Clear();
            _dataBase.CurrentOwner = 0;
            SaveData();
            var player = BasePlayer.FindByID(id);
            if (player != null) DrawUI_Alert(player);
            SendDiscordMessage(id.ToString());
            PrintWarning($"Winner : {id}");
        }

        private class StoredData
        {
            public uint CurrentOwner;
            public Vector3 CurrentPos;
            public Dictionary<ulong, int> MedalList = new Dictionary<ulong, int>();
        }

        private void SaveData() => Interface.Oxide.DataFileSystem.WriteObject(Name, _dataBase);

        private void LoadData()
        {
            try
            {
                _dataBase = Interface.GetMod().DataFileSystem.ReadObject<StoredData>(Name);
            }
            catch (Exception)
            {
                _dataBase = new StoredData();
            }
        }

        #endregion

        #region [Helpers] / [Вспомогательный код]

        private class DiscordMessage
        {
            public DiscordMessage(string content, params Embed[] embeds)
            {
                Content = content;
                Embeds = embeds.ToList();
            }

            // ReSharper disable once UnusedAutoPropertyAccessor.Local
            // ReSharper disable once AutoPropertyCanBeMadeGetOnly.Local
            [JsonProperty("content")] private string Content { get; set; }

            // ReSharper disable once UnusedAutoPropertyAccessor.Local
            // ReSharper disable once AutoPropertyCanBeMadeGetOnly.Local
            [JsonProperty("embeds")] private List<Embed> Embeds { get; set; }

            public string ToJson()
            {
                return JsonConvert.SerializeObject(this);
            }
        }

        private class Embed
        {
            // ReSharper disable once AutoPropertyCanBeMadeGetOnly.Local
            // ReSharper disable once CollectionNeverQueried.Local
            [JsonProperty("fields")] private List<Field> Fields { get; set; } = new List<Field>();

            public Embed AddField(string name, string value, bool inline)
            {
                Fields.Add(new Field(name, Regex.Replace(value, "<.*?>", string.Empty), inline));

                return this;
            }
        }

        private class Field
        {
            public Field(string name, string value, bool inline)
            {
                Name = name;
                Value = value;
                Inline = inline;
            }

            // ReSharper disable once UnusedAutoPropertyAccessor.Local
            // ReSharper disable once AutoPropertyCanBeMadeGetOnly.Local
            [JsonProperty("name")] private string Name { get; set; }

            // ReSharper disable once UnusedAutoPropertyAccessor.Local
            // ReSharper disable once AutoPropertyCanBeMadeGetOnly.Local
            [JsonProperty("value")] private string Value { get; set; }

            // ReSharper disable once UnusedAutoPropertyAccessor.Local
            // ReSharper disable once AutoPropertyCanBeMadeGetOnly.Local
            [JsonProperty("inline")] private bool Inline { get; set; }
        }

        private void SendDiscordMessage(string id)
        {
            var embed = new Embed().AddField("Winner ID:", id, true);

            webrequest.Enqueue(_config.MedalCfg.DiscordHook, new DiscordMessage("", embed).ToJson(),
                (code, response) => { },
                this,
                RequestMethod.POST, new Dictionary<string, string>
                {
                    {"Content-Type", "application/json"}
                });
        }

        private static string HexToRustFormat(string hex)
        {
            if (string.IsNullOrEmpty(hex))
            {
                hex = "#FFFFFFFF";
            }

            var str = hex.Trim('#');
            if (str.Length == 6)
                str += "FF";
            if (str.Length != 8)
            {
                throw new Exception(hex);
            }

            var r = byte.Parse(str.Substring(0, 2), NumberStyles.HexNumber);
            var g = byte.Parse(str.Substring(2, 2), NumberStyles.HexNumber);
            var b = byte.Parse(str.Substring(4, 2), NumberStyles.HexNumber);
            var a = byte.Parse(str.Substring(6, 2), NumberStyles.HexNumber);

            Color color = new Color32(r, g, b, a);
            return $"{color.r:F2} {color.g:F2} {color.b:F2} {color.a:F2}";
        }

        #endregion
    }
}

Автор
15FPS
Скачиваний
0
Просмотры
1
Первый выпуск
Обновление
Оценка
0.00 звёзд 0 оценок
Сверху