Lewati ke konten

Integrasi Plugin dengan RankForge API – Contoh Kode Lengkap

Halaman ini berisi contoh siap salin untuk mengintegrasikan plugin kamu dengan RankForge. Pastikan sudah menyelesaikan Setup Dependency.

Skeleton plugin dengan integrasi RankForge

Section titled “Skeleton plugin dengan integrasi RankForge”

Struktur proyek:

  • Directorysrc/main/
    • Directoryjava/com/example/myplugin/
      • MyPlugin.java
      • RankForgeHook.java
    • Directoryresources/
      • plugin.yml
name: MyPlugin
version: 1.0.0
main: com.example.myplugin.MyPlugin
api-version: '1.21'
folia-supported: true
softdepend: [RankForge]
commands:
mystats:
description: Lihat statistik RankForge kamu
usage: /mystats

RankForge hanya menjalankan rewards: tier pada alur kill dan hanya sekali per tier. Untuk reward sendiri atau reward dari perubahan poin lewat API, dengarkan PlayerTierUpEvent. Karena event bisa terpicu lagi jika poin naik-turun, catat reward yang sudah kamu berikan.

import org.bukkit.NamespacedKey;
import org.bukkit.persistence.PersistentDataContainer;
import org.bukkit.persistence.PersistentDataType;
private NamespacedKey claimedKey() {
return new NamespacedKey(plugin, "claimed_tiers");
}
@EventHandler
public void onTierUp(PlayerTierUpEvent event) {
Player player = event.getPlayer();
String tierId = event.getNewTier().id;
PersistentDataContainer pdc = player.getPersistentDataContainer();
String raw = pdc.getOrDefault(claimedKey(), PersistentDataType.STRING, "");
java.util.Set<String> claimed = new java.util.HashSet<>(
raw.isEmpty() ? java.util.List.of() : java.util.List.of(raw.split(",")));
if (!claimed.add(tierId)) {
return; // sudah pernah dapat reward ini
}
pdc.set(claimedKey(), PersistentDataType.STRING, String.join(",", claimed));
// Berikan reward kamu sendiri
player.getInventory().addItem(new org.bukkit.inventory.ItemStack(org.bukkit.Material.DIAMOND, 8));
player.sendMessage("§aReward tier " + event.getNewTier().display + " §adiberikan!");
}

Contoh: memberi poin saat pemain menyelesaikan event buatanmu. Panggil dari thread server.

public void rewardEventWinner(Player winner) {
IRankForgeAPI api = RankForgeAPI.get();
api.addPoints(winner, 25); // memicu PlayerPointsChangeEvent, dan TierUp jika naik tier
winner.sendMessage("§a+25 poin RankForge!");
}
@EventHandler
public void onPointsChange(PlayerPointsChangeEvent event) {
if (event.getDifference() <= 0) return;
Player online = event.getPlayer().getPlayer();
if (online != null && online.hasPermission("myplugin.vip")) {
int extra = (int) Math.ceil(event.getDifference() * 0.10);
event.setNewPoints(event.getNewPoints() + extra);
}
}
import xyz.noxlydev.rankforge.model.PlayerData;
import xyz.noxlydev.rankforge.model.Tier;
public void sendTop(CommandSender sender, int limit) {
IRankForgeAPI api = RankForgeAPI.get();
int pos = 1;
for (PlayerData data : api.getTopPlayers(limit)) {
Tier tier = api.getTierByPoints(data.getPoints());
sender.sendMessage("§e#" + pos++ + " §f" + data.getName()
+ " §8- §6" + data.getPoints() + " Pts §8(" + (tier != null ? tier.display : "Unranked") + "§8)");
}
}

Placeholder buatan sendiri dari data RankForge

Section titled “Placeholder buatan sendiri dari data RankForge”

Contoh expansion PlaceholderAPI milik plugin kamu yang menampilkan nama tier berikutnya: %myplugin_next_rank%.

import me.clip.placeholderapi.expansion.PlaceholderExpansion;
public class MyExpansion extends PlaceholderExpansion {
@Override public String getIdentifier() { return "myplugin"; }
@Override public String getAuthor() { return "KamuDev"; }
@Override public String getVersion() { return "1.0.0"; }
@Override public boolean persist() { return true; }
@Override
public String onRequest(org.bukkit.OfflinePlayer player, String params) {
if (player == null || !RankForgeAPI.isAvailable()) return "";
if (params.equalsIgnoreCase("next_rank")) {
Tier next = RankForgeAPI.get().getNextTier(player);
return next != null ? next.display : "MAX";
}
return null;
}
}

Dipanggil dari thread async (termasuk Folia)

Section titled “Dipanggil dari thread async (termasuk Folia)”

Method tulis (setPoints, dll.) memicu event sinkron, jadi harus berjalan di thread server. Dari kode async, pindahkan eksekusinya dengan scheduler global yang tersedia di Paper dan Folia:

CompletableFuture.supplyAsync(() -> fetchRewardFromWebApi(player.getUniqueId()))
.thenAccept(amount -> Bukkit.getGlobalRegionScheduler().execute(plugin, () ->
RankForgeAPI.get().addPoints(player.getUniqueId(), amount)
));

Pastikan folia-supported: true ada di plugin.yml plugin kamu jika ingin berjalan di Folia.

import xyz.noxlydev.rankforge.api.RankForgeAPI
fun tierName(player: Player): String {
if (!RankForgeAPI.isAvailable()) return "N/A"
return RankForgeAPI.get().getTier(player)?.display ?: "Unranked"
}

Alternatif tanpa dependency: PlaceholderAPI

Section titled “Alternatif tanpa dependency: PlaceholderAPI”

Kalau kamu hanya perlu membaca nilai (bukan mengubah), tidak perlu dependency kode sama sekali. Pakai PlaceholderAPI:

String points = PlaceholderAPI.setPlaceholders(player, "%rankforge_points%");

Cocok untuk plugin yang sudah bergantung pada PlaceholderAPI. Daftar placeholder: PlaceholderAPI.