JAL-845 implement alignment of protein to match cDNA alignment
[jalview.git] / src / jalview / gui / AlignFrame.java
index 9f79999..9604458 100644 (file)
@@ -23,7 +23,6 @@ package jalview.gui;
 import jalview.analysis.AAFrequency;
 import jalview.analysis.AlignmentSorter;
 import jalview.analysis.AlignmentUtils;
-import jalview.analysis.AlignmentUtils.MappingResult;
 import jalview.analysis.Conservation;
 import jalview.analysis.CrossRef;
 import jalview.analysis.Dna;
@@ -33,6 +32,8 @@ import jalview.api.AlignViewControllerGuiI;
 import jalview.api.AlignViewControllerI;
 import jalview.api.AlignViewportI;
 import jalview.api.AlignmentViewPanel;
+import jalview.api.SplitContainerI;
+import jalview.api.ViewStyleI;
 import jalview.api.analysis.ScoreModelI;
 import jalview.bin.Cache;
 import jalview.commands.CommandI;
@@ -55,6 +56,7 @@ import jalview.datamodel.SeqCigar;
 import jalview.datamodel.Sequence;
 import jalview.datamodel.SequenceGroup;
 import jalview.datamodel.SequenceI;
+import jalview.gui.ViewSelectionMenu.ViewSetProvider;
 import jalview.io.AlignmentProperties;
 import jalview.io.AnnotationFile;
 import jalview.io.BioJsHTMLOutput;
@@ -87,7 +89,6 @@ import jalview.schemes.TaylorColourScheme;
 import jalview.schemes.TurnColourScheme;
 import jalview.schemes.UserColourScheme;
 import jalview.schemes.ZappoColourScheme;
-import jalview.structure.StructureSelectionManager;
 import jalview.util.MessageManager;
 import jalview.viewmodel.AlignmentViewport;
 import jalview.ws.jws1.Discoverer;
@@ -111,6 +112,8 @@ import java.awt.dnd.DropTargetEvent;
 import java.awt.dnd.DropTargetListener;
 import java.awt.event.ActionEvent;
 import java.awt.event.ActionListener;
+import java.awt.event.ItemEvent;
+import java.awt.event.ItemListener;
 import java.awt.event.KeyAdapter;
 import java.awt.event.KeyEvent;
 import java.awt.event.MouseAdapter;
@@ -346,7 +349,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     buildSortByAnnotationScoresMenu();
     buildTreeMenu();
     
-    if (viewport.wrapAlignment)
+    if (viewport.getWrapAlignment())
     {
       wrapMenuItem_actionPerformed(null);
     }
@@ -358,6 +361,59 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
 
     addKeyListener();
 
+    final List<AlignmentPanel> selviews = new ArrayList<AlignmentPanel>();
+    final List<AlignmentPanel> origview = new ArrayList<AlignmentPanel>();
+    ViewSelectionMenu vsel = new ViewSelectionMenu("Transfer colours from",
+            new ViewSetProvider()
+            {
+
+              @Override
+              public AlignmentPanel[] getAllAlignmentPanels()
+              {
+                origview.clear();
+                origview.add(alignPanel);
+                return Desktop.getAlignmentPanels(null);
+              }
+            }, selviews, new ItemListener()
+            {
+
+              @Override
+              public void itemStateChanged(ItemEvent e)
+              {
+                if (origview.size() > 0)
+                {
+                  ViewStyleI vs = selviews.get(0).getAlignViewport()
+                          .getViewStyle();
+                  origview.get(0).getAlignViewport().setViewStyle(vs);
+                  AlignViewportI complement = origview.get(0)
+                          .getAlignViewport().getCodingComplement();
+                  if (complement != null)
+                  {
+                    AlignFrame af = Desktop.getAlignFrameFor(complement);
+                    if (complement.isNucleotide())
+                    {
+                      complement.setViewStyle(vs);
+                      vs.setCharWidth(vs.getCharWidth() / 3);
+                    }
+                    else
+                    {
+                      int rw = vs.getCharWidth();
+                      vs.setCharWidth(rw * 3);
+                      complement.setViewStyle(vs);
+                      vs.setCharWidth(rw);
+                    }
+                    af.alignPanel.updateLayout();
+                    af.setMenusForViewport();
+                  }
+                  origview.get(0).updateLayout();
+                  origview.get(0).setSelected(true);
+                  origview.get(0).alignFrame.setMenusForViewport();
+
+                }
+              }
+            });
+    formatMenu.add(vsel);
+
   }
 
   /**
@@ -372,7 +428,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   public void setFileName(String file, String format)
   {
     fileName = file;
-    currentFileFormat = format;
+    setFileFormat(format);
     reload.setEnabled(true);
   }
 
@@ -553,7 +609,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
           break;
         }
         case KeyEvent.VK_PAGE_UP:
-          if (viewport.wrapAlignment)
+          if (viewport.getWrapAlignment())
           {
             alignPanel.scrollUp(true);
           }
@@ -564,7 +620,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
           }
           break;
         case KeyEvent.VK_PAGE_DOWN:
-          if (viewport.wrapAlignment)
+          if (viewport.getWrapAlignment())
           {
             alignPanel.scrollUp(false);
           }
@@ -712,104 +768,28 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     }).start();
   }
 
+  /**
+   * Configure menu items that vary according to whether the alignment is
+   * nucleotide or protein
+   * 
+   * @param nucleotide
+   */
   public void setGUINucleotide(boolean nucleotide)
   {
     showTranslation.setVisible(nucleotide);
-    cdna.setVisible(!nucleotide);
     conservationMenuItem.setEnabled(!nucleotide);
     modifyConservation.setEnabled(!nucleotide);
     showGroupConservation.setEnabled(!nucleotide);
     rnahelicesColour.setEnabled(nucleotide);
     purinePyrimidineColour.setEnabled(nucleotide);
+    showComplementMenuItem.setText(MessageManager
+            .getString(nucleotide ? "label.protein" : "label.nucleotide"));
+    setColourSelected(jalview.bin.Cache.getDefault(
+            nucleotide ? Preferences.DEFAULT_COLOUR_NUC
+                    : Preferences.DEFAULT_COLOUR_PROT, "None"));
   }
 
   /**
-   * Builds codon mappings from this (protein) alignment to any compatible
-   * nucleotide alignments. Mappings are built between sequences with the same
-   * name and compatible lengths. Also makes the cDNA alignment a
-   * CommandListener for the protein alignment so that edits are mirrored.
-   */
-  @Override
-  protected void linkCdna_actionPerformed()
-  {
-    int linkedCount = 0;
-    int alreadyLinkedCount = 0;
-    final AlignmentI thisAlignment = this.alignPanel.getAlignment();
-
-    for (AlignFrame af : Desktop.getAlignFrames())
-    {
-      if (af.alignPanel != null)
-      {
-        final AlignmentI thatAlignment = af.alignPanel.getAlignment();
-        if (thatAlignment.isNucleotide())
-        {
-          MappingResult mapped = AlignmentUtils.mapProteinToCdna(
-                  thisAlignment, thatAlignment);
-          if (mapped == MappingResult.AlreadyMapped)
-          {
-            alreadyLinkedCount++;
-          }
-          else if (mapped == MappingResult.Mapped)
-          {
-            final StructureSelectionManager ssm = StructureSelectionManager
-                    .getStructureSelectionManager(Desktop.instance);
-            ssm.addMappings(thisAlignment.getCodonFrames());
-            // enable the next line to enable linked editing
-            // ssm.addCommandListener(af.getViewport());
-            linkedCount++;
-          }
-        }
-      }
-    }
-    String msg = "";
-    if (linkedCount == 0 && alreadyLinkedCount == 0)
-    {
-      msg = MessageManager.getString("label.no_cdna");
-    }
-    else if (linkedCount > 0)
-    {
-      msg = MessageManager.formatMessage("label.linked_cdna", linkedCount);
-    }
-    else
-    {
-      msg = MessageManager.formatMessage("label.cdna_all_linked",
-              alreadyLinkedCount);
-    }
-    setStatus(msg);
-  }
-
-  /**
-   * Align any linked cDNA to match the alignment of this (protein) alignment.
-   * Any mapped sequence regions will be realigned, unmapped sequences are not
-   * affected.
-   */
-  @Override
-  protected void alignCdna_actionPerformed()
-  {
-    int seqCount = 0;
-    int alignCount = 0;
-    final AlignmentI thisAlignment = this.alignPanel.getAlignment();
-    for (AlignFrame af : Desktop.getAlignFrames())
-    {
-      if (af.alignPanel != null)
-      {
-        final AlignmentI thatAlignment = af.alignPanel.getAlignment();
-        if (thatAlignment.isNucleotide())
-        {
-          int seqsAligned = thatAlignment.alignAs(thisAlignment);
-          seqCount += seqsAligned;
-          if (seqsAligned > 0)
-          {
-            af.alignPanel.alignmentChanged();
-            alignCount++;
-          }
-        }
-      }
-    }
-    setStatus(MessageManager.formatMessage("label.cdna_aligned", seqCount,
-            alignCount));
-  }
-  /**
    * set up menus for the current viewport. This may be called after any
    * operation that affects the data in the current view (selection changed,
    * etc) to update the menus to reflect the new state.
@@ -829,17 +809,17 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   void setMenusFromViewport(AlignViewport av)
   {
     padGapsMenuitem.setSelected(av.isPadGaps());
-    colourTextMenuItem.setSelected(av.showColourText);
+    colourTextMenuItem.setSelected(av.isShowColourText());
     abovePIDThreshold.setSelected(av.getAbovePIDThreshold());
     conservationMenuItem.setSelected(av.getConservationSelected());
     seqLimits.setSelected(av.getShowJVSuffix());
     idRightAlign.setSelected(av.isRightAlignIds());
-    centreColumnLabelsMenuItem.setState(av.centreColumnLabels);
-    renderGapsMenuItem.setSelected(av.renderGaps);
-    wrapMenuItem.setSelected(av.wrapAlignment);
-    scaleAbove.setVisible(av.wrapAlignment);
-    scaleLeft.setVisible(av.wrapAlignment);
-    scaleRight.setVisible(av.wrapAlignment);
+    centreColumnLabelsMenuItem.setState(av.isCentreColumnLabels());
+    renderGapsMenuItem.setSelected(av.isRenderGaps());
+    wrapMenuItem.setSelected(av.getWrapAlignment());
+    scaleAbove.setVisible(av.getWrapAlignment());
+    scaleLeft.setVisible(av.getWrapAlignment());
+    scaleRight.setVisible(av.getWrapAlignment());
     annotationPanelMenuItem.setState(av.isShowAnnotation());
     /*
      * Show/hide annotations only enabled if annotation panel is shown
@@ -848,8 +828,8 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     hideAllSeqAnnotations.setEnabled(annotationPanelMenuItem.getState());
     showAllAlAnnotations.setEnabled(annotationPanelMenuItem.getState());
     hideAllAlAnnotations.setEnabled(annotationPanelMenuItem.getState());
-    viewBoxesMenuItem.setSelected(av.showBoxes);
-    viewTextMenuItem.setSelected(av.showText);
+    viewBoxesMenuItem.setSelected(av.getShowBoxes());
+    viewTextMenuItem.setSelected(av.getShowText());
     showNonconservedMenuItem.setSelected(av.getShowUnconserved());
     showGroupConsensus.setSelected(av.isShowGroupConsensus());
     showGroupConservation.setSelected(av.isShowGroupConservation());
@@ -861,10 +841,10 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
             .getGlobalColourScheme()));
 
     showSeqFeatures.setSelected(av.isShowSequenceFeatures());
-    hiddenMarkers.setState(av.showHiddenMarkers);
+    hiddenMarkers.setState(av.getShowHiddenMarkers());
     applyToAllGroups.setState(av.getColourAppliesToAllGroups());
-    showNpFeatsMenuitem.setSelected(av.isShowNpFeats());
-    showDbRefsMenuitem.setSelected(av.isShowDbRefs());
+    showNpFeatsMenuitem.setSelected(av.isShowNPFeats());
+    showDbRefsMenuitem.setSelected(av.isShowDBRefs());
     autoCalculate.setSelected(av.autoCalculateConsensus);
     sortByTree.setSelected(av.sortByTree);
     listenToViewSelections.setSelected(av.followSelection);
@@ -2329,15 +2309,9 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
       return;
     }
 
-    List<SequenceI> seqs = new ArrayList<SequenceI>(sg.getSize());
-    SequenceI seq;
-    for (int i = 0; i < sg.getSize(); i++)
-    {
-      seq = sg.getSequenceAt(i);
-      seqs.add(seq);
-    }
-
-    // If the cut affects all sequences, warn, remove highlighted columns
+    /*
+     * If the cut affects all sequences, warn, remove highlighted columns
+     */
     if (sg.getSize() == viewport.getAlignment().getHeight())
     {
       int confirm = JOptionPane.showConfirmDialog(this,
@@ -2354,15 +2328,9 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
               sg.getEndRes() + 1);
     }
 
-    SequenceI[] cut = new SequenceI[seqs.size()];
-    for (int i = 0; i < seqs.size(); i++)
-    {
-      cut[i] = seqs.get(i);
-    }
+    SequenceI[] cut = sg.getSequences()
+            .toArray(new SequenceI[sg.getSize()]);
 
-    /*
-     * //ADD HISTORY ITEM
-     */
     addHistoryItem(new EditCommand(
             MessageManager.getString("label.cut_sequences"), Action.CUT,
             cut, sg.getStartRes(), sg.getEndRes() - sg.getStartRes() + 1,
@@ -2721,7 +2689,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
       newap.av.getAlignment().deleteAllAnnotations(false);
     }
 
-    newap.av.gatherViewsHere = false;
+    newap.av.setGatherViewsHere(false);
 
     if (viewport.viewName == null)
     {
@@ -2744,7 +2712,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
 
     if (alignPanels.size() == 2)
     {
-      viewport.gatherViewsHere = true;
+      viewport.setGatherViewsHere(true);
     }
     tabbedPane.setSelectedIndex(tabbedPane.getTabCount() - 1);
     return newap;
@@ -2865,7 +2833,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   @Override
   public void centreColumnLabels_actionPerformed(ActionEvent e)
   {
-    viewport.centreColumnLabels = centreColumnLabelsMenuItem.getState();
+    viewport.setCentreColumnLabels(centreColumnLabelsMenuItem.getState());
     alignPanel.paintAlignment(true);
   }
 
@@ -2877,6 +2845,10 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   @Override
   protected void followHighlight_actionPerformed()
   {
+    /*
+     * Set the 'follow' flag on the Viewport (and scroll to position if now
+     * true).
+     */
     if (viewport.followHighlight = this.followHighlightMenuItem.getState())
     {
       alignPanel.scrollToPosition(
@@ -2910,7 +2882,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     scaleLeft.setVisible(wrapMenuItem.isSelected());
     scaleRight.setVisible(wrapMenuItem.isSelected());
     viewport.setWrapAlignment(wrapMenuItem.isSelected());
-    alignPanel.setWrapAlignment(wrapMenuItem.isSelected());
+    alignPanel.updateLayout();
   }
 
   @Override
@@ -2930,7 +2902,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   public void hideSelSequences_actionPerformed(ActionEvent e)
   {
     viewport.hideAllSelectedSeqs();
-    alignPanel.paintAlignment(true);
+//    alignPanel.paintAlignment(true);
   }
 
   /**
@@ -3214,11 +3186,11 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   {
     final boolean setVisible = annotationPanelMenuItem.isSelected();
     viewport.setShowAnnotation(setVisible);
-    alignPanel.setAnnotationVisible(setVisible);
     this.showAllSeqAnnotations.setEnabled(setVisible);
     this.hideAllSeqAnnotations.setEnabled(setVisible);
     this.showAllAlAnnotations.setEnabled(setVisible);
     this.hideAllAlAnnotations.setEnabled(setVisible);
+    alignPanel.updateLayout();
   }
 
   @Override
@@ -3460,11 +3432,11 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
       {
         threshold = SliderPanel.setPIDSliderSource(alignPanel, cs,
                 "Background");
-        cs.setThreshold(threshold, viewport.getIgnoreGapsConsensus());
+        cs.setThreshold(threshold, viewport.isIgnoreGapsConsensus());
       }
       else
       {
-        cs.setThreshold(0, viewport.getIgnoreGapsConsensus());
+        cs.setThreshold(0, viewport.isIgnoreGapsConsensus());
       }
 
       if (viewport.getConservationSelected())
@@ -3527,7 +3499,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
                 || cs instanceof PIDColourScheme
                 || cs instanceof Blosum62ColourScheme)
         {
-          sg.cs.setThreshold(threshold, viewport.getIgnoreGapsConsensus());
+          sg.cs.setThreshold(threshold, viewport.isIgnoreGapsConsensus());
 
           sg.cs.setConsensus(AAFrequency.calculate(
                   sg.getSequences(viewport.getHiddenRepSequences()),
@@ -3535,7 +3507,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
         }
         else
         {
-          sg.cs.setThreshold(0, viewport.getIgnoreGapsConsensus());
+          sg.cs.setThreshold(0, viewport.isIgnoreGapsConsensus());
         }
 
         if (viewport.getConservationSelected())
@@ -4753,7 +4725,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
           public void actionPerformed(ActionEvent e)
           {
             // TODO: new thread for this call with vis-delay
-            af.showProductsFor(af.viewport.getSequenceSelection(), ds,
+            af.showProductsFor(af.viewport.getSequenceSelection(),
                     isRegSel, dna, source);
           }
 
@@ -4772,14 +4744,9 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     return showp;
   }
 
-  protected void showProductsFor(SequenceI[] sel, Alignment ds,
-          boolean isRegSel, boolean dna, String source)
+  protected void showProductsFor(final SequenceI[] sel,
+          final boolean isRegSel, final boolean dna, final String source)
   {
-    final boolean fisRegSel = isRegSel;
-    final boolean fdna = dna;
-    final String fsrc = source;
-    final AlignFrame ths = this;
-    final SequenceI[] fsel = sel;
     Runnable foo = new Runnable()
     {
 
@@ -4787,15 +4754,16 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
       public void run()
       {
         final long sttime = System.currentTimeMillis();
-        ths.setProgressBar(MessageManager.formatMessage("status.searching_for_sequences_from", new Object[]{fsrc}), sttime);
+        AlignFrame.this.setProgressBar(MessageManager.formatMessage(
+                "status.searching_for_sequences_from", new Object[]
+                { source }), sttime);
         try
         {
-          Alignment ds = ths.getViewport().getAlignment().getDataset(); // update
-          // our local
-          // dataset
-          // reference
+          // update our local dataset reference
+          Alignment ds = AlignFrame.this.getViewport().getAlignment()
+                  .getDataset();
           Alignment prods = CrossRef
-                  .findXrefSequences(fsel, fdna, fsrc, ds);
+                  .findXrefSequences(sel, dna, source, ds);
           if (prods != null)
           {
             SequenceI[] sprods = new SequenceI[prods.getHeight()];
@@ -4819,16 +4787,38 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
             }
             AlignFrame naf = new AlignFrame(al, DEFAULT_WIDTH,
                     DEFAULT_HEIGHT);
-            String newtitle = "" + ((fdna) ? "Proteins " : "Nucleotides ")
-                    + " for " + ((fisRegSel) ? "selected region of " : "")
+            String newtitle = "" + ((dna) ? "Proteins" : "Nucleotides")
+                    + " for " + ((isRegSel) ? "selected region of " : "")
                     + getTitle();
-            Desktop.addInternalFrame(naf, newtitle, DEFAULT_WIDTH,
-                    DEFAULT_HEIGHT);
+            naf.setTitle(newtitle);
+
+            // remove this flag once confirmed we want a split view
+            boolean asSplitFrame = true;
+            if (asSplitFrame)
+            {
+              AlignFrame copyThis = new AlignFrame(
+                      AlignFrame.this.viewport.getAlignment(),
+                      AlignFrame.DEFAULT_WIDTH, AlignFrame.DEFAULT_HEIGHT);
+              copyThis.setTitle(AlignFrame.this.getTitle());
+              // SplitFrame with dna above, protein below
+              SplitFrame sf = new SplitFrame(dna ? copyThis : naf,
+                      dna ? naf : copyThis);
+              naf.setVisible(true);
+              copyThis.setVisible(true);
+              String linkedTitle = MessageManager
+                      .getString("label.linked_view_title");
+              Desktop.addInternalFrame(sf, linkedTitle, -1, -1);
+            }
+            else
+            {
+              Desktop.addInternalFrame(naf, newtitle, DEFAULT_WIDTH,
+                      DEFAULT_HEIGHT);
+            }
           }
           else
           {
             System.err.println("No Sequences generated for xRef type "
-                    + fsrc);
+                    + source);
           }
         } catch (Exception e)
         {
@@ -4842,7 +4832,10 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
           jalview.bin.Cache.log.error("Error when finding crossreferences",
                   e);
         }
-        ths.setProgressBar(MessageManager.formatMessage("status.finished_searching_for_sequences_from", new Object[]{fsrc}),
+        AlignFrame.this.setProgressBar(MessageManager.formatMessage(
+                "status.finished_searching_for_sequences_from",
+                new Object[]
+                { source }),
                 sttime);
       }
 
@@ -4870,7 +4863,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
 
   /**
    * Construct and display a new frame containing the translation of this
-   * frame's cDNA sequences to their aligned protein (amino acid) equivalents.
+   * frame's DNA sequences to their aligned protein (amino acid) equivalents.
    */
   @Override
   public void showTranslation_actionPerformed(ActionEvent e)
@@ -4906,15 +4899,30 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     else
     {
       AlignFrame af = new AlignFrame(al, DEFAULT_WIDTH, DEFAULT_HEIGHT);
-      Desktop.addInternalFrame(af, MessageManager.formatMessage(
+      af.setFileFormat(this.currentFileFormat);
+      final String newTitle = MessageManager.formatMessage(
               "label.translation_of_params", new Object[]
-              { this.getTitle() }), DEFAULT_WIDTH, DEFAULT_HEIGHT);
-      // enable next line for linked editing
-      // viewport.getStructureSelectionManager().addCommandListener(viewport);
+              { this.getTitle() });
+      af.setTitle(newTitle);
+      final SequenceI[] seqs = viewport.getSelectionGroup() == null ? viewport
+              .getAlignment().getSequencesArray() : viewport
+              .getSelectionAsNewSequence();
+      viewport.openSplitFrame(af, seqs, al.getCodonFrames());
+      // Desktop.addInternalFrame(af, newTitle, DEFAULT_WIDTH, DEFAULT_HEIGHT);
     }
   }
 
   /**
+   * Set the file format
+   * 
+   * @param fileFormat
+   */
+  public void setFileFormat(String fileFormat)
+  {
+    this.currentFileFormat = fileFormat;
+  }
+
+  /**
    * Try to load a features file onto the alignment.
    * 
    * @param file
@@ -5418,7 +5426,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   @Override
   protected void showDbRefs_actionPerformed(ActionEvent e)
   {
-    viewport.setShowDbRefs(showDbRefsMenuitem.isSelected());
+    viewport.setShowDBRefs(showDbRefsMenuitem.isSelected());
   }
 
   /*
@@ -5430,7 +5438,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   @Override
   protected void showNpFeats_actionPerformed(ActionEvent e)
   {
-    viewport.setShowNpFeats(showNpFeatsMenuitem.isSelected());
+    viewport.setShowNPFeats(showNpFeatsMenuitem.isSelected());
   }
 
   /**
@@ -5868,7 +5876,8 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
       throw new Error(MessageManager.getString("error.implementation_error_cannot_show_view_alignment_frame"));
     }
     if (tabbedPane != null
-            & alignPanels.indexOf(alignmentPanel) != tabbedPane
+            && tabbedPane.getTabCount() > 0
+            && alignPanels.indexOf(alignmentPanel) != tabbedPane
                     .getSelectedIndex())
     {
       tabbedPane.setSelectedIndex(alignPanels.indexOf(alignmentPanel));
@@ -5928,9 +5937,9 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
    * Open a new alignment window, with the cDNA associated with this (protein)
    * alignment, aligned as is the protein.
    */
-  @Override
   protected void viewAsCdna_actionPerformed()
   {
+    // TODO no longer a menu action - refactor as required
     final AlignmentI alignment = getViewport().getAlignment();
     Set<AlignedCodonFrame> mappings = alignment.getCodonFrames();
     if (mappings == null)
@@ -5969,7 +5978,21 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     Desktop.addInternalFrame(alignFrame, newtitle,
             AlignFrame.DEFAULT_WIDTH,
             AlignFrame.DEFAULT_HEIGHT);
+  }
 
+  /**
+   * Set visibility of dna/protein complement view (available when shown in a
+   * split frame).
+   * 
+   * @param show
+   */
+  @Override
+  protected void showComplement_actionPerformed(boolean show)
+  {
+    SplitContainerI sf = getSplitViewContainer();
+    if (sf != null) {
+      sf.setComplementVisible(this, show);
+    }
   }
 }