问题
I'm making a Maths Game application and recently began implementing MVC.
I have the following structure:
auiAs2
MigJPanel: extends
JPanel
ScreenInterface.java: contains global variables, fonts, and difficulty
enum
MathsGame.java: extends
JFrame
auiAs2.view
DiffView.java: extends
MigJPanel
implementsScreenInterface
GameView.java: extends
MigJPanel
implementsScreenInterface
EndGameView.java: extends
MigJPanel
implementsScreenInterface
auiAs2.controller
DiffControl.java
GameControl.java
EndGameControl.java
auiAs2.model
- Model.java: implements ScreenInterface
My MathsGame.java
contains a JPanel
set to CardLayout
which instances of DiffView
, GameView
, and EndGameView
are added to. When I run my program, the diffView
'card' is shown to the user.
If the user clicks "New Game", an ActionListener
in DiffControl.java
gets the selected difficulty.
public class DiffControl {
private DiffView diffView;
private Model model;
public DiffControl(DiffView diffView, Model model) {
this.diffView = diffView;
this.model = model;
this.diffView.addNewGameListener(new NewGameListener());
}
class NewGameListener implements ActionListener {
String selectedDiff;
@Override
public void actionPerformed(ActionEvent e) {
selectedDiff = diffView.getSelectedDiff();
//MathsGame.setLayCard(panContainer, "New Game"));
}
}
}
This is where I get stuck. Where should I switch between panels in my CardLayout
JPanel
layCard
? (MathsGame.java
is shown below with irrelevant code removed. The entire code for relevant classes is linked above if required)
public class MathsGame extends JFrame {
private JPanel panContainer = new JPanel();
private CardLayout layCard = new CardLayout();
public MathsGame() {
panContainer.setLayout(layCard);
setContentPane(panContainer);
setSize(new Dimension(WIDTH, HEIGHT));
setMinimumSize(new Dimension(MIN_WIDTH, MIN_HEIGHT));
setTitle(TITLE);
DiffView panDiffView = new DiffView();
panContainer.add(panDiffView, "Choose Difficulty");
GameView panGameView = new GameView();
panContainer.add(panGameView, "New Game");
EndGameView panEndGameView = new EndGameView();
panContainer.add(panEndGameView, "End Game");
Model model = new Model();
DiffControl diffControl = new DiffControl(panDiffView, model);
//GameControl gameControl = new GameControl(panGameView, model);
//EndGameControl EndGameControl = new EndGameControl(panEndGameView, model);
layCard.show(panContainer, "Choose Difficulty");
setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(MathsGame::new);
}
}
So my question is:
- Where would be the best place to put code related to switching between Views in my
CardLayout
container?
回答1:
The model will have a state field, perhaps an enum, that would reflect the view. You could make this a bound property using a SwingPropertyChangeSupport object. Then the view could listen to the state of this property and swap the Card based on its state. In fact the toString()
of each enum constant could be used to add card views to the CardLayout-using container.
Edit
You ask:
Could you elaborate on the usage of SwingPropertyChangeSupport?
You can find examples of this here, here, and especially here.
I've attempted using addPropertyChangeListener in the model. And how would the View control the card change when the CardLayout is in MathsGame.java?
The view would be notified of the state change of the model, and then when this happens, the view would call its code to swap cards.
I've had problems with doing that inside View for "calling a static method from a non-static context".
This is a completely different unrelated issue, a basic core Java issue, that I'm sure with a little work, you'll be able to solve. In brief -- don't try to call instance code in a static way. Always call it on a proper reference, not on the class.
来源:https://stackoverflow.com/questions/27584832/how-can-i-switch-between-jpanels-in-a-cardlayout-using-mvc