- mnoho změn
region-rework
jakub 2 weeks ago
parent e70e526d93
commit f355dcfa1e
  1. 19
      LICENSE.txt
  2. 33
      src/main/java/xyz/soukup/ecoCraftCore/EcoCraftCore.java
  3. 34
      src/main/java/xyz/soukup/ecoCraftCore/database/objects/Permission.java
  4. 284
      src/main/java/xyz/soukup/ecoCraftCore/database/objects/Region.java
  5. 2
      src/main/java/xyz/soukup/ecoCraftCore/islands/DatabaseIslandLoader.java
  6. 2
      src/main/java/xyz/soukup/ecoCraftCore/islands/IslandAdminCommand.java
  7. 8
      src/main/java/xyz/soukup/ecoCraftCore/islands/IslandManager.java
  8. 6
      src/main/java/xyz/soukup/ecoCraftCore/islands/IslandSelectorCommand.java
  9. 4
      src/main/java/xyz/soukup/ecoCraftCore/islands/UnloadIsland.java
  10. 16
      src/main/java/xyz/soukup/ecoCraftCore/messages/Messages.java
  11. 4
      src/main/java/xyz/soukup/ecoCraftCore/messages/PHHM.java
  12. 15
      src/main/java/xyz/soukup/ecoCraftCore/messages/Replace.java
  13. 2
      src/main/java/xyz/soukup/ecoCraftCore/mines/MineWorldManager.java
  14. 4
      src/main/java/xyz/soukup/ecoCraftCore/money/MoneyCommand.java
  15. 4
      src/main/java/xyz/soukup/ecoCraftCore/objects/Account.java
  16. 2
      src/main/java/xyz/soukup/ecoCraftCore/objects/ActiveServer.java
  17. 2
      src/main/java/xyz/soukup/ecoCraftCore/objects/Island.java
  18. 43
      src/main/java/xyz/soukup/ecoCraftCore/objects/Permission.java
  19. 32
      src/main/java/xyz/soukup/ecoCraftCore/objects/PermissionGroup.java
  20. 468
      src/main/java/xyz/soukup/ecoCraftCore/objects/Region.java
  21. 18
      src/main/java/xyz/soukup/ecoCraftCore/objects/RegionMember.java
  22. 4
      src/main/java/xyz/soukup/ecoCraftCore/objects/Shop.java
  23. 15
      src/main/java/xyz/soukup/ecoCraftCore/objects/Status.java
  24. 2
      src/main/java/xyz/soukup/ecoCraftCore/objects/TeleportRequest.java
  25. 2
      src/main/java/xyz/soukup/ecoCraftCore/objects/Transaction.java
  26. 2
      src/main/java/xyz/soukup/ecoCraftCore/objects/VirtualChest.java
  27. 2
      src/main/java/xyz/soukup/ecoCraftCore/player/PreparePlayer.java
  28. 2
      src/main/java/xyz/soukup/ecoCraftCore/player/TeleportRequestsHandler.java
  29. 2
      src/main/java/xyz/soukup/ecoCraftCore/regions/RegionAdminCommand.java
  30. 225
      src/main/java/xyz/soukup/ecoCraftCore/regions/RegionCommand.java
  31. 263
      src/main/java/xyz/soukup/ecoCraftCore/regions/RegionEvents.java
  32. 176
      src/main/java/xyz/soukup/ecoCraftCore/regions/RegionManager.java
  33. 4
      src/main/java/xyz/soukup/ecoCraftCore/shop/ShopCommand.java
  34. 8
      src/main/java/xyz/soukup/ecoCraftCore/shop/ShopLogic.java
  35. 2
      src/main/java/xyz/soukup/ecoCraftCore/sign/SignEditCommand.java
  36. 8
      src/main/java/xyz/soukup/ecoCraftCore/sit/LetMeSit.java
  37. 3
      src/main/java/xyz/soukup/ecoCraftCore/virtualChest/VirtualChestLogic.java
  38. 19
      src/main/resources/messages.yml

@ -0,0 +1,19 @@
Copyright (c) 2025-2026 Jakub Soukup, Erik Radovan and contributors
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 copy, modify, merge, publish, distribute, sublicense, and/or sell copies
of the Software, but NOT including the right to run, execute or use the
Software or any executable binaries built from the source code.
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

@ -1,3 +1,25 @@
/*
ECOCRAFT CORE
(c) 2025-2026 Jakub Soukup, Erik Radovan and contributors
This software is licensed under Passive Aggressive License
*/
package xyz.soukup.ecoCraftCore;
import com.github.retrooper.packetevents.event.EventManager;
@ -21,26 +43,22 @@ import org.bukkit.plugin.Plugin;
import org.bukkit.plugin.PluginManager;
import org.bukkit.plugin.java.JavaPlugin;
import org.jetbrains.annotations.NotNull;
import xyz.soukup.ecoCraftCore.database.objects.*;
import xyz.soukup.ecoCraftCore.islands.IslandAdminCommand;
import xyz.soukup.ecoCraftCore.islands.IslandSelectorCommand;
import xyz.soukup.ecoCraftCore.messages.JoinLeaveMessageSupress;
import xyz.soukup.ecoCraftCore.mines.MineCommand;
import xyz.soukup.ecoCraftCore.mines.MineWorldManager;
import xyz.soukup.ecoCraftCore.money.MoneyCommand;
import xyz.soukup.ecoCraftCore.objects.*;
import xyz.soukup.ecoCraftCore.player.OnKill;
import xyz.soukup.ecoCraftCore.player.PreparePlayer;
import xyz.soukup.ecoCraftCore.player.TeleportRequestsHandler;
import xyz.soukup.ecoCraftCore.positionMarker.MarkerCommand;
import xyz.soukup.ecoCraftCore.regions.RegionAdminCommand;
import xyz.soukup.ecoCraftCore.regions.RegionCommand;
import xyz.soukup.ecoCraftCore.regions.RegionEvents;
import xyz.soukup.ecoCraftCore.shop.ShopCommand;
import xyz.soukup.ecoCraftCore.database.objects.Account;
import xyz.soukup.ecoCraftCore.database.objects.Island;
import xyz.soukup.ecoCraftCore.database.objects.Shop;
import xyz.soukup.ecoCraftCore.database.objects.Transaction;
import io.papermc.paper.plugin.lifecycle.event.types.LifecycleEvents;
import xyz.soukup.ecoCraftCore.database.objects.VirtualChest;
import xyz.soukup.ecoCraftCore.positionMarker.MarkerEvent;
import xyz.soukup.ecoCraftCore.messages.Messages;
import xyz.soukup.ecoCraftCore.shop.ShopLogic;
@ -237,6 +255,7 @@ public final class EcoCraftCore extends JavaPlugin {
TableUtils.createTableIfNotExists(connectionSource, TeleportRequest.class);
TableUtils.createTableIfNotExists(connectionSource, Region.class);
TableUtils.createTableIfNotExists(connectionSource, RegionMember.class);
TableUtils.createTableIfNotExists(connectionSource, PermissionGroup.class);
ActiveServer.setDao(DaoManager.createDao(connectionSource, ActiveServer.class));
Transaction.setDao(DaoManager.createDao(connectionSource, Transaction.class));
@ -247,6 +266,7 @@ public final class EcoCraftCore extends JavaPlugin {
TeleportRequest.setDao(DaoManager.createDao(connectionSource, TeleportRequest.class));
Region.setDao(DaoManager.createDao(connectionSource, Region.class));
RegionMember.setDao(DaoManager.createDao(connectionSource, RegionMember.class));
PermissionGroup.setDao(DaoManager.createDao(connectionSource, PermissionGroup.class));
ActiveServer activeServer = new ActiveServer(config.getString("server.name"));
@ -289,6 +309,7 @@ public final class EcoCraftCore extends JavaPlugin {
lm.registerEventHandler(LifecycleEvents.COMMANDS, event -> event.registrar().register(MoneyCommand.getCommand().build()));
lm.registerEventHandler(LifecycleEvents.COMMANDS, event -> event.registrar().register(MineCommand.createCommand().build()));
lm.registerEventHandler(LifecycleEvents.COMMANDS, event -> event.registrar().register(SignEditCommand.getCommand().build()));
lm.registerEventHandler(LifecycleEvents.COMMANDS, event -> event.registrar().register(RegionCommand.command().build()));
}
private void registerEvents(){

@ -1,34 +0,0 @@
package xyz.soukup.ecoCraftCore.database.objects;
public enum Permission {
PLACE(1),
BREAK(2),
REDSTONE_INTERACT(3),
ENTITY_INTERACT(4),
VEHICLE_INTERACT(5),
ENTER(6),
EXIT(7),
MANAGE_MEMBERS(8),
MANAGE_GROUPS(9),
MANAGE_REGIONS(10),
TRANSFER_OWNERSHIP(11),
USE_HOPPER(12),
HARVEST(13),
PLANT(14),
PICKUP_ITEMS(15),
DROP_ITEMS(16),
PLOUGH(17),
SIT(18),
SHOP_INTERACT(19),
HARM_ENTITIES(20),
HARM_PLAYERS(21);
private final int bit;
Permission(int bit) {
this.bit = bit;
}
public int getBit() {
return bit;
}
}

@ -1,284 +0,0 @@
package xyz.soukup.ecoCraftCore.database.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.dao.ForeignCollection;
import com.j256.ormlite.field.DatabaseField;
import com.j256.ormlite.field.ForeignCollectionField;
import com.j256.ormlite.table.DatabaseTable;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import xyz.soukup.ecoCraftCore.messages.Messages;
import java.sql.SQLException;
import java.util.HashMap;
import java.util.List;
@DatabaseTable(tableName = "regions")
public class Region {
public static Dao<Region, Integer> dao;
public static void setDao(Dao<Region, Integer> dao) {
Region.dao = dao;
}
public static Dao<Region, Integer> getDao() {
return dao;
}
public static final HashMap<String, List<Region>> cache = new HashMap<>();
@DatabaseField(generatedId = true)
private int id;
@DatabaseField(canBeNull = false)
private String island;
@DatabaseField(columnName = "region_type", canBeNull = false)
private int regionType;
@DatabaseField(canBeNull = false)
private int x1;
@DatabaseField(canBeNull = false)
private int y1;
@DatabaseField(canBeNull = false)
private int z1;
@DatabaseField(canBeNull = false)
private int x2;
@DatabaseField(canBeNull = false)
private int y2;
@DatabaseField(canBeNull = false)
private int z2;
@ForeignCollectionField(eager = true)
private ForeignCollection<RegionMember> regionMembers;
@DatabaseField()
private Integer value;
public Region() {
}
public Region(String island, int regionType, int x1, int y1, int z1, int x2, int y2, int z2) {
this.island = island;
this.regionType = regionType;
this.x1 = Math.min(x1, x2);
this.y1 = Math.min(y1, y2);
this.x2 = Math.max(x1, x2);
this.y2 = Math.max(y1, y2);
this.z1 = Math.min(z1, z2);
this.z2 = Math.max(z1, z2);
save();
createDefaultGroupsAndReturnOwner();
}
public PermissionGroup getPermissionGroup(String name){
return PermissionGroup.getPermissionGroup(this, name);
}
public Region(String island, int regionType, int x1, int y1, int z1, int x2, int y2, int z2, Player owner) {
this.island = island;
this.regionType = regionType;
this.x1 = Math.min(x1, x2);
this.y1 = Math.min(y1, y2);
this.x2 = Math.max(x1, x2);
this.y2 = Math.max(y1, y2);
this.z1 = Math.min(z1, z2);
this.z2 = Math.max(z1, z2);
this.save();
PermissionGroup ownerGroup = this.createDefaultGroupsAndReturnOwner();
addRegionMember("player", owner.getName(), ownerGroup);
}
public int getId() {
return id;
}
public int getRegionType() {
return regionType;
}
public int getX1() {
return x1;
}
public int getZ1() {
return z1;
}
public int getZ2() {
return z2;
}
public int getY1() {
return y1;
}
public int getX2() {
return x2;
}
public int getY2() {
return y2;
}
public ForeignCollection<RegionMember> getRegionMembers() {
return regionMembers;
}
public Integer getValue() {
return value;
}
public String getIsland() {
return island;
}
public void setRegionType(int regionType) {
this.regionType = regionType;
}
public void setValue(Integer value) {
this.value = value;
}
public void save(){
try {
getDao().createOrUpdate(this);
List<Region> regions = cache.get(island);
if (regions == null) {
return;
}
regions.removeIf(region -> region.getId() == this.id);
regions.add(this);
} catch (Exception e) {
e.printStackTrace();
}
}
public void addRegionMember(String memberType, String member, PermissionGroup permissionGroup){
RegionMember regionMember = new RegionMember(this, memberType, member, permissionGroup);
regionMember.save();
List<Region> regions = cache.get(island);
if (regions == null) {
return;
}
regions.removeIf(region -> region.getId() == this.id);
regions.add(this);
}
public void removeRegionMember(String memberType, String member){
try {
RegionMember.getDao().queryBuilder().where().eq("region", this).query();
} catch (SQLException e) {
throw new RuntimeException(e);
}
}
public boolean isInside(int x, int y, int z) {
return x >= this.x1 && x <= this.x2 && y >= this.y1 && y <= this.y2 && z >= this.z1 && z <= this.z2;
}
public static Region findById(int id) {
try {
return getDao().queryForId(id);
} catch (Exception e) {
return null;
}
}
public static void cacheRegions(String island) {
try {
List<Region> regions = getDao().queryBuilder()
.where()
.eq("island", island)
.query();
cache.put(island, regions);
} catch (Exception e) {
}
}
public static Region findRegion(int x, int y, int z, String island) {
Region region = null;
int highestType = -1;
if (!cache.containsKey(island)) {
cacheRegions(island);
}
for (Region cachedRegion : cache.get(island)) {
if (!cachedRegion.isInside(x, y, z)) {
continue;
}
if (highestType >= cachedRegion.getRegionType()){
continue;
}
region = cachedRegion;
}
return region;
}
public void changeBoundaries(int x1, int y1, int z1, int x2, int y2, int z2){
this.x1 = Math.min(x1, x2);
this.y1 = Math.min(y1, y2);
this.x2 = Math.max(x1, x2);
this.y2 = Math.max(y1, y2);
this.z1 = Math.min(z1, z2);
this.z2 = Math.max(z1, z2);
}
public PermissionGroup createDefaultGroupsAndReturnOwner(){
String ownerDisplayName = Messages.getAsString("region.permission-groups.owner.name");
String ownerDescription = Messages.getAsString("region.permission-groups.owner.description");
PermissionGroup owner = new PermissionGroup(this, "owner", ownerDisplayName, ownerDescription, Material.RED_CONCRETE, false, false, 101);
owner.save();
String adminDisplayName = Messages.getAsString("region.permission-groups.admin.name");
String adminDescription = Messages.getAsString("region.permission-groups.admin.description");
PermissionGroup admin = new PermissionGroup(this, "admin", adminDisplayName, adminDescription, Material.YELLOW_CONCRETE, true, true, 90);
admin.save();
String memberDisplayName = Messages.getAsString("region.permission-groups.member.name");
String memberDescription = Messages.getAsString("region.permission-groups.member.description");
PermissionGroup member = new PermissionGroup(this, "member", memberDisplayName, memberDescription, Material.GREEN_CONCRETE, true, true, 10);
member.save();
String defaultDisplayName = Messages.getAsString("region.permission-groups.default");
String defaultDescription = Messages.getAsString("region.permission-groups.default.description");
PermissionGroup defaultGroup = new PermissionGroup(this, "default", defaultDisplayName, defaultDescription, Material.GRAY_CONCRETE, true, true, 0);
defaultGroup.save();
return owner;
}
}

@ -2,7 +2,7 @@ package xyz.soukup.ecoCraftCore.islands;
import com.infernalsuite.asp.api.exceptions.UnknownWorldException;
import com.infernalsuite.asp.api.loaders.SlimeLoader;
import com.j256.ormlite.stmt.DeleteBuilder;
import xyz.soukup.ecoCraftCore.database.objects.Island;
import xyz.soukup.ecoCraftCore.objects.Island;
import java.io.IOException;
import java.sql.SQLException;

@ -16,7 +16,7 @@ import org.bukkit.block.Biome;
import org.bukkit.entity.Player;
import org.bukkit.persistence.PersistentDataContainer;
import org.bukkit.persistence.PersistentDataType;
import xyz.soukup.ecoCraftCore.database.objects.Island;
import xyz.soukup.ecoCraftCore.objects.Island;
import xyz.soukup.ecoCraftCore.messages.Messages;
import java.io.IOException;

@ -17,10 +17,10 @@ import com.j256.ormlite.stmt.UpdateBuilder;
import org.bukkit.*;
import org.bukkit.entity.Player;
import org.bukkit.persistence.PersistentDataType;
import xyz.soukup.ecoCraftCore.database.objects.ActiveServer;
import xyz.soukup.ecoCraftCore.database.objects.Island;
import xyz.soukup.ecoCraftCore.database.objects.Region;
import xyz.soukup.ecoCraftCore.database.objects.TeleportRequest;
import xyz.soukup.ecoCraftCore.objects.ActiveServer;
import xyz.soukup.ecoCraftCore.objects.Island;
import xyz.soukup.ecoCraftCore.objects.Region;
import xyz.soukup.ecoCraftCore.objects.TeleportRequest;
import xyz.soukup.ecoCraftCore.utilities.PDC;
import java.io.IOException;

@ -17,9 +17,9 @@ import net.kyori.adventure.text.format.TextColor;
import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import xyz.soukup.ecoCraftCore.database.objects.Island;
import xyz.soukup.ecoCraftCore.database.objects.Region;
import xyz.soukup.ecoCraftCore.database.objects.RegionMember;
import xyz.soukup.ecoCraftCore.objects.Island;
import xyz.soukup.ecoCraftCore.objects.Region;
import xyz.soukup.ecoCraftCore.objects.RegionMember;
import xyz.soukup.ecoCraftCore.gui.GuiItemBuilder;
import xyz.soukup.ecoCraftCore.messages.Messages;

@ -1,4 +0,0 @@
package xyz.soukup.ecoCraftCore.islands;
public class UnloadIsland {
}

@ -53,9 +53,25 @@ public class Messages {
return MiniMessage.miniMessage().deserialize(string, resolverBuilder.build());
}
public static Component get(String key, Replace... replaces){
String string = getString(key);
TagResolver.Builder resolverBuilder = TagResolver.builder();
for (Replace replace: replaces){
string = replace.process(string);
}
return MiniMessage.miniMessage().deserialize(string, resolverBuilder.build());
}
public static void send(CommandSender sender, String key){
sender.sendMessage(get(key));
}
public static void send(CommandSender sender, String key, Replace... replaces){
sender.sendMessage(get(key, replaces));
}
public static void send(CommandSender sender, String key, HashMap<String, String> placeholders){
sender.sendMessage(get(key, placeholders));

@ -2,8 +2,8 @@ package xyz.soukup.ecoCraftCore.messages;
import org.bukkit.Location;
import xyz.soukup.ecoCraftCore.database.objects.Account;
import xyz.soukup.ecoCraftCore.database.objects.Transaction;
import xyz.soukup.ecoCraftCore.objects.Account;
import xyz.soukup.ecoCraftCore.objects.Transaction;
import java.util.HashMap;

@ -0,0 +1,15 @@
package xyz.soukup.ecoCraftCore.messages;
public class Replace {
private final String key;
private final String value;
public Replace(String key, String value) {
this.key = key;
this.value = value;
}
public String process(String input) {
return input.replace("<" + key + ">", value);
}
}

@ -21,7 +21,7 @@ import org.bukkit.event.player.PlayerItemDamageEvent;
import org.bukkit.event.player.PlayerJoinEvent;
import org.bukkit.potion.PotionEffect;
import org.bukkit.potion.PotionEffectType;
import xyz.soukup.ecoCraftCore.database.objects.Island;
import xyz.soukup.ecoCraftCore.objects.Island;
import xyz.soukup.ecoCraftCore.islands.DatabaseIslandLoader;
import java.util.function.Consumer;

@ -11,8 +11,8 @@ import io.papermc.paper.command.brigadier.argument.ArgumentTypes;
import io.papermc.paper.command.brigadier.argument.resolvers.selector.PlayerSelectorArgumentResolver;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import xyz.soukup.ecoCraftCore.database.objects.Account;
import xyz.soukup.ecoCraftCore.database.objects.Transaction;
import xyz.soukup.ecoCraftCore.objects.Account;
import xyz.soukup.ecoCraftCore.objects.Transaction;
import xyz.soukup.ecoCraftCore.messages.Messages;
import xyz.soukup.ecoCraftCore.messages.PHHM;

@ -1,4 +1,4 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.field.DatabaseField;
@ -24,7 +24,7 @@ public class Account {
}
public static void setDao(Dao<Account, Integer> dao) {
dao = dao;
Account.dao = dao;
}

@ -1,4 +1,4 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;

@ -1,4 +1,4 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.field.DataType;

@ -0,0 +1,43 @@
package xyz.soukup.ecoCraftCore.objects;
public enum Permission {
PLACE(0),
BREAK(1),
INTERACT(2),
ENTITY_INTERACT(3),
OPEN_CHESTS(4),
ENTER(5),
EXIT(6),
MANAGE_MEMBERS(7),
MANAGE_GROUPS(8),
MANAGE_REGIONS(9),
TRANSFER_OWNERSHIP(10),
USE_HOPPER(11),
HARVEST(12),
PLANT(13),
PICKUP_ITEMS(14),
DROP_ITEMS(15),
REDSTONE_INTERACT(16),
SIT(17),
SHOP_INTERACT(18),
HARM_ENTITIES(19),
HARM_PLAYERS(20),
VEHICLE_RIDE(21),
VEHICLE_PLACE(22),
VEHICLE_BREAK(23),
VEHICLE_INTERACT(24),
BUCKET_USE(25);
private final int mask;
Permission(int position) {
// This creates the power of two: 1, 2, 4, 8, 16...
this.mask = 1 << position;
}
public int getMask() {
return mask;
}
}

@ -1,11 +1,10 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.field.DatabaseField;
import com.j256.ormlite.table.DatabaseTable;
import org.bukkit.Material;
import java.security.Permissions;
import java.sql.SQLException;
@DatabaseTable(tableName = "permission_groups")
@ -55,6 +54,10 @@ public class PermissionGroup {
}
public PermissionGroup(int permissionsNumber){
this.permissionsNumber = permissionsNumber;
}
public PermissionGroup(Region region, String name, String displayName, String description, Material icon){
this.region = region;
this.name = name;
@ -90,22 +93,36 @@ public class PermissionGroup {
this.permissionsNumber = 0;
this.weight = 0;
for (Permission permission : permissions) {
this.permissionsNumber |= permission.getBit();
this.permissionsNumber |= permission.getMask();
}
}
public PermissionGroup copyTo(Region region) {
return new PermissionGroup(
region,
this.name,
this.displayName,
this.description,
this.icon,
this.editable,
this.deletable,
this.weight,
this.permissionsNumber
);
}
public boolean hasPermission(Permission permission) {
return (this.permissionsNumber & permission.getBit()) != 0;
return (this.permissionsNumber & permission.getMask()) != 0;
}
public void addPermission(Permission... permissions) {
for (Permission permission : permissions){
this.permissionsNumber |= permission.getBit();
this.permissionsNumber |= permission.getMask();
}
}
public void removePermission(Permission permission) {
this.permissionsNumber &= ~permission.getBit();
this.permissionsNumber &= ~permission.getMask();
}
public String getName() {
@ -143,6 +160,7 @@ public class PermissionGroup {
public void save(){
try {
getDao().createOrUpdate(this);
region.refreshCache();
} catch (SQLException e) {
throw new RuntimeException(e);
}
@ -150,7 +168,7 @@ public class PermissionGroup {
public static PermissionGroup getPermissionGroup(Region region, String name){
try {
return getDao().queryBuilder().where().eq("region", region).and().eq("name", name).queryForFirst();
return getDao().queryBuilder().where().eq("region_id", region.getId()).and().eq("name", name).queryForFirst();
} catch (SQLException e) {
throw new RuntimeException(e);
}

@ -0,0 +1,468 @@
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.dao.ForeignCollection;
import com.j256.ormlite.field.DatabaseField;
import com.j256.ormlite.field.ForeignCollectionField;
import com.j256.ormlite.stmt.DeleteBuilder;
import com.j256.ormlite.stmt.Where;
import com.j256.ormlite.table.DatabaseTable;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import xyz.soukup.ecoCraftCore.messages.Messages;
import java.sql.SQLException;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@DatabaseTable(tableName = "regions")
public class Region {
public static Dao<Region, Integer> dao;
public static void setDao(Dao<Region, Integer> dao) {
Region.dao = dao;
}
public static Dao<Region, Integer> getDao() {
return dao;
}
public static final HashMap<String, List<Region>> cache = new HashMap<>();
@DatabaseField(generatedId = true)
private int id;
@DatabaseField(canBeNull = false)
private String island;
@DatabaseField(columnName = "region_level", canBeNull = false)
private int regionLevel;
@DatabaseField(canBeNull = false)
private int x1;
@DatabaseField(canBeNull = false)
private int y1;
@DatabaseField(canBeNull = false)
private int z1;
@DatabaseField(canBeNull = false)
private int x2;
@DatabaseField(canBeNull = false)
private int y2;
@DatabaseField(canBeNull = false)
private int z2;
@ForeignCollectionField(eager = true)
private ForeignCollection<RegionMember> regionMembers;
@DatabaseField()
private Integer value;
public Region() {
}
public Region(String island, int regionLevel, int x1, int y1, int z1, int x2, int y2, int z2) {
this.island = island;
this.regionLevel = regionLevel;
this.x1 = Math.min(x1, x2);
this.y1 = Math.min(y1, y2);
this.x2 = Math.max(x1, x2);
this.y2 = Math.max(y1, y2);
this.z1 = Math.min(z1, z2);
this.z2 = Math.max(z1, z2);
save();
createDefaultGroupsAndReturnOwner();
}
public PermissionGroup getPermissionGroup(String name){
return PermissionGroup.getPermissionGroup(this, name);
}
public Region(Region parentRegion, int x1, int y1, int z1, int x2, int y2, int z2) {
this.island = parentRegion.getIsland();
this.regionLevel = parentRegion.getRegionLevel() + 1;
this.x1 = Math.min(x1, x2);
this.y1 = Math.min(y1, y2);
this.x2 = Math.max(x1, x2);
this.y2 = Math.max(y1, y2);
this.z1 = Math.min(z1, z2);
this.z2 = Math.max(z1, z2);
save();
copyDataFrom(parentRegion);
}
private void copyDataFrom(Region source) {
try {
Map<String, PermissionGroup> groupMapping = new HashMap<>();
List<PermissionGroup> sourceGroups = PermissionGroup.getDao().queryBuilder()
.where().eq("region_id", source.getId()).query();
for (PermissionGroup sourceGroup : sourceGroups) {
PermissionGroup clonedGroup = sourceGroup.copyTo(this);
clonedGroup.save();
groupMapping.put(clonedGroup.getName(), clonedGroup);
}
for (RegionMember sourceMember : source.getRegionMembers()) {
PermissionGroup targetGroup = groupMapping.get(sourceMember.getPermissionGroup().getName());
if (targetGroup != null) {
addRegionMember(sourceMember.getMemberType(), sourceMember.getName(), targetGroup);
}
}
} catch (SQLException e) {
e.printStackTrace();
}
}
public Region(String island, int regionType, int x1, int y1, int z1, int x2, int y2, int z2, Player owner) {
this.island = island;
this.regionLevel = regionType;
this.x1 = Math.min(x1, x2);
this.y1 = Math.min(y1, y2);
this.x2 = Math.max(x1, x2);
this.y2 = Math.max(y1, y2);
this.z1 = Math.min(z1, z2);
this.z2 = Math.max(z1, z2);
this.save();
PermissionGroup ownerGroup = this.createDefaultGroupsAndReturnOwner();
addRegionMember("player", owner.getName(), ownerGroup);
}
public int getId() {
return id;
}
public int getRegionLevel() {
return regionLevel;
}
public int getX1() {
return x1;
}
public int getZ1() {
return z1;
}
public int getZ2() {
return z2;
}
public int getY1() {
return y1;
}
public int getX2() {
return x2;
}
public int getY2() {
return y2;
}
public ForeignCollection<RegionMember> getRegionMembers() {
return regionMembers;
}
public Integer getValue() {
return value;
}
public String getIsland() {
return island;
}
public void setRegionLevel(int regionLevel) {
this.regionLevel = regionLevel;
}
public void setValue(Integer value) {
this.value = value;
}
public void save(){
try {
getDao().createOrUpdate(this);
List<Region> regions = cache.get(island);
if (regions == null) {
return;
}
regions.removeIf(region -> region.getId() == this.id);
regions.add(this);
} catch (Exception e) {
e.printStackTrace();
}
}
public void refreshCache(){
List<Region> regions = cache.get(island);
if (regions == null) {
return;
}
try {
Region fefreshedRegion = getDao().queryForId(this.id);
regions.removeIf(region -> region.getId() == this.id);
regions.add(fefreshedRegion);
} catch (SQLException e) {
throw new RuntimeException(e);
}
}
public void addRegionMember(Player player, PermissionGroup group){
addRegionMember("player", player.getName(), group);
}
public void addRegionMember(String memberType, String member, PermissionGroup permissionGroup){
RegionMember regionMember = new RegionMember(this, memberType, member, permissionGroup);
regionMember.save();
List<Region> regions = cache.get(island);
if (regions == null) {
return;
}
regions.removeIf(region -> region.getId() == this.id);
regions.add(this);
}
public void removeRegionMember(Player player){
removeRegionMember("player", player.getName());
}
public void removeRegionMember(String memberType, String member){
try {
RegionMember.getDao().queryBuilder().where().eq("region", this).query();
} catch (SQLException e) {
throw new RuntimeException(e);
}
}
public RegionMember getRegionMember(Player player){
return getRegionMember("player", player.getName());
}
public boolean hasPermission(Player player, Permission permission){
RegionMember regionMember = getRegionMember(player);
PermissionGroup permissionGroup;
if (regionMember == null) {
permissionGroup = getPermissionGroup("default");
}else {
permissionGroup = regionMember.getPermissionGroup();
}
return permissionGroup.hasPermission(permission);
}
public boolean hasPermission(String memberType, String memberName, Permission permission){
RegionMember regionMember = getRegionMember(memberType, memberName);
PermissionGroup permissionGroup;
if (regionMember == null) {
permissionGroup = getPermissionGroup("default");
}else {
permissionGroup = regionMember.getPermissionGroup();
}
return permissionGroup.hasPermission(permission);
}
public static List<Region> getOverlappingRegions(Location loc1, Location loc2) {
if (loc1.getWorld() != loc2.getWorld()){
return null;
}
String island = loc1.getWorld().getName();
List<Region> overlapping = new java.util.ArrayList<>();
if (!cache.containsKey(island)) {
cacheRegions(island);
}
int minX = Math.min(loc1.getBlockX(), loc2.getBlockX());
int maxX = Math.max(loc1.getBlockX(), loc2.getBlockX());
int minY = Math.min(loc1.getBlockY(), loc2.getBlockY());
int maxY = Math.max(loc1.getBlockY(), loc2.getBlockY());
int minZ = Math.min(loc1.getBlockZ(), loc2.getBlockZ());
int maxZ = Math.max(loc1.getBlockZ(), loc2.getBlockZ());
for (Region region : cache.get(island)) {
if ((region.getX1() <= maxX
&& region.getX2() >= minX) && (region.getY1() <= maxY
&& region.getY2() >= minY) && (region.getZ1() <= maxZ
&& region.getZ2() >= minZ)) {
overlapping.add(region);
}
}
return overlapping;
}
public static Region getHighestLevelRegion(Location loc1, Location loc2) {
List<Region> regions = getOverlappingRegions(loc1, loc2);
if (regions.isEmpty()) {
return null;
}
return regions.stream().max(Comparator.comparingInt(Region::getRegionLevel)).orElse(null);
}
public RegionMember getRegionMember(String type, String name){
return this.regionMembers.stream().filter(regionMember -> regionMember.getMemberType().equals(type) && regionMember.getName().equals(name)).findFirst().orElse(null);
}
public boolean isInside(int x, int y, int z) {
return x >= this.x1 && x <= this.x2 && y >= this.y1 && y <= this.y2 && z >= this.z1 && z <= this.z2;
}
public boolean envelops(Location loc1, Location loc2) {
int minX = Math.min(loc1.getBlockX(), loc2.getBlockX());
int maxX = Math.max(loc1.getBlockX(), loc2.getBlockX());
int minY = Math.min(loc1.getBlockY(), loc2.getBlockY());
int maxY = Math.max(loc1.getBlockY(), loc2.getBlockY());
int minZ = Math.min(loc1.getBlockZ(), loc2.getBlockZ());
int maxZ = Math.max(loc1.getBlockZ(), loc2.getBlockZ());
return this.x1 <= minX && this.x2 >= maxX &&
this.y1 <= minY && this.y2 >= maxY &&
this.z1 <= minZ && this.z2 >= maxZ;
}
public static Region findById(int id) {
try {
return getDao().queryForId(id);
} catch (Exception e) {
return null;
}
}
public static void cacheRegions(String island) {
try {
List<Region> regions = getDao().queryBuilder()
.where()
.eq("island", island)
.query();
cache.put(island, regions);
} catch (Exception e) {
}
}
public static Region findRegion(Location location){
return findRegion(location.getBlockX(), location.getBlockY(), location.getBlockZ(), location.getWorld().getName());
}
public static Region findRegion(int x, int y, int z, String island) {
Region region = null;
int highestType = -1;
if (!cache.containsKey(island)) {
cacheRegions(island);
}
for (Region cachedRegion : cache.get(island)) {
if (!cachedRegion.isInside(x, y, z)) {
continue;
}
if (highestType >= cachedRegion.getRegionLevel()){
continue;
}
region = cachedRegion;
}
return region;
}
public void changeBoundaries(int x1, int y1, int z1, int x2, int y2, int z2){
this.x1 = Math.min(x1, x2);
this.y1 = Math.min(y1, y2);
this.x2 = Math.max(x1, x2);
this.y2 = Math.max(y1, y2);
this.z1 = Math.min(z1, z2);
this.z2 = Math.max(z1, z2);
}
public PermissionGroup createDefaultGroupsAndReturnOwner(){
String ownerDisplayName = Messages.getAsString("region.permission-groups.owner.name");
String ownerDescription = Messages.getAsString("region.permission-groups.owner.description");
PermissionGroup owner = new PermissionGroup(this, "owner", ownerDisplayName, ownerDescription, Material.RED_CONCRETE, false, false, 101, 2147483647);
owner.save();
String adminDisplayName = Messages.getAsString("region.permission-groups.admin.name");
String adminDescription = Messages.getAsString("region.permission-groups.admin.description");
PermissionGroup admin = new PermissionGroup(this, "admin", adminDisplayName, adminDescription, Material.YELLOW_CONCRETE, true, true, 90, 2147482623);
admin.save();
String memberDisplayName = Messages.getAsString("region.permission-groups.member.name");
String memberDescription = Messages.getAsString("region.permission-groups.member.description");
PermissionGroup member = new PermissionGroup(this, "member", memberDisplayName, memberDescription, Material.GREEN_CONCRETE, true, true, 10, 2095231);
member.save();
String defaultDisplayName = Messages.getAsString("region.permission-groups.default");
String defaultDescription = Messages.getAsString("region.permission-groups.default.description");
PermissionGroup defaultGroup = new PermissionGroup(this, "default", defaultDisplayName, defaultDescription, Material.GRAY_CONCRETE, true, false, 0,96);
defaultGroup.save();
return owner;
}
public void delete() {
try {
getDao().delete(this);
cache.get(this.island).remove(this);
Dao<PermissionGroup, Integer> permissionGroupDao = PermissionGroup.getDao();
Dao<RegionMember, Integer> regionMemberDao = RegionMember.getDao();
DeleteBuilder<PermissionGroup, Integer> groupDeleteBuilder = permissionGroupDao.deleteBuilder();
groupDeleteBuilder.where().eq("region_id", this.id);
groupDeleteBuilder.delete();
DeleteBuilder<RegionMember, Integer> memberDeleteBuilder= regionMemberDao.deleteBuilder();
memberDeleteBuilder.where().eq("region_id", this.id);
memberDeleteBuilder.delete();
} catch (SQLException e) {
throw new RuntimeException(e);
}
}
}

@ -1,4 +1,4 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.field.DatabaseField;
@ -25,8 +25,8 @@ public class RegionMember {
@DatabaseField(foreign = true, foreignAutoRefresh = true)
private Region region;
@DatabaseField(columnName = "member_group", canBeNull = false)
private String memberGroup;
@DatabaseField(columnName = "member_type", canBeNull = false)
private String memberType;
@DatabaseField(columnName = "member_name", canBeNull = false)
private String memberName;
@ -40,7 +40,7 @@ public class RegionMember {
public RegionMember(Region region, String membertype, String memberName, PermissionGroup permissionGroup){
this.region = region;
this.memberGroup = membertype;
this.memberType = membertype;
this.memberName = memberName;
this.permissionGroup = permissionGroup;
}
@ -49,8 +49,8 @@ public class RegionMember {
return region;
}
public String getMemberGroup() {
return memberGroup;
public String getMemberType() {
return memberType;
}
public String getName() {
@ -66,9 +66,14 @@ public class RegionMember {
save();
}
public boolean hasPermission(Permission permission){
return getPermissionGroup().hasPermission(permission);
}
public void save(){
try {
getDao().createOrUpdate(this);
region.refreshCache();
} catch (SQLException e) {
throw new RuntimeException(e);
}
@ -77,6 +82,7 @@ public class RegionMember {
public void delete(){
try {
getDao().delete(this);
region.refreshCache();
} catch (SQLException e) {
throw new RuntimeException(e);
}

@ -1,4 +1,4 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.field.DatabaseField;
import com.j256.ormlite.table.DatabaseTable;
@ -27,7 +27,7 @@ public class Shop {
}
public static void setDao(Dao<Shop, Integer> dao) {
dao = dao;
Shop.dao = dao;
}
@DatabaseField(generatedId = true)

@ -0,0 +1,15 @@
package xyz.soukup.ecoCraftCore.objects;
public enum Status {
OK,
INVALID_SELECTION,
NO_PERMISSION,
NO_SELECTION,
REGION_NOT_ENVELOPS,
NOT_EXIST,
PLAYER_NOT_ON_ISLAND,
NOT_EXIST_GROUP,
ALREADY_MEMBER,
NOT_MEMBER,
}

@ -1,4 +1,4 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.field.DatabaseField;

@ -1,4 +1,4 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.field.DatabaseField;

@ -1,4 +1,4 @@
package xyz.soukup.ecoCraftCore.database.objects;
package xyz.soukup.ecoCraftCore.objects;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.field.DataType;

@ -3,7 +3,7 @@ package xyz.soukup.ecoCraftCore.player;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.player.PlayerJoinEvent;
import xyz.soukup.ecoCraftCore.database.objects.Account;
import xyz.soukup.ecoCraftCore.objects.Account;
public class PreparePlayer implements Listener {

@ -5,7 +5,7 @@ import org.bukkit.entity.Player;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.player.PlayerJoinEvent;
import xyz.soukup.ecoCraftCore.database.objects.TeleportRequest;
import xyz.soukup.ecoCraftCore.objects.TeleportRequest;
import xyz.soukup.ecoCraftCore.islands.IslandManager;
import java.sql.SQLException;

@ -9,7 +9,7 @@ import io.papermc.paper.command.brigadier.CommandSourceStack;
import io.papermc.paper.command.brigadier.Commands;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import xyz.soukup.ecoCraftCore.database.objects.Region;
import xyz.soukup.ecoCraftCore.objects.Region;
import xyz.soukup.ecoCraftCore.messages.Messages;
import java.sql.SQLException;

@ -0,0 +1,225 @@
package xyz.soukup.ecoCraftCore.regions;
import com.j256.ormlite.stmt.QueryBuilder;
import com.mojang.brigadier.arguments.IntegerArgumentType;
import com.mojang.brigadier.arguments.StringArgumentType;
import com.mojang.brigadier.builder.LiteralArgumentBuilder;
import com.mojang.brigadier.builder.RequiredArgumentBuilder;
import com.mojang.brigadier.context.CommandContext;
import com.mojang.brigadier.exceptions.CommandSyntaxException;
import com.mojang.brigadier.suggestion.Suggestions;
import com.mojang.brigadier.suggestion.SuggestionsBuilder;
import io.papermc.paper.command.brigadier.CommandSourceStack;
import io.papermc.paper.command.brigadier.Commands;
import io.papermc.paper.command.brigadier.argument.ArgumentTypes;
import io.papermc.paper.command.brigadier.argument.resolvers.selector.PlayerSelectorArgumentResolver;
import io.papermc.paper.registry.RegistryKey;
import org.bukkit.Material;
import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemStack;
import xyz.soukup.ecoCraftCore.messages.Messages;
import xyz.soukup.ecoCraftCore.messages.Replace;
import xyz.soukup.ecoCraftCore.objects.Permission;
import xyz.soukup.ecoCraftCore.objects.PermissionGroup;
import xyz.soukup.ecoCraftCore.objects.Region;
import xyz.soukup.ecoCraftCore.objects.RegionMember;
import java.sql.SQLException;
import java.util.List;
import java.util.concurrent.CompletableFuture;
public class RegionCommand {
public static LiteralArgumentBuilder<CommandSourceStack> command(){
LiteralArgumentBuilder<CommandSourceStack> confirm = Commands.literal("confirm");
RequiredArgumentBuilder<CommandSourceStack, PlayerSelectorArgumentResolver> playerArgument = Commands.argument("player", ArgumentTypes.player());
RequiredArgumentBuilder<CommandSourceStack, String> memberArgument = Commands.argument("member", StringArgumentType.word()).suggests(RegionCommand::memberGroupSuggestions);
RequiredArgumentBuilder<CommandSourceStack, String> groupArgument = Commands.argument("group", StringArgumentType.word()).suggests(RegionCommand::memberGroupSuggestions);
RequiredArgumentBuilder<CommandSourceStack, ItemStack> materialArgument = Commands.argument("icon", ArgumentTypes.itemStack());
LiteralArgumentBuilder<CommandSourceStack> create = Commands.literal("create")
.executes(RegionCommand::create);
LiteralArgumentBuilder<CommandSourceStack> delete = Commands.literal("delete")
.executes(RegionCommand::delete)
.then(confirm.executes(RegionCommand::delete));
LiteralArgumentBuilder<CommandSourceStack> addMember = Commands.literal("add-member")
.then(playerArgument.then(groupArgument.executes(RegionCommand::addMember)));
LiteralArgumentBuilder<CommandSourceStack> removeMember = Commands.literal("remove-member")
.then(playerArgument.executes(RegionCommand::removeMember));
LiteralArgumentBuilder<CommandSourceStack> member = Commands.literal("member")
.then(addMember)
.then(removeMember);
LiteralArgumentBuilder<CommandSourceStack> group = Commands.literal("group");
LiteralArgumentBuilder<CommandSourceStack> groupAdd = Commands.literal("create")
;
LiteralArgumentBuilder<CommandSourceStack> groupRemove = Commands.literal("remove");
RequiredArgumentBuilder<CommandSourceStack, Integer> regionEdits = Commands.argument("id", IntegerArgumentType.integer(1, 2147483647))
.then(delete)
.then(member)
.then(group);
return Commands.literal("region")
.requires(c -> c.getSender() instanceof Player)
.then(create)
.then(regionEdits);
}
private static CompletableFuture<Suggestions> memberGroupSuggestions(CommandContext<CommandSourceStack> context, SuggestionsBuilder builder){
Player player = (Player) context.getSource().getSender();
int id = context.getArgument("id", Integer.class);
Region region = Region.findById(id);
if (region == null){
return builder.buildFuture();
}
if (!region.hasPermission(player, Permission.MANAGE_MEMBERS)){
return builder.buildFuture();
}
RegionMember regionMember = region.getRegionMember(player);
if (regionMember == null){
return builder.buildFuture();
}
PermissionGroup senderGroup = regionMember.getPermissionGroup();
QueryBuilder<PermissionGroup, Integer> queryBuilder = PermissionGroup.getDao().queryBuilder();
try {
queryBuilder.selectColumns("name");
queryBuilder.where().eq("region_id", id).and().lt("weight", senderGroup.getWeight());
List<PermissionGroup> permissionGroups = queryBuilder.query();
for (PermissionGroup permissionGroup : permissionGroups){
builder.suggest(permissionGroup.getName());
}
} catch (SQLException e) {
throw new RuntimeException(e);
}
return builder.buildFuture();
}
private static CompletableFuture<Suggestions> memberSuggestions(CommandContext<CommandSourceStack> context, SuggestionsBuilder builder){
Player player = (Player) context.getSource().getSender();
int id = context.getArgument("id", Integer.class);
Region region = Region.findById(id);
if (region == null){
return builder.buildFuture();
}
if (!region.hasPermission(player, Permission.MANAGE_MEMBERS)){
return builder.buildFuture();
}
RegionMember regionMember = region.getRegionMember(player);
if (regionMember == null){
return builder.buildFuture();
}
PermissionGroup senderGroup = regionMember.getPermissionGroup();
QueryBuilder<RegionMember, Integer> queryBuilder = RegionMember.getDao().queryBuilder();
try {
queryBuilder.selectColumns("member_name");
queryBuilder.where().eq("region_id", id);
List<RegionMember> regionMembers = queryBuilder.query();
for (RegionMember member : regionMembers){
if (member.getPermissionGroup().getWeight() >= senderGroup.getWeight()){
continue;
}
builder.suggest(member.getName());
}
} catch (SQLException e) {
throw new RuntimeException(e);
}
return builder.buildFuture();
}
private static int removeMember(CommandContext<CommandSourceStack> context) {
int id = context.getArgument("id", Integer.class);
Player senderPlayer = (Player) context.getSource().getSender();
String memberToRemove = context.getArgument("member", String.class);
switch (RegionManager.removeMemberSafely(id, memberToRemove, senderPlayer)){
case OK -> Messages.send(senderPlayer, "region.command.removed-member");
case NOT_EXIST -> Messages.send(senderPlayer, "region.command.error.not-exist");
case NO_PERMISSION -> Messages.send(senderPlayer, "region.command.error.no-permission");
case NOT_MEMBER -> Messages.send(senderPlayer, "region.command.error.not-member");
}
return 0;
}
private static int addMember(CommandContext<CommandSourceStack> context){
int id = context.getArgument("id", Integer.class);
String groupName = context.getArgument("group", String.class);
Player senderPlayer = (Player) context.getSource().getSender();
PlayerSelectorArgumentResolver playerSelectorArgumentResolver = context.getArgument("player", PlayerSelectorArgumentResolver.class);
try {
Player playerToAdd = playerSelectorArgumentResolver.resolve(context.getSource()).getFirst();
switch (RegionManager.addMemberSafely(id, playerToAdd, senderPlayer, groupName)){
case OK -> Messages.send(senderPlayer, "region.command.added-member");
case NOT_EXIST -> Messages.send(senderPlayer, "region.command.error.not-exist");
case NO_PERMISSION -> Messages.send(senderPlayer, "region.command.error.no-permission");
case NOT_EXIST_GROUP -> Messages.send(senderPlayer, "region.command.error.not-exist-group");
case PLAYER_NOT_ON_ISLAND -> Messages.send(senderPlayer, "region.command.error.player-not-on-island");
case ALREADY_MEMBER -> Messages.send(senderPlayer, "region.command.error.already-member");
}
} catch (CommandSyntaxException e) {
throw new RuntimeException(e);
}
return 0;
}
private static int delete(CommandContext<CommandSourceStack> context) {
Player player = (Player) context.getSource().getSender();
int id = context.getArgument("id", Integer.class);
if (!context.getInput().endsWith("confirm")){
Messages.send(player, "region.command.confirm-warning.delete", new Replace("id", String.valueOf(id)));
return 1;
}
switch (RegionManager.deleteRegionSafely(id, player)){
case OK -> Messages.send(player, "region.command.deleted");
case NOT_EXIST -> Messages.send(player, "region.command.error.not-exist");
case NO_PERMISSION -> Messages.send(player, "region.command.error.no-permission");
}
return 0;
}
private static int create(CommandContext<CommandSourceStack> context) {
Player player = (Player) context.getSource().getSender();
switch (RegionManager.createRegionSafely(player)){
case OK -> Messages.send(player, "region.command.created");
case NO_SELECTION -> Messages.send(player, "region.command.error.no-selection");
case NO_PERMISSION -> Messages.send(player, "region.command.error.no-permission");
case INVALID_SELECTION -> Messages.send(player, "region.command.error.invalid-selection");
case REGION_NOT_ENVELOPS -> Messages.send(player, "region.command.error.region-not-envelops");
}
return 0;
}
}

@ -1,8 +1,13 @@
package xyz.soukup.ecoCraftCore.regions;
import org.bukkit.Bukkit;
import org.bukkit.Location;
import org.bukkit.Material;
import org.bukkit.NamespacedKey;
import org.bukkit.block.Barrel;
import org.bukkit.block.Block;
import org.bukkit.block.Chest;
import org.bukkit.block.DoubleChest;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Item;
import org.bukkit.entity.Player;
@ -12,14 +17,20 @@ import org.bukkit.event.block.Action;
import org.bukkit.event.block.BlockBreakEvent;
import org.bukkit.event.block.BlockPlaceEvent;
import org.bukkit.event.entity.EntityDamageByEntityEvent;
import org.bukkit.event.entity.EntityMountEvent;
import org.bukkit.event.entity.EntityPickupItemEvent;
import org.bukkit.event.inventory.InventoryOpenEvent;
import org.bukkit.event.inventory.InventoryPickupItemEvent;
import org.bukkit.event.player.*;
import org.bukkit.event.vehicle.VehicleDestroyEvent;
import org.bukkit.event.vehicle.VehicleEntityCollisionEvent;
import org.bukkit.inventory.InventoryHolder;
import org.bukkit.inventory.ItemStack;
import org.bukkit.persistence.PersistentDataContainer;
import org.bukkit.persistence.PersistentDataType;
import xyz.soukup.ecoCraftCore.database.objects.Region;
import xyz.soukup.ecoCraftCore.database.objects.RegionMember;
import org.bukkit.util.Vector;
import xyz.soukup.ecoCraftCore.objects.Permission;
import xyz.soukup.ecoCraftCore.objects.Region;
import static xyz.soukup.ecoCraftCore.EcoCraftCore.plugin;
@ -27,35 +38,31 @@ public class RegionEvents implements Listener {
@EventHandler
public void onPlayerInteract(PlayerInteractEvent event){
switch (event.getAction()) {
case RIGHT_CLICK_BLOCK:
case LEFT_CLICK_BLOCK:
break;
default:
return;
}
if (event.getAction() != Action.RIGHT_CLICK_BLOCK) return;
Block block = event.getClickedBlock();
ItemStack item = event.getItem();
if (block == null) return;
if (item != null && item.getType().isBlock() && !block.getType().isInteractable()) {
ItemStack item = event.getItem();
Player player = event.getPlayer();
boolean interactable = block.getType().isInteractable();
if ((!interactable || player.isSneaking()) && item != null && item.getType().isBlock()) {
return;
}
boolean allowed = isAllowedToInteract(
block.getWorld().getName(),
event.getPlayer(),
block.getX(),
block.getY(),
block.getZ()
);
boolean harvestAllowed = RegionManager.hasPermission(player, block.getLocation(), Permission.HARVEST);
if (allowed){
if (isCrop(block.getType()) && harvestAllowed) {
return;
}
boolean interactAllowed = RegionManager.hasPermission(player, block.getLocation(), Permission.INTERACT);
if (interactAllowed) {
return;
}
event.setCancelled(true);
}
@ -68,13 +75,7 @@ public class RegionEvents implements Listener {
Player player = event.getPlayer();
Location location = player.getLocation();
boolean allowed = isAllowedToInteract(
location.getWorld().getName(),
player,
location.getBlockX(),
location.getBlockY(),
location.getBlockZ()
);
boolean allowed = RegionManager.hasPermission(player, location, Permission.REDSTONE_INTERACT);
if (allowed){
return;
@ -88,15 +89,15 @@ public class RegionEvents implements Listener {
public void onBlockPlace(BlockPlaceEvent event) {
Block block = event.getBlockPlaced();
boolean allowed = isAllowedToInteract(
block.getWorld().getName(),
event.getPlayer(),
block.getX(),
block.getY(),
block.getZ()
);
boolean placeAllowed = RegionManager.hasPermission(event.getPlayer(), block.getLocation(), Permission.PLACE);
if (allowed){
if (placeAllowed){
return;
}
boolean plantAllowed = RegionManager.hasPermission(event.getPlayer(), block.getLocation(), Permission.PLANT);
if (plantAllowed && isCrop(block.getType())){
return;
}
@ -108,15 +109,15 @@ public class RegionEvents implements Listener {
Block block = event.getBlock();
boolean allowed = isAllowedToInteract(
block.getWorld().getName(),
event.getPlayer(),
block.getX(),
block.getY(),
block.getZ()
);
boolean breakAllowed = RegionManager.hasPermission(event.getPlayer(), block.getLocation(), Permission.BREAK);
if (allowed){
if (breakAllowed){
return;
}
boolean harvestAllowed = RegionManager.hasPermission(event.getPlayer(), block.getLocation(), Permission.HARVEST);
if (isCrop(block.getType()) && harvestAllowed) {
return;
}
@ -127,13 +128,7 @@ public class RegionEvents implements Listener {
public void onBucketUse(PlayerBucketEmptyEvent event) {
Block clickedBlock = event.getBlockClicked();
boolean allowed = isAllowedToInteract(
clickedBlock.getWorld().getName(),
event.getPlayer(),
clickedBlock.getX(),
clickedBlock.getY(),
clickedBlock.getZ()
);
boolean allowed = RegionManager.hasPermission(event.getPlayer(), clickedBlock.getLocation(), Permission.BUCKET_USE);
if (allowed){
return;
@ -146,13 +141,7 @@ public class RegionEvents implements Listener {
public void onBucketUse(PlayerBucketFillEvent event) {
Block clickedBlock = event.getBlockClicked();
boolean allowed = isAllowedToInteract(
clickedBlock.getWorld().getName(),
event.getPlayer(),
clickedBlock.getX(),
clickedBlock.getY(),
clickedBlock.getZ()
);
boolean allowed = RegionManager.hasPermission(event.getPlayer(), clickedBlock.getLocation(), Permission.BUCKET_USE);
if (allowed){
return;
@ -167,12 +156,7 @@ public class RegionEvents implements Listener {
Location location = entity.getLocation();
boolean allowed = isAllowedToInteract(
location.getWorld().getName(),
event.getPlayer(),
location.getBlockX(),
location.getBlockY(),
location.getBlockZ());
boolean allowed = RegionManager.hasPermission(event.getPlayer(), location, Permission.ENTITY_INTERACT);
if (allowed){
return;
@ -191,12 +175,7 @@ public class RegionEvents implements Listener {
Entity entity = event.getEntity();
Location location = entity.getLocation();
boolean allowed = isAllowedToInteract(
location.getWorld().getName(),
player,
location.getBlockX(),
location.getBlockY(),
location.getBlockZ());
boolean allowed = RegionManager.hasPermission(player, location, Permission.HARM_ENTITIES);
if (allowed){
return;
@ -215,48 +194,74 @@ public class RegionEvents implements Listener {
Location location = event.getVehicle().getLocation();
boolean allowed = isAllowedToInteract(
location.getWorld().getName(),
player,
location.getBlockX(),
location.getBlockY(),
location.getBlockZ());
boolean allowed = RegionManager.hasPermission(player, location, Permission.VEHICLE_INTERACT);
if (allowed){
return;
}
event.setCancelled(true);
event.getVehicle().setVelocity(new Vector(0, 0, 0));
}
//Preventing hopper interaction :P
@EventHandler
public void onDrop(PlayerDropItemEvent event) {
Player player = event.getPlayer();
Location location = player.getLocation();
boolean allowed = isAllowedToInteract(
location.getWorld().getName(),
player,
location.getBlockX(),
location.getBlockY(),
location.getBlockZ());
boolean allowed = RegionManager.hasPermission(player, location, Permission.DROP_ITEMS);
if (allowed){
if (!allowed){
event.setCancelled(true);
return;
}
Item item = event.getItemDrop();
item.getPersistentDataContainer().set(new NamespacedKey(plugin, "hopper_stopper"), PersistentDataType.BYTE, (byte) 1);
item.getPersistentDataContainer().set(new NamespacedKey(plugin, "player-who-dropped"), PersistentDataType.BYTE, (byte) 1);
}
@EventHandler
public void onPickup(EntityPickupItemEvent event){
if (!(event.getEntity() instanceof Player player)){
return;
}
Location location = event.getItem().getLocation();
boolean allowed = RegionManager.hasPermission(player, location, Permission.PICKUP_ITEMS);
if (allowed) return;
event.setCancelled(true);
}
@EventHandler
public void onHopperPickup(InventoryPickupItemEvent event) {
Item item = event.getItem();
PersistentDataContainer dataContainer = item.getPersistentDataContainer();
if (!dataContainer.has(new NamespacedKey(plugin, "player-who-dropped"), PersistentDataType.STRING)) {
return;
}
String playerName = dataContainer.get(new NamespacedKey(plugin, "player-who-dropped"), PersistentDataType.STRING);
assert playerName != null;
Player player = Bukkit.getPlayer(playerName);
if (!item.getPersistentDataContainer().has(new NamespacedKey(plugin, "hopper_stopper"), PersistentDataType.BYTE)) {
if (player == null){
event.setCancelled(true);
return;
}
boolean allowed = RegionManager.hasPermission(player, item.getLocation(), Permission.USE_HOPPER);
if (allowed){
return;
}
@ -271,12 +276,7 @@ public class RegionEvents implements Listener {
Location location = event.getVehicle().getLocation();
boolean allowed = isAllowedToInteract(
location.getWorld().getName(),
player,
location.getBlockX(),
location.getBlockY(),
location.getBlockZ());
boolean allowed = RegionManager.hasPermission(player, location, Permission.VEHICLE_BREAK);
if (allowed){
return;
@ -285,34 +285,89 @@ public class RegionEvents implements Listener {
event.setCancelled(true);
}
@EventHandler
public void onOpenChest(InventoryOpenEvent event) {
InventoryHolder holder = event.getInventory().getHolder();
Player player = (Player) event.getPlayer();
Location location = player.getLocation();
if (!(holder instanceof Chest || holder instanceof DoubleChest || holder instanceof Barrel)){
return;
}
boolean allowed = RegionManager.hasPermission(player, location, Permission.OPEN_CHESTS);
if (allowed){
return;
}
event.setCancelled(true);
private boolean isAllowedToInteract(String island, Player player, Location location){
return isAllowedToInteract(island, player, location.getBlockX(), location.getBlockY(), location.getBlockZ());
}
private boolean isAllowedToInteract(String island, Player player, int x, int y, int z){
if (player.isOp()){
return true;
@EventHandler
public void onMove(PlayerMoveEvent event) {
if (event.getFrom().getBlockX() == event.getTo().getBlockX()
&& event.getFrom().getBlockY() == event.getTo().getBlockY()
&& event.getFrom().getBlockZ() == event.getTo().getBlockZ()) {
return;
}
Region region = Region.findRegion(x, y, z, island);
Player player = event.getPlayer();
Location from = event.getFrom();
Location to = event.getTo();
if (region == null){
return false;
Region fromRegion = Region.findRegion(from);
Region toRegion = Region.findRegion(to);
if (fromRegion == toRegion){
return;
}
String name = player.getName();
boolean allowedToEnter = RegionManager.hasPermission(player, toRegion, Permission.ENTER);
boolean allowedToExit = RegionManager.hasPermission(player, fromRegion, Permission.EXIT);
for (RegionMember regionMember : region.getRegionMembers()){
if (allowedToEnter && allowedToExit){
return;
}
if (regionMember.getMemberGroup().equals("player") && regionMember.getName().equals(name)){
return true;
event.setCancelled(true);
}
@EventHandler
public void onMountVehicle(EntityMountEvent event) {
if (!(event.getEntity() instanceof Player player)){
return;
}
return false;
Entity mount = event.getMount();
String entityType = mount.getType().name();
if (!(entityType.contains("BOAT") || entityType.contains("MINECART"))){
return;
}
Location location = mount.getLocation();
boolean allowed = RegionManager.hasPermission(player, location, Permission.VEHICLE_RIDE);
if (allowed){
return;
}
event.setCancelled(true);
}
private boolean isCrop(Material material) {
String name = material.name();
return name.endsWith("_SAPLING") || name.endsWith("_CROPS") ||
material == Material.WHEAT || material == Material.CARROTS ||
material == Material.POTATOES || material == Material.BEETROOTS ||
material == Material.NETHER_WART || material == Material.SWEET_BERRY_BUSH ||
material == Material.SUGAR_CANE || material == Material.CACTUS ||
material == Material.PUMPKIN_STEM || material == Material.MELON_STEM;
}
}

@ -2,12 +2,14 @@ package xyz.soukup.ecoCraftCore.regions;
import org.bukkit.Location;
import org.bukkit.entity.Player;
import xyz.soukup.ecoCraftCore.database.objects.Region;
import xyz.soukup.ecoCraftCore.database.objects.RegionMember;
import xyz.soukup.ecoCraftCore.objects.*;
import xyz.soukup.ecoCraftCore.positionMarker.MarkerEvent;
public class RegionManager {
public static int createRegion(Player player, Integer type, String owner, String ownerType){
public static PermissionGroup defaultPermissions = new PermissionGroup(409696);
public static int createRegion(Player player, Integer level, String owner, String ownerType){
Location primaryLocation = MarkerEvent.primaryLocations.get(player);
Location secondaryLocation = MarkerEvent.secondaryLocations.get(player);
@ -27,7 +29,7 @@ public class RegionManager {
int y2 = secondaryLocation.getBlockY();
int z2 = secondaryLocation.getBlockZ();
Region region = new Region(worldName, type, x1, y1, z1, x2, y2, z2);
Region region = new Region(worldName, level, x1, y1, z1, x2, y2, z2);
region.save();
region.addRegionMember(ownerType, owner, region.getPermissionGroup("owner"));
@ -68,11 +70,175 @@ public class RegionManager {
for (RegionMember regionMember : region.getRegionMembers()){
if (regionMember.getMemberGroup().equals("player") && regionMember.getName().equals(name)){
if (regionMember.getMemberType().equals("player") && regionMember.getName().equals(name)){
return true;
}
}
return false;
}
public static boolean hasPermission(Player player, Location location, Permission permission){
if (player.hasPermission("ecocraftcore.region.bypass")){
return true;
}
int x = location.getBlockX();
int y = location.getBlockY();
int z = location.getBlockZ();
String island = location.getWorld().getName();
Region region = Region.findRegion(x, y, z, island);
return hasPermission(player, region, permission);
}
public static boolean hasPermission(Player player, Region region, Permission permission){
if (player.hasPermission("ecocraftcore.region.bypass")){
return true;
}
if (region == null){
return defaultPermissions.hasPermission(permission);
}
return region.hasPermission(player, permission);
}
public static boolean hasPermission(String memberType, String memberName, Location location, Permission permission){
int x = location.getBlockX();
int y = location.getBlockY();
int z = location.getBlockZ();
String island = location.getWorld().getName();
Region region = Region.findRegion(x, y, z, island);
return hasPermission(memberType, memberName, region, permission);
}
public static boolean hasPermission(String memberType, String memberName, Region region, Permission permission){
if (region == null){
return defaultPermissions.hasPermission(permission);
}
return region.hasPermission(memberType, memberName, permission);
}
public static Status deleteRegionSafely(int regionId, Player player){
Region region = Region.findById(regionId);
if (region == null){
return Status.NOT_EXIST;
}
if (!region.hasPermission(player, Permission.MANAGE_REGIONS)){
return Status.NO_PERMISSION;
}
region.delete();
return Status.OK;
}
public static Status createRegionSafely(Player player){
Location primaryLocation = MarkerEvent.primaryLocations.get(player);
Location secondaryLocation = MarkerEvent.secondaryLocations.get(player);
if (primaryLocation == null || secondaryLocation == null){
return Status.NO_SELECTION;
}
Region region = Region.getHighestLevelRegion(primaryLocation, secondaryLocation);
if (region == null){
return Status.INVALID_SELECTION;
}
if (!region.hasPermission(player, Permission.MANAGE_REGIONS)){
return Status.NO_PERMISSION;
}
if (!region.envelops(primaryLocation, secondaryLocation)){
return Status.REGION_NOT_ENVELOPS;
}
int x1 = primaryLocation.getBlockX();
int y1 = primaryLocation.getBlockY();
int z1 = primaryLocation.getBlockZ();
int x2 = secondaryLocation.getBlockX();
int y2 = secondaryLocation.getBlockY();
int z2 = secondaryLocation.getBlockZ();
new Region(region, x1, y1, z1, x2, y2, z2);
return Status.OK;
}
public static Status addMemberSafely(int id, Player playerToAdd, Player senderPlayer, String permissionGroupName) {
Region region = Region.findById(id);
if (region == null){
return Status.NOT_EXIST;
}
PermissionGroup group = region.getPermissionGroup(permissionGroupName);
PermissionGroup senderGroup = region.getRegionMember(senderPlayer).getPermissionGroup();
if (group == null){
return Status.NOT_EXIST_GROUP;
}
if (playerToAdd.getWorld().getName().equals(region.getIsland())){
return Status.PLAYER_NOT_ON_ISLAND;
}
if (!(region.hasPermission(senderPlayer, Permission.MANAGE_MEMBERS) && senderGroup.getWeight() > group.getWeight())){
return Status.NO_PERMISSION;
}
if (region.getRegionMember(playerToAdd) != null){
return Status.ALREADY_MEMBER;
}
region.addRegionMember(playerToAdd, group);
return Status.OK;
}
public static Status removeMemberSafely(int id, String memberToRemove, Player senderPlayer){
Region region = Region.findById(id);
if (region == null){
return Status.NOT_EXIST;
}
RegionMember regionMember = region.getRegionMember( "player", memberToRemove);
if (regionMember == null){
return Status.NOT_MEMBER;
}
PermissionGroup GroupOfRemoved = regionMember.getPermissionGroup();
RegionMember senderAsMember = region.getRegionMember(senderPlayer);
if (senderAsMember == null){
return Status.NO_PERMISSION;
}
PermissionGroup senderGroup = senderAsMember.getPermissionGroup();
if (!(region.hasPermission(senderPlayer, Permission.MANAGE_MEMBERS) && senderGroup.getWeight() > GroupOfRemoved.getWeight())){
return Status.NO_PERMISSION;
}
region.removeRegionMember("player", memberToRemove);
return Status.OK;
}
}

@ -10,8 +10,8 @@ import org.bukkit.block.Sign;
import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemStack;
import xyz.soukup.ecoCraftCore.positionMarker.MarkerEvent;
import xyz.soukup.ecoCraftCore.database.objects.Shop;
import xyz.soukup.ecoCraftCore.database.objects.VirtualChest;
import xyz.soukup.ecoCraftCore.objects.Shop;
import xyz.soukup.ecoCraftCore.objects.VirtualChest;
import xyz.soukup.ecoCraftCore.inventory.InventoryUtils;
import xyz.soukup.ecoCraftCore.messages.Messages;
import xyz.soukup.ecoCraftCore.utilities.PDC;

@ -31,10 +31,10 @@ import xyz.soukup.ecoCraftCore.virtualChest.VirtualChestLogic;
import xyz.soukup.ecoCraftCore.gui.GuiItemBuilder;
import xyz.soukup.ecoCraftCore.inventory.InventoryUtils;
import xyz.soukup.ecoCraftCore.messages.Messages;
import xyz.soukup.ecoCraftCore.database.objects.Account;
import xyz.soukup.ecoCraftCore.database.objects.Shop;
import xyz.soukup.ecoCraftCore.database.objects.Transaction;
import xyz.soukup.ecoCraftCore.database.objects.VirtualChest;
import xyz.soukup.ecoCraftCore.objects.Account;
import xyz.soukup.ecoCraftCore.objects.Shop;
import xyz.soukup.ecoCraftCore.objects.Transaction;
import xyz.soukup.ecoCraftCore.objects.VirtualChest;
import xyz.soukup.ecoCraftCore.utilities.*;
import java.util.HashMap;

@ -23,12 +23,10 @@ import org.bukkit.block.sign.Side;
import org.bukkit.block.sign.SignSide;
import org.bukkit.entity.Player;
import org.bukkit.persistence.PersistentDataType;
import xyz.soukup.ecoCraftCore.database.objects.Shop;
import xyz.soukup.ecoCraftCore.messages.Messages;
import xyz.soukup.ecoCraftCore.regions.RegionManager;
import xyz.soukup.ecoCraftCore.utilities.PDC;
import javax.sound.sampled.Line;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

@ -16,6 +16,8 @@ import org.bukkit.event.player.PlayerQuitEvent;
import org.bukkit.event.player.PlayerTeleportEvent;
import org.bukkit.event.vehicle.VehicleExitEvent;
import org.bukkit.persistence.PersistentDataType;
import xyz.soukup.ecoCraftCore.objects.Permission;
import xyz.soukup.ecoCraftCore.regions.RegionManager;
import xyz.soukup.ecoCraftCore.utilities.PDC;
@ -55,6 +57,12 @@ public class LetMeSit implements Listener {
return;
}
boolean allowed = RegionManager.hasPermission(player, block.getLocation(), Permission.SIT);
if (!allowed){
return;
}
float yaw = switch (stairs.getFacing()) {
case NORTH -> 0f;
case WEST -> -90f;

@ -15,9 +15,8 @@ import org.bukkit.event.inventory.InventoryMoveItemEvent;
import org.bukkit.event.inventory.InventoryOpenEvent;
import org.bukkit.inventory.InventoryHolder;
import org.bukkit.inventory.ItemStack;
import xyz.soukup.ecoCraftCore.database.objects.Shop;
import xyz.soukup.ecoCraftCore.gui.GuiItemBuilder;
import xyz.soukup.ecoCraftCore.database.objects.VirtualChest;
import xyz.soukup.ecoCraftCore.objects.VirtualChest;
import xyz.soukup.ecoCraftCore.messages.Messages;
import xyz.soukup.ecoCraftCore.utilities.PDC;

@ -1,6 +1,6 @@
generic:
success:
creat ed: <green>Vytvořeno.
created: <green>Vytvořeno.
error:
not-player: "<red>Na tuto akci musíš být hráč"
no-funds:
@ -13,6 +13,23 @@ generic:
self: "<red>Nemáš dostatek itemů"
shop: "<red>Obchod nemá dostatek itemů"
region:
command:
created: "<green>Pozemek vytvořen."
deleted: "<green>Pozemek odstraněn."
added-member: "<green>Hráč přidán do pozemku."
removed-member: "<green>Hráč odebrán z pozemku."
confirm-warning:
delete: "<gold><b>!! </b>Chystáš se odstranit pozemek<b> !!</b><br>Pokud nemáš nadřadný pozemek přijdeš o území<br><red><bold><hover:show_text:'<red><bold>ODSTRANIT POZEMEK<br><dark_red>NELZE VRÁTIT ZPĚT'><click:run_command:'/region <id> delete confirm'>-> POTVRDIT A ODSTRANIT <-</click></hover>"
error:
no-selection: "<red>Musíš označit pozice"
no-permission: "<red>Zde nemáš povolení vytvořit pozemky"
invalid-selection: "<red>Neplatná pozice"
region-not-envelops: "<red>Podřadný pozemek musí být vytvořen na jednom stávajícím pozemku"
not-exist: "<red>Region neexistuje"
not-esist-group: "<red>Skupina, do které se snažíš zařadit hráče neexistuje"
player-not-on-island: "<red>Hráš musí být na stejném ostrově jako pozemek"
already-member: "<red>Hráč je již členem tohoto pozemku"
not-member: "<red>Hráč není členem tohoto pozemku"
permission-groups:
owner:
name: "<red>Majitel"

Loading…
Cancel
Save