javajoptionpaneaccesscontrolexceptionicedtea

JOptionPane on applet, accessEventQueue accessControlException


I wrote an application that generates quiz applets. I could't find a portable way to sign the generated applets automatically so they are not signed. But this simple piece of code as far as I know doesn't require the Applet to be signed, yet it is throwing accessControlException about "accessEventQueue" on linux. I'm running it on IceTea7, OpenJDK7, I tried on both Chrome and Opera.

System.out.println("This will display...");

int r = JOptionPane.showConfirmDialog(null,"End the quiz now?",
    "Quiz",
    JOptionPane.YES_NO_OPTION,                  
    JOptionPane.INFORMATION_MESSAGE);

System.out.println("This won't...");

Surfing a little I found this info about a bug on IcedTea. I've tried the applet myself on windows and it isn't throwing any Exception there.

If what I've found is really a bug, is there any workaround or I'll have to implement my own confirmation dialog...?

Is there any way to popup a JOptionPane dialog without interfering with the AWT event queue?


Solution

  • As I heard from the developers, it's an actual bug.

    Here's my naive implementation of a confirmation dialog to save you some coding time:

    public class ConfirmDialog implements ActionListener {
        JFrame main;
        ConfirmCallback callback;
    
        public ConfirmDialog(String msg,String[] opts, ConfirmCallback lc) {
            this(msg,"Selection",opts,lc);
        }
    
        public ConfirmDialog(String msg,String title ,String[] opts,  ConfirmCallback lc) {
            main = new JFrame();
            main.setTitle(title);
            this.callback = lc;
            main.setDefaultCloseOperation(WindowConstants.DO_NOTHING_ON_CLOSE);
            GridBagConstraints gbc = new GridBagConstraints();
            GridBagLayout layout = new GridBagLayout();
    
            JPanel panel = new JPanel();
            panel.setLayout(layout);
            panel.setBorder(BorderFactory.createEmptyBorder(5,5,5,5));
            gbc.fill = GridBagConstraints.HORIZONTAL;
            gbc.gridx = 0; gbc.gridy =0;
            gbc.gridwidth = opts.length; gbc.gridheight = 1;
            gbc.insets = new Insets(3,3,3,3);
    
            JLabel mainLabel = new JLabel(msg);
    
            layout.setConstraints(mainLabel, gbc);
            panel.add(mainLabel);
    
            gbc.gridy = 1;
            gbc.gridwidth= 1;
    
            int cnt = 0;
            for (String s: opts) {
                JButton submitButton = new JButton(s);
                submitButton.setActionCommand(Integer.toString(cnt++));
                submitButton.addActionListener(this);   
                gbc.gridx = cnt;
                layout.setConstraints(submitButton, gbc);
                panel.add(submitButton);
            }
            main.add(panel);
            main.pack();
            main.setLocationRelativeTo(null);
            main.setVisible(true);
    
        }
    
        public ConfirmDialog() {}
    
        @Override
        public void actionPerformed(ActionEvent e) {
            callback.run(Integer.decode(e.getActionCommand()));
            main.dispose();
        }
    
        public void Test() {
            ConfirmCallback cb = new ConfirmCallback(){
                @Override
                public void run(int arg) {
                    JOptionPane.showMessageDialog(null, "The user just entered: "+arg);
                }
            };
            new ConfirmDialog("Please choose",new String[] {"a","b","c"},cb);
        }
    
        public static void main(String args[]) {
            new ConfirmDialog().Test();
        }
    }
    

    And here is the callback it uses:

    public abstract class ConfirmCallback {
        public abstract void run(int arg);
    }