71 lines
2.5 KiB
Java
71 lines
2.5 KiB
Java
package net.scopenet.integration;
|
|
|
|
import com.google.gson.JsonArray;
|
|
import com.google.gson.JsonObject;
|
|
import java.util.List;
|
|
import java.util.concurrent.Executors;
|
|
import java.util.concurrent.ScheduledExecutorService;
|
|
import java.util.concurrent.TimeUnit;
|
|
|
|
/** Sends live player positions to the panel for the in-app BlueMap territory view. */
|
|
public final class LiveMapSync implements AutoCloseable {
|
|
public record Player(String uuid, String name, String dimension, double x, double y, double z, float yaw, float pitch) {}
|
|
|
|
private final PanelClient client;
|
|
private final ScheduledExecutorService worker = Executors.newSingleThreadScheduledExecutor(task -> {
|
|
Thread thread = new Thread(task, "scopenet-positions");
|
|
thread.setDaemon(true);
|
|
return thread;
|
|
});
|
|
private volatile List<Player> players = List.of();
|
|
private volatile boolean changed;
|
|
private volatile boolean closed;
|
|
private long lastSent;
|
|
|
|
public LiveMapSync(PanelClient client) { this.client = client; }
|
|
|
|
public void start() { worker.scheduleWithFixedDelay(this::sendSafely, 1, 1, TimeUnit.SECONDS); }
|
|
|
|
public void offerPlayers(List<Player> next) {
|
|
if (!next.equals(players)) {
|
|
players = List.copyOf(next);
|
|
changed = true;
|
|
}
|
|
}
|
|
|
|
private void sendSafely() {
|
|
if (closed) return;
|
|
long now = System.nanoTime();
|
|
if (!changed && now - lastSent < TimeUnit.SECONDS.toNanos(10)) return;
|
|
JsonArray list = new JsonArray();
|
|
for (Player p : players) {
|
|
JsonObject entry = new JsonObject();
|
|
entry.addProperty("uuid", p.uuid());
|
|
entry.addProperty("name", p.name());
|
|
entry.addProperty("dimension", p.dimension());
|
|
entry.addProperty("x", p.x());
|
|
entry.addProperty("y", p.y());
|
|
entry.addProperty("z", p.z());
|
|
entry.addProperty("yaw", p.yaw());
|
|
entry.addProperty("pitch", p.pitch());
|
|
list.add(entry);
|
|
}
|
|
JsonObject body = new JsonObject();
|
|
body.add("players", list);
|
|
try {
|
|
client.post("livemap/players", body);
|
|
changed = false;
|
|
lastSent = now;
|
|
} catch (InterruptedException e) {
|
|
Thread.currentThread().interrupt();
|
|
} catch (Exception ignored) {
|
|
// Keep the latest snapshot and retry on the next interval.
|
|
}
|
|
}
|
|
|
|
@Override public void close() {
|
|
closed = true;
|
|
worker.shutdownNow();
|
|
}
|
|
}
|