zhthemagician
zhthemagician

Reputation: 27

How to know which reference is static in Java

I am currently working on GUI of simple food ordering system. I created a button that whenever user clicks it it will go to another frame, however I am facing problem when I want to close the first frame (setVisible(false)).

This is my first frame

public class MainFrame extends JFrame {
    
    private Manager manager = new Manager();
    private JPanel titlepane;
    private JLabel title;
    
    MainFrame(String name){
        setTitle(name);
    }
    
    public void content() {
        Font titlefont = new Font("Times New Roman", Font.PLAIN, 22);
        setLayout(new BorderLayout());
        
        titlepane = new JPanel();
        title = new JLabel("Welcome to POS!");
        title.setFont(titlefont);
        titlepane.add(title);
        manager.LoginGUI();
        
        add(titlepane,BorderLayout.NORTH);
        add(manager,BorderLayout.CENTER);
    }
    
    public void runGUI() {
        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                content();
                setSize(700,700);
                setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                setVisible(true);
                setLocationRelativeTo(null);
            }
        });
    }

This is another class where the button is

public class Manager extends JPanel implements ActionListener {

    private ArrayList<AccountInfo> manager = new ArrayList<AccountInfo>();
    private GridBagConstraints gbc = new GridBagConstraints();

    private JLabel id;
    private JLabel pw;

    private JTextField idfill;
    private JTextField pwfill;

    private JButton login;

    private int isManager = 0;

    private String idinput, pwinput;
    private int temp = -1;

    Manager() {
        this.manager.add(new AccountInfo("admin", "1234"));
    }

    public void addManager(AccountInfo newManager) {
        this.manager.add(newManager);
    }

    public void LoginGUI() {
        Font standard = new Font("Times New Roman", Font.PLAIN, 18);
        setLayout(new GridBagLayout());

        id = new JLabel("ID");
        id.setFont(standard);
        // Alignment
        gbc.gridx = 0;
        gbc.gridy = 0;
        gbc.ipadx = 10;
        gbc.ipady = 10;
        gbc.fill = GridBagConstraints.HORIZONTAL;
        gbc.fill = GridBagConstraints.VERTICAL;
        gbc.anchor = GridBagConstraints.FIRST_LINE_START;
        add(id, gbc);

        idfill = new JTextField(10);
        idfill.setFont(standard);
        // Alignment
        gbc.gridx = 1;
        gbc.gridy = 0;
        gbc.anchor = GridBagConstraints.FIRST_LINE_START;
        add(idfill, gbc);

        pw = new JLabel("Password");
        pw.setFont(standard);
        // Alignment
        gbc.gridx = 0;
        gbc.gridy = 1;
        gbc.anchor = GridBagConstraints.FIRST_LINE_START;
        add(pw, gbc);

        pwfill = new JTextField(10);
        pwfill.setFont(standard);
        // Alignment
        gbc.gridx = 1;
        gbc.gridy = 1;
        gbc.anchor = GridBagConstraints.FIRST_LINE_START;
        add(pwfill, gbc);

        login = new JButton("Login");
        login.setFont(standard);
        login.addActionListener(this);
        // Alignment
        gbc.gridx = 1;
        gbc.gridy = 2;
        gbc.insets = new Insets(5, 5, 5, 5);
        gbc.anchor = GridBagConstraints.FIRST_LINE_START;
        add(login, gbc);
    }

    public void actionPerformed(ActionEvent e) {
        verify();
        if(isManager == 1) {
            MenuFrame menu = new MenuFrame("Menu");
            menu.runGUI();
            MainFrame.setVisible(false);    // This is the problem
        }
    }

    private void verify() {
        idinput = idfill.getText().trim();
        pwinput = pwfill.getText();
        for (int i = 0; i < manager.size(); i++) {
            if (idinput.equals(manager.get(i).id)) {
                temp = i;
            }
        }
        
        if(temp == -1) {
            JOptionPane.showMessageDialog(null, "Id or password incorrect, try again");
        } else if(pwinput.equals(manager.get(temp).password)) {
            isManager = 1;
        } else 
            JOptionPane.showMessageDialog(null, "Id or password incorrect, try again");
    }
}

(The codes are a bit lengthy as I am not confident that the other part was correct. All I know this has nothing to do with MenuFrame)

I get this error:

Cannot make a static reference to the non-static method setVisible(boolean) from the type Window

It might be my fault where it is not obvious enough for me to know which part of Manager or MainFrame is static. I also came across other posts regarding the same issue but none relates with mine. (Other post was having obvious static method)

Also tried the create an MainFrame object in Manager but it made it worse, please help, thank you!

Upvotes: 0

Views: 56

Answers (1)

Joop Eggen
Joop Eggen

Reputation: 109603

You indeed need to keep the MainFrame object somewhere accessible, keep a reference to it. For this MVC, Model-View-Controller, is a nice paradigm.

  1. Use MVC

I personally have my main method for swing in a Controller class (so the controller is the application class). It creates the main frame (View) and the controller is passed.

public void actionPerformed(ActionEvent e) {
    verify();
    if(isManager == 1) {
        MenuFrame menu = new MenuFrame("Menu");
        menu.runGUI();
        controller.setMainFrameVisible(false);
    }
}

Controller:

private MainFrame mainFrame;

public setMainFrameVisible(boolean visible) {
    MainFrame.setVisible(visible);
}
  1. Pass the MainFrame instance.

However you may also pass the MainFrame:

private final MainFrame mainFrame;

Manager(MainFrame mainFrame) {
    this.mainFrame = mainFrame;
}

public void actionPerformed(ActionEvent e) {
    verify();
    if(isManager == 1) {
        MenuFrame menu = new MenuFrame("Menu");
        menu.runGUI();
        mainFrame.setVisible(false);
    }
}
  1. If the panel is inside the MainFrame

    ((JFrame) getTopLevelAncestor()).setVisible(false);


Tip:

Should the application exit (EXIT_ON_CLOSE), change the default close operation.

MainFrame(String name){
    setTitle(name);
    setDefaultCloseOperation(JFrame.DO_NOTHING_ON_CLOSE);
}

Upvotes: 1

Related Questions