+ @Override
+ public void actionPerformed(ActionEvent e)
+ {
+ new Thread(new Runnable()
+ {
+ @Override
+ public void run()
+ {
+ showLink(url);
+ }
+ }).start();
+ }
+ });
+ linkMenu.add(item);
+ }
+ }
+
+ /**
+ * Opens the provided url in the default web browser, or shows an error
+ * message if this fails
+ *
+ * @param url
+ */
+ static void showLink(String url)
+ {
+ try
+ {
+ jalview.util.BrowserLauncher.openURL(url);
+ } catch (Exception ex)
+ {
+ JvOptionPane.showInternalMessageDialog(Desktop.desktop,
+ MessageManager.getString("label.web_browser_not_found_unix"),
+ MessageManager.getString("label.web_browser_not_found"),
+ JvOptionPane.WARNING_MESSAGE);
+
+ ex.printStackTrace();
+ }
+ }
+
+ /**
+ * add a late bound groupURL item to the given linkMenu
+ *
+ * @param linkMenu
+ * @param label
+ * - menu label string
+ * @param urlgenerator
+ * GroupURLLink used to generate URL
+ * @param urlstub
+ * Object array returned from the makeUrlStubs function.
+ */
+ static void addshowLink(JMenu linkMenu, String label,
+ final GroupUrlLink urlgenerator, final Object[] urlstub)
+ {
+ JMenuItem item = new JMenuItem(label);
+ item.setToolTipText(MessageManager
+ .formatMessage("label.open_url_seqs_param", new Object[]
+ { urlgenerator.getUrl_prefix(),
+ urlgenerator.getNumberInvolved(urlstub) }));
+ // TODO: put in info about what is being sent.
+ item.addActionListener(new ActionListener()
+ {
+ @Override
+ public void actionPerformed(ActionEvent e)
+ {
+ new Thread(new Runnable()
+ {
+
+ @Override
+ public void run()
+ {
+ try
+ {
+ showLink(urlgenerator.constructFrom(urlstub));
+ } catch (UrlStringTooLongException e2)
+ {
+ }
+ }
+
+ }).start();
+ }
+ });
+
+ linkMenu.add(item);
+ }
+
+ /**
+ * Constructor for a PopupMenu for a click in the alignment panel (on a residue)
+ *
+ * @param ap
+ * the panel in which the mouse is clicked
+ * @param seq
+ * the sequence under the mouse
+ * @throws NullPointerException
+ * if seq is null
+ */
+ public PopupMenu(final AlignmentPanel ap, SequenceI seq, int column)
+ {
+ this(false, ap, seq, column, null);
+ }
+
+ /**
+ * Constructor for a PopupMenu for a click in the sequence id panel
+ *
+ * @param alignPanel
+ * the panel in which the mouse is clicked
+ * @param seq
+ * the sequence under the mouse click
+ * @param groupLinks
+ * templates for sequence external links
+ * @throws NullPointerException
+ * if seq is null
+ */
+ public PopupMenu(final AlignmentPanel alignPanel, final SequenceI seq,
+ List<String> groupLinks)
+ {
+ this(true, alignPanel, seq, -1, groupLinks);
+ }
+
+ /**
+ * Private constructor that constructs a popup menu for either sequence ID
+ * Panel, or alignment context
+ *
+ * @param fromIdPanel
+ * @param alignPanel
+ * @param seq
+ * @param column
+ * aligned column position (0...)
+ * @param groupLinks
+ */
+ private PopupMenu(boolean fromIdPanel,
+ final AlignmentPanel alignPanel,
+ final SequenceI seq, final int column, List<String> groupLinks)
+ {
+ Objects.requireNonNull(seq);
+ this.forIdPanel = fromIdPanel;
+ this.ap = alignPanel;
+ sequence = seq;
+
+ for (String ff : FileFormats.getInstance().getWritableFormats(true))
+ {
+ JMenuItem item = new JMenuItem(ff);
+
+ item.addActionListener(new ActionListener()
+ {
+ @Override