简体   繁体   English

通过revalidate()和repaint()更新Swing中的JMenu不起作用

[英]Update JMenu in Swing via revalidate() and repaint() not working

In the process of logging in, if the administrator is being logged in I want to enable JMenuItem called Admin . 在登录过程中,如果管理员正在登录,我要启用名为Admin的 JMenuItem。 When program starts, its visibility is set to false. 程序启动时,其可见性设置为false。 So when a user clicks Log In I run JMenu again and trying to recreate it just with Admin now set on true. 因此,当用户单击“ 登录”时,我再次运行JMenu并尝试仅将Admin设置为true来重新创建它。 Here's the code of my initialize method that's being run if it detects the user is an admin. 如果检测到用户是管理员,这是我正在运行的initialize方法的代码。 The method is inside the JMenuBar class that the application uses. 该方法位于应用程序使用的JMenuBar类内部。

public void initialize() {

    file = new JMenu("File");
    file.setName("File Menu");
    file.addMouseListener(this);

    help = new JMenu("Help");
    help.setName("Help Menu");
    help.addMouseListener(this);

    login = new JMenu("Login");
    login.setName("Login Menu");
    login.addMouseListener(this);

    language = new JMenu("Language");
    language.setName("Language Menu");
    language.addMouseListener(this);

    admin = new JMenu("Admin");
    admin.setName("Admin Menu");
    if(LoginDialog.AdminLoggedIn) {
        admin.setEnabled(true);
    } else
        admin.setEnabled(false);
    admin.addMouseListener(this);   

    add(file);
    add(login);
    add(help);
    add(language);
    add(admin);

    this.revalidate();
    this.repaint();

}

Thanks. 谢谢。

I would suggest not re-creating your JMenu but rather modifying it, depending on the Administrator state of your program. 我建议不要重新创建JMenu,而是根据程序的Administrator状态对其进行修改。 You could give the program a Privileges enum, one with REGULAR and ADMINISTRATOR (and possibly other) fields, something like: 您可以给该程序一个Privileges枚举,其中一个包含REGULAR和ADMINISTRATOR(可能还有其他)字段,例如:

public enum Privileges {
    REGULAR("Regular"), ADMINISTRATOR("Administrator");
    private String text;
    private Privileges(String text) {
        this.text = text;
    }

    @Override
    public String toString() {
        return text;
    }
}

And then change the state of your JMenu depending on the program's Privileges state. 然后根据程序的权限状态更改JMenu的状态。 Also side note: don't use a MouseListener on your menus since these do not respect the enabled/disabled state of your menus / menuitems / buttons. 另外请注意:不要在菜单上使用MouseListener,因为它们不尊重菜单/菜单项/按钮的启用/禁用状态。 For example, here is my small MVCE example, one that uses a Model-View-Controller structure (of sorts): 例如,这是我的小型MVCE示例,其中使用了Model-View-Controller结构(某种形式):

import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.event.KeyEvent;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;

import javax.swing.*;
import javax.swing.event.SwingPropertyChangeSupport;

@SuppressWarnings("serial")
public class MenuChanger extends JPanel {
    private CreateMenu createMenu = new CreateMenu();
    private MenuChngModel model = new MenuChngModel();
    private ButtonGroup buttonGroup = new ButtonGroup();

    public MenuChanger() {
        setPreferredSize(new Dimension(400, 300));
        model.addPropertyChangeListener(MenuChngModel.PRIVILEGES, new ModelListener());

        JPanel privilegesPanel = new JPanel();
        privilegesPanel.setLayout(new GridLayout(0, 1, 5, 5));
        privilegesPanel.setBorder(BorderFactory.createTitledBorder("Privileges"));

        for (final Privileges privileges : Privileges.values()) {
            JRadioButton rBtn = new JRadioButton(privileges.toString());
            if (privileges == Privileges.REGULAR) {
                rBtn.setSelected(true);
            }
            rBtn.addActionListener(e -> {
                createMenu.setPrivileges(privileges);
            });
            buttonGroup.add(rBtn);
            privilegesPanel.add(rBtn);
        }

        add(privilegesPanel);

    }

    public CreateMenu getCreateMenu() {
        return createMenu;
    }

    private class ModelListener implements PropertyChangeListener {
        @Override
        public void propertyChange(PropertyChangeEvent evt) {
            Privileges privileges = (Privileges) evt.getNewValue();
            createMenu.setPrivileges(privileges);
        }
    }

    private static void createAndShowGui() {
        MenuChanger mainPanel = new MenuChanger();

        JFrame frame = new JFrame("MenuChanger");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.getContentPane().add(mainPanel);
        frame.setJMenuBar(mainPanel.getCreateMenu().getMenubar());
        frame.pack();
        frame.setLocationRelativeTo(null);
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        SwingUtilities.invokeLater(() -> createAndShowGui());
    }
}

class MenuChngModel {
    public static final String PRIVILEGES = "privileges";
    private SwingPropertyChangeSupport pcSupport = new SwingPropertyChangeSupport(this);
    private Privileges privileges = Privileges.REGULAR;

    public Privileges getPrivileges() {
        return privileges;
    }

    public void setPrivileges(Privileges privileges) {
        Privileges oldValue = this.privileges;
        Privileges newValue = privileges;
        this.privileges = privileges;
        pcSupport.firePropertyChange(PRIVILEGES, oldValue, newValue);
    }

    public void addPropertyChangeListener(PropertyChangeListener listener) {
        pcSupport.addPropertyChangeListener(listener);
    }

    public void removePropertyChangeListener(PropertyChangeListener listener) {
        pcSupport.removePropertyChangeListener(listener);
    }

    public void addPropertyChangeListener(String name, PropertyChangeListener listener) {
        pcSupport.addPropertyChangeListener(name, listener);
    }

    public void removePropertyChangeListener(String name, PropertyChangeListener listener) {
        pcSupport.removePropertyChangeListener(name, listener);
    }

}

enum Privileges {
    REGULAR("Regular"), ADMINISTRATOR("Administrator");
    private String text;
    private Privileges(String text) {
        this.text = text;
    }

    @Override
    public String toString() {
        return text;
    }
}

class CreateMenu {
    private JMenuBar menubar = new JMenuBar();
    private JMenu fileMenu = new JMenu("File");
    private JMenu adminMenu = new JMenu("Administrator");
    private JMenuItem fileMenuItem = new JMenuItem("File Menu Item");
    private JMenuItem adminFileMenuItem = new JMenuItem("Admin File Menu Item");


    public CreateMenu() {
        fileMenu.setMnemonic(KeyEvent.VK_F);
        adminMenu.setMnemonic(KeyEvent.VK_A);

        fileMenu.add(fileMenuItem);
        fileMenu.add(adminFileMenuItem);       
        adminMenu.add(new JMenuItem("Foo 1"));
        adminMenu.add(new JMenuItem("Foo 2"));
        adminFileMenuItem.setEnabled(false);
        adminMenu.setEnabled(false);
        menubar.add(fileMenu);
        menubar.add(adminMenu);
    }

    public void setPrivileges(Privileges privileges) {
        switch (privileges) {
        case REGULAR:
            adminMenu.setEnabled(false);
            adminFileMenuItem.setEnabled(false);
            break;
        case ADMINISTRATOR:
            adminMenu.setEnabled(true);
            adminFileMenuItem.setEnabled(true);
            break;

        default:
            break;
        }
    }

    public JMenuBar getMenubar() {
        return menubar;
    }

}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM