You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Minecraft Bukkit插件中为武器添加射击冷却机制?

解决Minecraft Bukkit插件武器射击冷却问题

核心思路

通过玩家元数据标记特定武器的冷却状态,结合Bukkit Scheduler在冷却时间结束后移除标记,实现每把武器独立的射速限制。

修改步骤及代码实现

1. 完善事件监听类(OnPlayerInteract.java)

在右键事件中先检查冷却状态,只有未冷却时才允许射击,射击后启动计时器移除冷却标记:

package me.imhartash.imhartashguns.Events;

import me.imhartash.imhartashguns.Handler.Gun;
import me.imhartash.imhartashguns.ImHartashGuns;
import org.bukkit.Bukkit;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.block.Action;
import org.bukkit.event.player.PlayerInteractEvent;
import org.bukkit.metadata.FixedMetadataValue;

public class OnPlayerInteract implements Listener {

    private final ImHartashGuns plugin;

    // 构造函数传入插件实例,用于Scheduler和元数据管理
    public OnPlayerInteract(ImHartashGuns plugin) {
        this.plugin = plugin;
    }

    @EventHandler
    public void onPlayerInteract(PlayerInteractEvent event) {
        // 只处理右键空气/方块动作
        if (event.getAction() != Action.RIGHT_CLICK_AIR && event.getAction() != Action.RIGHT_CLICK_BLOCK) {
            return;
        }

        Gun gun = Gun.GetGunByItem(event.getItem());
        if (gun == null) {
            return;
        }

        String cooldownKey = "gun_cooldown_" + gun.getName();
        // 检查玩家是否处于当前武器的冷却中
        if (event.getPlayer().hasMetadata(cooldownKey)) {
            long remainingTicks = event.getPlayer().getMetadata(cooldownKey).get(0).asLong();
            double remainingSeconds = remainingTicks / 20.0;
            event.getPlayer().sendMessage("[" + gun.getName() + "] 冷却中,剩余 " + String.format("%.1f", remainingSeconds) + " 秒");
            event.setCancelled(true); // 取消事件,避免触发其他右键行为
            return;
        }

        // 执行射击逻辑
        gun.shot(event.getItem(), event.getPlayer());

        // 设置冷却标记,值为冷却时长(ticks)
        event.getPlayer().setMetadata(cooldownKey, new FixedMetadataValue(plugin, gun.getCD()));

        // 启动Scheduler,冷却结束后移除标记
        Bukkit.getScheduler().runTaskLater(plugin, () -> {
            if (event.getPlayer().isOnline() && event.getPlayer().hasMetadata(cooldownKey)) {
                event.getPlayer().removeMetadata(cooldownKey, plugin);
            }
        }, gun.getCD());
    }
}

2. 注册事件时传入插件实例

在主类ImHartashGuns的onEnable方法中,注册事件时必须传入插件实例,否则Scheduler会失效:

@Override
public void onEnable() {
    // 注册事件监听
    getServer().getPluginManager().registerEvents(new OnPlayerInteract(this), this);
    // 其他初始化逻辑...
}

3. 添加AWP武器定义(Gun.java)

在枚举中加入AWP的配置,设置合理的冷却时长(20 ticks = 1秒,CS原版AWP射速约1.5秒,对应30 ticks):

public enum Gun {
    AKM("AKM", 30, Material.GOLD_INGOT, 10, 20),
    GLOCK18("Glock-18", 18, Material.IRON_INGOT, 2, 200),
    AWP("AWP", 10, Material.DIAMOND_INGOT, 100, 30); // 新增AWP配置

    // 原有枚举字段、构造函数、方法保持不变...
}

关键细节说明

  • 冷却与玩家绑定:使用玩家元数据而非物品数据,确保玩家切换武器时,不同武器的冷却独立计算。
  • Scheduler必须传插件实例:Bukkit的Scheduler需要插件上下文才能正常运行,这是之前冷却失效的常见原因。
  • 取消事件:冷却中调用event.setCancelled(true),避免玩家在冷却时触发其他右键动作(比如用武器材质方块放置)。

内容的提问来源于stack exchange,提问作者ImHartash

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.03 12:58:17