ein Spiel schreiben - was für eine Klassenstruktur/-hierarchie?


  • Mod

    SeppJ schrieb:

    Den Logger sehe ich ja noch ein, aber wieso die Anwendungskonfiguration? Kann es da nur eine Anwendung geben?

    wie sonst? eine anwendung ist doch eine anwendung? ich glaube mehrere anwendungen in einem process zu starten ist eher eine ausnahme.

    Wieso gehört die Konfiguration nicht zur Anwendung?

    es gehoert zu einem process/anwendung z.b. ob man Direct3D oder OpenGL als output benutzen will ist ein teil der konfig und fuer die ganze anwendung/den ganzen process gleich. genau wie aufloesung, input settings etc.
    ich wueste nicht wieso man sein program multi konfig faehig machen sollte. vielleicht ein beispiel?

    Wenn es nicht "die" Anwendung gibt, sondern diese aus Unterteilen besteht, warum ist dann die Konfiguration überhaupt ein übergreifendes Objekt und nicht auf die Unterteile verteilt? Das ist vermutlich genau das, worauf Bashar hinaus wollte.

    ich verstehe das ehrlichgesagt nicht.
    du startest ein spiel, einen editor oder einen game server, der hat seinen resolution, skin oder port. wozu mehrere instanzen dieser konfig und wie soll sich das auswirken? mehrere skins? resolutions? ports? ...? zur gleichen zeit?

    bei mir ist die konfig teil der konsole und lebt mit seinem environment das nur einmal vorhanden ist. es gibt mehrere wege das auszulesen oder zu veraendern was status quo ist, aber da ich keinen process als child starte etc. wie es bei linux waere, hab ich keine kapselung.

    ich wuerde eher log als nicht singleton verstehen (da man pro subsystem einen channel mit unterschiedlichen priorities etc. filtern koennte), also bei konfigurationsvariablen.


  • Mod

    rapso schrieb:

    SeppJ schrieb:

    Den Logger sehe ich ja noch ein, aber wieso die Anwendungskonfiguration? Kann es da nur eine Anwendung geben?

    wie sonst? eine anwendung ist doch eine anwendung? ich glaube mehrere anwendungen in einem process zu starten ist eher eine ausnahme.

    Wieso gehört die Konfiguration nicht zur Anwendung?

    es gehoert zu einem process/anwendung z.b. ob man Direct3D oder OpenGL als output benutzen will ist ein teil der konfig und fuer die ganze anwendung/den ganzen process gleich. genau wie aufloesung, input settings etc.
    ich wueste nicht wieso man sein program multi konfig faehig machen sollte. vielleicht ein beispiel?

    Wenn es nicht "die" Anwendung gibt, sondern diese aus Unterteilen besteht, warum ist dann die Konfiguration überhaupt ein übergreifendes Objekt und nicht auf die Unterteile verteilt? Das ist vermutlich genau das, worauf Bashar hinaus wollte.

    ich verstehe das ehrlichgesagt nicht.
    du startest ein spiel, einen editor oder einen game server, der hat seinen resolution, skin oder port. wozu mehrere instanzen dieser konfig und wie soll sich das auswirken? mehrere skins? resolutions? ports? ...? zur gleichen zeit?

    bei mir ist die konfig teil der konsole und lebt mit seinem environment das nur einmal vorhanden ist. es gibt mehrere wege das auszulesen oder zu veraendern was status quo ist, aber da ich keinen process als child starte etc. wie es bei linux waere, hab ich keine kapselung.

    ich wuerde eher log als nicht singleton verstehen (da man pro subsystem einen channel mit unterschiedlichen priorities etc. filtern koennte), also bei konfigurationsvariablen.

    Ich glaube wir verstehen beide was anderes unter Konfiguration. Ein DirectX- oder OpenGL-Output ist natürlich ein Singleton, da es aus technischen Gründen nur einen geben kann und der hat dann auch seine Konfiguration. Ich habe eher den Eindruck bekommen, dass Morle so Sachen als globale Variablen Singleton modelliert, die man eigentlich eine Eigenschaft eines Objektes sein sollten, bloß weil sie die Gemeinsamkeit haben, aus einer Konfigurationsdatei gelesen zu werden oder in einem Einstellungsdialog aufzutauchen.



  • Selbstverständlich kann es beliebig viele Direct3D oder OpenGL "Outputs" geben, selbst auf meinem normalen PC...


  • Mod

    dot schrieb:

    Selbstverständlich kann es beliebig viele Direct3D oder OpenGL "Outputs" geben, selbst auf meinem normalen PC...

    In einem Programm? Ich bin nicht so der Experte was Grafikprogrammierung angeht, aber ich hatte bei meinen bisherigen Experimenten den Eindruck bekommen, dass man nur einen Context pro Programm haben kann. Ich lasse mich gerne eines besseren belehren, meine Tutorials kamen mir nicht so dolle vor, aber ich hätte nicht gedacht, dass sie solche Grundlagen falsch machen. Es wurde nämlich betont, dass dies eine der wenigen Gelegenheiten ist, in einem Programm mal einen echten globalen Zustand zu haben.



  • SeppJ schrieb:

    dot schrieb:

    Selbstverständlich kann es beliebig viele Direct3D oder OpenGL "Outputs" geben, selbst auf meinem normalen PC...

    In einem Programm?

    Natürlich, denk nur z.B. an Multidisplayanwendungen 😉



  • @SeppJ
    Bei OGL ist das etwas doof gelöst.
    Bei D3D kannst du so viele Devices und SwapChains und was nicht noch alles haben wie du willst.
    Mach ein kleines Programm, pack zwei MediaPlayer Controls rein die je ein Video spielen => fertig ist das Programm das zwei D3D "Outputs" parallel verwendet.
    Mal mit noch einen drehenden Würfel mit D3D drunter und es sind 3.


  • Mod

    SeppJ schrieb:

    ....Ich habe eher den Eindruck bekommen, dass Morle so Sachen als globale Variablen Singleton modelliert, die man eigentlich eine Eigenschaft eines Objektes sein sollten, bloß weil sie die Gemeinsamkeit haben, aus einer Konfigurationsdatei gelesen zu werden oder in einem Einstellungsdialog aufzutauchen.

    sowas wie: renderer waehlen, motion blur, HDR, shadow quality, texture size etc. ?
    das laeuft bei den engines die ich kenne ueber globale konfigurationen.

    dot schrieb:

    Selbstverständlich kann es beliebig viele Direct3D oder OpenGL "Outputs" geben, selbst auf meinem normalen PC...

    hypothetisch kann man sicher auch eine ganze anwendung als eine klasse die ein singleton ist implementieren.
    wenn wir nicht den normal/durchschnittsfall nehmen, bauen wir luftschloesser und dann hat overengineering freien lauf, dann braucht man garkein singleton und alles ist pure data driven.



  • rapso schrieb:

    wenn wir nicht den normal/durchschnittsfall nehmen, bauen wir luftschloesser und dann hat overengineering freien lauf, dann braucht man garkein singleton und alles ist pure data driven.

    Und genau diese Denkweise ist der Grund, wieso ich immer noch keinen Screensaver gefunden hab, der auf beiden meiner Bildschirme läuft 😉



  • SeppJ schrieb:

    Ich habe eher den Eindruck bekommen, dass Morle so Sachen als globale Variablen Singleton modelliert, die man eigentlich eine Eigenschaft eines Objektes sein sollten, bloß weil sie die Gemeinsamkeit haben, aus einer Konfigurationsdatei gelesen zu werden oder in einem Einstellungsdialog aufzutauchen.

    Zum Verständnis: Die Konfiguration bezieht sich auf eine XML Datei, in der die einzelnen Anwendungsteile konfiguriert sind (z.B. IP Adressen eines TCP-Clients). Das Singleton kapselt den Zugriff auf diese Datei im Sinne von ".GetConfigValue(key)"
    Und ich sagte übrigens auch, dass der Verweis auf die Konfiguration vom Designaspekt wohl besser ein Klassenmember der Klasse sein sollte, die etwas aus der Konfig lesen will, aber aus Gründen der Übersichtlichkeit eben bei mir oft ein Singleton sind.

    Es ergeben sich nämlich daraus andere Probleme: Man müsste die Referenz auf die Konfig dann immer mitschleppen damit man sie dem Konstruktor der Klasse übergeben kann. Unschön, wenn man z.B. die Klasse von Punkten im Programm aus erstellt, wo man die Konfiguration eigentlich gar nicht braucht und sie nur extra deswegen selbst "bis dahin" mitschleppen müsste.

    Es ist IMHO nicht alles schwarz/weiss sondern durchaus grau.



  • rapso schrieb:

    SeppJ schrieb:

    ....Ich habe eher den Eindruck bekommen, dass Morle so Sachen als globale Variablen Singleton modelliert, die man eigentlich eine Eigenschaft eines Objektes sein sollten, bloß weil sie die Gemeinsamkeit haben, aus einer Konfigurationsdatei gelesen zu werden oder in einem Einstellungsdialog aufzutauchen.

    sowas wie: renderer waehlen, motion blur, HDR, shadow quality, texture size etc. ?
    das laeuft bei den engines die ich kenne ueber globale konfigurationen.

    dot schrieb:

    Selbstverständlich kann es beliebig viele Direct3D oder OpenGL "Outputs" geben, selbst auf meinem normalen PC...

    hypothetisch kann man sicher auch eine ganze anwendung als eine klasse die ein singleton ist implementieren.
    wenn wir nicht den normal/durchschnittsfall nehmen, bauen wir luftschloesser und dann hat overengineering freien lauf, dann braucht man garkein singleton und alles ist pure data driven.

    Ich bin der Meinung es macht auch einen Unterschied um was für eine Art Engine es sich handelt. Wenn es eine "general purpose" Grafik-Engine sein soll, dann ist es Kacke wenn diese Dinge globale Config-Settings sind.
    Weil man dadurch in vielen Applikationen Schwierigkeiten bekommt, die "sowas mit Grafik" an mehreren Stellen brauchen, aber nicht unbedingt immer mit den gleichen Einstellungen. Da ist es angesagt wenn man sich von der Engine ein Ding holen Kann (Context oder wie auch immer man es nennen mag), und alle Einstellungen Ding-spezifisch und nicht global sind.

    Wenn man dagegen eine Game-Engine macht, kann man eher davon ausgehen dass es im gesamten Prozess nur einen "Client" der Engine gibt, nämlich das eine Spiel das in dem Prozess läuft.
    In dem Fall kann man vermutlich viele Dinge global machen, und die damit gesparte Zeit sinnvoll in was anderes investieren.

    ----

    Am wichtigsten ist mir allerdings der Punkt: Singleton hat im Vergleich zu globalen Variablen zwar ein paar Vorteile. Der mMn. grösste Nachteil bleibt aber, nämlich dass es halt nur eine Kopie gibt. Daher ist "Singleton statt global" mMn. nur grösstenteils Augenauswischerei. Die Settings sind global? Na dann sind die halt global, kann man doch einfach so sagen. Wenns für ein Projekt Sinn macht, ist es doch auch kein Problem. Muss man nicht "Singleton" dazu sagen nur damit's besser klingt.
    Bzw. sich nicht einbilden man hätte das grundlegende Problem der Sache gelöst, indem man ein Singleton drüberstülpt. Wenn es das Problem nicht gibt, muss man es nicht lösen. Und wenn es das Problem gibt, dann löst man es nicht mit einem Singleton.


  • Mod

    Offtopic: Wenn man sagt, der größte Nachteil eines Singletons wäre, dass es nur eine Instanz gibt, dann ist das ist so als wenn man als größten Nachteil eines Automobils benennen würde, dass es sich aus eigener Kraft fortbewegen kann.


  • Mod

    hustbaer schrieb:

    ...
    Ich bin der Meinung es macht auch einen Unterschied um was für eine Art Engine es sich handelt. Wenn es eine "general purpose" Grafik-Engine sein soll, dann ist es Kacke wenn diese Dinge globale Config-Settings sind.
    Weil man dadurch in vielen Applikationen Schwierigkeiten bekommt, die "sowas mit Grafik" an mehreren Stellen brauchen, aber nicht unbedingt immer mit den gleichen Einstellungen. Da ist es angesagt wenn man sich von der Engine ein Ding holen Kann (Context oder wie auch immer man es nennen mag), und alle Einstellungen Ding-spezifisch und nicht global sind.

    klar, aber genauso gut kannst du sagen, dass eine engine nur auf windows oder mit d3d laeuft und du durch diese globale entscheidung sie jetzt nicht auf linux oder ohne graphik api nutzen kannst.
    es ist nunmal eine engine mit zielen und kein konstrukt das unter einem 'inner platform effekt' leiden sollte. das bedeutet natuerlich, dass man zum wohle einiger features entscheidungen trifft, die andere features unmoeglich machen.
    "it's not a bug, it's a feature"

    Wenn man dagegen eine Game-Engine macht, kann man eher davon ausgehen dass es im gesamten Prozess nur einen "Client" der Engine gibt, nämlich das eine Spiel das in dem Prozess läuft.
    In dem Fall kann man vermutlich viele Dinge global machen, und die damit gesparte Zeit sinnvoll in was anderes investieren.

    ----

    Am wichtigsten ist mir allerdings der Punkt: Singleton hat im Vergleich zu globalen Variablen zwar ein paar Vorteile. Der mMn. grösste Nachteil bleibt aber, nämlich dass es halt nur eine Kopie gibt. Daher ist "Singleton statt global" mMn. nur grösstenteils Augenauswischerei. Die Settings sind global? Na dann sind die halt global, kann man doch einfach so sagen. Wenns für ein Projekt Sinn macht, ist es doch auch kein Problem. Muss man nicht "Singleton" dazu sagen nur damit's besser klingt.
    Bzw. sich nicht einbilden man hätte das grundlegende Problem der Sache gelöst, indem man ein Singleton drüberstülpt. Wenn es das Problem nicht gibt, muss man es nicht lösen. Und wenn es das Problem gibt, dann löst man es nicht mit einem Singleton.

    wie SeppJ schon sagt, ein singleton hat gewisse eigenschaften, wenn man ein problem hat, dass diese eigenschaften benoetigt um es zu bewaeltigen, ist es kein defekt, sondern eine loesung.
    Es macht irgendwie keinen Sinn komplexerere loesungen einzubauen, wenn ein Singleton voll ausreicht.



  • Das Problem bei Singletons ist die starke Bindung. Man erstellt eine Klasse, davon kann es nur eine Instanz geben, und dann kommen tausend andere Klassen und benutzen diese eine Instanz. Passt. Aber dann ist die Anwendung über Jahre gewachsen und man überlegt sich, jetzt wärs aber schön, aus dieser Klasse eine Schnittstelle zu extrahieren und verschiedene Implementierungen davon anzubieten. Oder vielleicht doch mal eine andere Instanz zu erstellen, was vorher nicht gewünscht war. Und schon hat man das Problem das man alles umbauen und testen muss. Testen ist das nächste Problem, Singletons sind schlecht für Unit Tests. Wenn sich jedes Objekt, das man testen will einfach die Singleton Instanz schnappt, kann man schlecht ein Mockup Objekt mit genau definiertem Verhalten reingeben. Diese Probleme habe ich schon sehr oft gesehen.
    Nichts destotrotz haben Singletons durchaus ihre Daseinsberechtigung, man muss nur verstehen, worauf man sich einlässt.


Anmelden zum Antworten