0

I have a class Game which cannot be made static for serialization purposes. I would like to instantiate Game from a method and have the new instance accessible elsewhere in the code.

If I try this:

    public void btnNewGame_Click(object sender, EventArgs e)
    {
        Game game = new Game();
    }

The new instance is unusable outside of this method. Is there any way to instantiate Game within the method and have the instance accessible elsewhere? Or are there any workarounds? The thing is that I don't want Game to be instantiated before this button is clicked.

Any advice would be appreciated.

Jason D
  • 2,634
  • 6
  • 33
  • 67
  • 1
    Why not have a static Game _game outside of the method and instantiate Game inside the method and make _game = game. This way you would have a static variable which holds an instance of Game. – AliK May 14 '13 at 23:52
  • Consider moving the "serializable" properties of `Game` to a separate `GameState` object. Serialize/deserialize the `GameState` and have a method `Game.LoadFromState(GameState)` which would read/assign whatever data is applicable. This way the centralized `Game` class can be static (if that's what you want) and can store non-serializable content; perhaps more importantly, the saving/loading mechanism can be abstracted to store/read from different locations (database, file system, etc.) or better maintain backward compatibility to slightly older versions of your game. – Chris Sinclair May 15 '13 at 00:31
  • @ChrisSinclair Thanks for the tip. I'll go ahead and do that. – Jason D May 15 '13 at 00:33

2 Answers2

1

The singleton pattern with lazy instantiation is your friend here.

Check out this answer of mine for an example.

Community
  • 1
  • 1
Jan Dörrenhaus
  • 6,581
  • 2
  • 34
  • 45
  • Can Singletons be serialized without any problems? – Jason D May 14 '13 at 23:47
  • Yes. A singleton is just a regular class with regular fields, only with magic that makes sure that there is only one instance of it, and that this instance is accessible anywhere in the code. :) – Jan Dörrenhaus May 14 '13 at 23:50
  • I'll play around with this. I suppose my only concern is deserialization if the instance is already active (IE, if the the player loads an old save from the pause screen). We'll see, I suppose. – Jason D May 14 '13 at 23:53
  • In that case, you would have to write a specialized setter that not just anyone can call, I guess. By the way, the pattern I gave is NOT threadsafe. – Jan Dörrenhaus May 14 '13 at 23:55
1

You could create a static property that returns the one and only Game object that exists. For example:

public class Game
{
    private static Game instance;
    public static Game Instance
    {
        get
        {
            if (instance == null)
                instance = new Game();
            return instance;
        }
    }
}

And use it like this:

Game theOneAndOnlyGame = Game.Instance;

Or, if you can't change the Game class:

public static class MyGameEngine
{
    private static Game game;
    public static Game Game
    {
        get
        {
            if (game == null)
                game = new Game();
            return game;
        }
    }
}

And use it like this:

Game theOneAndOnlyGame = MyGameEngine.Game;
Daniel A.A. Pelsmaeker
  • 47,471
  • 20
  • 111
  • 157