C#:
using System.Linq;
using System;
using System.Collections.Generic;
using System.Globalization;
using Newtonsoft.Json;
using Oxide.Core.Plugins;
using Oxide.Game.Rust.Cui;
using UnityEngine;
using Oxide.Core;
namespace Oxide.Plugins
{
[Info("Capsules", "Drop Dead", "1.0.0")]
public class Capsules : RustPlugin
{
[PluginReference] private Plugin ImageLibrary;
bool addday = false;
string Layer = "Capsules.Main";
public Dictionary<ulong, int> time = new Dictionary<ulong, int>();
public List<int> day = new List<int>();
public Dictionary<ulong, int> taked = new Dictionary<ulong, int>();
public List<ulong> openedui = new List<ulong>();
public class random
{
[JsonProperty("Шанс выпадения")]
public int chance;
[JsonProperty("Минимальное количество")]
public int min;
[JsonProperty("Максимальное количество")]
public int max;
}
public class Capsule
{
[JsonProperty("Время до открытия капсулы")]
public int time = 10;
[JsonProperty("Картинка капуслы")]
public string image = "https://i.imgur.com/6Clq50h.png";
[JsonProperty("Предметы которые могут выпасть при открытии", ObjectCreationHandling = ObjectCreationHandling.Replace)]
public Dictionary<string, random> itemsdrop = new Dictionary<string, random>
{
["sulfur"] = new random { chance = 100, min = 10, max = 50},
["metal.fragments"] = new random { chance = 50, min = 50, max = 150},
};
[JsonProperty("Команды могут выпасть при открытии, их шанс", ObjectCreationHandling = ObjectCreationHandling.Replace)]
public Dictionary<string, int> commands = new Dictionary<string, int>
{
["say %steamid%"] = 100,
["example"] = 50,
};
}
private PluginConfig cfg;
public class PluginConfig
{
[JsonProperty("Настройки капсул")]
public MainSettings settings = new MainSettings();
public class MainSettings
{
[JsonProperty("День капсулы, её настройки", ObjectCreationHandling = ObjectCreationHandling.Replace)]
public Dictionary<string, Capsule> capsules = new Dictionary<string, Capsule>()
{
["1"] = new Capsule(),
["2"] = new Capsule(),
["3"] = new Capsule(),
["4"] = new Capsule(),
["5"] = new Capsule(),
};
}
}
private void Init()
{
cfg = Config.ReadObject<PluginConfig>();
Config.WriteObject(cfg);
}
protected override void LoadDefaultConfig()
{
Config.WriteObject(new PluginConfig(), true);
}
private void SaveData()
{
Interface.Oxide.DataFileSystem.WriteObject($"{Title}/PlayersData", taked);
Interface.Oxide.DataFileSystem.WriteObject($"{Title}/Cooldown", time);
Interface.Oxide.DataFileSystem.WriteObject($"{Title}/Day", day);
}
private void LoadData()
{
if (Interface.Oxide.DataFileSystem.ExistsDatafile($"{Title}/PlayersData"))
taked = Interface.Oxide.DataFileSystem.ReadObject<Dictionary<ulong, int>>($"{Title}/PlayersData");
if (Interface.Oxide.DataFileSystem.ExistsDatafile($"{Title}/Cooldown"))
time = Interface.Oxide.DataFileSystem.ReadObject<Dictionary<ulong, int>>($"{Title}/Cooldown");
if (Interface.Oxide.DataFileSystem.ExistsDatafile($"{Title}/Day"))
day = Interface.Oxide.DataFileSystem.ReadObject<List<int>>($"{Title}/Day");
}
void OnServerInitialized()
{
if (!plugins.Exists("ImageLibrary"))
{
PrintError("ImageLibrary not found.Install it and reload plugin!");
return;
}
foreach (var capsule in cfg.settings.capsules)
{
ImageLibrary.Call("AddImage", capsule.Value.image, capsule.Value.image);
}
LoadData();
if (day.Count() < 1) day.Add(1);
SaveData();
if (BasePlayer.activePlayerList.Count > 0) foreach (var player in BasePlayer.activePlayerList) OnPlayerConnected(player);
InvokeHandler.Instance.InvokeRepeating(UpdateUI, 1f, 1f);
InvokeHandler.Instance.InvokeRepeating(UpdateTime, 60f, 60f);
}
void OnServerSave()
{
SaveData();
}
void Unload()
{
InvokeHandler.Instance.CancelInvoke(UpdateUI);
InvokeHandler.Instance.CancelInvoke(UpdateTime);
openedui.Clear();
foreach (var player in BasePlayer.activePlayerList) CuiHelper.DestroyUi(player, Layer);
SaveData();
}
void OnPlayerConnected(BasePlayer player)
{
if (player.IsReceivingSnapshot)
{
NextTick(() => OnPlayerConnected(player));
return;
}
if (!time.ContainsKey(player.userID)) time.Add(player.userID, 0);
}
int GetWipeDay()
{
if (day.Count > 0) return day[0];
else return 0;
}
bool Cooldown(BasePlayer player, int Day)
{
if (!time.ContainsKey(player.userID)) time.Add(player.userID, 0);
foreach (var i in cfg.settings.capsules)
{
if (Day.ToString() != i.Key) continue;
var cooldown = time[player.userID];
if (cooldown >= i.Value.time) return false;
}
return true;
}
int GetCooldown(BasePlayer player, int Day)
{
if (!time.ContainsKey(player.userID)) time.Add(player.userID, 0);
int amount = 0;
foreach (var i in cfg.settings.capsules)
{
if (Day.ToString() != i.Key) continue;
var cooldown = time[player.userID];
amount = i.Value.time - cooldown;
if (amount < 0) return 0;
}
return amount;
}
[ChatCommand("capsule")]
private void CapsulesCommand(BasePlayer player)
{
if (player == null) return;
DrawUI(player);
}
[ConsoleCommand("TakeCapsule")]
private void TakeCapsule(ConsoleSystem.Arg args)
{
BasePlayer player = args.Player();
if (player == null) return;
if (!args.HasArgs(1)) return;
var day = args.Args[0];
if (!Cooldown(player, int.Parse(day)));
if (taked.ContainsKey(player.userID) && taked[player.userID] >= int.Parse(day)) return;
foreach (var capsule in cfg.settings.capsules)
{
if (capsule.Key != day) continue;
foreach (var item in capsule.Value.itemsdrop)
{
if (UnityEngine.Random.Range(0, 100) < item.Value.chance)
{
var amount = Oxide.Core.Random.Range(item.Value.min, item.Value.max);
var newItem = ItemManager.CreateByName(item.Key, amount);
if (newItem == null) continue;
if (!player.inventory.GiveItem(newItem))
newItem.Drop(player.inventory.containerMain.dropPosition, player.inventory.containerMain.dropVelocity, new Quaternion());
}
}
foreach (var cmd in capsule.Value.commands)
{
if (UnityEngine.Random.Range(0, 100) < cmd.Value)
{
Server.Command(cmd.Key.Replace("%steamid%", player.UserIDString));
}
}
}
if (taked.ContainsKey(player.userID)) taked[player.userID] = int.Parse(day);
else taked.Add(player.userID, int.Parse(day));
var effect = new Effect("assets/prefabs/misc/xmas/presents/effects/unwrap.prefab", player, 0, Vector3.zero, Vector3.forward);
EffectNetwork.Send(effect, player.net.connection);
player.SendConsoleCommand("CloseUI");
}
[ConsoleCommand("CloseUI")]
private void CloseUI(ConsoleSystem.Arg args)
{
BasePlayer player = args.Player();
if (player == null) return;
if (openedui.Contains(player.userID)) openedui.Remove(player.userID);
CuiHelper.DestroyUi(player, Layer);
}
string GetText(BasePlayer player, int Day)
{
string text = "НЕДОСТУПНО";
if (GetWipeDay() == Day) text = "ДОСТУПНО";
if (GetWipeDay() != Day) text = "НЕДОСТУПНО";
if (Cooldown(player, Day) == true) text = "НЕДОСТУПНО";
if (GetCooldown(player, Day) >= 0 && Cooldown(player, Day) == true) text = "МОЖНО ОТКРЫТЬ ЧЕРЕЗ: " + TimeToString(GetCooldown(player, Day)).ToUpper();
if (taked.ContainsKey(player.userID) && taked[player.userID] >= Day) text = "ПОЛУЧЕНО";
return text;
}
void UpdateUI()
{
foreach (var player in BasePlayer.activePlayerList)
{
if (!time.ContainsKey(player.userID)) time.Add(player.userID, 0);
time[player.userID]++;
if (openedui.Contains(player.userID)) DrawUI(player);
}
}
void UpdateTime()
{
if (DateTime.UtcNow.AddHours(3).ToString("HH:mm") == "23:55")
{
if (day.Count > 0)
{
day[0]++;
//Puts("Started new day..");
time.Clear();
SaveData();
}
}
}
void DrawUI(BasePlayer player)
{
if (!openedui.Contains(player.userID)) openedui.Add(player.userID);
CuiHelper.DestroyUi(player, Layer);
var container = new CuiElementContainer();
container.Add(new CuiPanel
{
Image = { Color = "0 0 0 0.7" },
RectTransform = { AnchorMin = "0 0", AnchorMax = "1 1" },
CursorEnabled = true,
}, "Overlay", Layer);
container.Add(new CuiElement
{
Parent = Layer,
Components =
{
new CuiTextComponent { Text = "КАПСУЛЫ", Align = TextAnchor.MiddleCenter, FontSize = 45, Font = "RobotoCondensed-bold.ttf" },
new CuiRectTransformComponent {AnchorMin = "0 0.7370382", AnchorMax = "1 0.8092604"}
}
});
container.Add(new CuiElement
{
Parent = Layer,
Components =
{
new CuiTextComponent { Text = "Играйте на сервере и <b>гарантированно</b> получайте капсулы каждый день!", Align = TextAnchor.MiddleCenter, FontSize = 25, Font = "RobotoCondensed-regular.ttf" },
new CuiRectTransformComponent {AnchorMin = "0 0.7018541", AnchorMax = "1 0.7555578"}
}
});
container.Add(new CuiElement
{
Parent = Layer,
Components =
{
new CuiTextComponent { Text = "Чтобы закрыть это меню нажмите <b>по пустому</b> месту на экране", Align = TextAnchor.MiddleCenter, FontSize = 25, Font = "RobotoCondensed-regular.ttf" },
new CuiRectTransformComponent {AnchorMin = "0 0.2759336", AnchorMax = "1 0.329639"}
}
});
container.Add(new CuiButton
{
RectTransform = { AnchorMin = "0 0", AnchorMax = "1 1" },
Button = { Color = "0 0 0 0", Command = "CloseUI"},
Text = { Text = "" }
}, Layer);
const double startAnMinX = 0.1765623;
const double startAnMaxX = 0.3031229;
double anMinX = startAnMinX;
double anMaxX = startAnMaxX;
var dict = cfg.settings.capsules;
for (int i = 0; i < dict.Count(); i++)
{
var day = dict.Keys.ToList()[i];
var value = dict.Values.ToList()[i];
bool wipeday = GetWipeDay().ToString() == day;
bool cooldown = Cooldown(player, int.Parse(day));
container.Add(new CuiElement
{
Parent = Layer,
Name = Layer + day,
Components =
{
new CuiImageComponent {Color = "0 0 0 0"},
new CuiRectTransformComponent {
AnchorMin = $"{anMinX} 0.3666666",
AnchorMax = $"{anMaxX} 0.6694444" }
}
});
container.Add(new CuiElement
{
Parent = Layer + day,
Components =
{
new CuiRawImageComponent {Png = (string)ImageLibrary.Call("GetImage", value.image) },
new CuiRectTransformComponent {AnchorMin = "0.08912048 0.2577301", AnchorMax = "0.9121643 0.8693509"}
}
});
container.Add(new CuiElement
{
Parent = Layer + day,
Components =
{
new CuiTextComponent { Text = !wipeday ? "НЕДОСТУПНО" : GetText(player, int.Parse(day)), Align = TextAnchor.MiddleCenter, FontSize = 15, Font = "RobotoCondensed-regular.ttf" },
new CuiRectTransformComponent {AnchorMin = "0 0.01223265", AnchorMax = "1 0.2263"}
}
});
if (wipeday && !cooldown)
{
container.Add(new CuiButton
{
RectTransform = { AnchorMin = "0 0", AnchorMax = "1 1" },
Button = { Color = "0 0 0 0", Command = "TakeCapsule " + day },
Text = { Text = "" }
}, Layer + day);
}
anMinX += 0.1291671;
anMaxX += 0.129166;
}
CuiHelper.AddUi(player, container);
}
public string TimeToString(double time)
{
TimeSpan elapsedTime = TimeSpan.FromSeconds(time);
int hours = elapsedTime.Hours;
int minutes = elapsedTime.Minutes;
int seconds = elapsedTime.Seconds;
int days = Mathf.FloorToInt((float)elapsedTime.TotalDays);
string s = "";
if (days > 0) s += $"{days} дн.";
if (hours > 0) s += $"{hours} ч.";
if (minutes > 0) s += $"{minutes} мин.";
if (seconds >= 0) s += $"{seconds} сек.";
else s = s.TrimEnd(' ');
return s;
}
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);
throw new InvalidOperationException("Cannot convert a wrong format.");
}
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 string.Format("{0:F2} {1:F2} {2:F2} {3:F2}", color.r, color.g, color.b, color.a);
}
}
}