Hi Leute
ich hab gerade überlegt ein eigenes Game-projekt zu beginnen. Dachte dabei vor allem an eine art Zelda-Klon. Im Freeware-Bereich gibts da schon Zelda Classic, aber das ist leider nicht OSS. Dann gibts noch OpenLynks, aber das ist kurz nach dem Übergang auf SDL eingeschlafen (C++).
Bin jetzt am überlegen, was sinnvoller ist: mich mal an die Wiederbelebung von OpenLynks zu wagen oder das ganze mit pygame anzugehen,
Als Endziel wäre es schön eine freie Alternative zu Zelda Classic zu haben, aber mir gehts vorerst eher mal ums Programmieren aus Spass.
http://openlynks.sourceforge.net/
Zelda
-
- Python-Forum Veteran
- Beiträge: 16025
- Registriert: Freitag 20. Juni 2003, 16:30
- Kontaktdaten:
Also mein Zelda-Klon mit Pygame ist schon seit Ewigkeiten tot.mkallas hat geschrieben:Ich glaube, ein verwaistes Projekt umzustricken macht lange nicht so viel Spaß wie alles neu zu schreiben.
My god, it's full of CARs! | Leonidasvoice vs (former) Modvoice
- Hyperion
- Moderator
- Beiträge: 7478
- Registriert: Freitag 4. August 2006, 14:56
- Wohnort: Hamburg
- Kontaktdaten:
Du hast mal ein Spiel programmiert?Leonidas hat geschrieben:Also mein Zelda-Klon mit Pygame ist schon seit Ewigkeiten tot.mkallas hat geschrieben:Ich glaube, ein verwaistes Projekt umzustricken macht lange nicht so viel Spaß wie alles neu zu schreiben.
-
- Python-Forum Veteran
- Beiträge: 16025
- Registriert: Freitag 20. Juni 2003, 16:30
- Kontaktdaten:
Ich bin über Spieleprogrammierung überhaupt erst zu Python gekommen. Nicht dass ich da jemals irgendwas interessantes zusammengebracht habeHyperion hat geschrieben:Du hast mal ein Spiel programmiert?

My god, it's full of CARs! | Leonidasvoice vs (former) Modvoice
Hatte gestern einen Text geschrieben, der behandelte, dass ich die Schwierigkeit bei einen Spiel wie Zelda (was ich nie gespielt habe - ich beziehe mein Wissen von Roguelike-Spielen, die ebenfalls Mitte der 80er populär waren) nicht in der Darstellung sondern im Spielprinzip sehe. Hatte mir weiterhin Regel ausgedacht und beschrieben, leider hat mein TextMate das eben alles in die ewigen Speichergründe gerissen, weil ich DOOF nicht gespeichert hatte.
Habe nur noch den Python-Code, der da lautet:
Erklärung: Jede Kreatur (Helden, Monster, usw.) hat drei primäre Eigenschaften: Wie gut kann sie kämpfen, wie gut zaubern und wie verletzlich ist sie. Gegenstände können diese Werte beeinflussen. Waffen erhöhen so den Kampfwert, Zauberfoci den Zauberwert und Rüstungen reduzieren den Schaden.
Ich benutze 7-seitige Würfel, einfach weil ich's kann:
Erklärung: Ich werfe n Würfel. Eine 6 oder 7 ist ein Erfolg, bei 7 würfle ich den Würfel erneut. Soll ich weniger als einen Würfel werden, nehme ich einen "Schicksalswürfel", wo nur eine 7 (die aber öfters) ein Erfolg ist.
Und hier ist mein Beispiel:
Und ein Totenbeschwörer kann neue Skelette erschaffen:
Dazu kommen jetzt noch einige Funktionen, um Gegenstände aufzuheben, wegzuwerfen, zu benutzen und jede Menge Kreativität für besondere Gegenstände, Monster und Zaubersprüche. Packt man Monster und Gegenstände auf ein Spielbrett, hat man eigentlich ein Roguelike-Spiel, wie zum Beispiel Zelda.
Stefan
Habe nur noch den Python-Code, der da lautet:
Code: Alles auswählen
class Creature(object):
def __init__(self, combat, magick, health):
self._combat, self._magick, self._health = combat, magick, health
self._defense, self._soak = 2, 0
self.weapon, self.armor, self.focus = None, None, None
@property
def combat(self):
return self._combat + (self.weapon.combat if self.weapon else 0)
@property
def magick(self):
return self._magick + (self.focus.magick if self.focus else 0)
@property
def defense(self):
return self._defense + self._combat / 3
@property
def soak(self):
return self._soak + (self.armor.soak if self.armor else 0)
def attack(self, opponent):
damage = roll(self.combat - opponent.defense)
opponent.health -= max(damage - opponent.soak, 0)
return opponent.health > 0
def cast(self, spell):
spell.effect(roll(self.magick - spell.magick))
class Item(object):
def __init__(self, name, combat=0, magick=0, soak=0):
self.name, self.combat, self.magick, self.soak = name, combat, magick, soak
Ich benutze 7-seitige Würfel, einfach weil ich's kann:
Code: Alles auswählen
def roll(n):
successes = 0
if n < 1:
while True:
r = random.randrange(7)
if r < 6: break
successes += 1
else:
while n > 0:
r = random.randrange(7)
if r > 4:
successes += 1
if r < 6:
n -= 1
return successes
Und hier ist mein Beispiel:
Code: Alles auswählen
hero = Creature(7, 3, 11)
hero.weapon = Item("Breitschwert", combat=5)
hero.armor = Item("Lederrüstung", soak=1)
skeletons = [Creature(8, 6, 6) for i in range(3)]
while hero.health > 0 and skeletons:
skeleton = random.choice(skeletons)
if hero.attack(skeleton):
skeleton.attack(hero)
else:
skeletons.remove(skeleton)
Code: Alles auswählen
necromancer = Creature(3, 11, 8)
necromancer.weapon = Item("Knochenstab", combat=3, magick=8, soak=1)
necromancer.armor = necromancer.focus = necromancer.weapon
def raise_skeletons_effect(power):
for i in range(power):
skeletons.append(Creature(8, 6, 3 + power))
raise_skeletons_spell = Item("Skelett beleben", magick=6, effect=raise_skeletons_effect)
necromancer.cast(raise_skeletons_spell)
Stefan
- Rebecca
- User
- Beiträge: 1662
- Registriert: Freitag 3. Februar 2006, 12:28
- Wohnort: DN, Heimat: HB
- Kontaktdaten:
Die meiste Arbeit macht vor allem, eine fortlaufende Geschichte zu erarbeiten, die Spielwelt mit den NPC, Levels mit aufsteigendem Schwierigkeitsgrad, Raetsel etc. Zelda hatte z.B. auch immer das Prinzip, dass man in jedem Level eine neue Waffe/einen neuen magischen Gegenstand bekam, mit dem man dann neue Gebiete der Spielwelt erschliessen kann, sodass man nach und nach die Spielwelt kennen lernt etc.
Offizielles Python-Tutorial (Deutsche Version)
Urheberrecht, Datenschutz, Informationsfreiheit: Piratenpartei
Urheberrecht, Datenschutz, Informationsfreiheit: Piratenpartei
-
- Python-Forum Veteran
- Beiträge: 16025
- Registriert: Freitag 20. Juni 2003, 16:30
- Kontaktdaten:
Das schöne war, dass man eigentlich ganz oft durch die selben Orte ging und je nachdem was man schon für Gegenstände hatte weiter und weiter gehen konnte. Am schluss ging das so weit, dass bereits in der Gameboy-Classic-Version Teleporter eingeführt worden, weil man sonst nur noch am laufen gewesen wäre.Rebecca hat geschrieben:Zelda hatte z.B. auch immer das Prinzip, dass man in jedem Level eine neue Waffe/einen neuen magischen Gegenstand bekam, mit dem man dann neue Gebiete der Spielwelt erschliessen kann, sodass man nach und nach die Spielwelt kennen lernt etc.
Zelda hat mit Roguelike-Spielen wenig zu tun, der Kampf ist einfacher, weil ein Treffer mit einer Waffe (Schwert oder der Bumerang, Bogen, oder auch mit rumstehenden Vasen, Elefantenstatuen, Eistenkugeln, etc.) dem Gegner einen Trefferpunkt abzieht. Vorrausgesetzt man trifft ihn an einer verwundbaren Stelle und auch mit der richtigen Waffe. Das L2-Schwert teilt doppelt so starke Treffer aus, der Wirbelklingen-Angriff verdoppelt unabhängig vom Schwert-Level die Angriffspunkte. Wenn der Gegner 0 Trefferpunkte hat, verschwindet er und lässt unter Umständen einen Gegenstand übrig. In neueren Zelda-Versionen (auf dem Handhelf, die Konsolen-Versionen sind wiederrum etwas anders) konnte man den Wirbelklingen-Angriff nicht nur einmal ausführen sondern beliebig oft hintereinander wirbeln. Das System ist eigentlich ganz simpel, da Treffer gleich Treffer ist, es gibt keine Rettungswürfe etc. das einzige was durch Würfeln bestimmt wird ist ob Gegner Gegenstände liegen lassen, aber das war je nach Gegner und benutzer Waffe unterschiedlich warscheinlich.
My god, it's full of CARs! | Leonidasvoice vs (former) Modvoice
so, hab den code von Leonidas mal ein wenig umgeschrieben. Hab aber keine Ahnung, wo ich so ein Projekt hausen lassen soll - BerliOS ? Leonidas meinte SF wäre mitlerweile out - bin da nicht so auf dem neusten Stand (schon garnicht was python angeht).
Link tänzelt jetzt lustig im Fenster herum
@Spielsystem. Also interessanter finde ich da die Kollisionabfrage. Bei Zelda 3 war es soweit ich mich erinnere möglich nur das Schwert des Gegners zu treffen (Schwert an Schwert) - somit war das wohl selbst noch ein eigenes Objekt (?)
Ich find auch in den Grundzügen gleicht Zelda einem Rogue-Game. Aber die genannten Elemente lassen es dann doch zu was besonderem werden.
Hab mir jedenfalls keine zu hohe Messlatte gesetzt, da bei Zelda doch einiges zusammenkommt. Ich versuch mich demnächst mal am Kampfsystem.
Link tänzelt jetzt lustig im Fenster herum

@Spielsystem. Also interessanter finde ich da die Kollisionabfrage. Bei Zelda 3 war es soweit ich mich erinnere möglich nur das Schwert des Gegners zu treffen (Schwert an Schwert) - somit war das wohl selbst noch ein eigenes Objekt (?)
Ich find auch in den Grundzügen gleicht Zelda einem Rogue-Game. Aber die genannten Elemente lassen es dann doch zu was besonderem werden.
Hab mir jedenfalls keine zu hohe Messlatte gesetzt, da bei Zelda doch einiges zusammenkommt. Ich versuch mich demnächst mal am Kampfsystem.
-
- Python-Forum Veteran
- Beiträge: 16025
- Registriert: Freitag 20. Juni 2003, 16:30
- Kontaktdaten:
Google Code war letztens populär, alternativ auch Origo. Vielleicht reicht ja auch das was Github oder Bitbucket zur Verfügung stellen?MilesTeg hat geschrieben:so, hab den code von Leonidas mal ein wenig umgeschrieben. Hab aber keine Ahnung, wo ich so ein Projekt hausen lassen soll - BerliOS ? Leonidas meinte SF wäre mitlerweile out - bin da nicht so auf dem neusten Stand (schon garnicht was python angeht).
My god, it's full of CARs! | Leonidasvoice vs (former) Modvoice
Ja, diese war bei Hack und Co zugegeben dünn: Hole das Amulett von Yendor ("), töte alles, was sich bewegt, überlebe :)Rebecca hat geschrieben:Die meiste Arbeit macht vor allem, eine fortlaufende Geschichte zu erarbeiten
Die von Leonidas angesprochenen Orte sind doch aber nur 2D-Karten mit schachbrettartigen Feldern, die betretbar oder unbetretbar sind und Gegenstände und/oder Monster enthalten können. Man könnte bestimmte Gegenstände wie Tore haben, die einen dann (vielleicht nur, wenn man einen bestimmten Gegenstand besitzt) zu einem anderen Ort auf der Karte (oder einer anderen Karte) transportiert.
Wenn es darauf ankommt, wo man einen Gegner trifft, ist Zelda komplexer als Rogue, denn dort lief man einfach auf den Gegner, was zu einem Angriff mit der aktuell geführten Waffe führt, wobei so krude D&D-Regeln gelten, d.h. es werden n x-seitige Würfel geworfen, addiert, davon der Rüstungsschutz des Gegners subtrahiert und der Rest von dessen Lebenspunkten abgezogen. Doch wie kann man bei der auf dem Screenshot abgebildeten Klötzchengrafik zielen?
Ich verstehe das nicht so ganz: Ich kann also angreifen (sagen wir, mit einer bestimmten Taste) und richtige automatisch einen Punkt Schaden an. Sagen wir, der Gegner muss 3x getroffen werden. Schlägt er zurück? Richtet er auch automatisch Schaden an? Dann lebt er doch einfach 3 Runde, richtet dabei 3 Punkte Schaden an und man könnte mir doch einfach die 3 Punkte von meinen eigenen Lebenspunkten abziehen. Wo ist da ein Spiel? Und wieso hängt es von meiner Waffe ab, was der Gegner für einen Gegenstand besitzt?Leonidas hat geschrieben:Das System ist eigentlich ganz simpel, da Treffer gleich Treffer ist, es gibt keine Rettungswürfe etc. das einzige was durch Würfeln bestimmt wird ist ob Gegner Gegenstände liegen lassen, aber das war je nach Gegner und benutzer Waffe unterschiedlich warscheinlich.
Ich glaube, ich finde meinen Roguelike-Ansatz besser ;)
Stefan
-
- Python-Forum Veteran
- Beiträge: 16025
- Registriert: Freitag 20. Juni 2003, 16:30
- Kontaktdaten:
Natürlich schlägt er zurück. Er greift auch von selbst an, wenn er dich sieht.sma hat geschrieben:Ich verstehe das nicht so ganz: Ich kann also angreifen (sagen wir, mit einer bestimmten Taste) und richtige automatisch einen Punkt Schaden an. Sagen wir, der Gegner muss 3x getroffen werden. Schlägt er zurück?
Nein, er richtet nur schaden an, wenn er dich auch trifft und du nicht den Schild nutzt. Aber man kann ja durchaus auch den Waffen der Gegner ausweichen, etwa durch davonlaufen oder springen. Das ist möglich, weil Zelda eben nicht rundenbasiert ist sondern in Realtime läuft.sma hat geschrieben:Richtet er auch automatisch Schaden an? Dann lebt er doch einfach 3 Runde, richtet dabei 3 Punkte Schaden an und man könnte mir doch einfach die 3 Punkte von meinen eigenen Lebenspunkten abziehen.
Baldurs Gate zwar auch, aber dort hat man die AD&D-Regeln und bis auf Waffe auswählen, Kämpfen anklicken hat man dort recht wenig und nur indirekten Einfluss auf das Kampfgeschehen. In Zelda steuert man Link, die Spielfigur direkt.
Das war wohl ein Goodie in Links Awakening, dass wenn man die Schaufel gegen einen Bumerang eintauscht und mit dem Bumerang bestimmte Gegner in Verließen erledigt (die außer vom Bumerang gar nicht verwundet werden können), dann kommt eine Fee, die mehr Lebenspunkte zurückgibt als ein Herz.sma hat geschrieben:Und wieso hängt es von meiner Waffe ab, was der Gegner für einen Gegenstand besitzt?
Ok, gut stimmt - die Waffe beeinträchtigt nicht, was der Gegner liegenlässt, da habe ich mich geirrt.
My god, it's full of CARs! | Leonidasvoice vs (former) Modvoice
- Rebecca
- User
- Beiträge: 1662
- Registriert: Freitag 3. Februar 2006, 12:28
- Wohnort: DN, Heimat: HB
- Kontaktdaten:
Mmh, mit so einem 2D-Schachbrett muesste man das bei Zelda aber hinbekommen. (Zumindest, was ich vom GameBoy classic kenne). Bei den meisten Gegnern ist es egal, wo man sie trifft. Dann gibt es einige, die kann man nur von einer Seite treffen (oder von einer Seite nicht treffen, weil sie da z.B. ein Schild halten), das passt aber auch in das Schachbrettmuster). Dann gab es noch Wuermer, die mehrere Felder einnahmen, die man nur am Schwanz treffen konne, was wahrscheinlich auch wieder einem Feld entspricht. Dann gibt's Gegner, die kann man nicht immer treffen (weil sie dann z.B. in die Luft springen oder sich "einigeln"), und viele Gegner, bei denen man nur mit speziellen Gegenstaenden etwas bewirken kann.sma hat geschrieben:Wenn es darauf ankommt, wo man einen Gegner trifft, ist Zelda komplexer als Rogue, denn dort lief man einfach auf den Gegner, was zu einem Angriff mit der aktuell geführten Waffe führt, wobei so krude D&D-Regeln gelten, d.h. es werden n x-seitige Würfel geworfen, addiert, davon der Rüstungsschutz des Gegners subtrahiert und der Rest von dessen Lebenspunkten abgezogen. Doch wie kann man bei der auf dem Screenshot abgebildeten Klötzchengrafik zielen?
Waehrend du versuchtst, den Gegner zu treffen, versucht er wiederum, dich zu treffen oder zu beruehren, und wenn du nicht ausweichst oder dein Schild zueckst, nimmst du Schaden. Da ist Zelda eben mehr Action-Spiel als Rollenspiel, der Kampf wird nicht ausgewuerfelt, sondern richtig ausgespielt.Ich verstehe das nicht so ganz: Ich kann also angreifen (sagen wir, mit einer bestimmten Taste) und richtige automatisch einen Punkt Schaden an. Sagen wir, der Gegner muss 3x getroffen werden. Schlägt er zurück? Richtet er auch automatisch Schaden an? Dann lebt er doch einfach 3 Runde, richtet dabei 3 Punkte Schaden an und man könnte mir doch einfach die 3 Punkte von meinen eigenen
Offizielles Python-Tutorial (Deutsche Version)
Urheberrecht, Datenschutz, Informationsfreiheit: Piratenpartei
Urheberrecht, Datenschutz, Informationsfreiheit: Piratenpartei
ganz einfach wie bei SuperMarioWorld oder Metroid: Es gibt bestimmte Map-Tiles, die nach einem Trigger verschwinden (Bei Mario warens gelbe, blaue grüne Blöcke etc.) oder die man mit einer speziellen Waffe zerstören kann (harte Steinwände bei Metroid)sma hat geschrieben:Man könnte bestimmte Gegenstände wie Tore haben, die einen dann (vielleicht nur, wenn man einen bestimmten Gegenstand besitzt) zu einem anderen Ort auf der Karte (oder einer anderen Karte) transportiert.
Ich dachte eher an so was:
Und wenn ich jetzt meinen `Tile`s Koordinaten gebe und sie auf einer `TileMap` anordne, kann ich mich sogar richtig bewegen:
Vielleicht noch einen Wächter für das Portal?
Und dazu jetzt ein simples Kampfsystem: Jeder Angriff vom Helden ohne Waffe: 1 Punkt Schaden, mit Waffe entsprechend mehr. Jetzt hat ein Held ohne Schwert keine Chance gegen den Wächter, der ihn tötet, bevor der dritte Angriff erfolgt.
Mit Schwert jedoch sieht es anders aus:
Hey, das macht Spass :)
Stefan
Code: Alles auswählen
class Tile(object):
def __init__(self, creature=None, items=None):
self.creature, self.items = creature, items or []
if creature: creature.tile = self
for item in self.items: item.tile = self
def can_enter(self, creature):
return not self.creature and all(item.allow_enter(creature) for item in self.items)
def enter(self, creature):
if creature.tile:
creature.tile.leave(creature)
creature.tile = self
for item in self.items: item.notify_enter(creature)
def leave(self, creature):
for item in self.items: item.notify_leave(creature)
creature.tile = None
class Item(object):
pass
class PortalItem(Item):
def allow_enter(self, creature):
return creature.has_item_of_type(KeyItem)
def notify_enter(self, creature):
creature.move_to(self.dest_tile)
def notify_leave(self, creature):
pass
class KeyItem(Item):
pass
class Creature(object):
def __init__(self, items=None):
self.items = items or []
def add_item(self, item):
self.items.append(item)
def has_item_of_type(self, cls):
return any(isinstance(item, cls) for item in self.items)
def move_to(self, tile):
if self.tile != tile:
if tile.can_enter(self):
tile.enter(self)
return True
hero = Creature()
portal = PortalItem()
t1 = Tile(hero)
t2 = Tile(None, [portal])
t3 = Tile()
portal.dest_tile = t3
print hero.move_to(t2), hero.tile
hero.add_item(KeyItem())
print hero.move_to(t2), hero.tile
Code: Alles auswählen
class TileMap(object):
def __init__(self):
self.tiles = {}
def __setitem__(self, index, tile):
self.tiles[index] = tile
tile.coord = index
tile.tilemap = self
def __getitem__(self, index):
return self.tiles[index]
class Tile...
def east(self):
x, y = self.coord; return self.tilemap[x + 1, y]
class Creature...
def move_east(self):
return self.move_to(self.tile.east())
hero = Creature()
portal = PortalItem()
tilemap = TileMap()
tilemap[0, 1] = Tile(hero)
tilemap[1, 1] = Tile(None, [portal])
tilemap[3, 3] = portal.dest_tile = Tile()
print hero.tile.coord
hero.move_east()
print hero.tile.coord
hero.add_item(KeyItem())
hero.move_east()
print hero.tile.coord
Code: Alles auswählen
class Guardian(Creature):
pass
tilemap[1, 1] = Tile(Guardian(), [portal])
hero.move_to(tilemap[0, 1])
print hero.move_east()
Code: Alles auswählen
Item.damage = 0
class Creature(object):
tile = None
health = 3
damage = 1
def __init__(self, items=None):
self.items = items or []
def combat(self, opponent):
self.attack(opponent)
if opponent.health > 0:
opponent.attack(self)
if self.health < 1:
raise SystemExit
else:
opponent.remove()
def attack(self, opponent):
opponent.health -= self.damage
if self.items:
opponent.health -= max(item.damage for item in self.items)
def remove(self):
if self.tile: self.tile.leave(self)
class Guardian(Creature):
health = 4
damage = 2
class Hero(Creature):
health = 3
damage = 1
hero = Hero([])
guardian = Guardian()
hero.combat(guardian)
hero.combat(guardian) # hero died!
Code: Alles auswählen
class SwordItem(Item):
damage = 1
hero = Hero([SwordItem()])
guardian = Guardian()
hero.combat(guardian)
hero.combat(guardian) # guardian defeated
Stefan
Hab unter den Gamelets noch etwas nettes gefunden: Adventure of Einar
http://www.pygame.org/gamelets/
Da ist schon viel eingebaut. Werd mir definitiv das eine oder andere abschauen
Beim Kampfsystem werd ich mich in jedem Fall stark an Zelda orientieren (also so ähnlich wie bei AoEinar zu sehen).
http://www.pygame.org/gamelets/
Da ist schon viel eingebaut. Werd mir definitiv das eine oder andere abschauen

Beim Kampfsystem werd ich mich in jedem Fall stark an Zelda orientieren (also so ähnlich wie bei AoEinar zu sehen).
Hi Leute!
Ich würde gerne am Zelda Projekt mitarbeiten, aber :
-> Ich habe noch nicht so viel Erfahrung mit python.
-> Ich habe nicht SO viel Zeit.
d.h. ich weiß nicht wie viel Zeit ich dafür pro Tag / Woche aufwenden
könnte.
Ich denke am Tag so 1-2 Stunden max.
Bei Interesse oder eben keinem Interesse bitte
einfach eine PN an mich.
MfG Jonas
Ich würde gerne am Zelda Projekt mitarbeiten, aber :
-> Ich habe noch nicht so viel Erfahrung mit python.
-> Ich habe nicht SO viel Zeit.
d.h. ich weiß nicht wie viel Zeit ich dafür pro Tag / Woche aufwenden
könnte.
Ich denke am Tag so 1-2 Stunden max.
Bei Interesse oder eben keinem Interesse bitte
einfach eine PN an mich.
MfG Jonas