javaswingmodel-view-controllergui-builder

Can you build a Swing GUI for an MVC-style game if the Controller doesn't have a reference to the Model?


I couldn't find any similar answers on here, but apologies if this it too specific to my own problem.

I am building a simple game using in Java that has both a command line interface and a GUI (activated using a command line flag). The way that the game is written is that the game logic (Model) has a reference to the input (Controller) and the output (View), but neither the input or output have a reference to the model (this was a requirement). The flow of the game is therefore controlled by a loop in the application model similar to:

while (!gameFinished) {
    InputType in = input.getUserInput(); //1
    performAction(in);
}

Now that I am trying to build a Swing GUI for this (not something I have experience in), I am struggling to see how it could work with event listening. It would ideally work in the way that when a button is pressed (new game, save game, exit game etc.), an InputType would be sent to the Model (essentially doing the same that the commented line does) to be handled accordingly. But if it doesn't hold a reference to the Model, it can't 'send' the InputType. I suppose I am looking to build a GUI that works with the Model 'asking' for input, rather than 'listening' for it.

Is this possible? And if so, can anyone provide me with any useful resources for solving this? If not, an explanation or potential alternative solution suggestion would be appreciated.


Solution

  • I'm not gonna go into whether your flow is right or wrong.

    Pseudo code:

        class Controller{
        Queue<UIEvent> events;
    
        void setupUI(){
            button.addEventListener( new EventListener(){
                 Model.this.events.add(new TappedButtonEvent());
            });
        }
    
        UIEvent dequeueEvent(){
            if(events.size() > 0){
                return events.pop()
            }
            return null;
        }
    
        }
    
        class Model{
    
        public void loop(){
            while (!gameFinished) {
                 UIEvent in = input.dequeueEvent();
                 if(in != null){
                      performAction(in);
                 }
            }
        }
        }