# Teams

Teams bündeln Spieler mit eigenem Namen, freiem Rangsystem, Bank, Score/Level, Team-Home, Warps, geteilter Enderchest, Kisten-Claims und Diplomatie (Allianzen, Team-/Ally-Chat). Bedienbar über `/team`, die Team-GUI (`/team` ohne Argumente) und das [Web-Interface](web-interface.md).

Wichtig zum Verständnis: Die Bukkit-Permission (z. B. `team.invite`) entscheidet, ob ein Spieler das Feature grundsätzlich nutzen darf. Das **Rang-Recht** (z. B. `INVITE_MEMBERS`) entscheidet, ob sein Rang im Team die Aktion ausführen darf. Der Owner-Rang (Gewicht 0) hat immer alle Rechte.

## Commands

| Command | Syntax | Permission | Default | Rang-Recht | Beschreibung |
|---|---|---|---|---|---|
| Erstellen | `/team create <name>` | `team.create` | `true` | - | Erstellt ein Team, Ersteller wird Owner |
| Auflösen | `/team disband` | `team.disband` | `true` | `DISBAND_TEAM` | Löst nach Chat-Bestätigung auf; offene Allianzanfragen werden verworfen, eine geöffnete Team-Enderchest geschlossen |
| Umbenennen | `/team name <name>` | `team.manage` | `true` | `EDIT_NAME` | Ein Wort; Custom-Ränge, Rechte, Rangzuweisungen, offene Allianzanfragen und eine geöffnete Team-Enderchest werden übernommen |
| Beschreibung | `/team description [text]` | `team.manage` | `true` | `EDIT_DESCRIPTION` | Setzt/löscht die Beschreibung |
| Farbe | `/team color <farbe>` | `team.manage` | `true` | `EDIT_COLOR` | Benannt oder Hex; die Farbauswahl im Team-Menü kostet dasselbe (`change-costs.color`) |
| Tag | `/team tag [tag]` | `team.manage` | `true` | `EDIT_TAG` | Setzt/entfernt das Kürzel |
| Info | `/team info [team\|spieler]` | `team.info` | `true` | - | Details zu einem Team |
| Menü | `/team menu` | `team.menu` | `true` | - | Öffnet die Team-GUI |
| Einladen | `/team invite <spieler>` | `team.invite` | `true` | `INVITE_MEMBERS` | Max. eine offene Einladung pro Ziel, läuft nach `invite-timeout` ab |
| Beitreten | `/team join [team]` | `team.join` | `true` | - | Nimmt Einladung an oder tritt offenem Team bei |
| Ablehnen | `/team deny` | `team.deny` | `true` | - | Lehnt die eigene Einladung ab |
| Verlassen | `/team leave` | `team.leave` | `true` | - | Owner muss vorher übergeben oder auflösen |
| Offen/zu | `/team open` | `team.open` | `true` | `TOGGLE_OPEN` | Freier Beitritt an/aus |
| Kick | `/team kick <spieler>` | `team.kick` | `true` | `KICK_MEMBERS` | Nur bei strikt höherem Rang |
| Bann | `/team ban <spieler>` / `unban` | `team.ban` | `true` | `BAN_MEMBERS` | Bannt (kickt vorher) bzw. entbannt |
| Ränge | `/team ranks <list\|create\|rename\|delete\|perms\|moveup\|movedown>` | `team.rank.manage` | `true` | `MANAGE_RANKS` | Verwaltet die Rang-Liste (nur Ränge unterhalb des eigenen) |
| Rang zuweisen | `/team ranks assign <spieler> <rang>` | `team.rank.assign` | `true` | `PROMOTE_MEMBERS` oder `DEMOTE_MEMBERS` | Nur Ränge unterhalb des eigenen |
| Kontostand | `/team bal` | `team.bal` | `true` | `VIEW_BALANCE` | Team-Kasse anzeigen |
| Einzahlen | `/team deposit <betrag>` | `team.deposit` | `true` | `DEPOSIT` | Spielergeld in die Kasse |
| Abheben | `/team withdraw <betrag>` | `team.withdraw` | `true` | `WITHDRAW` | Kasse an den Spieler |
| Bank-Topliste | `/team baltop [seite]` | `team.baltop` | `true` | - | Teams nach Kontostand (30 s Cache) |
| Level-Info | `/team rank` | `team.rank` | `true` | - | Aktuelles Level und Anforderungen |
| Level-Up | `/team rankup` | `team.rankup` | `true` | `RANKUP_TEAM` | Stuft hoch, wenn Score und Kasse reichen |
| Score-Topliste | `/team top [seite]` | `team.top` | `true` | - | Teams nach Score (30 s Cache) |
| Home | `/team sethome` / `home` / `delhome` | `team.home` | `true` | `SET_HOME` / `USE_HOME` | Team-Home (Warmup/Cooldown/Kosten über `teamhome`) |
| Warps | `/team setwarp <name>` / `warp [name]` / `delwarp <name>` | `team.warp` | `true` | `MANAGE_WARPS` / `USE_WARPS` | Team-Warps im einheitlichen Warp-System, Details auf der [Warps-Seite](warps.md) |
| Enderchest | `/team echest` | `team.echest` | `true` | `USE_ECHEST` | Geteilte 27-Slot-Enderchest in Echtzeit |
| Kisten | `/team chest <claim\|remove\|removeall>` | `team.chest` | `true` | `MANAGE_CHEST_CLAIMS` | Kisten/Fässer fürs Team beanspruchen |
| Shop umwandeln | `/team shop` (Shop anvisieren) | `team.shop` | `true` | `EDIT_TEAM_SHOPS` | Eigenen Chest-Shop in einen Team-Shop umwandeln |
| Allianz | `/team ally <team>` / `neutral <team>` | `team.ally` | `true` | `MANAGE_ALLIES` | Beidseitige Bestätigung; `neutral` wirkt einseitig und zieht nur die Allianzanfrage zwischen den beiden Teams zurück (eigene ausgehende oder eingehende des anderen Teams), andere offene Anfragen bleiben |
| Team-Chat | `/team chat [text]` | `team.chat` | `true` | `USE_TEAM_CHAT` | Ohne Text: Dauer-Umschalter |
| Ally-Chat | `/team allychat [text]` | `team.allychat` | `true` | `USE_ALLY_CHAT` | Team + Verbündete; schließt Team-Chat aus |
| PvP | `/team pvp` | `team.pvp` | `true` | `TOGGLE_PVP` | Internes Friendly Fire an/aus |
| Owner übergeben | `/team setowner <spieler>` | `team.setowner` | `true` | `TRANSFER_OWNERSHIP` | Überträgt die Eigentümerschaft |

**Team- und Ally-Chat:** `/team chat <text>` und `/team allychat <text>` sind stummgeschaltet, solange der Spieler gemutet ist (wie der öffentliche Chat), und werden von `/teama chatspy` genauso mitgelesen wie der Dauer-Umschalter. Der Platzhalter für die Teamfarbe in den Chat-Formaten ist `<team_color>` (siehe [Chat](chat.md)).

## Weitere Permissions

| Permission | Default | Beschreibung |
|---|---|---|
| `team.bypass.createcost` | false | Team-Erstellung kostenlos |
| `team.bypass.changecost` | false | Änderungskosten (Name, Tag, Farbe, ...) umgehen |
| `team.bypass.friendlyfire` / `team.bypass.allyfriendlyfire` | false | Schadet Team-/Ally-Mitgliedern trotz Schutz |
| `team.bypass.chestclaim` | false | Öffnet/bricht fremde Team-Kisten |
| `team.bypass.depositcooldown` / `team.bypass.withdrawcooldown` | false | Bank-Cooldowns umgehen |
| `team.bypass.limit` | false | Warp-/Rang-Limits umgehen |
| `team.admin.manage_ranks` | op | Hebt die Rang-Hierarchie für Admins auf: Ränge und Rechte jedes Teams bearbeiten und zuweisen, unabhängig vom eigenen Rang |

## Rang-Rechte

Jedes Recht ist pro Rang einzeln vergebbar (`/team ranks perms` oder GUI). Ränge haben ID, Anzeigename (3 bis 24 Zeichen), Gewicht (0 = Owner, höher = niedriger), Icon und Rechte. Rang-Limit: 3 Preset-Ränge + `max-ranks` + Level-Bonus, hart gedeckelt bei 16. Das Rang-Menü der Team-GUI zeigt alle Ränge des Teams (bis zu 16).

| Kategorie | Rechte |
|---|---|
| Mitglieder | `INVITE_MEMBERS`, `KICK_MEMBERS`, `BAN_MEMBERS`, `PROMOTE_MEMBERS`, `DEMOTE_MEMBERS`, `MANAGE_RANKS` |
| Identität | `EDIT_NAME`, `EDIT_TAG`, `EDIT_DESCRIPTION`, `EDIT_COLOR`, `TOGGLE_OPEN`, `TOGGLE_PVP` |
| Diplomatie | `MANAGE_ALLIES`, `USE_ALLY_CHAT`, `USE_TEAM_CHAT` |
| Wirtschaft | `VIEW_BALANCE`, `DEPOSIT`, `WITHDRAW`, `RANKUP_TEAM` |
| Orte | `USE_HOME`, `SET_HOME`, `USE_WARPS`, `MANAGE_WARPS` |
| Lagerung | `USE_ECHEST`, `MANAGE_CHEST_CLAIMS` |
| Gefahrenzone | `DISBAND_TEAM`, `TRANSFER_OWNERSHIP` |
| Claims & Shops | `BUILD_IN_TEAM_SUBDIVISIONS`, `BUILD_IN_ALLY_SUBDIVISIONS`, `MANAGE_TEAM_CLAIM_FLAGS` (genutzt vom [Claim-Modul](claim-overview.md)), `EDIT_TEAM_SHOPS` (Shop-System + Web) |

Preset-Rechte: Owner alles; Admin alles außer `EDIT_NAME`, `DISBAND_TEAM`, `TRANSFER_OWNERSHIP`, `RANKUP_TEAM`; Member `USE_TEAM_CHAT`, `USE_ALLY_CHAT`, `VIEW_BALANCE`, `DEPOSIT`, `USE_HOME`, `USE_WARPS`, `USE_ECHEST`, `BUILD_IN_TEAM_SUBDIVISIONS`.

**Rangverwaltung:** Mitglieder mit `MANAGE_RANKS` können nur Ränge bearbeiten, verschieben und löschen, die unterhalb ihres eigenen Rangs liegen, und einem Rang nur Rechte geben, die sie selbst besitzen. Der letzte Rang neben Owner kann nicht gelöscht werden. Beim Zuweisen eines Rangs (`/team ranks assign`, Mitglieder-Menü, Web-Panel) braucht Hochstufen `PROMOTE_MEMBERS` und Herabstufen `DEMOTE_MEMBERS`; erlaubt sind nur Ränge unterhalb des eigenen und nur für Mitglieder unterhalb des eigenen Rangs. Der Team-Owner behält den Owner-Rang, bis er die Führung per `/team setowner` übergibt. Rangzuweisungen werden sofort gespeichert und überleben einen Server-Neustart. Admins mit `team.admin.manage_ranks` sind von dieser Hierarchie ausgenommen.

> **Hinweis:** Kick, Bann, Befördern, Degradieren und Rang-Zuweisung prüfen zusätzlich die Hierarchie (nur strikt höherer Rang darf handeln, Owner steht über allen). Die Rechte werden überall gleich durchgesetzt: Befehle, GUI und Web-Interface, bei Team-/Ally-Chat sogar pro Nachricht neu.

## Score und Level

PvP-Kills zwischen verschiedenen Teams geben dem Killer-Team `per-kill` Punkte und ziehen dem Opfer-Team `per-death` ab (nie unter 0). Zwei Schutzmechanismen: gleiche IP von Killer und Opfer wird komplett ignoriert (`ip-check`), und ab `spam-kill-max-kills` Kills am selben Gegner innerhalb von `spam-kill-window` Sekunden gibt es keinen Score mehr.

`/team rankup` prüft erst den benötigten Score, bucht dann den Level-Preis aus der Team-Kasse ab. Die Bonus-Werte jedes Levels addieren sich auf die Basis-Limits; `bonus-shops` erhöht `max-shops-per-team` aus dem [Shop-Modul](shop.md). `bank-limit` deckelt die Team-Kasse auf dem jeweiligen Level (0 nutzt `max-balance`).

> **Hinweis:** In der Standard-Config ist `required-score` überall 0, der Aufstieg ist also nur durch Geld begrenzt. Wer PvP-Score als Aufstiegs-Bedingung will, setzt `required-score` pro Level hoch.

## Kisten-Claims

Claimbar sind Truhen, Fallentruhen und Fässer (Doppeltruhen immer als Ganzes). Geschützt sind sie gegen Öffnen durch Fremde, Abbau (nur mit `MANAGE_CHEST_CLAIMS`), Hopper (auch teameigene) und Explosionen. ChestShops und Team-Kisten schließen sich gegenseitig aus. Mit eingeschaltetem [Claim-Modul](claim-overview.md) muss die Kiste in einem Team-Claim des eigenen Teams liegen. Limit: `max-chest-claims` + Level-Bonus.

## Admin-Commands (/teama)

Alle mit Permission `team.admin.<subcommand>`, Default `op`.

| Command | Syntax | Beschreibung |
|---|---|---|
| `/teama disband\|name\|description\|color\|tag` | `/teama <sub> <team> [wert]` | Beliebiges Team zwangsverwalten |
| `/teama join` / `leave` | `/teama join <team> <spieler>` / `/teama leave <spieler>` | Spieler in Team zwingen/entfernen |
| `/teama promote` / `demote` / `setowner` | `/teama <sub> <spieler>` | Rang-Schritt hoch/runter bzw. Owner erzwingen |
| `/teama rank` | `/teama rank <team> <create\|delete\|rename\|list\|perms\|assign\|moveup\|movedown\|reset>` | Vollzugriff aufs Rangsystem, `reset` = zurück auf 3 Standard-Ränge |
| `/teama score` / `money` | `/teama <sub> <set\|add\|remove> <team> <wert>` | Score/Kasse direkt ändern |
| `/teama home` / `echest` / `chest` | `/teama <sub> <team> [...]` | Home betreten, Enderchest öffnen, Kisten-Claims verwalten |
| `/teama purge` | `/teama purge` | Score ALLER Teams auf 0 |
| `/teama chatspy` | `/teama chatspy` | Team-/Ally-Chat mitlesen |
| `/teama reload` | `/teama reload` | Team-Config neu laden |

`/teama money set` lehnt `NaN` und `Infinity` ab. `/team info <spieler>`, `/team ban|unban <spieler>` und `/teama join|leave|promote|demote|setowner <spieler>` lösen unbekannte Namen im Hintergrund auf (keine Tick-Aussetzer mehr); läuft bereits eine Abfrage, antwortet der Befehl mit "lookup-busy", also kurz warten.

## Konfiguration (modules/team.yml)

```yaml
# Schaltet das Team-Modul ein oder aus.
enabled: true

team:
  # Basis-Limits, Level-Boni kommen oben drauf.
  max-team-size: 20
  min-name-length: 3
  max-name-length: 8
  # MiniMessage in Teamnamen erlauben (dann zählt die sichtbare Länge).
  allow-minimessage-names: false
  min-tag-length: 2
  max-tag-length: 4
  max-description-length: 100
  max-warps: 1
  # Eigene Rang-Plätze auf Level 1, ZUSÄTZLICH zu den 3 Preset-Rängen.
  # Effektiv = 3 + max-ranks + bonus-ranks des Levels, Deckel bei 16.
  max-ranks: 2
  # Basis-Kisten-Claims, plus bonus-claims des Levels.
  max-chest-claims: 25
  max-allies: 3
  # Preis der Team-Erstellung. 0 = kostenlos.
  create-cost: 5000.0
  # Preis pro Änderung; Entfernen von Tag/Beschreibung ist immer
  # kostenlos, abgebucht wird erst nach erfolgreicher Änderung.
  change-costs:
    rename: 0.0
    tag: 0.0
    color: 0.0
    description: 0.0
    sethome: 0.0
  # Obergrenzen für Kasse und Score.
  max-balance: 1000000000.0
  max-score: 1000000
  # PvP-Standard neuer Teams, serverweiter Ally-Friendly-Fire-Schalter
  # und Kollisions-Abschaltung zwischen Mitgliedern.
  friendly-fire-default: false
  ally-friendly-fire: false
  collision-disabled: false
  # Verbotene Namensbestandteile (Substring-Filter).
  blocked-names: ["admin", "server", "staff", "moderator", "console", "system"]
  # Sekunden bis eine Einladung abläuft.
  invite-timeout: 60
  score:
    per-kill: 10
    per-death: 5
    spam-kill-window: 300
    spam-kill-max-kills: 3
    ip-check: true
  # Level: required-score und cost gelten für den Aufstieg AUF das Level,
  # bonus-* addiert sich auf die Basis-Limits.
  levels:
    1: { name: "Bronze",  required-score: 0, cost: 0,      bonus-members: 0,  bonus-warps: 0, bonus-claims: 0,   bonus-ranks: 0, bonus-shops: 0 }
    2: { name: "Silver",  required-score: 0, cost: 5000,   bonus-members: 5,  bonus-warps: 1, bonus-claims: 25,  bonus-ranks: 2, bonus-shops: 5 }
    3: { name: "Gold",    required-score: 0, cost: 25000,  bonus-members: 10, bonus-warps: 2, bonus-claims: 50,  bonus-ranks: 4, bonus-shops: 10 }
    4: { name: "Diamond", required-score: 0, cost: 100000, bonus-members: 20, bonus-warps: 3, bonus-claims: 75,  bonus-ranks: 6, bonus-shops: 20 }
    5: { name: "Emerald", required-score: 0, cost: 500000, bonus-members: 30, bonus-warps: 5, bonus-claims: 100, bonus-ranks: 8, bonus-shops: 40 }
  ranks:
    min-name-length: 3
    max-name-length: 24
    name-blacklist: ["owner"]
    # Material-Auswahl für Rang-Icons. Leer = eingebaute Liste.
    icon-picker-materials: []
  gui:
    members-per-page: 28
    # /team ohne Argumente öffnet die GUI.
    open-on-empty-command: true
    # Doppelte Bestätigung für zerstörerische Aktionen.
    danger-double-confirm: true
  integrations:
    coreprotect:
      # Protokolliert Kisten-Claim-Abbau (#teamclaim-<spieler>).
      chest-claim-logging: true

cooldown:
  commands:
    teamhome: 300
    teamwarp: 300
    teamdeposit: 5
    teamwithdraw: 10
    teamcreate: 5
    teamrankup: 5

cost:
  commands:
    teamhome: 0
    teamwarp: 0

warmup:
  commands:
    teamhome:
      duration: 5
    teamwarp:
      duration: 5
```

## Komplette Beispiel-Config

```yaml
enabled: true

team:
  max-team-size: 10
  min-name-length: 3
  max-name-length: 12
  allow-minimessage-names: false
  min-tag-length: 2
  max-tag-length: 5
  max-description-length: 80
  max-warps: 2
  max-ranks: 3
  max-chest-claims: 15
  max-allies: 2
  create-cost: 10000.0
  change-costs:
    rename: 2500.0
    tag: 1000.0
    color: 500.0
    description: 0.0
    sethome: 500.0
  max-balance: 50000000.0
  max-score: 100000
  friendly-fire-default: false
  ally-friendly-fire: false
  collision-disabled: true
  blocked-names: ["admin", "server", "staff", "mod"]
  invite-timeout: 120
  score:
    per-kill: 15
    per-death: 10
    spam-kill-window: 600
    spam-kill-max-kills: 2
    ip-check: true
  levels:
    1: { name: "Rekrut",  required-score: 0,     cost: 0,      bonus-members: 0,  bonus-warps: 0, bonus-claims: 0,  bonus-ranks: 0, bonus-shops: 0 }
    2: { name: "Veteran", required-score: 500,   cost: 20000,  bonus-members: 5,  bonus-warps: 1, bonus-claims: 10, bonus-ranks: 2, bonus-shops: 5 }
    3: { name: "Elite",   required-score: 2500,  cost: 100000, bonus-members: 10, bonus-warps: 2, bonus-claims: 25, bonus-ranks: 4, bonus-shops: 10 }
  ranks:
    min-name-length: 3
    max-name-length: 16
    name-blacklist: ["owner", "admin"]
    icon-picker-materials: []
  gui:
    members-per-page: 28
    open-on-empty-command: true
    danger-double-confirm: true
  integrations:
    coreprotect:
      chest-claim-logging: true

cooldown:
  commands:
    teamhome: 30
    teamwarp: 30
    teamdeposit: 5
    teamwithdraw: 30
    teamcreate: 60
    teamrankup: 10

cost:
  commands:
    teamhome: 10.0
    teamwarp: 10.0

warmup:
  commands:
    teamhome:
      duration: 5
    teamwarp:
      duration: 5
```
