+ /**
+ * Builds the group colour sub-menu, including any user-defined colours which
+ * were loaded at startup or during the Jalview session
+ */
+ protected void buildColourMenu()
+ {
+ SequenceGroup sg = getGroup();
+ colourMenu.removeAll();
+ colourMenu.add(textColour);
+ colourMenu.addSeparator();
+ colourMenu.add(noColourmenuItem);
+ colourMenu.add(clustalColour);
+ // in Java 8, isApplicableTo can be a static method on the interface
+ clustalColour.setEnabled(new ClustalxColourScheme(sg, null)
+ .isApplicableTo(sg));
+ colourMenu.add(BLOSUM62Colour);
+ BLOSUM62Colour
+ .setEnabled(new Blosum62ColourScheme().isApplicableTo(sg));
+ colourMenu.add(PIDColour);
+ PIDColour.setEnabled(new PIDColourScheme().isApplicableTo(sg));
+ colourMenu.add(zappoColour);
+ zappoColour.setEnabled(new ZappoColourScheme().isApplicableTo(sg));
+ colourMenu.add(taylorColour);
+ taylorColour.setEnabled(new TaylorColourScheme().isApplicableTo(sg));
+ colourMenu.add(hydrophobicityColour);
+ hydrophobicityColour.setEnabled(new HydrophobicColourScheme()
+ .isApplicableTo(sg));
+ colourMenu.add(helixColour);
+ helixColour.setEnabled(new HelixColourScheme().isApplicableTo(sg));
+ colourMenu.add(strandColour);
+ strandColour.setEnabled(new StrandColourScheme().isApplicableTo(sg));
+ colourMenu.add(turnColour);
+ turnColour.setEnabled(new TurnColourScheme().isApplicableTo(sg));
+ colourMenu.add(buriedColour);
+ buriedColour.setEnabled(new BuriedColourScheme().isApplicableTo(sg));
+ colourMenu.add(nucleotideColour);
+ nucleotideColour.setEnabled(new NucleotideColourScheme()
+ .isApplicableTo(sg));
+ colourMenu.add(purinePyrimidineColour);
+ purinePyrimidineColour.setEnabled(new PurinePyrimidineColourScheme()
+ .isApplicableTo(sg));
+ colourMenu.add(tcoffeeColour);
+ tcoffeeColour
+ .setEnabled(new TCoffeeColourScheme(sg).isApplicableTo(sg));
+
+ /*
+ * add some of these items to a ButtonGroup so their
+ * selection is mutually exclusive
+ */
+ ButtonGroup colours = new ButtonGroup();
+
+ /*
+ * add any user-defined colours loaded on startup or
+ * during the application session
+ */
+ SortedMap<String, UserColourScheme> userColourSchemes = UserDefinedColours
+ .getUserColourSchemes();
+ if (userColourSchemes != null)
+ {
+ for (String userColour : userColourSchemes.keySet())
+ {
+ JRadioButtonMenuItem item = new JRadioButtonMenuItem(userColour);
+ item.setName(userColour); // button name identifies selected colour
+ item.addActionListener(new ActionListener()
+ {
+ @Override
+ public void actionPerformed(ActionEvent evt)
+ {
+ userDefinedColour_actionPerformed(evt);
+ }
+ });
+ colourMenu.add(item);
+ colours.add(item);
+ }
+ }
+ colourMenu.add(userDefinedColour);
+
+ colourMenu.addSeparator();
+ colourMenu.add(conservationMenuItem);
+ colourMenu.add(abovePIDColour);
+
+ colours.add(noColourmenuItem);
+ colours.add(clustalColour);
+ colours.add(BLOSUM62Colour);
+ colours.add(PIDColour);
+ colours.add(zappoColour);
+ colours.add(taylorColour);
+ colours.add(hydrophobicityColour);
+ colours.add(helixColour);
+ colours.add(strandColour);
+ colours.add(turnColour);
+ colours.add(buriedColour);
+ colours.add(purinePyrimidineColour);
+ colours.add(tcoffeeColour);
+ colours.add(nucleotideColour);
+ colours.add(userDefinedColour);
+ colours.add(abovePIDColour);
+ // colours.add(RNAInteractionColour);
+
+ }
+
+ /**
+ * Check for any annotations on the underlying dataset sequences (for the
+ * current selection group) which are not 'on the alignment'.If any are found,
+ * enable the option to add them to the alignment. The criteria for 'on the
+ * alignment' is finding an alignment annotation on the alignment, matched on
+ * calcId, label and sequenceRef.
+ *
+ * A tooltip is also constructed that displays the source (calcId) and type
+ * (label) of the annotations that can be added.
+ *
+ * @param menuItem
+ * @param forSequences
+ */
+ protected void configureReferenceAnnotationsMenu(JMenuItem menuItem,
+ List<SequenceI> forSequences)
+ {
+ menuItem.setEnabled(false);
+
+ /*
+ * Temporary store to hold distinct calcId / type pairs for the tooltip.
+ * Using TreeMap means calcIds are shown in alphabetical order.
+ */
+ SortedMap<String, String> tipEntries = new TreeMap<String, String>();
+ final Map<SequenceI, List<AlignmentAnnotation>> candidates = new LinkedHashMap<SequenceI, List<AlignmentAnnotation>>();
+ AlignmentI al = this.ap.av.getAlignment();
+ AlignmentUtils.findAddableReferenceAnnotations(forSequences,
+ tipEntries, candidates, al);
+ if (!candidates.isEmpty())
+ {
+ StringBuilder tooltip = new StringBuilder(64);
+ tooltip.append(MessageManager.getString("label.add_annotations_for"));
+
+ /*
+ * Found annotations that could be added. Enable the menu item, and
+ * configure its tooltip and action.
+ */
+ menuItem.setEnabled(true);
+ for (String calcId : tipEntries.keySet())
+ {
+ tooltip.append("<br/>" + calcId + "/" + tipEntries.get(calcId));
+ }
+ String tooltipText = JvSwingUtils.wrapTooltip(true,
+ tooltip.toString());
+ menuItem.setToolTipText(tooltipText);
+
+ menuItem.addActionListener(new ActionListener()
+ {
+ @Override
+ public void actionPerformed(ActionEvent e)
+ {
+ addReferenceAnnotations_actionPerformed(candidates);
+ }
+ });
+ }
+ }
+
+ /**
+ * Add annotations to the sequences and to the alignment.
+ *
+ * @param candidates
+ * a map whose keys are sequences on the alignment, and values a list
+ * of annotations to add to each sequence
+ */
+ protected void addReferenceAnnotations_actionPerformed(
+ Map<SequenceI, List<AlignmentAnnotation>> candidates)
+ {
+ final SequenceGroup selectionGroup = this.ap.av.getSelectionGroup();
+ final AlignmentI alignment = this.ap.getAlignment();
+ AlignmentUtils.addReferenceAnnotations(candidates, alignment,
+ selectionGroup);
+ refresh();
+ }
+
+ protected void makeReferenceSeq_actionPerformed(ActionEvent actionEvent)
+ {
+ if (!ap.av.getAlignment().hasSeqrep())
+ {
+ // initialise the display flags so the user sees something happen
+ ap.av.setDisplayReferenceSeq(true);
+ ap.av.setColourByReferenceSeq(true);
+ ap.av.getAlignment().setSeqrep(sequence);
+ }
+ else
+ {
+ if (ap.av.getAlignment().getSeqrep() == sequence)
+ {
+ ap.av.getAlignment().setSeqrep(null);
+ }
+ else
+ {
+ ap.av.getAlignment().setSeqrep(sequence);
+ }
+ }
+ refresh();
+ }
+
+ protected void hideInsertions_actionPerformed(ActionEvent actionEvent)
+ {
+ if (sequence != null)
+ {
+ ColumnSelection cs = ap.av.getColumnSelection();
+ if (cs == null)
+ {
+ cs = new ColumnSelection();
+ }
+ cs.hideInsertionsFor(sequence);
+ ap.av.setColumnSelection(cs);
+ }
+ refresh();
+ }
+
+ protected void sequenceSelectionDetails_actionPerformed()
+ {
+ createSequenceDetailsReport(ap.av.getSequenceSelection());
+ }
+
+ protected void sequenceDetails_actionPerformed()
+ {
+ createSequenceDetailsReport(new SequenceI[] { sequence });
+ }
+
+ public void createSequenceDetailsReport(SequenceI[] sequences)
+ {
+ CutAndPasteHtmlTransfer cap = new CutAndPasteHtmlTransfer();
+ StringBuilder contents = new StringBuilder(128);
+ for (SequenceI seq : sequences)
+ {
+ contents.append("<p><h2>"
+ + MessageManager
+ .formatMessage(
+ "label.create_sequence_details_report_annotation_for",
+ new Object[] { seq.getDisplayId(true) })
+ + "</h2></p><p>");
+ new SequenceAnnotationReport(null)
+ .createSequenceAnnotationReport(
+ contents,
+ seq,
+ true,
+ true,
+ (ap.getSeqPanel().seqCanvas.fr != null) ? ap
+ .getSeqPanel().seqCanvas.fr.getMinMax()
+ : null);
+ contents.append("</p>");
+ }
+ cap.setText("<html>" + contents.toString() + "</html>");
+
+ Desktop.addInternalFrame(cap, MessageManager.formatMessage(
+ "label.sequence_details_for",
+ (sequences.length == 1 ? new Object[] { sequences[0]
+ .getDisplayId(true) } : new Object[] { MessageManager
+ .getString("label.selection") })), 500, 400);
+
+ }
+