Вызов метода внутри Anonymous ActionListener, который генерирует исключение, без использования try / catch - PullRequest
1 голос
/ 28 октября 2011
public class Test {
public void buildGUI()
{
    JFrame frame = new JFrame();
    JButton send = new JButton("Send");
    send.addActionListener(new ActionListener()
    {
        public void actionPerformed(ActionEvent e)
        {
            send();
            frame.dispose();
        }
    });
    frame.add(send);
    frame.pack();
    frame.setVisible(true);
}
}

если метод send () выбрасывает MyException, как бы я мог, чтобы это исключение мигрировало свой путь из потока Swing в мой класс?

То, что я хочу сделать с генерируемым Исключением, - это создать другой класс, который создает экземпляр для перехвата исключения следующим образом.

public class AnotherTest
{
    public AnotherTest()
    {
         Test t = new Test();
         try
         {
             t.buildGUI();
         }
         catch(MyException e)
         {
             //do stuff.
         }
     }
}

Я хочу, чтобы это произошло концептуально, однако я знаю, что buildGUI завершится до того, как будет вызван actionPerformed. Итак, как бы я поймал потенциальное исключение в actionPerformed в AnotherTest?

Ответы [ 4 ]

1 голос
/ 28 октября 2011

Класс не может быть исключением. Могут только методы.

И класс - это не то, что может быть выполнено. Метод может быть выполнен.

И то, что выполняет метод слушателя действия, является потоком отправки события Swing. Единственное, что вы можете сделать, если какой-то метод выдает исключение в слушателе, это перехватить его и как-то отобразить: открыв диалоговое окно с ошибкой, или поместив сообщение об исключении в текстовую область, или что-нибудь еще.

    public void actionPerformed(ActionEvent e) {
        try {
            send();
        }
        catch (MyException e) {
            someTextArea.setText(e.getMessage());
        }
    }

Если вы действительно хотите обмениваться данными из Swing EDT с основным потоком, вы можете использовать BlockingQueue и запросить главный поток take в очереди, а слушатель offer - исключение из очереди.

Подойдет любой другой механизм связи потоков. Но убедитесь, что не заблокировали EDT, иначе весь графический интерфейс будет зависать.

1 голос
/ 28 октября 2011

Класс не может выдать исключение, только методы могут, поэтому самая первая строка является ошибкой. Во-вторых, вы можете окружить send () блоком try ... catch () для обработки этого исключения, в котором вы можете либо предпринять какое-либо действие по восстановлению после ошибки, либо отобразить сообщение об ошибке или что-то в этом роде, и это все равно будет служить вашим целям.

0 голосов
/ 29 октября 2011

Swing не является поточно-ориентированным, тогда идея построить Swing GUI внутри блока try - catch - finally более чем контрпродуктивна, вам нужно готовить все безопасные для кода блоки отдельно

1) Я начинаю с очень плохого пути -> ваша идея должна быть заключена в invokeLater(), если есть трудная и долгая работа Stream, File I/O, DB Conenction, тогда попытайтесь обернуть это в invokAndWait()

но вы загружаете эти данные из какого-либо существующего графического интерфейса, у вас есть много времени для

2) подготовить и загрузить данные (Stream, File I/O, DB Conenction) до того, как они вам понадобятся, затем поместить эти объекты в графический интерфейс, когда вам нужно (would be wrapped into invokeLater)

3) создайте GUI (would be wrapped into invokeLater), покажите это Container, затем загрузите данные (Stream, File I/O, DB Conenction), если успешно, затем добавьте показ этих данных в GUI

3) создать графический интерфейс (would be wrapped into invokeLater), показать это Container, загрузить данные только для одного из JComponents, если с успехом, то показать это JComponent, то же самое для 2-го. и так далее ...

для всех трех опций требуется перенаправление (Stream, File I/O, DB Conenction) загрузки этих данных, значение для JComponent(s), в Background Task(s), у вас есть два правильных способа сделать это,

с помощью

  • Runnable#Thread

  • SwingWorker

0 голосов
/ 28 октября 2011

Ну, почему бы просто не сделать это? И вместо этого заставьте send() вызвать какой-то другой поток, где работает ваша логика? И если этот поток встречает исключение, вы можете обработать его там.

Нет способа выбросить исключение через границы потока. Вы можете send() передать информацию о возникшем исключении во внешний мир, установив некоторый внешний флаг, который виден другим потокам вашего приложения.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...