Как закрыть окно на основе JFrame с событием щелчка JButton - PullRequest
3 голосов
/ 25 июня 2010

Я новичок во всех диалоговых окнах Java Swing / AWT (которые объясняют, как непонятен этот диалог ниже, любая помощь в его улучшении приветствуется :), и я пытаюсь закрыть это всплывающее окно, когда любой из двух JButton нажаты.

Я уже пробовал варианты, такие как frame.dispose(), frame.setVisible(false) и даже SwingUtilities.getWindowAncestor(this).dispose();

Опять же, это вторичное всплывающее окно, вызываемое другим основным запущенным процессом, поэтому я просто хочу, чтобы это конкретное всплывающее окно закрывалось и не влияло на основной процесс. В противном случае я мог бы использовать System.exit

Как я уже говорил, приветствуются любые другие предложения по улучшению общего вида и ощущения диалога.

Весь мой код показан ниже:

import java.awt.Color;
import java.awt.Component;
import java.awt.Font;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextArea;
import javax.swing.SwingUtilities;

public class UpgradePopupWindow extends JPanel implements ActionListener {
  public static UpgradePopupWindow mainWindow;

  static final long serialVersionUID = 0;

  final String upgrade = "Continue Upgrade";
  final String restore = "Restore";

  JPanel panels;
  JButton flashMe;
  JButton helpMe;
  JTextArea Message;
  JFrame frame;

  protected JTextArea addText(String text, boolean visible, int fontStyle) {
    JTextArea textArea = new JTextArea(text);

    textArea.setFont(new Font("SansSerif", fontStyle, 12)); //$NON-NLS-1$

    textArea.setLineWrap(true);
    textArea.setWrapStyleWord(true);
    textArea.setEditable(false);
    textArea.setForeground(Color.WHITE);
    textArea.setOpaque(false);
    textArea.setVisible(visible);
    textArea.setAlignmentX(Component.CENTER_ALIGNMENT);

    add(textArea);

    return textArea;
  }

  public UpgradePopupWindow(Object ft) {
    String text = "This is the random text for now. I will bother about the actual content later";
    addLabel(text, Font.PLAIN, 12);

    flashMe = new JButton(upgrade);
    flashMe.setActionCommand("upgrade");
    flashMe.addActionListener(this);
    flashMe.setEnabled(true);
    add(flashMe);


    helpMe = new JButton(restore);
    helpMe.setActionCommand("restore");
    helpMe.addActionListener(this);
    helpMe.setEnabled(true);
    add(helpMe);
  }

  protected JLabel addLabel(String text, int fontStyle, int size) {
    JLabel label = new JLabel(text);
    label.setFont(new Font("SansSerif", fontStyle, size)); 
    label.setAlignmentX(Component.CENTER_ALIGNMENT);
    label.setOpaque(false);
    label.setVisible(true);
    label.setForeground(Color.BLUE);

    add(label);
    return label;
  }

  public void createGUI(Object obj) {
    //Create and set up the frame.
    frame = new JFrame("PopUp Dialog");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    //create and setup the content pane
    UpgradePopupWindow popUpContentPane = new UpgradePopupWindow(obj);

    popUpContentPane.setOpaque(true);
    frame.setContentPane(popUpContentPane);

    frame.pack();
    frame.setVisible(true);
  }

  public void actionPerformed(ActionEvent e) {
    if("restore".equals(e.getActionCommand())) {
      System.out.println("restore button selected");
      frame.dispose();
      SwingUtilities.getWindowAncestor(this).dispose();
    } else if ("upgrade".equals(e.getActionCommand())) {
      System.out.println("upgrade button selected");
      frame.dispose();
    }
  }
}

Ответы [ 4 ]

2 голосов
/ 25 июня 2010

Ваш метод createGUI () немного сбит с толку, он создает ДРУГОЙ экземпляр этого класса, и в итоге вы получите один экземпляр с фреймом и один без него.Минимальное изменение, чтобы заставить его работать - это изменить ваш метод createGUI:

  public void createGUI(Object obj) {
    //Create and set up the frame.
    frame = new JFrame("PopUp Dialog");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

//    //create and setup the content pane
//    UpgradePopupWindow popUpContentPane = new UpgradePopupWindow(obj);

    setOpaque(true);
    frame.setContentPane(this);

    frame.pack();
    frame.setVisible(true);
  }
2 голосов
/ 25 июня 2010

Проблема в том, что ваш метод createGUI не является статическим. Итак, я полагаю, что вы сначала создаете окно UpgradePopupWindow, вызывая на нем createGUI, что, в свою очередь, создает Enw UpgradePopupWindow.

Попробуйте вместо этого:

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

public class TempTest
{
    public static void main(String[] args)
    {
        UpgradePopupWindow.createGUI(null);
    }
}


class UpgradePopupWindow extends JPanel implements ActionListener {
  public static UpgradePopupWindow mainWindow;

  static final long serialVersionUID = 0;

  final String upgrade = "Continue Upgrade";
  final String restore = "Restore";

  JPanel panels;
  JButton flashMe;
  JButton helpMe;
  JTextArea Message;
    JFrame frame;


    protected JTextArea addText(String text, boolean visible, int fontStyle) {
    JTextArea textArea = new JTextArea(text);

    textArea.setFont(new Font("SansSerif", fontStyle, 12)); //$NON-NLS-1$

    textArea.setLineWrap(true);
    textArea.setWrapStyleWord(true);
    textArea.setEditable(false);
    textArea.setForeground(Color.WHITE);
    textArea.setOpaque(false);
    textArea.setVisible(visible);
    textArea.setAlignmentX(Component.CENTER_ALIGNMENT);

    add(textArea);

    return textArea;
  }

  public UpgradePopupWindow(JFrame frm, Object ft2) {
    String text = "This is the random text for now. I will bother about the actual content later";
    addLabel(text, Font.PLAIN, 12);
      frame = frm;
    flashMe = new JButton(upgrade);
    flashMe.setActionCommand("upgrade");
    flashMe.addActionListener(this);
    flashMe.setEnabled(true);
    add(flashMe);


    helpMe = new JButton(restore);
    helpMe.setActionCommand("restore");
    helpMe.addActionListener(this);
    helpMe.setEnabled(true);
    add(helpMe);
  }

  protected JLabel addLabel(String text, int fontStyle, int size) {
    JLabel label = new JLabel(text);
    label.setFont(new Font("SansSerif", fontStyle, size));
    label.setAlignmentX(Component.CENTER_ALIGNMENT);
    label.setOpaque(false);
    label.setVisible(true);
    label.setForeground(Color.BLUE);

    add(label);
    return label;
  }

  public static void createGUI(Object obj) {
    //Create and set up the frame.
    JFrame frame = new JFrame("PopUp Dialog");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    //create and setup the content pane
    UpgradePopupWindow popUpContentPane = new UpgradePopupWindow(frame, obj);

    popUpContentPane.setOpaque(true);
    frame.setContentPane(popUpContentPane);

    frame.pack();
    frame.setVisible(true);
  }

  public void actionPerformed(ActionEvent e) {
    if("restore".equals(e.getActionCommand())) {
      System.out.println("restore button selected");
      frame.dispose();
      SwingUtilities.getWindowAncestor(this).dispose();
    } else if ("upgrade".equals(e.getActionCommand())) {
      System.out.println("upgrade button selected");
      frame.dispose();
    }
  }

}

Основным изменением является то, что createUI является статическим, а UpgradePopupWindow принимает кадр в конструкторе.

0 голосов
/ 25 июня 2010

Внутри метода createGUI() вы создаете экземпляр переменной frame и задаете для ее панели содержимого другой экземпляр UpgradePopupWindow. Но вы не создаете экземпляр переменной frame этого второго экземпляра. Когда нажимаются кнопки «Восстановить» или «Обновить», вызывается метод actionPerformed() этого экземпляра second , поэтому frame.dispose() и frame.setVisible(false) не будут работать, поскольку frame равно нулю.

Я бы предложил, чтобы ваш класс UpgradePopupWindow расширялся JFrame вместо JPanel. Таким образом, вы можете вызвать метод dispose() напрямую. Кроме того, имеет смысл иметь один класс == одно окно (JPanel - это не окно, а группа виджетов с графическим интерфейсом). Затем создайте JPanel в конструкторе и добавьте к нему виджеты. Вы также можете избавиться от этой неприятной mainWindow статической переменной.

Кроме того, я не думаю, что JFrame.EXIT_ON_CLOSE - это то, что вы хотите использовать здесь. Вы хотите закрыть окно, а не завершить все приложение. JFrame.DISPOSE_ON_CLOSE будет располагать только окном, когда оно закрыто.

Вы также можете более точно настроить реакцию своего диалога на события окна, реализовав интерфейс WindowListener.

Внешний вид выглядит нормально для меня. Просто и прямо.

public class Main{
  public static void main(String args[]){
    //display the window from your main window
    UpgradePopupWindow upw = new UpgradePopupWindow(obj);
    upw.setVisible(true);
  }
}

public class UpgradePopupWindow extends JFrame implements ActionListener, WindowListener {
  //...

  public UpgradePopupWindow(Object ft) {
    super("PopUp Dialog");
    JPanel panel = new JPanel();
    //...
    setContentPane(panel);
    setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
    pack();
  }

  public void actionPerformed(ActionEvent e) {
    if("restore".equals(e.getActionCommand())) {
      System.out.println("restore button selected");
      dispose();
    } else if ("upgrade".equals(e.getActionCommand())) {
      System.out.println("upgrade button selected");
      dispose();
    }
  }

  public void windowClosed(WindowEvent e) { 
    System.out.println("Window closed!");
  }
  //other WindowListener methods
}
0 голосов
/ 25 июня 2010

Проблема в том, что у вас есть два экземпляра вашего класса UpgradePopupWindow. Сначала вам нужно создать экземпляр, чтобы вы могли вызвать метод createGUI (). Затем в методе createGUI вы создаете еще один экземпляр класса. Я уверен, что это не то, что вы хотели.

Одно из решений - сделать метод createGUI () статическим. Я удалил переменную frame из класса и сделал следующие изменения:

  public static void createGUI(Object obj) {
    //Create and set up the frame.
    JFrame frame = new JFrame("PopUp Dialog");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    //create and setup the content pane
    UpgradePopupWindow popUpContentPane = new UpgradePopupWindow(obj);

    popUpContentPane.setOpaque(true);
    frame.setContentPane(popUpContentPane);

    frame.pack();
    frame.setVisible(true);
  }

  public void actionPerformed(ActionEvent e) {
    if("restore".equals(e.getActionCommand())) {
      System.out.println("restore button selected");
//      frame.dispose();
      SwingUtilities.getWindowAncestor(this).dispose();
    } else if ("upgrade".equals(e.getActionCommand())) {
      System.out.println("upgrade button selected");
//      frame.dispose();
      SwingUtilities.getWindowAncestor(this).dispose();
    }
  }

    public static void main(String[] args)
    {
        UpgradePopupWindow.createGUI(null);
    }
...