Howto play AntMe! 2.0

Veröffentlicht: 31 März 2014 in AntMe!, Development

tomEine der wichtigsten Fragen, wenn es um AntMe! 2.0 geht, ist sicher die Frage nach dem Gameplay. Ich kann alle beruhigen, die mir gesagt haben, dass es weiterhin so simpel bleiben muss wie bisher. „Bitte kein Neustart“, „bitte nicht alles anders“ haben mir viele Lehrer und Trainer gesagt, als ich ihnen von der neuen Version erzählt habe. Das habe ich mir sehr zu Herzen genommen. Daher wird einem die neue Ameisen-API sehr, sehr vertraut vorkommen. Die Ameisen werden weiterhin mit Events funktionieren. Allerdings bekommt der Spieler wesentlich mehr Informationen über seine Umgebung, sodass die aktuelle Situation wesentlich besser analysiert werden kann. Allerdings kommt mit AntMe! 2.0 auch die Möglichkeit hinzu, die Wanzen zu programmieren. Damit das nicht langweilig wird, arbeiten diese Kollegen nach einem komplett anderen Programmier-Konzept. Man darf gespannt sein. In diesem Artikel gehts nämlich erstmal nur um die Ameisen.

Templates

Besonders wichtig bei der Neuumsetzung des Spiels war die Überarbeitung des Erstellungsprozesses von neuen Ameisen. Bisher wars ja so, dass der Spieler händisch das Ameisen-Projekt kopieren musste. Das ist recht heikel, weil der Spieler im Normalfall ja nicht wirklich weiß, was er da tut. Mal ganz abgesehen davon, dass die Runtime diverse technische Schwierigkeiten bekommt, da alle Spieler-Dateien ja scheinbar aus dem selben Projekt stammen, aber unterschiedliche Inhalte aufweisen. Diese kleine Hürde wird dem Spieler in Zukunft genommen. Ein Generator für diese Ameisen-Templates erstellt dem Spieler erstmal ein Grundgerüst für jegliche unterstützte Kombination an Entwicklungsumgebung, Sprache und Programmiersprache. Der Spieler wählt also „Visual Studio 2013“, „C#“, dann „Deutsch“ und am Ende fällt ein fertiges Visual Studio Projekt heraus mit dem es dann los gehen kann. Realisiert wird das über Code-Generatoren. Darüber schreibe ich aber mal, wenn es um die Erweiterbarkeit von AntMe! 2.0 geht.

Lokalisiert Spielen

Bekannt aus vorherigen AntMe! Versionen spielt der Spieler wieder lokalisiert in seiner Muttersprache. Das ist und bleibt eines der Grundkonzepte der Ameisen, weil wir extem positive Erfahrungen damit gemacht haben, den Spieler nicht gleichzeitig mit der Programmier-Herausforderung auch noch mit einer Sprachbarriere zu konfrontieren. Die Ameisen reagieren also weiterhin auf ein GeheGeradeaus() oder Nimm(zucker) und verfügt über Events wie Sieht(Zucker zucker). Kontrollstrukturen und Schlüsselworte bleiben natürlich weiter C#-üblich.

Ameisen produzieren

Eine kleine Änderung gibts dann aber doch – zu Gunsten einer korrekten Umsetzung der OOP. Der Generator erzeugt nämlich direkt zwei Klassen im Projekt. Neben der Klasse, die die Ameise repräsentiert, gibt es noch eine übergeordnete Rolle, die die komplette Kolonie darstellt. Diese zweite Klasse übernimmt die Aufgabe der bisher statischen BestimmeTyp()-Methode der alten Version. Sie gliedert die Aufgabe der Erzeugung neuer Ameisen in eigenen Aufgabenbereich aus, damit der Spieler bei der Erstellung seiner Ameisen etwas freier ist. Eine ganze Reihe von Informationen über das aktuelle Volk (Punktestand, Ameisen-Typ Verteilung, Kampf- und Ressourcen-Statistiken) unterstützen den Spieler bei der Entscheidung, welche Ameise als nächstes erzeugt werden soll. Ganz nebenbei erfüllt diese Klasse auch direkt die Funktion eines Fabric-Patterns, wodurch hier auch schon die ersten Informatik-Pattern äußerst plastisch dargestellt werden.

Ameisen spezialisieren

Die Auslagerung der Erzeugungsklasse hat aber nicht nur positive Auswirkungen auf die Code-Struktur, sondern erlaubt es auch, dem Spieler etwas mehr Freiheit bei der Spezialisierung seiner Ameisen zu machen. Ameisen konnten ja bislang mit Hilfe der Kasten-Attribute in Gruppen unterteilt werden. Der Code, der alles steuert, befand sich aber weiterhin in einer einzigen Datei. Wollte man den „Sammler“ anders agieren lassen, als den „Kämpfer“, so musste man als Programmierer in jeder Methode eine Weiche einbauen. Das ist nicht ganz im Sinne der objektorientierten Programmierung. AntMe! 2.0 löst dieses Problem weitaus besser: Die zentrale Klasse des Volkes wird in Zukunft nicht mehr die Ameise, sondern die Ameisen-Fabrik, die Colony-Klasse, sein. Die Implementierung der Ameise verläuft dann vollkommen frei und kann beliebig vererbt werden. Das Kaste-Attribut gibt es zwar weiterhin, aber nur um eine konkrete Implementierung mit der Fertigkeitsverteilung zu belegen – also nutzen wir nur noch die deklarative Funktionsweise eines Attributs. Es wird also möglich sein für sein Volk eine Basisameise zu implementieren, die Grundfunktionen wie die Wegfindung, Dekodierung von Markierungen,… übernimmt. Die Spezialisierung zum Kämpfer oder Sammler kann dann in einer spezialisierten Klasse passieren – ganz im Sinne der OOP.

Wahrnehmung der Welt

Wesentliche Verbesserungen sind bei der Wahrnehmung der Umgebung vorgenommen worden. Wo die alte Version pro Event immer nur das erstbeste Objekt geliefert hat, kann die Ameise in Zukunft ihre Umwelt vollkommen frei analysieren. Richtig kritisch ist dieses Problem bei der Verfolgung einer Markierungsspur. Die alte API liefert bei Riecht(Markierung) lediglich die Markierung, die zuerst gesichtet wurde – und das auch nur ein einziges mal bei Sichtung. Es ist also wirklich schwer eine Ameisenstraße zu analysieren um die Herkunft zu ermitteln. Ein paar Hilfsvariablen wie AmeisenInSichtweite, die die Menge der benachbarten Ameisen zurück geliefert hat, war leider nur selten hilfreich. In Zukunft wird dem Spieler eine Liste von sichtbaren Elementen zur Verfügung gestellt. Eine Variable RiechbareMarkierungen liefert alle wahrgenommenen Markierungen. Das ist der Moment, in dem Schleifen und Lambdas in Spiel kommen. So lässt sich mit RiechbareMarkierungen.OrderBy((m) => (m.Entfernung)). FirstOrDefault() die Markierung ermitteln, die der Ameise am nächsten steht.

So funktionieren die Ameisen im Hintergrund

Alles in allem hat sich die Architektur von Version 2.0 wesentlich generischer entwickelt, um wirklich sehr flexibel bei zukünftigen Entwicklungen zu bleiben und ein Höchstmaß an Erweiterbarkeit zu sichern. Ich will mich bei der Beschreibung hier aber erstmal auf den Ablauf bei den Ameisen beschränken. Im Übrigen funktioniert bei den Wanzen auch wieder alles ganz anders 😉 Alles fängt damit an, dass es eine generische Implementierung von Factions, also Fraktionen, Parteien, Rassen,… gibt die von beiden Rassen (Ameisen und Wanzen) gleichermaßen verwendet werden. Die konkrete Implementierung bestimmt dann, wie der Ablauf dieser Rasse im Spiel abläuft (Wann neue Einheiten erstellt werden, wie neue Einheiten erstellt werden,…). Im Ameisenfall ist festgelegt, dass es eine Colony-Klasse geben muss – mehr erstmal nicht. Die Colony-Klasse verfügt in Zukunft auch über das Spieler-Attribut, das Auskunft über den Kolonie-Namen und die Autoren-Referenz gibt. Geht eine Simulation los, wird beim erzeugen einer Ameise diese Colony gefragt, welche neue Ameise erzeugt werden soll. Der Rückgabewert ist hier ein schlichter Type der von der AntFaction untersucht wird. Handelt es sich hierbei um eine gültige Ameisen-Klasse (erbt sie von einer Basisklasse, verfügt sie über ein Kasten-Attribut), wird eine Instanz davon erzeugt und die Simulation erhält einen Repräsentaten in Form einer Ameise. Erlebt die Ameise innerhalb der Simulation irgendetwas spannendes (sieht Zucker oder so), wird dem Programmierer mit Hilfe eines Interop-Objektes ein Ereignis geworfen, das letztendlich zur Ausführung der entsprechenden Methode führt.

Basis API

Das eben erwähnte Interop-Objekt ist – im Gegensatz zur vorherigen Version der Lokalisierung – die zentrale Schnittstelle zwischen dem Ameisen-Objekt der Simulation und der lokalisierten API für den Spieler. Dieses Interop-Objekt verfügt über wesentlich rohere Daten als die übersetzte API. Was bei der deutschen Lokalisierung noch SichtbareAmeisen, SichtbareWanzen,… heißt, ist im Interop-Objekt noch in VisibleItems zusammengefasst. Das kann in manchen Situationen sehr, sehr nützlich sein. Ebenso sind die Events, die eintreffen, etwas generischer. So gibt es nur ein Spots(Something)-Event – ohne Differenzierung des Element-Typs. Ameisenvererbung Profis können das für sich nutzen. Einerseits steht dem Programmierer bereits in den Standard-Templates ein Interop-Objekt zur Verfügung, auf das frei zugegriffen werden kann. Der Spieler kann aber auch von Anfang an über das Erben einer anderen, wesentlich niedrigeren Version der Basisameise Zugriff darauf verschaffen und seine API nach eigenem Ermessen basteln.

Willst du die Alpha testen?

So! Die erste spielbare Alpha steht bereits fast vor der Tür. Leider lässt hier der Komfort und Unterstützung durch Dokumentation und Hilfe-Dialoge noch etwas zu wünschen übrig, weshalb das hier sicher nur was für Leute ist, denen der Prozess des Erstellens eigener Projekte, Referenzierung von Assemblies und Einbinden von Namespaces nicht unbekannt ist. Da ich aber gerade jetzt, wenn es um die Gestaltung des Spiel-Interfaces geht, gaaaanz, ganz viel Feedback brauche, würde ich gerne ein paar Leute zum geschlossenen Test einladen. Fühlst du dich angesprochen, dann schreib mir doch bitte direkt eine Email (tom@antme.net) mit ein paar Worten dazu, was du so machst und in welchem Zusammenhang du zum Ameisen-Projekt stehst. Ich würde mir wünschen, wenn sich auf diesem Weg ein paar Lehrer, Trainer und Pädagogen bei mir melden, damit ich hier möglichst früh noch euer Feedback einbeziehen kann. Danke für euer Unterstützung!

Kommentare
  1. Die bisherigen Lizenzbedingungen „Die Lizenz von AntMe! erlaubt die kostenfreie Nutzung für den privaten Gebrauch. Auch für den Einsatz in Lehre und Forschung ist AntMe! kostenfrei, jedoch würden wir uns freuen, wenn wir wüssten, wo AntMe! überall eingesetzt wird“

    unterscheiden sich nun mal stark von einer MIT-Lizenz
    und sind natürlich nicht wirklich geeignet,

    z.B. Forks bzw. Varianten für C# Ökosyteme
    – Unity ( http://www.unity3d.com/ )
    – Delta Engine ( http://www.deltaengine.net/ )

    zu ermöglichen. Bei Relisierung auf solchen Platformen – unter Wahrung der Spiel-Idee, der Business-Rules ( Ameisen-API für Spieler,… ) aber eben im Sinne von eigenständigen MVC / MVVM, bzw. einer Abstraktion des Spiels so daß es wirklch gleichberechtigte DirectX / Unity / 3D-Framework Treiber gibt,

    so daß in beiden Fällen sogar echte Multiuser-Games auf existierenden Platformen entstehen könnten.

    Die Abstraktion „wie muss ich die GUI-Schnittstelle schneiden, so daß sowohl OpenGL, DirectX und Unity damit zufrieden sind, fasziniert mich schon….

    Tja.. neben Versions- auch Lizenz-Updates?!

    Viele Grüße
    Rolf

    • tomwendel sagt:

      Hallo Rolf,

      gut, dass du das Thema Lizenz schon ansprichst. Leider sind wir bisher nicht soweit, dass man da schon was konkretes sagen könnte. Ich arbeite gerade mit einem Marken- und Lizenz-Profi an der perfekten Lösung.

      Wir bleiben unserer Philosophie aber weiterhin treu: Der Einsatz für Lehre und Forschung bleibt weiter frei.

      Und zum Thema Schnittstellen: Die alte AntMe!-Version läuft ja auf .NET Framework 2.0 und ist damit grundsätzlich kompatibel mit dem Mono-Framework. Das Spiel lässt sich daher auf andere Plattformen portieren. Ärger hat da nur die 3D-Ansicht gemacht, da die auf Managed DirectX basiert. Da es aber von Haus aus eine Schnittstelle für Visualisierungen gibt, hätte man jederzeit eine OpenGL oder Unity-Version bauen können. Das wird im Übrigen auch weiterhin so bleiben.

      Beste Grüße
      Tom

  2. AntMe ist (auch) als Lernsprache für C# geeignet :-), dass man das ganze „compilieren“ muss war eher naturgegeben.

    Interessant wäre eine Einbindung von Powershell ( der Beispielcode den ich dazu gesehen habe, umfasst wenige als 1 Bildschirmseite ?! ), so daß man wie in/seit grauer Vorzeit einst Microsoft-Office von „draussen“ alles scripten kann.

    Das würde echte Server-Anwendungen ermöglichen, wo klar ist daß das Spiel-Team eben NICHT für jede Algorithmus-Verbesserung einen Server-Upload machen muss / darf,
    sondern dass da – wie heute bei typischen objektorientierten Skriptsprachen ( Python, Perl,.. ) möglich, die Eigenintelligenz der Anwendung DYNAMISCH aufgebaut wird. Natürlich müsste man dann irgendwie den Spielstand bzw. -status speichern.

    Ich gebe aber offen zu, daß diese Überlegung, die Spielentwicklung dynamisch zur Laufzeit zu machen,vom ursprünglichen gesponsorte Konzept „Wir zeigen wie man in .NET eine DirectX-Graphikanwendung macht, die zum Mitentwickeln reizt“ :-).

    Kann .NET irgendwie auch „dynamisch“ programmiert werden :-)?! Ideen?! Anregungen ?!

    Aber wir sind ja 2014.

    Viele Grüße
    Rolf

    • tomwendel sagt:

      Hey Rolf,

      bin genau an einem solchen Thema dran 😉 Leider macht es einem die .NET Runtime nicht besonders leicht diese Art der Dynamik zu verwenden. Für das Ändern des Codes zur Laufzeit gibt es mehrere mögliche Ansätze:

      1) Man baut fertige Skriptblöcke und erlaubst dem Spieler das Setzen von Variablen, die den Ablauf dieser Blöcke steuern. Das wäre die perfekte Lösung, wenn man den Spieler auf bestimmte Möglichkeiten beschränkt, wie das bei einem visuellen Editor für Prozess-Abläufe der Fall wäre.

      2) Man lädt den User-Code in eine AppDomain pro Spieler. Diese erlaubt nämlich das Entladen von Assemblies. Leider ist die Kommunikation über die AppDomain-Grenze relativ langsam und versaut hier enorm die Performance.

      3) Man ignoriert das Problem des Entladens von Code und erlaubt dem Spieler nur eine begrenzte Menge von „Timeouts“ um den Code zu updaten. Der geänderte Code wird einfach parallel zum vorhandenen Code geladen und Stück für Stück ausgetauscht. Dies scheint mir persönlich auch die beste Variante zu sein, deinen Plan zu verwirklichen.

      Alles in allem erlaubt die neue AntMe! Runtime das alles (siehe Klassen-Diagramm meines Blog-Eintrags). Interop- und Spiel-Item bleiben gleich. Lediglich die Steuerungsklasse muss ausgetauscht werden. Es gibt da ein paar Kleinigkeiten, die noch gelöst werden müssen, aber denkbar ist es.

Hinterlasse einen Kommentar