Comment concevoir un moteur de jeu dans un langage orienté objet? [fermé]

26

Chaque fois que j'essaie d'écrire un jeu dans n'importe quel langage orienté objet, le premier problème auquel je suis toujours confronté (après avoir réfléchi au type de jeu à écrire) est de savoir comment concevoir le moteur. Même si j'utilise des bibliothèques ou des frameworks existants comme SDL, je dois toujours prendre certaines décisions pour chaque jeu, comme l'utilisation d'une machine à états pour gérer les menus, le type de classe à utiliser pour le chargement des ressources, etc.

Qu'est-ce qu'une bonne conception et comment serait-elle mise en œuvre? Quels sont les compromis à faire et leurs avantages / inconvénients?

moteur extropique
la source
12
Qu'est-ce qui ne va pas avec l'impulsion et la refactorisation à partir de là plutôt que de souffrir de paralysie de l'analyse?
The Communist Duck
7
@TheCommunistDuck Parce que l'impulsion est l'approche que j'ai adoptée dans tous mes projets précédents - et chacun frappe un mur après quelques mois lorsque je constate que toute nouvelle fonctionnalité nécessite un effort et une complexité monumentaux à ajouter. En ce moment, je passe plus de temps à réécrire mes moteurs que je n'écris le jeu lui-même, alors j'espère qu'avec un peu de réflexion et de planification, je gagnerai du temps à long terme.
moteur extropique
3
@chuzzum, bon point. Une chose que je recommanderais alors est de vérifier l'architecture du moteur C4, c'est-à-dire; terathon.com/c4engine/images/architecture.png Cela peut être beaucoup plus élevé que ce dont vous avez besoin, mais cela pourrait vous donner quelques idées ;-)
The Communist Duck
1
i.imgur.com/81zIY.png
The Communist Duck
3
Cette question est également un peu vague. Prenez peut-être un de vos exemples et faites-en une ou deux questions plus approfondies.
Tetrad

Réponses:

24

Je doute que quelqu'un puisse dire "Vous devez faire ceci et cela et ceci et cela avec ce modèle X".

Cependant, quelques ressources utiles:
Enginuity - une série d'articles sur la construction de moteurs sur Gamedev.net.
Game Coding Complete - Je possède ce livre, et il couvre bien tous (enfin, presque) tous les aspects de la programmation de jeux. Il a également un moteur construit tout au long du livre.
Game Engine Architecture - Ceci est un autre grand livre pour la conception de moteurs.
Disposition du moteur C4 - Tiré de mon commentaire, mais cela montre une manière de haut niveau d'assembler chaque partie du moteur ensemble.

Celles-ci peuvent être un peu trop pour ce dont vous avez besoin, mais vous ne pouvez pas en savoir trop sur quelque chose, et je suis sûr que vous obtiendrez un bon plan de leur part.

EDIT: J'ai oublié que les articles Gamedev ont été archivés depuis le nouveau site, corrigé :)

Le canard communiste
la source
Le lien Enginuity a été rompu et la recherche sur les articles a semblé montrer qu'ils ne sont plus sur le Web. (?) Les livres semblent être de bonnes ressources, et je suis toujours à l'
affût
De plus, en ce qui concerne votre premier commentaire, je ne m'attends pas à ce que quelqu'un propose un plan directeur qui convienne à chaque jeu. Je viens de remarquer, au cours du développement de quelques jeux, que les modèles communs ont tendance à apparaître souvent, alors je me suis demandé ce que les autres utilisaient dans leurs jeux.
moteur extropique
1
Correction du lien.
The Communist Duck
+1 pour enginuité. @chuzzum Examinez simplement quelques moteurs de jeu, laissez-les vous inspirer et dérivez vous-même l'architecture optimale. De plus: il est souvent préférable de rendre votre composant de moteur de jeu basé sur hiérarchique, voir cowboyprogramming.com/2007/01/05/evolve-your-heirachy
Dave O.
1
Je ne dirais pas que c'est le moteur qui doit être agrégé, plus la partie framework d'entité.
The Communist Duck
7

À titre d'exemple, voici comment mon projet roguelike actuel est structuré (en Java). Il utilise un moteur graphique 2D, donc une grande partie du code de rendu a déjà été pris en charge pour moi. La critique est la bienvenue.

class Game
Cette classe configure la machine d'état qui gère l'état actuel du jeu. (dans un menu vs commencer une nouvelle partie vs jouer une partie enregistrée)

interface State
Chaque classe State contient deux boucles: une boucle pour la mise à jour de la logique et une boucle pour le rendu. Ils contiennent également du code pour appeler la Gameclasse et demander un changement dans un état différent.

class ResourceManager
Singleton qui est initialisé par la Gameclasse qui charge toutes les ressources nécessaires et permet d'y accéder. Je n'aime pas cette conception car elle rend difficile le chargement / déchargement des ressources à différents niveaux, par exemple. Je concevoirais probablement ceci différemment si je recommençais.

class Map
Une carte contient un tableau de tuiles et une liste de toutes les créatures et objets sur la carte. C'est une classe assez basique.

class Creature
Les créatures contiennent des informations sur elles-mêmes, y compris des calculs de mouvement (leur demandant de savoir dans quelle carte elles se trouvent et de pouvoir l'interroger pour connaître les obstacles). Décider de faire cela, ou de faire en sorte qu'une classe de manager s'en occupe pour toutes les créatures est une chose avec laquelle je me bats.

interface AITask
Les créatures peuvent avoir une liste de tâches AIT, qui sont exécutées chaque fois que la boucle logique de la créature est exécutée. L'AITask a sa propre boucle logique qui émet des commandes à la créature, et une condition de terminaison qui détermine si la tâche s'est terminée avec succès ou non.

interface UIElement
J'ai implémenté ma propre interface utilisateur pour ce moteur. Chaque UIElement a une boucle de rendu et une boucle logique. Ils ont également une boucle pour le traitement des entrées clavier / souris. Tous les éléments peuvent avoir un certain nombre d'éléments enfants, qui sont rendus après leurs parents, et prennent en charge l'entrée clavier / souris. Cela vous permet d'avoir des menus avec des sous-menus, par exemple.

moteur extropique
la source
Qu'est-ce qui ne va pas exactement avec ça? Cela me semble parfaitement bien.
The Communist Duck
@TheCommunistDuck Cela ne ressort pas vraiment dans les exemples que j'ai choisis, mais j'ai beaucoup de problèmes avec ce code. La classe ResourceManager est l'une d'entre elles, mais j'ai aussi des problèmes avec les états - je me retrouve avec une énorme prolifération d'entre eux et je copie beaucoup de code. Surtout dans un RPG, où le joueur a beaucoup de choix à tout moment, vous pouvez vous retrouver avec des graphiques d'état vraiment complexes. Exemple: lancer un sort. Va de NormalState -> SelectSpellState -> SelectTargetState -> InvalidTargetState (en cas d'échec) -> DoSpellAnimationState -> NormalState. Et ce n'est qu'une action.
extropic-engine
1
Non non. Non . NAN. Je t'en prie, non. Oh, attendez, vous avez dit que vous ne l'aimez pas.
Bartek Banachewicz
6

Le premier point important à souligner est qu'il n'y a pas de «bonne» réponse à cette question.

La chose la plus proche d'une bonne réponse serait quelque chose comme: cela dépend beaucoup du type de jeu, de la plate-forme cible, des contraintes (temps) etc.

Cela dit, il existe de très bons articles qui vous montreront comment d'autres personnes ont essayé de répondre à ce problème (comme j'ai essayé de trouver des informations à ce sujet dans le passé).
Comme The Canard communiste l'a mentionné, l' article sur l' ingénierie des développeurs de jeux m'a aidé à comprendre certaines parties de l'architecture des jeux.

Ma conception actuelle est un hybride de Quake3 / Doom3 et un peu de la bibliothèque de classes .NET :)

J'ai deux bibliothèques (statique ou dynamique dépend de la façon dont vous voulez construire / livrer) le Frameworket le Library.

La bibliothèque contient toutes les classes d'assistance qui sont là pour aider à la production de logiciels de jeu, mais ne se limitent pas à ce type de produit. c'est-à-dire qu'il a une implémentation d'une liste chaînée qui est optimisée pour le code du jeu mais pourrait être utilisée par tout ce qui a besoin du service d'une liste chaînée.

Le Framework est le courage du «moteur» si vous voulez l'appeler ainsi. Beaucoup de ceci suit les philosophies de conception de Quake3 (juste d'une manière plus orientée objet). Il contient la CLI , la gestion du temps, le code spécifique au système d'exploitation, et éventuellement les couches réseau, etc.

Ces deux sont ensuite liés à l'application réelle en cours de production. Le Gamesi vous le souhaitez, qui contient le code spécifique au jeu. De la même manière, Quake3 charge les DLL en fonction du «mod» en cours de lecture.

Pour vous donner une idée de la structure, voici une ventilation rapide des dossiers et du contenu de chaque bibliothèque:


  • Cadre
    • IO (classes de gestion de fichiers spécialisées, classes d'impression de texte (par exemple vers la CLI), et journalisation, etc.)
    • Réseau
      • Client (classes qui représentent ce que le Framework considère comme une «personne jouant / connectée au jeu»)
      • Serveur (classes pour gérer la connexion au framework et gérer le (s) joueur (s))
    • Plateforme (clavier / souris / contrôleurs gérant des classes, routines spécifiques au système d'exploitation comme getTime ())
    • Système (classes de très bas niveau comme une classe d'erreur pour faciliter l'impression des messages d'erreur, les classes de synchronisation et la CLI elle-même.)
    • Rendu (auto-explicatif)
    • etc.

  • Bibliothèque
    • Collections (classes qui représentent des collections de données, listes / tables de hachage liées, etc.)
    • Math (classes d'aide de base en mathématiques comme les vecteurs et les matrices)
    • etc.

HTH! Devrait vous donner quelques conseils ...

Adam Naylor
la source
Lien alternatif vers la série
Enginuity
-3

Choses à considérer

  • Les langages orientés objet ont des problèmes car ils n'ont généralement pas de fonctions de première classe ou toutes les données ne sont pas des objets (comme des nombres entiers ou flottants en Java). Les modèles de conception répondent à ces problèmes avec plusieurs modèles. Il est généralement plus rapide de coder et plus facile à maintenir d'utiliser un langage capable de les faire (objets de première classe); par exemple Python (qui permet également la conception orientée objet), vous aurez une vitesse plus lente.
  • Calcul d'événement, à l'IA au moins
  • Logique Hoare, utilisez les conditions préalables et postconditions pour au moins tester votre code
  • Agents, regardez les entités Quake
  • Bases de données relationnelles, un moyen puissant de stocker des données

Bon design

  • faire un diagramme ER
  • le rendre correct
  • créez votre base de données, vos objets ou vos structures de données

Les données sont essentielles à la programmation. Si vous concevez vos données correctement, un algorithme en émerge généralement (si vous ne comptez pas certains algorithmes numériques, comme le déterminant informatique).

user712092
la source
-1 car cette réponse est très vague et déroutante. Les bases de données relationnelles n'ont absolument rien à voir avec un moteur OO. Je peux comprendre que l'anglais n'est pas votre première langue, mais pourriez-vous expliquer ce que vous voulez dire dans votre premier paragraphe? Cela semble contradictoire (les langages OO ont des problèmes mais il est plus facile de programmer dans des langages avec des modèles de conception ... même si les modèles de conception sont presque toujours des structures OO).
The Communist Duck
@duck Contradictory? OO a des problèmes qui n'existent pas dans d'autres langues, DP les résout voir c2.com/cgi/wiki?DesignPatternsInDynamicProgramming .
user712092
@Duck 1) Vous pouvez utiliser SQL en C ++ 2) Vous pouvez déduire des attributs d'objets à partir d'ER (bien que ce ne soit pas une pratique recommandée) 3) Vous pouvez structurer des données à partir de relations (ceci est une liste car j'ai besoin de réorganiser les elemenents à willm c'est un hachage car j'ai besoin d'une recherche rapide)
user712092
@Duck, je m'excuse, j'ai fait une erreur en réorganisant. Je ne voulais pas prétendre que "les DP sont plus faciles à XY" mais "les langues qui peuvent faire de première classe sont ...". :)
user712092
Oui, les langages fonctionnels peuvent présenter des avantages. Cependant, même de manière impartiale, je pense qu'une approche OO est logique d'un point de vue gamedev. De plus, il n'y a aucune raison d' avoir besoin d' une base de données relationnelle. Bien sûr, ils peuvent être utiles. Cependant, il ne devient un composant nécessaire nulle part.
The Communist Duck