문제

마우스 클릭 이벤트의 경우 JDeskToPPane에 추가되는 여러 jInternalFrames 을 사용하여 스윙 응용 프로그램을 만들었습니다. 동일한 내부 프레임 의 한 인스턴스 사용자가 사용자가 두 번 나타나지 않아도됩니다.프레임을 엽니 다.프레임이 이미 열려 있으면 오류 메시지가 나타납니다.!

감사합니다.)

도움이 되었습니까?

해결책

싱글 톤 항 - 패턴으로 귀찮게하지 마십시오.대신 클래스의 생성자 또는 변수 선언에서 jInternalFrame의 클래스를 jInternalFrame 필드로 만들고 하나의 인스턴스 을 작성하고 마우스 클릭에 새 하나를 만들지 마십시오.이미 생성되었습니다.예를 들어 MousePressed 메서드에서는 myInternalFrame.setVisible(true)를 호출하기 만하면됩니다.이렇게하면 보이지 않으면 이제는 보이고 이미 보이는 경우 여전히 보이지 않고 변하지 않습니다.간단하고 간단합니다.

다른 팁

여러 개의 jInternalFrames로 스윙 응용 프로그램을 만들었습니다 ...

동일한 내부 프레임의 인스턴스 만 하나만 원한다면 ...

싱글 톤 패턴 클래스가 Singleton 패턴을 준수하면 클래스의 한 번만 사용할 수 있습니다.

hovercrafffullofeeels, 내 마음을 가진 남자는 싱글 톤 패턴을 사용하지 말고 나는 동의하지 않을 것입니다. Singleton은 사물을 간소화하고 보일러 플레이트 코드를 피하고 시스템을 강력하고 쉽게 유지할 수있는 매우 강력한 방법이 될 수 있습니다. 또한 이미 열린 JInternalFrame를 단순히 표시하는 그의 제안은 두 가지 방법으로 결함이 있습니다. 1) 최종 사용자가 닫을 때 코드 수준에서 관리하기가 어렵고 시스템을 깨지기 어렵고 2) 시스템을 깨지기 쉽고 어렵습니다. 화면을 다시 엽니다면 새로 고침 된 데이터와 브랜드 새 구성 요소가있는 새 인스턴스 을 기대합니다. 폐쇄 및 재개가 동일한 경우가 될 것으로 예상되지는 않습니다.

다른 답변은 싱글 톤을 사용하지만 구체적인 예를 제공하지 않습니다. 그래서, 나는 당신에게 내가 응용 프로그램을 위해 개발 한 코드를 제공 할 것입니다 :

이것은 Singleton JInternalFrame의 클래스입니다 (참고 : Gui Builder에서 쉽게 사용할 수 있도록 JPanel가 쉽게 사용할 수 있도록 확장 된 이유) :

public abstract class VPanel extends JPanel {

    public static JDesktopPane desktopPane;

    public static void installDesktopPane(JDesktopPane desktopPane) {
        VPanel.desktopPane = desktopPane;
    }

    public VPanel(String name) {
        this.name = name;
        if(desktopPane == null)
            throw new IllegalStateException("VPanel is being used with a null desktop pane.");
    }
    static LinkedHashMap<Class, VPanel> self_panel_map;

    JInternalFrame self_jif;
    protected VPanel self_panel;
    boolean loading;
    boolean showing;

    public final String name;
    public abstract void init();

    public static VPanel showPanel(VPanel newInstance) {
        if(self_panel_map == null)
            self_panel_map = new LinkedHashMap<>();
        Class newInstanceClass = newInstance.getClass();
        if(self_panel_map.containsKey(newInstanceClass)) {
            VPanel oldInstance = self_panel_map.get(newInstanceClass);
            oldInstance.showing = oldInstance.self_jif.isVisible();
            if(!oldInstance.loading && !oldInstance.showing) {
                newInstance.loading = true;
                newInstance.self_panel = newInstance;
                newInstance.self_jif = new JInternalFrame(newInstance.name, true, true, true, true);
                newInstance.self_panel.init();
                self_panel_map.put(newInstanceClass, newInstance);
                return newInstance;
            } else if(oldInstance.showing) {
                try {
                    oldInstance.self_jif.setSelected(true);
                } catch (PropertyVetoException e) {
                    handleError(e);
                }
            }
            return oldInstance;
        } else {
            newInstance.loading = true;
            newInstance.self_panel = newInstance;
            newInstance.self_jif = new JInternalFrame(newInstance.name, true, true, true, true);
            newInstance.self_panel.init();
            self_panel_map.put(newInstanceClass, newInstance);
            return newInstance;
        }
    }

    public void setVisible() {

        self_jif.add(self_panel);
        self_jif.pack();
        self_jif.setVisible(true);
        desktopPane.add(self_jif);
        centerJIF();
        try {
            self_jif.setSelected(true);
        } catch (PropertyVetoException e) {
            handleError(e);
        }
        loading = false;
    }

    private static void handleError(Exception e) {
        e.printStackTrace();
    }

    public void centerJIF() {
        Dimension desktopSize = desktopPane.getSize();
        Dimension JInternalFrameSize = self_jif.getSize();
        int width = (desktopSize.width - JInternalFrameSize.width) / 2;
        int height = (desktopSize.height - JInternalFrameSize.height) / 2;
        self_jif.setLocation(width, height);
    }
}
.

여기를 구현할 샘플 코드가 있습니다.

public static void main(String[] args) {
    JFrame jf = new JFrame("MainFrame");
    JDesktopPane jdp = new JDesktopPane();
    jf.setExtendedState( jf.getExtendedState()|JFrame.MAXIMIZED_BOTH );

    VPanel.installDesktopPane(jdp); // This only needs to happen once throughout the entire application lifecycle.

    JMenuBar menuBar = new JMenuBar();
    JMenu menu = new JMenu("Panels");
    JMenuItem menuItem = new JMenuItem("Open Test Panel");
    menuItem.addActionListener(new ActionListener() {
        @Override
        public void actionPerformed(ActionEvent e) {
            Test_VPanel.showPanel(new Test_VPanel()); // Every time you show the panel, you create a new instance.
            // But this new instance is only used if it is needed. The init() method is only called if it is going
            // To show a new instance.
        }
    });
    menu.add(menuItem);
    menuBar.add(menu);
    jf.setJMenuBar(menuBar);


    jf.setContentPane(jdp);

    jf.setVisible(true);
    jf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}

static class Test_VPanel extends VPanel {

    public Test_VPanel() {
        super("Test Panel");
    }

    @Override
    public void init() {
        setLayout(new GridBagLayout());
        GridBagConstraints gbc = new GridBagConstraints();

        JLabel label = new JLabel("JLabel");
        JTextField textField = new JTextField();

        gbc.fill = GridBagConstraints.HORIZONTAL;
        gbc.weightx = 1;
        gbc.gridwidth = 1;
        gbc.gridy = 0;
        gbc.insets = new Insets(4,4,4,4);
        add(label, gbc);

        gbc.gridy = 1;
        add(textField, gbc);

        setVisible(); // This needs to be called at the end of init()
    }
}
.

새 인스턴스로 아무 것도 수행 할 수있는 호출 방법이 필요하지만 INCASE는 showPanel가 이전 인스턴스 또는 새 인스턴스인지 여부에 관계없이 사용 된 인스턴스를 반환합니다. 따라서 인스턴스로 뭔가를 해야하는 경우 다음을 수행하십시오.

Test_VPanel panel = Test_VPanel.showPanel(new Test_VPanel());
panel.something();
...
.

싱글 톤 JIF 로이 경로가되기로 결정하면

인생이 훨씬 쉽습니다. 적극적으로 권장됩니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top