I started not so long ago learning Java through tutorials and videos, and after understanding a few things (how buttons, layouts, audio, and a few other things work) one of my goal now is to create a little interactive game.
I wrote a pretty big part of the game in the Main Class and it was working good, but it got messy after a while.
So I decided to try another time from the beginning using different classes for every part of the game to make the code look more clear and understandable.
But I have a problem from the very beginning and after a few hours of searching tutorials, answers on forums and not finding a precise answer, I think it's the best if you will see exactly my problem (which is very simple!)
-So I just constructed the JFrame in a class (I use the main Class only to launch the frame, and it works fine) :
import javax.swing.*;
import java.awt.*;
public class principalFrame {
public principalFrame(){
JFrame mainFrame = new JFrame();
mainFrame.setVisible(true);
mainFrame.setSize(1200,750);
mainFrame.getContentPane().setBackground(Color.BLACK);
mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
mainFrame.setResizable(false);
}
}
and I created a JPanel in another class :
import javax.swing.*;
import java.awt.*;
public class mainMenu{
public mainMenu(){
JPanel menuPanel = new JPanel();
menuPanel.setSize(300,300);
menuPanel.setBackground(Color.BLUE);
}
}
And my goal is to add the JPanel inside the JFrame. And... I don't understand how to do it.
I tried to add the menuPanel class as an object in the mainFrame class so I could add the JPanel but it did'nt work. Then tried a bunch of other solutions from what I read on older questions but nothing really helped me.
PS : I know that I didn't add any layout manager or any other things in the code here because I want to keep the code very simple for the question.
CodePudding user response:
So if you want to make a separate class for mainMenu, you should make it extend JPanel. This way, your mainFrame class can instantiate it.
Here is what I would tell you about the lessons I learned in building things in swing:
You (almost) never need a separate class to create a JFrame. If you create a class that extends JPanel, it is easy enough to create a JFrame in a static method (like main) to put your JPanel in. That being said, if you also want to use the JLayeredPane or want to add menus on a JMenuBar, there might be a case of subclassing JFrame. The advantage of not subclassing JFrame is that it makes it easier to stick your JPanel into a JFrame, a JDialog (via JOptionPane) or a JWindow.
Unless you have a Component that you think could be useful in other applications, you should build your entire GUI in one class, and also use that class as the
Controller
. What is an example of a Component that could be used in other applications? Back in the day, I made a "ColorButton" swing class, for color picking. This component has a self-contained model, has its own controller and an API to get the picked color. (https://sourceforge.net/p/tus/code/HEAD/tree/tjacobs/ui/ex/) which makes it reuseable. But normally, the elements of the GUI you are building aren't really reuseable outside of what you are doing in that class.
With that said, to the code you posted above:
Your mainMenu JPanel isn't accessible outside the class, so that is probably a problem. As I said in the paragraph above, if you're not sure that the Component you are creating could be used in another place, it is better to put the entire view
and model
building in the same class as the controller
CodePudding user response:
You were close. You have to be able to get the JPanel
from the MainMenu
class.
The JFrame
methods must be called in a specific order. This is the order I use for my Swing applications.
Class names start with an upper case character.
Here's one way you could code your MainMenu
class.
public class PrincipalFrame {
public PrincipalFrame() {
JFrame mainFrame = new JFrame();
mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
mainFrame.add(new MainMenu().getMenuPanel(), BorderLayout.CENTER);
mainFrame.setSize(1200, 750);
mainFrame.setResizable(false);
mainFrame.setVisible(true);
}
}
public class MainMenu {
private final JPanel menuPanel;
public MainMenu() {
this.menuPanel = new JPanel();
this.menuPanel.setPreferredSize(300, 300);
this.menuPanel.setBackground(Color.BLUE);
}
public JPanel getMenuPanel() {
return menuPanel;
}
}