Tagebuch: Game Jams

Ok. Hab jetzt mal spaßeshalber die mobile Steuerung eingebaut und das ganze mal auf meinem Androiden deployed.

Und was soll ich sagen: Es läuft :slight_smile: und zwar sehr gut sogar!

Einem Android-Port steht also nichts im Weg :slight_smile:

Hmm. Tatsächlich scheint gerade das komplizierteste das GUI zu sein. Ich würde das auf dem Android gerne etwas anders haben.

Ich bin mir jetzt nur noch nicht sicher, wie ich das mache. Aber ich glaube ich muss tatsächlich zwei verschiedene Versionen davon pflegen.

:smile:

Ich hatte das mal versucht die QBasic-Variante in AmigaBasic auf einem A500 umzusetzen. Nein, der A500 hatte nicht mal annähernd die CPU-Power um es wie in QBasic zu machen. Musste mir dann eine eigene Variante für das auflösen des Schlangenschwanzes machen.

Anschließend habe ich noch Geschwindigkeiten eingebaut: je langsamer man spielte, um so länger wurde man beim Fressen. Also statte ein Feld länger, eben (z.B.) 5 Felder.

Wobei mir der auch ganz schöne Problem anfangs gemacht hat. Ursprünglich wollte ich es so bauen, dass dir die Aliens folgen. Das war aber alles andere als einfach. Die sind überall hingelaufen nur nicht dahin wo sie sollten. Irgendwann bin ich drauf gekommen, dass ich einen/mehrere Pfade generieren müsste. Aber auch damit war das Ergebnis alles andere als zufrieden stellend. Irgendwann kam mir dann die Idee: spawn die Aliens an Ort uns Stelle und gut ist.

Auch eine interessante Idee. Ich ziehe ja einfach punkte pro Sekunde ab. Irgendwie muss man ja einen Anreiz schaffen, dass der Spieler weiter macht.
Ich glaub ich hab bei meiner Variante noch nie länger als 1:35 oder so überlebt. Aber dadurch das ich Punkte verlier und möglichst viel haben möchte, kommt mir es vor als ob die Zeit viel schneller vergeht. Ganz oft das ich dachte: „Jetzt müsstest du an der 2min-Marke sein“ und war dann bei 30 oder 40 Sekunden ^^.

Sieht richtig gut aus, gefällt mir! :slight_smile:

Wie heißt du dort? Der hier ist es nicht, oder? :smiley:

EDIT: Ok, gefunden, ich Fuchs :see_no_evil:

1 Like

Danke :slight_smile:

Dabei hab ich mich doch so gut getarnt ^^ … und ich weiß nicht, was ich von dem Tomatensalat halten soll. Zum einen: sehr unkreativer Name und zum anderen ist das verdammt nah an meinem dran. Ich wusste, ich hätte den als Marke eintragen lassen sollen :frowning:

So. Es gibt ein neues Update (was vermutlich auch das letzte ist). World Snake hat nun eine Highscore und man kann die Drehgeschwindigkeit vom Spieler verändern. Dafür bekommt der Spieler in den Einstellungen nun 3 Voreinstellungen zur Verfügung:

  • Normal (standard)
  • Fast
  • Very Fast

Das Update gilt für alle Plattformen: web, win, mac, linux und android.

Letzteres muss aber erst noch durch den review-prozess. Ich hoffe, das Google direkt die letzte Version reviewed und nicht die von gestern und dann die von heute. Ich fände es gut, wenn das Spiel direkt in der aktuellen Version released wird :slight_smile:.

Hier nochmal der Link zum Spiel: https://tomate-salat.itch.io/world-snake

Ich wünsche viel Spaß :slight_smile:

Ging doch schneller als 7 Tage :slight_smile: :

Bin mittlerweile an einem neuen Game-Jam dran. War mir nicht sicher, ob ich da teilnehmen sollte. Denn er hat eine gemeine Restriktion: Source Code öffentlich machen.

Das Problem ist nicht der öffentliche Source-Code. Das Problem resultiert eher daraus. Denn öffentlicher Source-Code bedeutete auch: keine gekauften assets verwenden! Somit kann ich Bolt nicht einsetzen. Und ohne Bolt, kann ich meine eigene JFruit-Lib nicht einsetzen.

Also hab ich mir gedacht, ich gucke mal weiter. Hab auch 2 weitere Jams gefunden, die für sich auch interessant waren. Einer vor allem deswegen, weil die Juroren jedes Spiel im Live-Stream spielen und kommentieren. Hätte mich mega interessiert was jemand zu meinem Spiel sagt. Aber basierend darauf den Jam auswählen? Irgendwie schon - immerhin geht es ums Feedback. Aber ich bin mir sicher: solche Jams kommen immer wieder. Und wenn ich so an meine Spiele denke? World Snake hätte ich gerne im Live Stream gesehen. Doginx hingegen - muss nicht wirklich. Rawbot wäre auch nett gewesen, aber nur wenn der Stream es bis Ende spielt.

Aber egal - ich hatte zum Schluss also 3 Jams vor mir und nach kurzer Zeit vergessen, welcher der mit dem Stream war. Musste ich wieder suchen, hab ihn gefunden und endgültig entschieden: Davon mach ichs nicht abhängig.

Wie ich es einleitend schon gespoilert hab: ich hab mich für den ersten entschieden. Warum? Aus 2 Gründen:

  1. Ich fand das Thema „Zeit“ war das interessanteste von allen. Und ich hatte das Gefühl da was bauen zu können
  2. Die Tatsache, dass ich keine weiteren Jams angeschaut hätte - wenn Bolt erlaubt wäre.

Nein. Punkt zwei ist tatsächlich ein Pro-Argument und kein Kontra. Warum? Ganz einfach: meine Tools sollten mich unterstützen und ich sollte nich Abhängig von Ihnen sein. Außerdem sehe ich es als Möglichkeit an, meine JFuit-Lib aufzuräumen.

So. Ich bin jetzt schon seit vorgestern dabei und habe heute in der Mittagspause etwas gemacht, wovor es mir immer gekraut hatte. Partikel Systeme. Nicht, dass ich die nicht toll fände - ich kann sie nur nicht benutzen. Deswegen hab ich bisher auch viel Abstand zu denen gehalten. Aber man will ja was lernen. Und hier das Resultat meiner Mittagspause:

So. Ich drück mich gerade etwas vorm nächsten Partikeleffekt, deswegen schreib ich mal hier ein update ^^.

@TMII hat mir den Tipp gegeben, die Partikeleeffekte beim Laden zu verändern und das hab ich auch genau so übernommen. Schaut definitiv besser aus.

Zudem können die Gegner nur Schaden nehmen. Wie viel Effekt der Schuss hatte, sieht der Spieler in Form von Zahlen die über dem Gegner auftauchen. Je mehr Schaden in Relation zu den verbleibenden HP gemacht wurde, desto roter die Textfarbe. Und ich überlege noch, ob ich dem Spieler die verbleibenden HP überhaupt anzeigen soll. Irgendwie möchte ich nicht so wirklich, dass er es weiß. Vllt auch ein Kompromiss: der Spiele sieht die Lebenspunkte nur von dem Gegner, über dem die Maus steht.

Des weiteren verlieren die Kugeln jetzt nach jeder Kollision die hälfte Ihres Schadens.

Das ganze könnt Ihr hier schon sehen :slight_smile::

Hab richtig guten Fortschritt heute gemacht. Der Kern vom Spiel steht schonmal. Dabei hab ich heute bisher folgendes eingebaut:

  • Partikeleffekte für Explosionen (Spieler und Bomben)
  • Cache-System für Gegner (so kann ich die GameObjects wiederverwenden und Unity muss diese nicht bei jedem Spawn neu erstellen)
  • Spieler kann sterben
  • Systeme schalten sich ab wenn Spieler tot
  • SpawnSystem: zwar nicht neu, aber ziemlich stark überarbeitet. Vor allem werden die Gegner nun an Ihrem finalen Platz erstellt.
  • Und eben das im Post über diesem Post)

Natürlich ist ein Video immer am besten. Deswegen könnt Ihr hier das ganze in Action sehen :slight_smile:

So. Ich hab mal wieder nette Fortschritte gemacht. Ich hab relativ viel Zeit gebraucht selber eine StateMachine zu designen. Dabei hab ich mehrere Konzepte gebaut und zwei sind auch zum Einsatz gekommen. Aber nicht parallel. Ich hatte erst eine und dachte ich wäre damit zufrieden gewesen. Aber es war mir zu sehr ein Proxy.

Deswegen musste ich das ganze nochmal Umsetzen. Und die StateMachine kommt von der Funktionsweise sehr nahe an das Prinzip von Bolt ran (natürlich ohne irgendwas visuelles). Aber es fühlt sich von der Arbeitsbeweise her ziemlich gleich an. Darum bin ich damit auch sehr zufrieden.

Des weiteren hab ich heute mein Lightning-Problem behoben. Ich wollte schon einmal meine Scene besser beleuchten und nachdem ich die meine Lichter „gebacken“ hatte, war alles dunkel. Ich hab es nicht hell bekommen. Das Problem war zwar einfach zu lösen - aber nicht einfach zu finden. Es lag letztendlich einfach daran, dass meine 3D-Modelle keine sinnvollen UVMap haben. Also sie macht schon Sinn für die Textur - aber die UVs sind halt absolut unbrauchbar für LightMaps und Shader. Glücklicherweise kann Unity zusätzliche UVMaps automatisch erstellen. Das hat letztendlich mein Problem mit der Beleuchtung gelöst :slight_smile:.

Zu guter letzt hab ich heute dann noch ein paar PostProcessing Effekte dazu gepackt und bin recht zufrieden mit dem Ergebnis bisher. Auch wenn ich glaub noch am PostProcessing schrauben werde ^^.

Oh - und bevor ichs vergesse. Am Hauptmenü hab ich auch noch ein paar Sachen umgestrickt.

Wie immer gilt: Video > Text. Also hier auch ein Video zu dem aktuellen Stand:

Hab mich die Tage um Musik und Einstellungen gekümmert. Heute kam dann noch die Spiel-Statistik hinzu.

Außerdem hab ich noch einen weiteren Post-Process-Effekt eingebaut. Damit wirkt das ganze noch ein wenig surrealer. Und ich find surreal passt sehr gut zu meiner Spielidee :slight_smile:.

Das es damit doch schon wieder einiges zu Zeigen gibt, hab ich direkt mal ein neues Video aufgenommen.

Also hier diesmal ein Video mit Ton: https://youtu.be/QSeFfhaDxb0

Was sagt mehr aus als ein Video? Richtig: ein Spiel. Hab heute morgen noch ein schönes intro-erklärungsvideo eingebaut :slight_smile:.

Das Spiel findet ihr hier:

Ich wünsche viel Spaß :slight_smile:

P.S.: Ich schaffs nicht weiter als lvl 4. Wäre interessant zu hören, ob hier jemand mehr packt :slight_smile:


Ach ja. Die sourcen findet ihr hier: https://github.com/tomate-salat/keep-your-memory

erste Runde
image

ich würde noch eine Hover für die Buttons vorschalgen - ansonsten verdammt gute arbeit

1 Like

Hab heute 3 Kommentare gelesen. Die Bomben tot zu bekommen ist für viele schwieriger als erwartet. Kann mir aber nur vorstellen, dass der eigenen Schuss zu wenig aufgeladen wird. Auch wenn er recht klein ist. Bleibt man kurz stehen, dann laufen die Bomben in einer geraden Linie auf einen drauf zu.

Irgendwie hab ich das Gefühl das Spiel macht ist sehr ambitioniert darin, die Leute unter Stress zu setzen. Man hat nämlich gerade am Anfang eigentlich noch genug Zeit zu Chargen und ein paar Bomben der mit einem Schuss zu erledigen. Dann hat man auch eine Lücke durch die man durch kommt und „etwas Zeit gewonnen“ sich um die restlichen zu kümmern.

Die Buttons haben einen Hover. Aber der ist einfach nur verdammt schlecht zu sehen ^^. Generell hatte ich mit der Farbpalette sehr viele Schwierigkeiten, einfach weil sie überwiegend Dunkel ist und die wenigen hellen Farben nicht alle gut gepasst haben. Letztendlich verwende ich glaub auch nur die hälfte der Farbpalette im Spiel - der Rest wollte irgendwie nicht harmonieren. Ka - vllt einfach meine Unfähigkeit.

Danke. Bin auch mega stolz auf das Ergebnis. Ich hab wieder extrem viel gelernt und gerade gestern war extrem frustrierend. Vor allem das Intro hätte ich fast wieder komplett verworfen, weil ich mich selber die Physik über 3 ecken zerhauen hab und ich lange nicht verstanden hab, wieso.

Ich bin aktuell gerade sehr beschäftigt mit machine learning. Unity bietet da eine nette Lib an die ich zufällig vor kurzem durch ein YouTube-Video entdeckt hab. Mein Ursprünglicher Plan war es, einen KI zu entwickeln, die Keep Your Memory besser spielt als ich.

Leider hab ich das nicht hinbekommen und mein Projekt war jetzt auch nicht gerade für KI-Training designed. Das macht es für einen Anfänger natürlich umso schwerer.

Also dachte ich: beginne ein neues Projekt, welches eine einfachere KI voraus setzt. Erstmal laaangsam anfangen.

Ich dachte auch, dass ich ein ganz gutes Anfangsprojekt habe, was ich auch für ein Spiel zu einem Game-Jam ausbauen könnte. Spielprinzip ist einfach: Straße muss überquert werden, ohne das man vom Auto getroffen wird.

Sollte recht einfach sein für den Anfang. Die KI muss wenig wissen und noch weniger Aktionen ausführen. Vergleichen wir mal die Aktionen.

Keep Your Memory

  • Drehen
  • Bewegen
  • Schuss chargen
  • Schießen

Neues Spiel

  • Bewegen

Ich wollte nicht mehr als 2 Aktionen und bin sogar nur bei 1er. Gut was :slight_smile:. Während ich viele Stunden schon KIs trainiert hab, haben die umgekehrt auch mich trainiert.

Im wesentlichen funktioniert es so. Die KI trifft in Abständen immer wieder eine Entscheidung. Ich kann jetzt mittels Rewards sagen ob die gut oder schlecht war.

  • Positive Zahl = gut
  • Negative Zahl = schlecht

Damit kann ich also belohnen und bestrafen. Im wesentlichen schaut mein Model derzeit so aus:

  • Ziel erreichen: 1.0 (fix)
  • Vom Auto getroffen werden: -1.0 (fix)
  • Am leben sein: -0.001
  • Nach vorne Bewegen: 0.002
  • Zurück bewegen: -0.2

Kurz noch eine Erklärung was ich mit fix meine. Ein Agent (also das Teil was lernt) lernt in Episoden. Eine Episode ist vorbei wenn das Ziel erreicht wurde oder er von einem Auto getroffen wurde. Danach setzte ich den Agent auf seine Startposition zurück und beginne eine neue Episode. In dieser Zeit bekommt er von seinem Reward je nach Aktion positive oder negative Punkte. Es kann also sein, dass der Agent mit einem derzeitigen Reward von -0.5 beim Ziel ankommt. Dann addiere ich aber keine 1 sondern setze den Wert auf. Ich möchte, dass der Wert am Ende immer positiv ist - weil er könnte da auch durchaus mit -60 ankommen. Und dann ist -59 nicht so gut wie eine 1 ;-).

An der Stelle merke ich übrigens, dass ich das nur machen sollte, wenn der Wert unter 0 ist um schnelles erreichen des Ziels zu belohnen!

So. Die Zahlen die ich habe sind meine aktuellen. Die waren nicht immer so. Ich hab da ziemlich viel mit rumgespielt über die Zeit!

Generell hab ich zu Anfang haufenweise dummer Fehler gemacht. Ob ich es jetzt richtig hab, weiß ich btw nicht. Aktuell trainiere ich gerade eine (hoffentlich) vielversprechende KI.

Einer meiner ersten Fehler war das Leveldesign. Ich dachte mir: lass die KI durch ein Level rennen, wie es später auch sein könnte. Ergo: die ersten Straßen sind leichter als die am Ende. Hat nur ein paar Nachtteile:

  • Warum sollte die KI erst lernen mit den einfachen Sachen klar zu kommen, wenn ich sie auch gleich gegen den härtesten Schwierigkeitsgrad trainieren lassen kann? Ich starte mit mehreren Agents parallel (50 Stück - gleiches Level). Davon kamen 1-3 bei den letzten Levels an. Somit können auch nur 3/50 meiner Agents die schweren Passagen trainieren.
  • Warum überhaupt ein komplettes Level? Diese sollten sich später eh in der Anzahl der Straßen unterscheiden können. Also reicht es doch aus eine Straße auf höchster Schwierigkeit zu haben.
  • Nur eine Straße haben ist dumm - zum Schluss funktioniert die KI nur wenn Autos von rechts kommen. Also hab ich eine gespiegelte Variante direkt daneben gepackt. Sodass beides trainiert wird.

Für den zweiten Punkt hab ich mehrere Tage gebraucht. Der dritte Punkt kam mir dann relativ schnell.

Ein weitere Fehler (den ich immerhin nach glaub einem Tag mit dem neuen Spiel bemerkt hatte): Meine KI weiß zu wenig! Meine KI hatte ein paar Raycasts und das wars. Irgendwann kam mir: vllt sollte sie wissen WO sie sich befindet!

Irgendwann hab ich mich gewundert, warum die KIs den Autos nicht wirklich ausweichen. Anfänglich dachte ich: die Strafe ist zu niedrig. Doch ich hab was entscheidendes gelernt: Überprüfe was deine KI sieht! Denn sie sahen die Autos nicht. Ich hatte das Auto-Gameobjekt falsch eingestellt. Die KI konnte es nicht sehen.
Als ich noch das große Level hatte, hatte ich nach jeder Straße einen Trigger aufgestellt, der die KIs belohnen soll beim durchlaufen. Negativ war: die Trigger haben wie eine Wand für die Trigger funktioniert. Meine KIs konnten schon wieder die Autos nicht erkennen.
Dann hatten meine Agents sich immer mal wieder gedreht (Phsyikalisch bedingt). Ich sende aber nur Rays nach vorne und zur Seite. D.h. nach hinten sind meine Agents Blind (aber gewollt). Was nicht gewollt ist: wenn meine KIs gedreht sind, dann schauen die nicht mehr nach vorne - sondern zur Seite oder sonst wo hin. Ergo: Sie konnten die Autos schon wieder nicht sehen (Das hatte ich aber zum Glück ziemlich Zeitgleich mit der Trigger-Wand entdeckt).

Und zu guter letzt (heute morgen rausgefunden). Nachdem ich gestern Stunden lang meine KI trainiert hatte, hatte die ein ganz seltsames Verhalten angenommen. Alle kuschelten unten rechts auf einem Fleck und ich wusste nicht warum. Ich dachte über eine erhöhte Strafe nach um Sie nach vorne zu bewegen.

Das Problem ist nur allzu menschlich! Ich würde mal sagen: die KI hatte schlicht Angst! Warum kann ich seit heute morgen kann ich es zu 100% nachvollziehen und würde mich absolut genauso verhalten. Es war nämlich folgendes:
Meine Agents kollidieren nicht miteinander. D.h. Sie verhalten sich zueinander mehr wie Geister die durch den anderen durch gehen können (sie sollen sich ja nicht gegenseitig beeinflussen). Was ich aber ich nicht eingestellt hatte, war das sie auch durcheinander durchschauen können. Somit können die nicht aneinander vorbei schauen.
Dementsprechend können die mitunter ankommende Autos nicht sehen. Die die vorbei gelaufen sind wurden also mit hoher Wahrscheinlichkeit direkt überfahren. Ich würde da auch lieber warten, bis der vor mir über die Straße gegangen ist, sodass ich sehe, was ankommt. Dummerweise hatten die dann alle noch ganz an der Seite geparkt und die Autos kommen durch eine Wand. Vllt hätte ich die Agents auch dadurch schauen lassen sollen. Aber ich wollte auch, dass sie wissen wo level-ende ist. Da wüsste ich derzeit auch nichtmal wie ich das Problem sinnvoll löse. Wobei - hab ich mehr oder weniger.

Denn dadurch, dass ich mein Trainings-level angepasst habe, gehen die Agents alle in die Mitte. Sie sehen ankommende Autos und können eine gute Möglichkeit abschätzen.

Und so schaut das level derzeit aus:

Das Thema an sich ist unglaublich spannend. Aber auch unglaublich komplex. Ihr habt jetzt nur eine sehr grobe Zusammenfassung bekommen. Denn da gibt es bei weitem noch sehr viel mehr zu beachten.

Also. Mein erstes Model was ich da raus bekommen hab sah tatsächlich sehr gut aus. Erfolgsrate 93% (Soviele wurden zumindest laut meinen Metriken nicht von einem Auto getroffen). Sobald aber die zweite Straße ins Spiel kommt, schaut es wieder ganz anders aus. Da haut es mir 80% der Agents weg.

Deshalb habe ich jetzt eine weitere Scene gebaut - bei dem es zwei Straßen gibt:

Und hier sieht man auch schön die Metric:

Orange zeigt das Modell an, welches mit nur einer Straße trainiert hatte. Rot zeigt das Modell an, welches mit zwei Straßen trainiert basierend auf dem orangen Modell! Also ich hab kein neues Training angefangen. Das einzige was sich verändert hat ist die Map.

Ich hoffe, dass danach die KI mit allen Richtungswechseln klar kommt.

Also das ist das beste was ich hinbekommen hab:

Und ich glaub besser wird es erstmal nicht. Deswegen lasse ich das ganze ruhen und werde einen anderen Kurs einschlagen.
So interessant das Thema auch ist. Im moment lenkt es mich zu Stark von meinem eigentlichen Vorhaben ab: Game Jams. Deswegen werde ich das ganze nur noch time-based verfolgen.

Ich stells mir so vor. Nachdem ich ein Spiel fertig hab, werde ich versuchen eine KI dafür zu entwickeln. Aber ich hab dafür nur einen Tag Zeit. Oder ich Sollte ich früher mit einem Spiel fertig sein, dass die restliche Zeit vom Game-Jam dafür nutze. Oder eben: ein Jam startet in ein zwei Tagen: Zur Überbrückung steht dann KI-Entwicklung an.

Hab es jetzt endlich geschafft einen Generator für komplexe Levels zu schreiben. Nachdem ich am Anfang versucht hab die Pfade komplett selber zu generieren bin ich über zu einer Semi-Prozeduralen-Lösung.

Heißt: ich hab ein paar vordefinierte Module und die werden aneinander gesteckt bis ein Level fertig ist. Das ganze schaut dann so aus:

Von der Logik her ist es auch tatsächlich recht simpel. Die einzelnen Module haben so genannte „ExtensionPoints“. Das sind praktisch leere Container in die ich ein Modul reinstecken kann. Vorteil: Das Modul befindet sich am richtigen Platz mit der richtigen Rotation. Das ganze könnt Ihr hier sehen:

Das komplett grüne sind ExtensionPoints. Die Linie über der grünen Platform zeigt an, in welche Richtung weiter gebaut wird.

Zu erkennen sind auch blaue rechteecke:

image

Alle außer die ExtensionPoints haben solche „Rechteecke“. Diese definieren einen Bereich, wo kein weiterer „Boden“ platziert werden darf. Somit verhindere ich Überschneidungen.

Das System funktioniert auch soweit echt verdammt gut und wie Ihr im Video seht: auch große Level sind absolut kein Problem :slight_smile:.