Du hast Dutzende Stationen gebaut, aber weißt beim nächsten Neustart nicht mehr, welche gut liefen, wie sie aufgebaut waren oder was du vielleicht doppelt gebaut hast?
Du willst deine Wirtschaft verstehen, ohne dich durch XML-Daten zu wühlen oder auf Online-Planer zu verlassen?
Dann ist dieses Tool genau das Richtige für dich.
---
###
Ganz einfach: Es liest deinen X4-Spielstand direkt aus – genauer gesagt die XML-Datei – und erstellt daraus eine **übersichtliche CSV-Datei**, die du in Excel, LibreOffice oder Google Sheets öffnen kannst.
Du bekommst eine komplette Übersicht über **alle Stationen, die dir gehören** – mit allen Details, die wirklich zählen:
---
###
Pro Station bekommst du:
* **Name der Station**: So wie im Spiel – z. B. „Argon Prime Handelsdock Alpha“
* **Status**: Ist sie aktiv, leer, oder nur Lager?
* **Produktionsmodule**: Was wird produziert und wie oft – z. B. „Produktion: Medizin x2, Produktion: Energiezellen x4“
* **Dockmodule**: Welche Größen sind verbaut – z. B. „Dock M x3, Dock L x1“
* **Schiffswerften**: Falls vorhanden – z. B. „L-Schiffswerft x1, XL-Schiffswerft x1“
* **Ausrüstungsdock**: Ja oder Nein
* **Lagerarten**: Gibt’s Container-, Feststoff- oder Flüssiglager? Wie viele?
* **Drohnen**: Anzahl der Handels-, Kampf- und Reparaturdrohnen
* **Rohstoffe**: Welche Waren wurden eingekauft oder verkauft – z. B. „Graphen, Silizium, Energiezellen“
---
Du siehst: **alles auf einen Blick** – kein Ratespiel, keine XML-Qual. Du weißt sofort, was die Station kann, was sie braucht, und ob du sie beim nächsten Durchgang wieder genau so bauen willst.###**Ein Beispiel? Gern. So könnte eine Zeile in der CSV aussehen:**
```csv
"Argon Prime Handelsdock Alpha";"aktiv";"Produktion: Medizin x2, Produktion: Nahrung x1";"Graphen, Wasser, Medizin";1;0;0;5;2;1;"Ja";"Ja";"Dock M x2, Dock L x1";"L-Schiffswerft x1"
```
---
###
Hier ein paar ganz reale Gründe:
*
Du findest heraus, welche Stationen sich wirklich gelohnt haben – und baust sie 1:1 neu.
*
Du siehst, wo du zu viele gleiche Produktionen hattest, wo dir Lager gefehlt haben oder wo Werften ohne Docks standen.
*
Du kannst dein Imperium archivieren – und später vergleichen, wie du dich entwickelt hast.
*
Kein Web-Tool, keine Cloud – dein Spielstand bleibt lokal. Das Tool läuft komplett ohne Internet.
---
###
Das Tool macht keine Magie – es **analysiert den Aufbau** deiner Stationen. Es zeigt nicht, **wie viel produziert wurde**, sondern **was gebaut wurde**.
Aber: Die Basis steht. Wenn du willst, kann es in Zukunft erweitert werden – zum Beispiel um Lagerfüllstände, Produktionsraten oder sogar Gewinnberechnung.
---
###
Wenn du in X4 wirklich verstehen willst, **was du gebaut hast**,
wenn du Stationen vergleichen, nachbauen oder verbessern willst,
und wenn du ein Tool suchst, das **einfach funktioniert**, **ohne Schnickschnack, ohne Onlinepflicht** –
dann ist das hier dein Werkzeug.
**X4-Stationen-Analyse – Klartext für dein Imperium.**
---
Code: Select all
import xml.etree.ElementTree as ET
import csv
from collections import Counter
SAVE_PATH = "save_001.xml"
OUTPUT_CSV = "X4_Stationen_Analyse.csv"
WERFTMODULE = {
"buildmodule_s_macro",
"buildmodule_m_macro",
"buildmodule_l_macro",
"buildmodule_xl_macro",
"buildmodule_shipyard_macro",
"buildmodule_gen_ships_s_macro",
"buildmodule_gen_ships_m_macro",
"buildmodule_gen_ships_m_dockarea_01_macro",
"buildmodule_gen_ships_m_dockarea_02_macro",
"buildmodule_gen_ships_l_macro",
"buildmodule_gen_ships_l_dockarea_01_macro",
"buildmodule_gen_ships_xl_macro",
"buildmodule_gen_ships_xl_dockarea_01_macro"
}
AUSRUESTUNGSMODULE = {
"buildmodule_gen_equip_m_dockarea_01_macro",
"buildmodule_gen_equip_l_macro",
"buildmodule_gen_equip_xl_macro"
}
def klartext_modulname(macro):
macro = macro.lower().strip()
# Produktion: Alle prod_ Module, z.B. prod_gen_, prod_ter_, prod_har_ etc.
if macro.startswith("prod_"):
# Beispiel: prod_ter_proteinpaste_macro → Proteinpaste
# Extrahiere Produkt zwischen zweitem Unterstrich und _macro
parts = macro.split("_")
if len(parts) >= 3:
ware = parts[2]
return f"Produktion: {ware.capitalize()}"
else:
return f"Produktion: {macro}"
# Schiffswerften
if "buildmodule_gen_ships_" in macro or "shipyard" in macro or "buildmodule_" in macro:
if "xl" in macro:
return "XL-Schiffswerft"
elif "_l_" in macro:
return "L-Schiffswerft"
elif "_m_" in macro:
return "M-Schiffswerft"
elif "_s_" in macro:
return "S-Schiffswerft"
else:
return "Schiffswerft"
# Ausrüstungsdocks
if "equip" in macro or "eqdock" in macro or "equipmentdock" in macro:
if "xl" in macro:
return "Ausrüstungsdock (XL)"
elif "_l" in macro:
return "Ausrüstungsdock (L)"
elif "_m" in macro:
return "Ausrüstungsdock (M)"
elif "_s" in macro:
return "Ausrüstungsdock (S)"
else:
return "Ausrüstungsdock"
# Dockmodule
if "dockarea_" in macro or "piers" in macro:
if "xl" in macro:
return "Dock XL"
elif "_l_" in macro:
return "Dock L"
elif "_m_" in macro:
return "Dock M"
elif "_s_" in macro:
return "Dock S"
else:
return "Dockbereich"
# Lager
if "storage" in macro:
if "container" in macro:
return "Lager: Container"
elif "solid" in macro:
return "Lager: Feststoff"
elif "liquid" in macro:
return "Lager: Flüssig"
else:
return "Lager"
return f"Unbekannt: {macro}"
def finde_drohnen_aus_ammunition(station):
handels = verteidigung = reparatur = 0
ammo = station.find("ammunition")
if ammo is not None:
available = ammo.find("available")
if available is not None:
for item in available.findall("item"):
macro = item.attrib.get("macro", "").lower()
menge = int(item.attrib.get("amount", "0"))
if "cargodrone" in macro:
handels += menge
elif "fightingdrone" in macro:
verteidigung += menge
elif "repairdrone" in macro:
reparatur += menge
return handels, verteidigung, reparatur
def analysiere_stationen(xml_path):
try:
tree = ET.parse(xml_path)
root = tree.getroot()
except Exception as e:
print(f"❌ Fehler beim Parsen: {e}")
return
with open(OUTPUT_CSV, mode="w", newline="", encoding="utf-8") as file:
writer = csv.writer(file, delimiter=";", quotechar='"', quoting=csv.QUOTE_ALL)
writer.writerow([
"Station", "Status", "Module", "Rohstoffe",
"Container", "Feststoff", "Flüssig",
"Handels-", "Verteidigungs-", "Reparatur-",
"Schiffsbau", "Ausrüstung", "Dockmodule", "Schiffsbau-Module"
])
for station in root.iter("component"):
if station.attrib.get("class") != "station":
continue
if station.attrib.get("owner") != "player":
continue
name = station.attrib.get("name") or f"Station_{station.attrib.get('id', '?')}"
status = "leer"
prod_counter = Counter()
dock_modules = Counter()
shipyard_modules = Counter()
equipment_present = False
construction = station.find("construction")
if construction is not None:
for entry in construction.findall(".//entry"):
macro = entry.attrib.get("macro", "").lower()
modulname = klartext_modulname(macro)
# Produktionsmodule (prod_)
if macro.startswith("prod_"):
prod_counter[modulname] += 1
# Dockmodule
if "dockarea_" in macro or "piers" in macro:
dock_modules[modulname] += 1
# Schiffswerften
if macro in WERFTMODULE:
shipyard_modules[modulname] += 1
# Ausrüstungsdock
if macro in AUSRUESTUNGSMODULE:
equipment_present = True
# Status bestimmen
if prod_counter or dock_modules or shipyard_modules or equipment_present:
status = "aktiv"
# Lager zählen
lager_counter = Counter()
if construction is not None:
for entry in construction.findall(".//entry"):
macro = entry.attrib.get("macro", "").lower()
if "storage" in macro:
if "container" in macro:
lager_counter["container"] += 1
elif "solid" in macro:
lager_counter["solid"] += 1
elif "liquid" in macro:
lager_counter["liquid"] += 1
if status == "leer" and lager_counter:
status = "nur Lager"
# Rohstoffe sammeln
rohstoffe = set()
trade = station.find("trade")
if trade is not None:
reservations = trade.find("reservations")
if reservations is not None:
for res in reservations.findall("reservation"):
ware = res.attrib.get("ware", "")
flags = res.attrib.get("flags", "")
if "buyer" in res.attrib and "buyermoneyvirtual" in flags:
rohstoffe.add(ware)
offers = trade.find("offers")
if offers is not None:
for prod in offers.findall(".//trade"):
if prod.attrib.get("buyer") == station.attrib.get("id"):
rohstoffe.add(prod.attrib.get("ware"))
rohstoff_string = ", ".join(sorted(rohstoffe)) or "-"
# Drohnen zählen
d_handels, d_verteidigung, d_reparatur = finde_drohnen_aus_ammunition(station)
# Module-Strings für CSV
module_string = ", ".join(f"{typ} x{anzahl}" for typ, anzahl in sorted(prod_counter.items())) or "-"
dock_string = ", ".join(f"{typ} x{anzahl}" for typ, anzahl in sorted(dock_modules.items())) or "-"
shipyard_string = ", ".join(f"{typ} x{anzahl}" for typ, anzahl in sorted(shipyard_modules.items())) or "-"
ausruestung_string = "Ja" if equipment_present else "Nein"
writer.writerow([
name,
status,
module_string,
rohstoff_string,
lager_counter.get("container", 0),
lager_counter.get("solid", 0),
lager_counter.get("liquid", 0),
d_handels,
d_verteidigung,
d_reparatur,
"Ja" if shipyard_string != "-" else "Nein",
ausruestung_string,
dock_string,
shipyard_string
])
print(f"✅ CSV erstellt: {OUTPUT_CSV}")
if __name__ == "__main__":
analysiere_stationen(SAVE_PATH)
---
##
1. **Spielstand exportieren**
* Öffne X4: Foundations
* Lade den gewünschten Spielstand
* Erstelle eine **manuelle Sicherung** (damit du die XML bekommst)
* Gehe zu deinem X4-Savegame-Ordner:
`Dokumente\Egosoft\X4\<Benutzer-ID>\save`
* Entpacke den gewünschten `.xml.gz`-Spielstand mit einem Tool wie **7-Zip** oder **WinRAR**
* Die entpackte Datei muss **`save_001.xml`** heißen (oder im Skript umbenannt werden)
2. **Datei speichern**
* Lege die Datei `save_001.xml` **in den gleichen Ordner wie das Python-Skript**
3. **Python installieren (falls noch nicht vorhanden)**
* [https://www.python.org/downloads/](https://www.python.org/downloads/)
* Während der Installation: Haken setzen bei „Add Python to PATH“
4. **Skript starten**
* Öffne eine Konsole (CMD oder Terminal) im Ordner des Skripts
* Führe aus:
```bash
python dein_scriptname.py
```
5. **Ergebnis prüfen**
* Es wird eine Datei namens **`X4_Stationen_Analyse.csv`** erstellt
* Diese kannst du mit Excel, LibreOffice oder Google Sheets öffnen
---
ich bin da bei es noch besser zu machen .. wenn wer ne idee hat immer her damit