Skip to content

A real integration

This is a working integration rather than a toy one. A faction event plugin hooks SomaHider into two events, a KoTH and a giant totem. The shape is the same both times: the zone opens around the arena when the event starts, reveals a few groups, and closes when it ends.

Both events go through a small helper, so the API is touched in exactly one place. It gets the API, maps each player to their faction, applies the disguise read from the config, and opens the zone.

public static HiderZone open(ConfigurationSection hider, Region region, VisibilityRule... reveal) {
SomaHider somaHider = SomaHiderProvider.getOrNull();
if (somaHider == null || region == null) {
return null;
}
if (hider != null && !hider.getBoolean("enabled", true)) {
return null;
}
return somaHider.hide(region)
.groupResolver(Hiders::factionId) // each player -> their faction id
.disguise(hider)
.reveal(reveal)
.open();
}
public static String factionId(Player player) {
Faction faction = FactionUtils.getFactionByPlayer(player);
return faction != null && faction.isNormal() ? faction.getId() : null;
}

getOrNull() and the check after it keep the plugin running when SomaHider is not installed, which is what softdepend implies. The resolver returns null for a player without a faction, and a null group is never revealed.

Passing the config section straight to disguise(...) means server owners tune the look of the disguise in the event’s own config file, with the same keys as config.yml, and the plugin needs no code for it.

At the start of the event a zone covers the arena. Everyone is hidden except your own faction and the one currently holding the KoTH. The owner is read live, so the reveal follows the capture.

// when the event starts
ConfigurationSection hider = getConfig().getConfigurationSection("koths." + koth.getName() + ".hider");
zone = Hiders.open(hider, Hiders.around(koth.getArea().getMiddle(), hider),
Reveal.sameGroup()
.or(Reveal.group(() -> Hiders.factionId(currentKoth.getOwner()))));
// when it stops
zone.close();

sameGroup() keeps teammates recognisable to each other. Reveal.group(Supplier) reveals the owning faction to everybody, and because it takes a supplier rather than a fixed id, the reveal moves to the new owner as soon as the point changes hands. No extra code runs on capture. While nobody holds the point the supplier returns null and only teammates see each other.

Giant totem: reveal the top of the standings

Section titled “Giant totem: reveal the top of the standings”

Same shape, different rule. Around the totem, reveal your own faction and the top three of the standings. When the standings move, the revealed set moves with them.

ConfigurationSection hider = getConfig().getConfigurationSection("giant-totems." + totem.getName() + ".hider");
zone = Hiders.open(hider, Hiders.around(totem.getLocation(), hider),
Reveal.sameGroup()
.or(Reveal.groupsTogether(() -> Hiders.top(standings, 3))));
public static List<String> top(List<EventData> standings, int count) {
List<String> ids = new ArrayList<>();
for (int i = 0; i < standings.size() && i < count; i++) {
ids.add(standings.get(i).getId());
}
return ids;
}

groupsTogether(Supplier) reveals the members of a set of groups to one another: viewer and target must both be in the set. Here the set is the leading factions, recomputed as the event goes, so the standings open up as they change.

A rule is evaluated for every viewer and target pair, several times a second. Reading the standings there once per pair would be expensive.

The supplier factories avoid it: SomaHider calls the supplier at most once per pass and hands the result to every pair evaluated in that pass. Build the lambda once, when you open the zone, as the examples above do. Creating a new lambda on each call would defeat the caching, which is keyed on the supplier instance.

  • One helper holds the API access, the group resolver and the disguise.
  • The zone opens when the event starts and closes with zone.close() when it ends.
  • Supplier-based rules follow game state on their own, with no extra logic to write.

The full catalogue of factories is in reveal rules.