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

FREE TimedRewards : 1.2.5 1.2.5

Нет прав для скачивания
C#:
// Все права принадлежат дискорд сообществу https://discord.gg/VgNHPpNrz6
/*
 * https://github.com/DocValerian/rust-plugins
 * Copyright (C) 2022 DocValerian
 * 
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.* 
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.See the
 * GNU General Public License for more details.* 
 * You should have received a copy of the GNU General Public License
 * along with this program.If not, see <http://www.gnu.org/licenses/>.* 
 * Questions and Support can be found in our Discord: https://discord.gg/8tkBFRjg3W
 * 
 */

using System.Collections.Generic;
using Oxide.Core;
using Oxide.Core.Plugins;
using UnityEngine;
using System.Linq;
using System;
using Oxide.Game.Rust.Cui;
using Newtonsoft.Json;

namespace Oxide.Plugins
{
    [Info("TimedRewards", "DocValerian", "1.2.5")]
    class TimedRewards : RustPlugin
    {
        static TimedRewards Plugin;

        [PluginReference]
        private Plugin PlaytimeTracker, ZNExperience;

        const string permUse = "timedrewards.use";
        bool HasPermission(string id, string perm) => permission.UserHasPermission(id, perm);

        #region ConfigDataLoad
        protected override void LoadDefaultConfig()
        {
            Cfg = new ConfigFile();
            Puts("Loaded default configuration file");
        }
        protected override void SaveConfig() => Config.WriteObject(Cfg);
        protected override void LoadConfig()
        {
            base.LoadConfig();

            try
            {
                Cfg = Config.ReadObject<ConfigFile>();
            }
            catch (JsonException ex)
            {
                Puts(ex.Message);
                PrintError("Your config file contains errors!");
                return;
            }
            catch (Exception ex)
            {
                Puts(ex.Message);
                LoadDefaultConfig();
            }

            if (Cfg == null)
            {
                Puts("Config is null");
                LoadDefaultConfig();
            }

            SaveConfig();
        }

        static ConfigFile Cfg = new ConfigFile();
        class ConfigFile
        {
            [JsonProperty(PropertyName = "Reward Item:amount per minute playtime (max 6)")]
            public Dictionary<int, Dictionary<string, int>> MinuteRewardLists = new Dictionary<int, Dictionary<string, int>>() {
                [0] = new Dictionary<string, int>()
                {
                    ["blueberries"] = 5,
                    ["lowgradefuel"] = 10,
                    ["pookie.bear"] = 1,
                    ["wood"] = 5000
                },
                [30] = new Dictionary<string, int>()
                {
                    ["metal.refined"] = 50,
                    ["blueberries"] = 10,
                    ["generator.wind.scrap"] = 1,
                    ["metal.refined"] = 50,
                    ["blood"] = 2000
                },
                [60] = new Dictionary<string, int>()
                {
                    ["ammo.rifle"] = 200,
                    ["blueberries"] = 20,
                    ["targeting.computer"] = 6,
                    ["diesel_barrel"] = 20,
                    ["keycard_blue"] = 1
                },
                [120] = new Dictionary<string, int>()
                {
                    ["ammo.rocket.basic"] = 4,
                    ["blueberries"] = 20,
                    ["lowgradefuel"] = 300,
                    ["metal.fragments"] = 1500,
                    ["scrap"] = 1000,
                    ["supply.signal"] = 1
                },
                [240] = new Dictionary<string, int>()
                {
                    ["blueberries"] = 20,
                    ["targeting.computer"] = 10,
                    ["rifle.ak"] = 1,
                    ["metal.refined"] = 200,
                    ["supply.signal"] = 1,
                    ["sulfur"] = 2000
                },
                [480] = new Dictionary<string, int>()
                {
                    ["sticks"] = 500,
                    ["blueberries"] = 40,
                    ["blood"] = 3000,
                    ["metal.refined"] = 150,
                    ["supply.signal"] = 1,
                    ["explosive.timed"] = 5
                }
            };

            [JsonProperty(PropertyName = "Chat command aliases")]
            public string[] commandAliasList = { "dr", "daily" };
        }
        class StoredData
        {
            public DateTime currentDay = DateTime.Now;
            public Dictionary<ulong, double> PlayerDayStartTimes = new Dictionary<ulong, double>();
            public Dictionary<ulong, List<int>> PlayerClaimedRewards = new Dictionary<ulong, List<int>>();
        }

        StoredData storedData;

        private int highestRewardTime = 0;
        void Loaded()
        {
            Cfg = Config.ReadObject<ConfigFile>();
            Plugin = this;
            permission.RegisterPermission(permUse, this);

            storedData = Interface.Oxide.DataFileSystem.ReadObject<StoredData>("TimedRewards");
            SaveData();
            highestRewardTime = Cfg.MinuteRewardLists.Keys.Max();
            string[] commandAliases = Cfg.commandAliasList;
            foreach (string cmdAlias in commandAliases)
                cmd.AddChatCommand(cmdAlias, this, "CommandOpenUi");
        }
        void Unload()
        {
            SaveData();
            foreach (var player in UiPlayers.ToList())
            {
                killUI(player);
            }
        }
        private void OnServerInitialized()
        {
            if (!PlaytimeTracker)
            {
                Debug.LogError("[TimedRewards] Error! PlaytimeTracker not loaded! Please fix this error before loading TimedRewards again.Unloading...");
                Interface.Oxide.UnloadPlugin(this.Title);
                return;
            }
            ensureDayChange();
            // add starting playtime of the day to players
            foreach (var p in BasePlayer.activePlayerList)
            {
                addStartingPlaytime(p);
            }
            SaveData();
        }

        private void OnNewSave()
        {
            storedData = new StoredData();
            SaveData();
        }
        void SaveData()
        {
            Interface.Oxide.DataFileSystem.WriteObject("TimedRewards", storedData);
        }

        #endregion

        #region Hooks
        private void OnPlayerConnected(BasePlayer player)
        {
            ensureDayChange();
            //add playtime if first login of the day.addStartingPlaytime(player);
            SaveData();
        }
        void OnPlayerDisconnected(BasePlayer player)
        {
            killUI(player);
        }
        #endregion

        #region Commands

        [ConsoleCommand("timedrewards.close")]
        private void CmdClose(ConsoleSystem.Arg arg)
        {
            var player = arg.Connection.player as BasePlayer;
            if (player == null)
                return;
            killUI(player);
        }

        [ConsoleCommand("timedrewards.claim")]
        private void CmdClaim(ConsoleSystem.Arg arg)
        {
            var player = arg.Connection.player as BasePlayer;
            if (player == null || !HasPermission(arg.Player().UserIDString, permUse))
                return;
            int package = arg.GetInt(0);
            claimLoot(player, package);
            reloadUI(player);
        }


        void CommandOpenUi(BasePlayer player, string command, string[] args)
        {
            if (!permCheckVerbose(player, permUse)) return;
            ensureDayChange();
            reloadUI(player);
        }


        #endregion

        #region Functions
        private bool permCheckVerbose(BasePlayer player, string perm)
        {
            if (HasPermission(player.UserIDString, perm)) return true;
            SendReply(player, "No permission to use this command!");
            return false;
        }

        private void claimLoot(BasePlayer player, int package)
        {
            if (!Cfg.MinuteRewardLists.ContainsKey(package)) return;
            if (storedData.PlayerClaimedRewards.ContainsKey(player.userID))
            {
                if (storedData.PlayerClaimedRewards[player.userID].Contains(package))
                {
                    SendReply(player, "You already claimed the " + package + "min reward!");
                    return;
                }
            }
            else
            {
                storedData.PlayerClaimedRewards.Add(player.userID, new List<int>());
            }
            storedData.PlayerClaimedRewards[player.userID].Add(package);

            Item item;
            foreach (KeyValuePair<string, int> loot in Cfg.MinuteRewardLists[package])
            {
                    item = ItemManager.CreateByName(loot.Key, loot.Value);
                    player.GiveItem(item, BaseEntity.GiveItemReason.PickedUp);
            }
            SendReply(player, "You have claimed the " + package + "min reward!");
            SaveData();
        }

        private int getTodayPlayTime(BasePlayer player)
        {
            if (!storedData.PlayerDayStartTimes.ContainsKey(player.userID))
            {
                addStartingPlaytime(player);
                SaveData();
                return 0;
            }
            var playerTime = PlaytimeTracker?.Call("GetPlayTime", player.UserIDString);
            if (playerTime == null) return 0;

            double playTime = (double)playerTime - storedData.PlayerDayStartTimes[player.userID];

            return (int)Math.Floor(playTime);
        }

        private void addStartingPlaytime(BasePlayer player)
        {
            // add only if player didn't login sooner today
            if (storedData.PlayerDayStartTimes.ContainsKey(player.userID))
            {
                return;
            }

            var playerTime = PlaytimeTracker?.Call("GetPlayTime", player.UserIDString);
            if (playerTime == null)
            {
                storedData.PlayerDayStartTimes.Add(player.userID, 0.0d);
            }
            else
            {
                storedData.PlayerDayStartTimes.Add(player.userID, (double)playerTime);
            }
        }

        private void ensureDayChange()
        {
            // reset every calendar day
            if (storedData.currentDay.Day != DateTime.Now.Day)
            {
                Puts("INFO: Daily rewards reset");
                storedData = new StoredData();
                // add starting playtime of the day to players
                foreach (var p in BasePlayer.activePlayerList)
                {
                    addStartingPlaytime(p);
                }
                SaveData();
            }
        }
        #endregion

        #region GUI

        private const string globalNoErrorString = "none";
        private const string mainName = "TimedRewards";
        private HashSet<BasePlayer> UiPlayers = new HashSet<BasePlayer>();
        private string[] uiElements =
        {
            mainName+"_head",
            mainName+"_content",
            mainName+"_foot"
        };
        private float globalLeftBoundary = 0.1f;
        private float globalRighttBoundary = 0.9f;
        private float globalTopBoundary = 0.90f;
        private float globalBottomBoundary = 0.2f;
        private float globalSpace = 0.01f;
        private float eContentWidth = 0.395f;
        private float eHeadHeight = 0.05f;
        private float eFootHeight = 0.05f;
        private float eSlotHeight = 0.123f;


        private void reloadUI(BasePlayer player, string errorMsg = globalNoErrorString)
        {
            if (!UiPlayers.Contains(player))
            {
                UiPlayers.Add(player);
            }
            foreach (string ui in uiElements)
            {
                CuiHelper.DestroyUi(player, ui);
            }

            displayUI(player, errorMsg);

        }
        private void killUI(BasePlayer player)
        {
            if (UiPlayers.Contains(player))
            {
                UiPlayers.Remove(player);
                foreach (string ui in uiElements)
                {
                    CuiHelper.DestroyUi(player, ui);
                }
            }
        }

        private void displayUI(BasePlayer player, string errorMsg = globalNoErrorString)
        {
            GUIHeaderElement(player, mainName + "_head", errorMsg);
            GUIContentElement(player, mainName + "_content");
            GUIFooterElement(player, mainName + "_foot");
        }
        private void GUIHeaderElement(BasePlayer player, string elUiId, string errorMsg = globalNoErrorString)
        {
            var elements = new CuiElementContainer();
            elements.Add(new CuiPanel
            {
                Image =
                {
                    Color = "0 0 0 0.8",
                    Material = "assets/content/ui/uibackgroundblur-ingamemenu.mat"
                },
                RectTransform =
                {
                    AnchorMin = globalLeftBoundary  +" " + (globalTopBoundary-eHeadHeight),
                    AnchorMax = globalRighttBoundary + " " + globalTopBoundary
                },
                CursorEnabled = true
            }, "Hud", elUiId);

            TimeSpan untilMidnight = DateTime.Today.AddDays(1.0) - DateTime.Now;
            string stateText = "Daily Timed Rewards (Day reset in: " + untilMidnight.Hours + "h " + untilMidnight.Minutes + "min)";
            elements.Add(new CuiLabel
            {
                Text =
                {
                    Text = stateText,
                    FontSize = 18,
                    Align = TextAnchor.MiddleLeft,
                    Color = "1 1 1 1"
                },
                RectTransform =
                {
                    AnchorMin = "0.005 0.005",
                    AnchorMax = "0.995 0.995"
                }
            }, elUiId);

            elements.Add(new CuiLabel
            {
                Text =
                {
                    Text = "v" + Plugin.Version + " by " + Plugin.Author,
                    FontSize = 10,
                    Align = TextAnchor.MiddleRight,
                    Color = "1 1 1 1"
                },
                RectTransform =
                {
                    AnchorMin = "0.005 0.005",
                    AnchorMax = "0.995 0.995"
                }
            }, elUiId);

            if (errorMsg != "none")
            {
                elements.Add(new CuiLabel
                {
                    Text =
                    {
                        Text = "Error: "+ errorMsg,
                        FontSize = 18,
                        Align = TextAnchor.MiddleCenter,
                        Color = "1 0 0 1"
                    },
                    RectTransform =
                    {
                        AnchorMin = "0.005 0.005",
                        AnchorMax = "0.995 0.995"
                    }
                }, elUiId);
            }

            CuiHelper.AddUi(player, elements);
        }


        private void GUIContentElement(BasePlayer player, string elUiId)
        {

            var elements = new CuiElementContainer();
            elements.Add(new CuiPanel
            {
                Image =
                {
                    Color = "0 0 0 0.5",
                    Material = "assets/content/ui/uibackgroundblur-ingamemenu.mat"
                },
                RectTransform =
                {
                    AnchorMin = globalLeftBoundary + " " + (globalBottomBoundary+eHeadHeight+globalSpace),
                    AnchorMax = globalRighttBoundary + " " + (globalTopBoundary-eHeadHeight-globalSpace)
                },
                CursorEnabled = true
            }, "Hud", elUiId);

            int rewardCount = Cfg.MinuteRewardLists.Count();
            float localSpace = 0.005f;
            float localboxWidth = (1f / rewardCount) - 1.5f * localSpace;
            float localLeftBound = 1.5f * localSpace;
            float localRightBound = rewardCount * (localboxWidth + localSpace);
            float perMinuteWidth = 0.95f / highestRewardTime;
            float playerTime = (float)Math.Floor(getTodayPlayTime(player) / 60f);
            float localRewardTimeLine = 0;
            string rewardPanelName = "";
            float localLootRowTop = 0f;
            float localLootLeft = 0.01f;
            bool isEvenRow = true;

            elements.Add(new CuiLabel
            {
                Text =
                    {
                        Text = "Your daily (active) playtime: <color=lime>" + playerTime + " minutes</color> ",
                        FontSize = 18,
                        Align = TextAnchor.UpperLeft,
                        Color = "1 1 1 1"
                    },
                RectTransform =
                    {
                        AnchorMin = localLeftBound + " 0.85",
                        AnchorMax = (localRightBound) + " 0.95"
                    }
            }, elUiId);
            elements.Add(new CuiLabel
            {
                Text =
                    {
                        Text = "* Time is counted over all game sessions between midnight->midnight Server Time!",
                        FontSize = 10,
                        Align = TextAnchor.UpperRight,
                        Color = "1 1 1 1"
                    },
                RectTransform =
                    {
                        AnchorMin = localLeftBound + " 0.85",
                        AnchorMax = (localRightBound) + " 0.95"
                    }
            }, elUiId);
            // for visualization, we need to cap that value
            if (playerTime > highestRewardTime) playerTime = highestRewardTime;


            elements.Add(new CuiPanel
            {
                Image =
                {
                    Color = "0 0 0 0.9",
                },
                RectTransform =
                {
                    AnchorMin = localLeftBound + " 0.74",
                    AnchorMax = (localRightBound) + " 0.84"
                },
                CursorEnabled = true
            }, elUiId, elUiId + "_bar");


            elements.Add(new CuiPanel
            {
                Image =
                {
                    Color = "0.5 0.8 0.0 0.9",
                },
                RectTransform =
                {
                    AnchorMin = "0.004 0.1",
                    AnchorMax = playerTime*perMinuteWidth + " 0.9"
                },
                CursorEnabled = true
            }, elUiId + "_bar", elUiId + "_bar_fill");

            foreach (KeyValuePair<int, Dictionary<string, int>> reward in Cfg.MinuteRewardLists.OrderBy(x => x.Key))
            {

                // the loading bar elements
                localRewardTimeLine = (reward.Key * perMinuteWidth);
                if (localRewardTimeLine == 0) localRewardTimeLine = 0.004f;
                elements.Add(new CuiPanel
                {
                    Image =
                {
                    Color = "1 1 1 0.9",
                },
                    RectTransform =
                {
                    AnchorMin = localRewardTimeLine + " 0.1",
                    AnchorMax = (localRewardTimeLine+0.001) + " 0.9"
                },
                    CursorEnabled = true
                }, elUiId + "_bar", elUiId + "_bar_line_" + reward.Key);
                elements.Add(new CuiLabel
                {
                    Text =
                    {
                        Text = reward.Key +"min",
                        FontSize = 11,
                        Align = TextAnchor.UpperLeft,
                        Color = "1 1 1 1"
                    },
                    RectTransform =
                    {
                        AnchorMin = (localRewardTimeLine+0.003) + " 0.1",
                        AnchorMax = (localRewardTimeLine+0.1) + " 0.9"
                    }
                }, elUiId + "_bar");


                // the loot panels
                rewardPanelName = elUiId + "r_" + reward.Key;
                elements.Add(new CuiPanel
                {
                    Image =
                {
                    Color = "0 0 0 0.7",
                },
                    RectTransform =
                {
                    AnchorMin = localLeftBound + " 0.01",
                    AnchorMax = (localLeftBound+localboxWidth) +" 0.7"
                },
                    CursorEnabled = true
                }, elUiId, rewardPanelName);

                elements.Add(new CuiLabel
                {
                    Text =
                    {
                        Text = "Reward for " + reward.Key +"min",
                        FontSize = 14,
                        Align = TextAnchor.MiddleLeft,
                        Color = "1 1 1 1"
                    },
                    RectTransform =
                    {
                        AnchorMin = "0.05 0.9",
                        AnchorMax = "1 0.995"
                    }
                }, rewardPanelName);

                //loot preview
                localLootRowTop = 0.89f;
                isEvenRow = true;
                foreach (KeyValuePair<string, int> loot in reward.Value)
                {
                    if (isEvenRow)
                    {
                        localLootLeft = 0.01f;
                        isEvenRow = false;
                    }
                    else
                    {
                        localLootLeft = 0.5f;
                        isEvenRow = true;
                    }
                    CuiRawImageComponent img;
                    elements.Add(new CuiElement
                    {
                        Name = CuiHelper.GetGuid(),
                        Parent = rewardPanelName,
                        Components =
                        {
                            new CuiRectTransformComponent {
                                AnchorMin = localLootLeft +" "+ (localLootRowTop-0.20f),
                                AnchorMax = (localLootLeft + 0.35f) + " " + localLootRowTop
                            },
                            new CuiImageComponent { ItemId = ItemManager.itemDictionaryByName[loot.Key].itemid }
                        }
                    });
                    elements.Add(new CuiLabel
                    {
                        Text =
                        {
                            Text = "x" + loot.Value,
                            FontSize = 10,
                            Align = TextAnchor.LowerRight,
                            Color = "1 1 1 1"
                        },
                        RectTransform =
                        {
                            AnchorMin = localLootLeft +" "+ (localLootRowTop-0.20f),
                            AnchorMax = (localLootLeft + 0.35f) + " " + localLootRowTop
                        }
                    }, rewardPanelName);

                    if(isEvenRow) localLootRowTop -= 0.25f;
                }

                // claiming button

                // already claimed!
                if(storedData.PlayerClaimedRewards.ContainsKey(player.userID) && storedData.PlayerClaimedRewards[player.userID].Contains(reward.Key))
                {
                    elements.Add(new CuiLabel
                    {
                        Text =
                    {
                        Text = "claimed",
                        FontSize = 14,
                        Align = TextAnchor.MiddleCenter,
                        Color = "0.5 0.8 0.0 1"
                    },
                        RectTransform =
                    {
                        AnchorMin = "0.05 0.01",
                        AnchorMax = "0.95 0.1"
                    }
                    }, rewardPanelName);

                }
                // not unlocked
                else if(playerTime < reward.Key)
                {
                    elements.Add(new CuiLabel
                    {
                        Text =
                    {
                        Text = "unlocked in " + (int)Math.Ceiling(reward.Key-playerTime) +"min",
                        FontSize = 14,
                        Align = TextAnchor.MiddleCenter,
                        Color = "1 1 1 1"
                    },
                        RectTransform =
                    {
                        AnchorMin = "0.05 0.01",
                        AnchorMax = "0.95 0.1"
                    }
                    }, rewardPanelName);
                }
                // allow claiming
                else
                {
                    var claimButton = new CuiButton
                    {
                        Button =
                        {
                            Command = "timedrewards.claim " + reward.Key,
                            Color = "0.5 0.8 0.0 1"
                        },
                        RectTransform =
                        {
                            AnchorMin = "0.05 0.01",
                            AnchorMax = "0.95 0.1"
                        },
                        Text =
                        {
                            Text = "Claim!",
                            FontSize = 12,
                            Align = TextAnchor.MiddleCenter,
                            Color = "1 1 1 1"
                        }
                    };
                    elements.Add(claimButton, rewardPanelName);
                }

                localLeftBound = localLeftBound + localboxWidth + localSpace;

            }


            CuiHelper.AddUi(player, elements);
        }

        private void GUIFooterElement(BasePlayer player, string elUiId)
        {

            var elements = new CuiElementContainer();
            elements.Add(new CuiPanel
            {
                Image =
                {
                    Color = "0 0 0 0.5",
                    Material = "assets/content/ui/uibackgroundblur-ingamemenu.mat"
                },
                RectTransform =
                {
                    AnchorMin = globalLeftBoundary + " " + globalBottomBoundary,
                    AnchorMax = globalRighttBoundary + " " + (globalBottomBoundary+eFootHeight)
                },
                CursorEnabled = true
            }, "Hud", elUiId);

            var closeButton = new CuiButton
            {
                Button =
                {
                    Command = "timedrewards.close",
                    Color = "0.56 0.12 0.12 1"
                },
                RectTransform =
                {
                    AnchorMin = "0 0",
                    AnchorMax = "1 1"
                },
                Text =
                {
                    Text = "CLOSE",
                    FontSize = 12,
                    Align = TextAnchor.MiddleCenter,
                    Color = "1 1 1 1"
                }
            };
            elements.Add(closeButton, elUiId);

            CuiHelper.AddUi(player, elements);
        }

        #endregion

    }
}

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