2017-08-05 4 views
0

J'ai donc essayé d'utiliser un pointeur partagé vers une structure pour contenir toutes les données de mon programme qui peuvent être partagées entre les états de ma machine d'état.Objets globaux interactifs avec des pointeurs partagés

struct GameData 
{ 
    StateMachine machine; 
    sf::RenderWindow window; 
    AssetManager assets; 
    InputManger input; 
    const int x = 1; 
}; 

typedef std::shared_ptr<GameData> GameDataRef; 

Ceci est un fichier qui fournit simplement une interface entre les ressources de données partagées. appelé GameData.cpp

GameDataRef _data = std::make_shared<GameData>(); 

Dans mon fichier game.cpp, si je comprends bien, make_shared crée l'objet et attribue le nom shared_ptr _data lui.

StateRef _splash = std::make_unique<State_Splash>(_data); 

Ceci est la ligne qui crée un état de base pour démarrer la partie. Peu importe n'importe quelle partie autre que cela prend le pointeur partagé comme argument.

GameDataRef _data; 

Je fais un autre pointeur partagé dans le State_Splash.cpp appelé _data

State_Splash::State_Splash(GameDataRef GDR) : _data(GDR) 

Dans le constructeur, je (oublié le terme pour ce qui vient après: ici)

std::cout << _data->x; 

ceci affiche 0 à la console, même si x est défini dans la structure comme 1. J'ai exécuté ce test car une texture que j'ai chargée dans _data-> assets dans Game.cpp était hors de portée (écran blanc vide) quand j'ai essayé référencer e à un sprite dans le State_Splash.cpp.

Ma question est, est-ce que je fais quelque chose de mal avec les pointeurs partagés? Ou existe-t-il une meilleure façon de créer un dépôt de ressources partagées pour l'ensemble du programme?

+0

Essayez 'cout << _data.get()'. Qu'est-ce que ça montre? –

+0

il renvoie 00221E40 –

+1

Les lignes que vous avez fournies semblent bonnes. Il doit y avoir quelque chose que vous ne remarquez pas ou que vous pensez que ce n'est pas important. Essayez de réduire l'exemple au minimum et voyez s'il se reproduit.Idéalement, tout le code devrait être dans un fichier cpp. Alors vous pouvez facilement le coller ici. – Sergei

Répondre

0

Ou est-il une meilleure façon de faire de dépôt de ressources partagées pour l'ensemble du programme?

Les singletons ont une mauvaise réputation. Une grande partie vient de pré-C++ 11 époque où il était difficile de les avoir raison. C++ 11 les rend sûrs. C'est aussi un objet global - donc il est sujet à toutes les considérations concernant les globals. Ils devraient être évités sauf quand ils améliorent votre programme.

Les singletons fonctionnent plutôt bien dans les applications de jeu. Je voudrais juste créer quelque chose comme GameContext singleton et oublier les pointeurs partagés. Vos données de jeu sont globales par conception.

Toutefois, si votre code est conçu pour avoir plusieurs objets de ce type, singleton ne fonctionnera pas pour vous.

0

Un singleton ou global de toute nature trash composition et testabilité. Il n'y a presque jamais de bonne raison pour de telles choses.

Mieux vaut utiliser l'injection de dépendance. Ensuite, vous pouvez tester les composants de votre jeu avec seulement un modèle de la dépendance.

#include <vector> 

struct StateMachine{}; 
namespace sf { struct RenderWindow {}; } 
struct AssetManager {}; 
struct InputManager {}; 

struct GameData 
{ 
    StateMachine machine; 
    sf::RenderWindow window; 
    AssetManager assets; 
    InputManager input; 
    const int x = 1; 
}; 

struct action {}; 
std::vector<action> checkInputs(InputManager&); 

void runGame(GameData& gameData) 
{ 
    while (1) { 
     auto inputActions = checkInputs(gameData.input); 
    } 

} 

int main() 
{ 
    GameData gameData; 

    runGame(gameData); 
}