Initial Deployment
This commit is contained in:
commit
66e385b6f5
363
ClaimPlayerRewards.cs
Normal file
363
ClaimPlayerRewards.cs
Normal file
@ -0,0 +1,363 @@
|
|||||||
|
using Oxide.Core.Plugins;
|
||||||
|
using Oxide.Core;
|
||||||
|
using Newtonsoft.Json;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
|
using UnityEngine;
|
||||||
|
using System;
|
||||||
|
using System.Globalization;
|
||||||
|
|
||||||
|
namespace Oxide.Plugins
|
||||||
|
{
|
||||||
|
[Info("Claim Player Rewards", "rustysats", "0.1.0")]
|
||||||
|
[Description("Allows players to claim rewards based on a JSON configuration file and logs claims.")]
|
||||||
|
|
||||||
|
public class ClaimPlayerRewards : RustPlugin
|
||||||
|
{
|
||||||
|
// Configurable parameters
|
||||||
|
private ConfigData config;
|
||||||
|
|
||||||
|
// Path to your JSON configuration files within a subfolder
|
||||||
|
private const string DataFolderPath = "oxide/data/ClaimPlayerRewards/";
|
||||||
|
private const string ConfigFilePath = DataFolderPath + "ClaimPlayerRewards.json";
|
||||||
|
private const string ClaimedRewardsFilePath = DataFolderPath + "ClaimedRewards.json";
|
||||||
|
|
||||||
|
// Permission name for using the claim command
|
||||||
|
private const string PermissionClaim = "claimplayerrewards.use";
|
||||||
|
|
||||||
|
// Data managers
|
||||||
|
private RewardDataManager rewardDataManager;
|
||||||
|
private ClaimDataManager claimDataManager;
|
||||||
|
|
||||||
|
// Configurable data structure
|
||||||
|
private class ConfigData
|
||||||
|
{
|
||||||
|
public string RewardItem { get; set; } = "blood"; // Default reward item
|
||||||
|
public ulong RewardSkinID { get; set; } = 0; // Default skin ID (0 means no skin)
|
||||||
|
}
|
||||||
|
|
||||||
|
void Init()
|
||||||
|
{
|
||||||
|
// Register the permission
|
||||||
|
permission.RegisterPermission(PermissionClaim, this);
|
||||||
|
|
||||||
|
// Ensure the data directory exists
|
||||||
|
if (!Directory.Exists(DataFolderPath))
|
||||||
|
{
|
||||||
|
Directory.CreateDirectory(DataFolderPath);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Load the configuration
|
||||||
|
LoadConfig();
|
||||||
|
|
||||||
|
// Initialize data managers
|
||||||
|
rewardDataManager = new RewardDataManager(ConfigFilePath, this);
|
||||||
|
claimDataManager = new ClaimDataManager(ClaimedRewardsFilePath, this);
|
||||||
|
|
||||||
|
// Load reward data from JSON file when the plugin initializes
|
||||||
|
rewardDataManager.LoadRewardData();
|
||||||
|
|
||||||
|
// Load claims data from JSON file when the plugin initializes
|
||||||
|
claimDataManager.LoadClaimedRewards();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Load plugin configuration and ensure defaults are saved if config is empty or missing
|
||||||
|
protected override void LoadDefaultConfig()
|
||||||
|
{
|
||||||
|
PrintWarning("Generating new configuration file...");
|
||||||
|
config = new ConfigData();
|
||||||
|
SaveConfig();
|
||||||
|
}
|
||||||
|
|
||||||
|
private new void LoadConfig()
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
config = Config.ReadObject<ConfigData>();
|
||||||
|
if (config == null)
|
||||||
|
{
|
||||||
|
PrintWarning("Config file was empty, creating new defaults...");
|
||||||
|
LoadDefaultConfig();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (IOException e)
|
||||||
|
{
|
||||||
|
PrintWarning($"IO error loading config: {e.Message}, generating default config...");
|
||||||
|
LoadDefaultConfig();
|
||||||
|
}
|
||||||
|
catch (JsonException e)
|
||||||
|
{
|
||||||
|
PrintWarning($"JSON error loading config: {e.Message}, generating default config...");
|
||||||
|
LoadDefaultConfig();
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
PrintWarning($"Unexpected error loading config: {e.Message}, generating default config...");
|
||||||
|
throw; // Rethrow the exception
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void SaveConfig()
|
||||||
|
{
|
||||||
|
Config.WriteObject(config, true); // Save with indentation for readability
|
||||||
|
PrintWarning("Configuration saved successfully.");
|
||||||
|
}
|
||||||
|
|
||||||
|
[ChatCommand("claim")]
|
||||||
|
private void ClaimCommand(BasePlayer player, string command, string[] args)
|
||||||
|
{
|
||||||
|
// Check if the player has permission
|
||||||
|
if (!permission.UserHasPermission(player.UserIDString, PermissionClaim))
|
||||||
|
{
|
||||||
|
SendReply(player, Lang("NoPermission", player.UserIDString));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
string playerSteamId = player.UserIDString;
|
||||||
|
|
||||||
|
if (rewardDataManager.HasReward(playerSteamId))
|
||||||
|
{
|
||||||
|
int amountToGive = rewardDataManager.GetRewardAmount(playerSteamId);
|
||||||
|
// Use the configured reward item and skin ID
|
||||||
|
GiveItem(player, config.RewardItem, amountToGive, config.RewardSkinID);
|
||||||
|
|
||||||
|
// Log the claim
|
||||||
|
claimDataManager.LogClaim(playerSteamId, amountToGive);
|
||||||
|
|
||||||
|
// Remove the player's entry from the rewardData after claiming
|
||||||
|
rewardDataManager.RemoveReward(playerSteamId);
|
||||||
|
|
||||||
|
SendReply(player, Lang("ClaimSuccess", player.UserIDString, amountToGive, config.RewardItem));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
SendReply(player, Lang("NothingToClaim", player.UserIDString));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void GiveItem(BasePlayer player, string itemShortName, int amount, ulong skinId)
|
||||||
|
{
|
||||||
|
// This function gives the specified item to the player with the defined skin ID
|
||||||
|
Item item = ItemManager.CreateByName(itemShortName, amount, skinId);
|
||||||
|
if (item != null)
|
||||||
|
{
|
||||||
|
player.GiveItem(item);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Localization with Lang API
|
||||||
|
protected override void LoadDefaultMessages()
|
||||||
|
{
|
||||||
|
lang.RegisterMessages(new Dictionary<string, string>
|
||||||
|
{
|
||||||
|
["ClaimSuccess"] = "You have claimed {0} {1}.",
|
||||||
|
["NothingToClaim"] = "Nothing to claim.",
|
||||||
|
["NoPermission"] = "You do not have permission to use this command."
|
||||||
|
}, this);
|
||||||
|
}
|
||||||
|
|
||||||
|
private string Lang(string key, string userId = null, params object[] args)
|
||||||
|
{
|
||||||
|
return string.Format(CultureInfo.InvariantCulture, lang.GetMessage(key, this, userId), args);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Nested class to handle reward data
|
||||||
|
private class RewardDataManager
|
||||||
|
{
|
||||||
|
private string filePath;
|
||||||
|
private Dictionary<string, int> rewardData;
|
||||||
|
private ClaimPlayerRewards plugin;
|
||||||
|
|
||||||
|
public RewardDataManager(string filePath, ClaimPlayerRewards plugin)
|
||||||
|
{
|
||||||
|
this.filePath = filePath;
|
||||||
|
this.plugin = plugin;
|
||||||
|
rewardData = new Dictionary<string, int>();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void LoadRewardData()
|
||||||
|
{
|
||||||
|
if (File.Exists(filePath))
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
string json = File.ReadAllText(filePath);
|
||||||
|
rewardData = JsonConvert.DeserializeObject<Dictionary<string, int>>(json) ?? new Dictionary<string, int>();
|
||||||
|
plugin.Puts("Reward data loaded successfully.");
|
||||||
|
}
|
||||||
|
catch (IOException ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"IO error loading reward data: {ex.Message}");
|
||||||
|
rewardData = new Dictionary<string, int>();
|
||||||
|
}
|
||||||
|
catch (JsonException ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"JSON error loading reward data: {ex.Message}");
|
||||||
|
rewardData = new Dictionary<string, int>();
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"Unexpected error loading reward data: {ex.Message}");
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
plugin.Puts("No reward data found, creating a new file.");
|
||||||
|
rewardData = new Dictionary<string, int>();
|
||||||
|
SaveRewardData();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SaveRewardData()
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
// Save the reward data back to the JSON file
|
||||||
|
string json = JsonConvert.SerializeObject(rewardData, Formatting.Indented);
|
||||||
|
File.WriteAllText(filePath, json);
|
||||||
|
plugin.Puts("Reward data saved successfully.");
|
||||||
|
}
|
||||||
|
catch (IOException ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"IO error saving reward data: {ex.Message}");
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
catch (JsonException ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"JSON error saving reward data: {ex.Message}");
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"Unexpected error saving reward data: {ex.Message}");
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool HasReward(string steamId)
|
||||||
|
{
|
||||||
|
return rewardData.ContainsKey(steamId);
|
||||||
|
}
|
||||||
|
|
||||||
|
public int GetRewardAmount(string steamId)
|
||||||
|
{
|
||||||
|
return rewardData.ContainsKey(steamId) ? rewardData[steamId] : 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void RemoveReward(string steamId)
|
||||||
|
{
|
||||||
|
if (rewardData.Remove(steamId))
|
||||||
|
{
|
||||||
|
SaveRewardData();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Nested class to handle claimed rewards data
|
||||||
|
private class ClaimDataManager
|
||||||
|
{
|
||||||
|
private string filePath;
|
||||||
|
private List<ClaimRecord> claims;
|
||||||
|
private ClaimPlayerRewards plugin;
|
||||||
|
|
||||||
|
public ClaimDataManager(string filePath, ClaimPlayerRewards plugin)
|
||||||
|
{
|
||||||
|
this.filePath = filePath;
|
||||||
|
this.plugin = plugin;
|
||||||
|
claims = new List<ClaimRecord>();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void LoadClaimedRewards()
|
||||||
|
{
|
||||||
|
if (File.Exists(filePath))
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
string json = File.ReadAllText(filePath);
|
||||||
|
var claimContainer = JsonConvert.DeserializeObject<ClaimContainer>(json);
|
||||||
|
claims = claimContainer.claims ?? new List<ClaimRecord>();
|
||||||
|
plugin.Puts("Claimed rewards data loaded successfully.");
|
||||||
|
}
|
||||||
|
catch (IOException ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"IO error loading claimed rewards data: {ex.Message}");
|
||||||
|
claims = new List<ClaimRecord>();
|
||||||
|
}
|
||||||
|
catch (JsonException ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"JSON error loading claimed rewards data: {ex.Message}");
|
||||||
|
claims = new List<ClaimRecord>();
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"Unexpected error loading claimed rewards data: {ex.Message}");
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
plugin.Puts("No claimed rewards data found, creating a new file.");
|
||||||
|
claims = new List<ClaimRecord>();
|
||||||
|
SaveClaimedRewards();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SaveClaimedRewards()
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
// Save the claims data back to the JSON file
|
||||||
|
var claimContainer = new ClaimContainer { claims = claims };
|
||||||
|
string json = JsonConvert.SerializeObject(claimContainer, Formatting.Indented);
|
||||||
|
File.WriteAllText(filePath, json);
|
||||||
|
plugin.Puts("Claimed rewards data saved successfully.");
|
||||||
|
}
|
||||||
|
catch (IOException ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"IO error saving claimed rewards data: {ex.Message}");
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
catch (JsonException ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"JSON error saving claimed rewards data: {ex.Message}");
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
plugin.Puts($"Unexpected error saving claimed rewards data: {ex.Message}");
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void LogClaim(string steamId, int amountClaimed)
|
||||||
|
{
|
||||||
|
// Create a new claim record
|
||||||
|
ClaimRecord newClaim = new ClaimRecord
|
||||||
|
{
|
||||||
|
steamid = steamId,
|
||||||
|
timestamp = DateTime.UtcNow.ToString("o", CultureInfo.InvariantCulture), // ISO 8601 format
|
||||||
|
amount_claimed = amountClaimed
|
||||||
|
};
|
||||||
|
|
||||||
|
// Add the new claim to the list
|
||||||
|
claims.Add(newClaim);
|
||||||
|
|
||||||
|
// Save the updated claims list to the JSON file
|
||||||
|
SaveClaimedRewards();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private class ClaimRecord
|
||||||
|
{
|
||||||
|
public string steamid { get; set; }
|
||||||
|
public string timestamp { get; set; }
|
||||||
|
public int amount_claimed { get; set; }
|
||||||
|
}
|
||||||
|
|
||||||
|
private class ClaimContainer
|
||||||
|
{
|
||||||
|
public List<ClaimRecord> claims { get; set; }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
21
LICENSE.txt
Normal file
21
LICENSE.txt
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
MIT License
|
||||||
|
|
||||||
|
Copyright (c) 2024 Patrick Ulrich
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
49
README.md
Normal file
49
README.md
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
## Overview
|
||||||
|
The **Claim Player Rewards** plugin allows players to claim rewards based on a pre-configured JSON file. Each reward claim is logged to prevent players from claiming multiple times.
|
||||||
|
|
||||||
|
This plugin is ideal for servers that want to distribute rewards to players based on specific achievements, events, or other criteria managed through a JSON configuration file.
|
||||||
|
|
||||||
|
### Features
|
||||||
|
- Allows players to claim pre-configured rewards.
|
||||||
|
- Stores reward configurations in a JSON file.
|
||||||
|
- Logs every successful reward claim to track claims and prevent duplicates.
|
||||||
|
- No external dependencies required.
|
||||||
|
|
||||||
|
## Installation
|
||||||
|
1. Download the plugin and place it in the `oxide/plugins/` directory.
|
||||||
|
2. Create the JSON configuration file `ClaimPlayerRewards.json` in the `oxide/data/ClaimPlayerRewards/` directory.
|
||||||
|
3. Configure the SteamIDs and reward amounts.
|
||||||
|
4. Restart your server or reload the plugin.
|
||||||
|
|
||||||
|
## Configuration
|
||||||
|
The plugin will automatically generate a configuration folder and file on first run. The configuration is stored at:
|
||||||
|
|
||||||
|
`oxide/data/ClaimPlayerRewards/ClaimPlayerRewards.json`
|
||||||
|
|
||||||
|
### Example Configuration:
|
||||||
|
```json
|
||||||
|
{
|
||||||
|
"76561198000000000": 10,
|
||||||
|
"76561198000000001": 5
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
In this example, the SteamID `76561198000000000` is entitled to 10 reward items, and the SteamID `76561198000000001` is entitled to 5 reward items.
|
||||||
|
|
||||||
|
### Claims Logging:
|
||||||
|
All claims are logged in a separate JSON file located at:
|
||||||
|
|
||||||
|
`oxide/data/ClaimPlayerRewards/ClaimedRewards.json`
|
||||||
|
|
||||||
|
Each log entry contains:
|
||||||
|
- **SteamID**: The player's SteamID.
|
||||||
|
- **Timestamp**: When the claim was made.
|
||||||
|
- **Amount Claimed**: The number of items claimed.
|
||||||
|
|
||||||
|
## Permissions
|
||||||
|
|
||||||
|
| Permission | Purpose |
|
||||||
|
|---------------------------|-------------------------------------------------------|
|
||||||
|
| `claimplayerrewards.use` | Required to allow players to claim their rewards. |
|
||||||
|
|
||||||
|
Make sure to assign the `claimplayerrewards.use` permission to players or groups you want to grant access to claim rewards.
|
Loading…
x
Reference in New Issue
Block a user