9
0
mirror of https://github.com/Xiao-MoMi/Custom-Crops.git synced 2025-12-19 15:09:25 +00:00

Added insight mode

This commit is contained in:
XiaoMoMi
2024-09-04 19:21:16 +08:00
parent b8eac47430
commit b6dc502138
14 changed files with 299 additions and 1 deletions

View File

@@ -21,6 +21,7 @@ import com.flowpowered.nbt.CompoundMap;
import com.flowpowered.nbt.IntTag;
import com.flowpowered.nbt.StringTag;
import com.flowpowered.nbt.Tag;
import net.kyori.adventure.text.format.NamedTextColor;
import net.momirealms.customcrops.api.core.world.CustomCropsBlockState;
import net.momirealms.customcrops.api.core.world.CustomCropsWorld;
import net.momirealms.customcrops.api.core.world.Pos3;
@@ -96,4 +97,9 @@ public abstract class AbstractCustomCropsBlock implements CustomCropsBlock {
@Override
public void onPlace(WrappedPlaceEvent event) {
}
@Override
public NamedTextColor insightColor() {
return NamedTextColor.WHITE;
}
}

View File

@@ -18,6 +18,7 @@
package net.momirealms.customcrops.api.core.block;
import com.flowpowered.nbt.IntTag;
import net.kyori.adventure.text.format.NamedTextColor;
import net.momirealms.customcrops.api.BukkitCustomCropsPlugin;
import net.momirealms.customcrops.api.action.ActionManager;
import net.momirealms.customcrops.api.context.Context;
@@ -386,4 +387,9 @@ public class CropBlock extends AbstractCustomCropsBlock {
public CropConfig config(CustomCropsBlockState state) {
return Registries.CROP.get(id(state));
}
@Override
public NamedTextColor insightColor() {
return NamedTextColor.GREEN;
}
}

View File

@@ -18,6 +18,7 @@
package net.momirealms.customcrops.api.core.block;
import com.flowpowered.nbt.CompoundMap;
import net.kyori.adventure.text.format.NamedTextColor;
import net.momirealms.customcrops.api.core.world.CustomCropsBlockState;
import net.momirealms.customcrops.api.core.world.CustomCropsWorld;
import net.momirealms.customcrops.api.core.world.Pos3;
@@ -45,4 +46,6 @@ public interface CustomCropsBlock {
void onPlace(WrappedPlaceEvent event);
boolean isBlockInstance(String id);
NamedTextColor insightColor();
}

View File

@@ -17,6 +17,7 @@
package net.momirealms.customcrops.api.core.block;
import net.kyori.adventure.text.format.NamedTextColor;
import net.momirealms.customcrops.api.BukkitCustomCropsPlugin;
import net.momirealms.customcrops.api.core.BuiltInBlockMechanics;
import net.momirealms.customcrops.api.core.ConfigManager;
@@ -115,4 +116,9 @@ public class GreenhouseBlock extends AbstractCustomCropsBlock {
});
return state;
}
@Override
public NamedTextColor insightColor() {
return NamedTextColor.GRAY;
}
}

View File

@@ -18,6 +18,7 @@
package net.momirealms.customcrops.api.core.block;
import com.flowpowered.nbt.*;
import net.kyori.adventure.text.format.NamedTextColor;
import net.momirealms.customcrops.api.BukkitCustomCropsPlugin;
import net.momirealms.customcrops.api.action.ActionManager;
import net.momirealms.customcrops.api.context.Context;
@@ -638,4 +639,9 @@ public class PotBlock extends AbstractCustomCropsBlock {
tag.put(new StringTag("id", fertilizer.id()));
return tag;
}
@Override
public NamedTextColor insightColor() {
return NamedTextColor.LIGHT_PURPLE;
}
}

View File

@@ -17,6 +17,7 @@
package net.momirealms.customcrops.api.core.block;
import net.kyori.adventure.text.format.NamedTextColor;
import net.momirealms.customcrops.api.BukkitCustomCropsPlugin;
import net.momirealms.customcrops.api.core.BuiltInBlockMechanics;
import net.momirealms.customcrops.api.core.ConfigManager;
@@ -115,4 +116,9 @@ public class ScarecrowBlock extends AbstractCustomCropsBlock {
});
return state;
}
@Override
public NamedTextColor insightColor() {
return NamedTextColor.YELLOW;
}
}

View File

@@ -19,6 +19,7 @@ package net.momirealms.customcrops.api.core.block;
import com.flowpowered.nbt.IntTag;
import com.flowpowered.nbt.Tag;
import net.kyori.adventure.text.format.NamedTextColor;
import net.momirealms.customcrops.api.BukkitCustomCropsPlugin;
import net.momirealms.customcrops.api.action.ActionManager;
import net.momirealms.customcrops.api.context.Context;
@@ -359,4 +360,9 @@ public class SprinklerBlock extends AbstractCustomCropsBlock {
FurnitureRotation rotation = BukkitCustomCropsPlugin.getInstance().getItemManager().remove(location, ExistenceForm.ANY);
BukkitCustomCropsPlugin.getInstance().getItemManager().place(location, config.existenceForm(), hasWater ? config.threeDItemWithWater() : config.threeDItem(), rotation);
}
@Override
public NamedTextColor insightColor() {
return NamedTextColor.AQUA;
}
}

View File

@@ -149,6 +149,13 @@ public interface CustomCropsWorld<W> {
*/
CustomCropsChunk[] loadedChunks();
/**
* Gets all the lazy chunks in this world.
*
* @return An array of {@link CustomCropsChunk} representing the lazy chunks.
*/
CustomCropsChunk[] lazyChunks();
/**
* Gets the block state at a specific location.
*

View File

@@ -137,6 +137,11 @@ public class CustomCropsWorldImpl<W> implements CustomCropsWorld<W> {
return loadedChunks.values().toArray(new CustomCropsChunk[0]);
}
@Override
public CustomCropsChunk[] lazyChunks() {
return lazyChunks.values().toArray(new CustomCropsChunk[0]);
}
@NotNull
@Override
public Optional<CustomCropsBlockState> getBlockState(Pos3 location) {

View File

@@ -41,7 +41,9 @@ public class BukkitCommandManager extends AbstractCommandManager<CommandSender>
new SetSeasonCommand(this),
new GetDateCommand(this),
new SetDateCommand(this),
new ForceTickCommand(this)
new ForceTickCommand(this),
new DebugWorldsCommand(this),
new DebugInsightCommand(this)
);
private final Index<String, CommandFeature<CommandSender>> INDEX = Index.create(CommandFeature::getFeatureID, FEATURES);

View File

@@ -0,0 +1,168 @@
/*
* Copyright (C) <2024> <XiaoMoMi>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
package net.momirealms.customcrops.bukkit.command.feature;
import net.momirealms.customcrops.api.BukkitCustomCropsPlugin;
import net.momirealms.customcrops.api.core.world.*;
import net.momirealms.customcrops.api.util.LocationUtils;
import net.momirealms.customcrops.bukkit.command.BukkitCommandFeature;
import net.momirealms.customcrops.common.command.CustomCropsCommandManager;
import net.momirealms.customcrops.common.helper.AdventureHelper;
import net.momirealms.customcrops.common.plugin.scheduler.SchedulerTask;
import net.momirealms.sparrow.heart.SparrowHeart;
import net.momirealms.sparrow.heart.feature.color.NamedTextColor;
import net.momirealms.sparrow.heart.feature.highlight.HighlightBlocks;
import org.bukkit.Bukkit;
import org.bukkit.Chunk;
import org.bukkit.Location;
import org.bukkit.World;
import org.bukkit.command.CommandSender;
import org.bukkit.entity.Player;
import org.bukkit.metadata.FixedMetadataValue;
import org.incendo.cloud.Command;
import org.incendo.cloud.CommandManager;
import java.util.*;
import java.util.concurrent.TimeUnit;
public class DebugInsightCommand extends BukkitCommandFeature<CommandSender> {
public DebugInsightCommand(CustomCropsCommandManager<CommandSender> commandManager) {
super(commandManager);
}
@Override
public Command.Builder<? extends CommandSender> assembleCommand(CommandManager<CommandSender> manager, Command.Builder<CommandSender> builder) {
return builder
.senderType(Player.class)
.handler(context -> {
BukkitCustomCropsPlugin plugin = BukkitCustomCropsPlugin.getInstance();
Player player = context.sender();
if (player.hasMetadata("customcrops:insight")) {
player.removeMetadata("customcrops:insight", plugin.getBoostrap());
plugin.getSenderFactory().wrap(player).sendMessage(AdventureHelper.miniMessage("<red>Insight mode: OFF"));
return;
}
player.setMetadata("customcrops:insight", new FixedMetadataValue(plugin.getBoostrap(), 1));
new InsightPlayer(player.getUniqueId());
plugin.getSenderFactory().wrap(player).sendMessage(AdventureHelper.miniMessage("<green>Insight mode: ON"));
plugin.getSenderFactory().wrap(player).sendMessage(AdventureHelper.miniMessage("<white>Note: "));
});
}
@Override
public String getFeatureID() {
return "debug_insight";
}
public static class InsightPlayer implements Runnable {
private final SchedulerTask task;
private final UUID uuid;
private final HashMap<ChunkPos, HighlightBlocks[]> highlightCache = new HashMap<>();
private ChunkPos currentPos = null;
private String currentWorld = null;
public InsightPlayer(UUID uuid) {
this.uuid = uuid;
this.task = BukkitCustomCropsPlugin.getInstance().getScheduler().asyncRepeating(this, 50, 50, TimeUnit.MILLISECONDS);
}
@Override
public void run() {
Player player = Bukkit.getPlayer(uuid);
if (player == null || !player.isOnline() || !player.hasMetadata("customcrops:insight")) {
for (HighlightBlocks[] blocks : highlightCache.values()) {
for (HighlightBlocks block : blocks) {
block.destroy(player);
}
}
highlightCache.clear();
task.cancel();
return;
}
World world = player.getWorld();
String worldName = player.getWorld().getName();
if (!worldName.equals(currentWorld)) {
currentWorld = worldName;
for (HighlightBlocks[] blocks : highlightCache.values()) {
for (HighlightBlocks block : blocks) {
block.destroy(player);
}
}
highlightCache.clear();
currentPos = null;
}
Optional<CustomCropsWorld<?>> optionWorld = BukkitCustomCropsPlugin.getInstance().getWorldManager().getWorld(world);
if (optionWorld.isEmpty()) {
return;
}
CustomCropsWorld<?> customCropsWorld = optionWorld.get();
Chunk chunk = player.getLocation().getChunk();
ChunkPos chunkPos = ChunkPos.fromBukkitChunk(chunk);
if (!chunkPos.equals(currentPos)) {
currentPos = chunkPos;
HashSet<ChunkPos> nearbyChunks = new HashSet<>();
for (int i = -2; i < 3; i++) {
for (int j = -2; j < 3; j++) {
nearbyChunks.add(ChunkPos.of(currentPos.x() + i, currentPos.z() + j));
}
}
ArrayList<ChunkPos> chunksToRemove = new ArrayList<>();
for (Map.Entry<ChunkPos, HighlightBlocks[]> entry : highlightCache.entrySet()) {
if (!nearbyChunks.contains(entry.getKey())) {
chunksToRemove.add(entry.getKey());
}
}
for (ChunkPos pos : chunksToRemove) {
HighlightBlocks[] blocks = highlightCache.remove(pos);
for (HighlightBlocks block : blocks) {
block.destroy(player);
}
}
for (ChunkPos pos : nearbyChunks) {
if (!highlightCache.containsKey(pos)) {
customCropsWorld.getChunk(pos).ifPresentOrElse(cropsChunk -> {
ArrayList<HighlightBlocks> highlightBlockList = new ArrayList<>();
HashMap<net.kyori.adventure.text.format.NamedTextColor, List<Location>> blockMap = new HashMap<>();
for (CustomCropsSection section : cropsChunk.sections()) {
for (Map.Entry<BlockPos, CustomCropsBlockState> entry : section.blockMap().entrySet()) {
net.kyori.adventure.text.format.NamedTextColor namedTextColor = entry.getValue().type().insightColor();
Location location = LocationUtils.toSurfaceCenterLocation(entry.getKey().toPos3(pos).toLocation(world));
List<Location> locations = blockMap.computeIfAbsent(namedTextColor, k -> new ArrayList<>());
locations.add(location);
}
}
for (Map.Entry<net.kyori.adventure.text.format.NamedTextColor, List<Location>> entry : blockMap.entrySet()) {
highlightBlockList.add(SparrowHeart.getInstance().highlightBlocks(
player, NamedTextColor.namedColor(entry.getKey().value()), entry.getValue().toArray(new Location[0])
));
}
highlightCache.put(pos, highlightBlockList.toArray(new HighlightBlocks[0]));
}, () -> {
highlightCache.put(pos, new HighlightBlocks[0]);
});
}
}
}
}
}
}

View File

@@ -0,0 +1,56 @@
/*
* Copyright (C) <2024> <XiaoMoMi>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
package net.momirealms.customcrops.bukkit.command.feature;
import net.momirealms.customcrops.api.BukkitCustomCropsPlugin;
import net.momirealms.customcrops.bukkit.command.BukkitCommandFeature;
import net.momirealms.customcrops.common.command.CustomCropsCommandManager;
import net.momirealms.customcrops.common.helper.AdventureHelper;
import net.momirealms.customcrops.common.sender.Sender;
import org.bukkit.Bukkit;
import org.bukkit.World;
import org.bukkit.command.CommandSender;
import org.incendo.cloud.Command;
import org.incendo.cloud.CommandManager;
public class DebugWorldsCommand extends BukkitCommandFeature<CommandSender> {
public DebugWorldsCommand(CustomCropsCommandManager<CommandSender> commandManager) {
super(commandManager);
}
@Override
public Command.Builder<? extends CommandSender> assembleCommand(CommandManager<CommandSender> manager, Command.Builder<CommandSender> builder) {
return builder
.handler(context -> {
Sender sender = BukkitCustomCropsPlugin.getInstance().getSenderFactory().wrap(context.sender());
for (World world : Bukkit.getWorlds()) {
BukkitCustomCropsPlugin.getInstance().getWorldManager().getWorld(world).ifPresent(w -> {
sender.sendMessage(AdventureHelper.miniMessage("<gold>World: " + world.getName() + "</gold>"));
sender.sendMessage(AdventureHelper.miniMessage(" - Loaded chunks: " + w.loadedChunks().length));
sender.sendMessage(AdventureHelper.miniMessage(" - Lazy chunks: " + w.lazyChunks().length));
});
}
});
}
@Override
public String getFeatureID() {
return "debug_worlds";
}
}

View File

@@ -143,6 +143,13 @@ public class BukkitConfigManager extends ConfigManager {
}
}
}
for (String id : scarecrow) {
Registries.BLOCKS.register(id, BuiltInBlockMechanics.SCARECROW.mechanic());
}
for (String id : greenhouse) {
Registries.BLOCKS.register(id, BuiltInBlockMechanics.GREENHOUSE.mechanic());
}
}
@Override

View File

@@ -51,6 +51,20 @@ debug_data:
- /customcrops debug data
- /ccrops debug data
debug_worlds:
enable: true
permission: customcrops.command.debug
usage:
- /customcrops debug worlds
- /ccrops debug worlds
debug_insight:
enable: true
permission: customcrops.command.debug
usage:
- /customcrops debug insight
- /ccrops debug insight
force_tick:
enable: true
permission: customcrops.command.force_tick