Skip to content
Snippets Groups Projects
JamView.java 40.9 KiB
Newer Older
  • Learn to ignore specific revisions
  • tjc's avatar
    tjc committed
            }
    
        addMouseListener(new PopupListener());
    
    tjc's avatar
    tjc committed
        setFocusable(true);
        requestFocusInWindow();
    
        addFocusListener(new FocusListener()
    
    tjc's avatar
    tjc committed
        {
    
          public void focusGained(FocusEvent fe){}
          public void focusLost(FocusEvent fe){}
    
    tjc's avatar
    tjc committed
        });
    
      }
      
      /**
       * Check to see if this component is contained by the display
       * (FeatureDisplay) component.
       * @return
       */
      private boolean containsComponent(JPanel topPanel, JPanel mainPanel)
      {
        Component[] c = mainPanel.getComponents();
        for(int i=0; i<c.length; i++)
    
          if(c[i].equals(topPanel))
            return true;
        }
        
        return false;
    
      }
      
      public void setVisible(boolean visible)
      {
        super.setVisible(visible);
        mainPanel.setVisible(visible);
    
    tjc's avatar
    tjc committed
      }
      
    
    tjc's avatar
    tjc committed
      private int getBaseAtStartOfView()
      {
        String refName = (String) combo.getSelectedItem();
        int seqLength = seqLengths.get(refName);
        double x = jspView.getViewport().getViewRect().getX();
    
    tjc's avatar
    tjc committed
        return (int) (seqLength * ( x / getWidth())) + 1;
    
    tjc's avatar
    tjc committed
      }
      
      /**
       * Set the panel size based on the number of bases visible
       * and repaint.
       * @param nbasesInView
       */
    
    tjc's avatar
    tjc committed
      private void setZoomLevel(final int nbasesInView)
      {
        this.nbasesInView = nbasesInView;
    
        int start = getBaseAtStartOfView();
    
    tjc's avatar
    tjc committed
    
        System.out.println("setZoomLevel "+start);
        String refName = (String) combo.getSelectedItem();
        int seqLength = seqLengths.get(refName);
        int width = jspView.getViewport().getViewRect().width;
        if(jspView.getVerticalScrollBar() != null)
          width += jspView.getVerticalScrollBar().getWidth();
        
        float pixPerBase = ((float)width)/(float)(nbasesInView); 
        
        if(pixPerBase*2 > ALIGNMENT_PIX_PER_BASE)
        {
          pixPerBase = ALIGNMENT_PIX_PER_BASE;
          checkBoxSingle.setVisible(false);
          jspView.getVerticalScrollBar().setValue(0);
          jspView.setColumnHeaderView(ruler);
          showBaseAlignment = true;
        }
        else if(jspView != null)
        {
          checkBoxSingle.setVisible(true);
          jspView.setColumnHeaderView(null);
          showBaseAlignment = false;
        }
        
        Dimension d = new Dimension();
        d.setSize((seqLength*pixPerBase), 800.d);
        setPreferredSize(d);
    
    tjc's avatar
    tjc committed
        revalidate();
    
    tjc's avatar
    tjc committed
    
    
    tjc's avatar
    tjc committed
        repaint();
    
    tjc's avatar
    tjc committed
      }
      
      /**
       * Set the ViewPort so it starts at the given base position.
       * @param base
       */
    
    tjc's avatar
    tjc committed
      private void goToBasePosition(int base)
    
    tjc's avatar
    tjc committed
      {
        Point p = jspView.getViewport().getViewPosition();
    
    tjc's avatar
    tjc committed
        String refName = (String) combo.getSelectedItem();
        int seqLength = seqLengths.get(refName);
    
    tjc's avatar
    tjc committed
        
        int width = getPreferredSize().width;
        
        p.x = Math.round((float)width*((float)(base-1)/(float)seqLength));
    
    tjc's avatar
    tjc committed
        jspView.getViewport().setViewPosition(p);
      }
    
    tjc's avatar
    tjc committed
      /**
    
       * Set the start and end base positions to display.
       * @param start
       * @param end
       * @param event
    
    tjc's avatar
    tjc committed
       */
    
      public void setDisplay(int start,
                             int end,
                             DisplayAdjustmentEvent event)
    
    tjc's avatar
    tjc committed
      {
    
        this.startBase = start;
        this.endBase   = end;
        
    
    tjc's avatar
    tjc committed
        String refName = (String) combo.getSelectedItem();
        int seqLength = seqLengths.get(refName);
    
    
        double pixPerBase = getPixPerBase(start, end);
        if(pixPerBase*2 > ALIGNMENT_PIX_PER_BASE)
    
    tjc's avatar
    tjc committed
        {
    
    tjc's avatar
    tjc committed
          pixPerBase = ALIGNMENT_PIX_PER_BASE;
    
    tjc's avatar
    tjc committed
          checkBoxSingle.setVisible(false);
    
    tjc's avatar
    tjc committed
          jspView.getVerticalScrollBar().setValue(0);
    
    tjc's avatar
    tjc committed
          jspView.setColumnHeaderView(ruler);
    
          showBaseAlignment = true;
    
    tjc's avatar
    tjc committed
        }
    
    tjc's avatar
    tjc committed
        else if(jspView != null)
    
    tjc's avatar
    tjc committed
        {
          checkBoxSingle.setVisible(true);
    
    tjc's avatar
    tjc committed
          jspView.setColumnHeaderView(null);
    
          showBaseAlignment = false;
    
    tjc's avatar
    tjc committed
        }
    
    tjc's avatar
    tjc committed
        Dimension d = new Dimension();
        d.setSize((seqLength*pixPerBase), 800.d);
        setPreferredSize(d);
    
        goToBasePosition(startBase);
        
    
    tjc's avatar
    tjc committed
        if(event == null)
        {
          this.startBase = -1;
          this.endBase   = -1;
        }
    
      }
      
      private double getPixPerBase(int start, int end)
      {
        if(feature_display == null)
          return 1000.d/(double)(end-start+1);
        else
          return feature_display.getWidth()/(double)(end-start+1);
    
    tjc's avatar
    tjc committed
      }
    
    tjc's avatar
    tjc committed
    
    
    tjc's avatar
    tjc committed
      /**
       * Return an Artemis entry from a file 
       * @param entryFileName
       * @param entryGroup
       * @return
       * @throws NoSequenceException
       */
      private Entry getEntry(final String entryFileName, final EntryGroup entryGroup) 
                       throws NoSequenceException
      {
        final Document entry_document = DocumentFactory.makeDocument(entryFileName);
        final EntryInformation artemis_entry_information =
          Options.getArtemisEntryInformation();
        
        System.out.println(entryFileName);
        final uk.ac.sanger.artemis.io.Entry new_embl_entry =
          EntryFileDialog.getEntryFromFile(null, entry_document,
                                           artemis_entry_information,
                                           false);
    
        if(new_embl_entry == null)  // the read failed
          return null;
    
        Entry entry = null;
        try
        {
          if(entryGroup.getSequenceEntry() != null)
            bases = entryGroup.getSequenceEntry().getBases();
    
    tjc's avatar
    tjc committed
          
    
    tjc's avatar
    tjc committed
          if(bases == null)
    
    tjc's avatar
    tjc committed
          {
    
    tjc's avatar
    tjc committed
            entry = new Entry(new_embl_entry);
    
    tjc's avatar
    tjc committed
            bases = entry.getBases();
          }
    
    tjc's avatar
    tjc committed
          else
            entry = new Entry(bases,new_embl_entry);
          
          entryGroup.add(entry);
        } 
        catch(OutOfRangeException e) 
        {
          new MessageDialog(null, "read failed: one of the features in " +
              entryFileName + " has an out of range " +
                            "location: " + e.getMessage());
        }
        return entry;
      }
    
      
      private boolean isShowScale()
      {
        return showScale;
      }
    
      public void setShowScale(boolean showScale)
      {
        this.showScale = showScale;
      }
      
      public JScrollPane getJspView()
      {
        return jspView;
      }
      
      public void setBases(Bases bases)
      {
        this.bases = bases;
      }
      
      /**
       * Remove JScrollPane border
       */
      public void removeBorder()
      {
        Border empty = new EmptyBorder(0,0,0,0);
        jspView.setBorder(empty);
      }
      
      /**
       *  Handle a mouse drag event on the drawing canvas.
       **/
    
      private void handleCanvasMouseDragOrClick(final MouseEvent event)
    
        if(!showBaseAlignment || event.isShiftDown()) 
    
    tjc's avatar
    tjc committed
    
    
        String refName = (String) combo.getSelectedItem();
        int seqLength = seqLengths.get(refName);
    
        float pixPerBase = ((float)getWidth())/(float)(seqLength);    
        int start = (int) Math.round(event.getPoint().getX()/pixPerBase);
        if(start < 1)
          start = 1;
        if(start > seqLength)
          start = seqLength;
    
        MarkerRange drag_range;
        try
    
          drag_range = new MarkerRange (bases.getForwardStrand(), start, start);
          getSelection().setMarkerRange(drag_range);
          repaint();
    
        catch (OutOfRangeException e)
    
          e.printStackTrace();
    
        }
      }
      
      private Selection getSelection()
      {
        return selection;
      }
      
    
    tjc's avatar
    tjc committed
      private class Ruler extends JPanel
    
    tjc's avatar
    tjc committed
      {
    
    tjc's avatar
    tjc committed
        private static final long serialVersionUID = 1L;
    
    tjc's avatar
    tjc committed
        int start;
        int end;
    
    tjc's avatar
    tjc committed
    
    
    tjc's avatar
    tjc committed
        public Ruler()
        {
          super();
          setPreferredSize(new Dimension(getPreferredSize().width, 15));
          setBackground(Color.white);
          setFont(getFont().deriveFont(11.f));
        }
    
    tjc's avatar
    tjc committed
    
    
    tjc's avatar
    tjc committed
        public void paintComponent(Graphics g)
        {
          super.paintComponent(g);
          Graphics2D g2 = (Graphics2D)g;
          drawBaseScale(g2, start, end, 12);
        }
    
    tjc's avatar
    tjc committed
    
        private void drawBaseScale(Graphics2D g2, int start, int end, int ypos)
        {
          int startMark = (((int)(start/10))*10)+1;
    
          for(int i=startMark; i<end; i+=10)
          {
            int xpos = (i-1-start)*ALIGNMENT_PIX_PER_BASE;
            g2.drawString(Integer.toString(i), xpos, ypos);
            
            xpos+=(ALIGNMENT_PIX_PER_BASE/2);
            g2.drawLine(xpos, ypos+1, xpos, ypos+5);
          }
        }
    
    tjc's avatar
    tjc committed
      }
      
    
      /**
      * Popup menu listener
      */
      class PopupListener extends MouseAdapter
      {
        public void mouseClicked(MouseEvent e)
        {
          JamView.this.requestFocus();
    
          handleCanvasMouseDragOrClick(e);
    
        }
        
        public void mousePressed(MouseEvent e)
        {
          maybeShowPopup(e);
        }
    
        public void mouseReleased(MouseEvent e)
        {
          maybeShowPopup(e);
        }
    
        private void maybeShowPopup(MouseEvent e)
        {
          if(e.isPopupTrigger())
            popup.show(e.getComponent(),
                    e.getX(), e.getY());
        }
      }
     
      
    
    tjc's avatar
    tjc committed
      class SAMRecordComparator implements Comparator<Object>
    
    tjc's avatar
    tjc committed
      {
        public int compare(Object o1, Object o2) 
        {
    
    tjc's avatar
    tjc committed
          SAMRecord pr1 = (SAMRecord) o1;
          SAMRecord pr2 = (SAMRecord) o2;
    
    tjc's avatar
    tjc committed
          
    
    tjc's avatar
    tjc committed
          int cmp = pr1.getReadName().compareTo(pr2.getReadName());
          
          if(cmp == 0)
          {
            if(pr1.getAlignmentStart() < pr2.getAlignmentStart())
              return -1;
            else
              return 1;
          }
          return cmp;
    
    tjc's avatar
    tjc committed
        }
      }
    
    tjc's avatar
    tjc committed
    
    
    tjc's avatar
    tjc committed
    
    
    tjc's avatar
    tjc committed
      public Dimension getPreferredScrollableViewportSize()
      {
        return getPreferredSize();
      }
    
      public int getScrollableBlockIncrement(Rectangle visibleRect,
          int orientation, int direction)
      {
        if (orientation == SwingConstants.HORIZONTAL)
          return visibleRect.width - maxUnitIncrement;
        else 
          return visibleRect.height - maxUnitIncrement;
      }
    
      public boolean getScrollableTracksViewportHeight()
      {
        return false;
      }
    
      public boolean getScrollableTracksViewportWidth()
      {
        return false;
      }
    
      public int getScrollableUnitIncrement(Rectangle visibleRect, int orientation,
                                            int direction)
      {
      //Get the current position.
        int currentPosition = 0;
        if (orientation == SwingConstants.HORIZONTAL) 
            currentPosition = visibleRect.x;
        else 
            currentPosition = visibleRect.y;
    
        //Return the number of pixels between currentPosition
        //and the nearest tick mark in the indicated direction.
        if (direction < 0)
        {
          int newPosition = currentPosition -
                            (currentPosition / maxUnitIncrement)
                             * maxUnitIncrement;
          return (newPosition == 0) ? maxUnitIncrement : newPosition;
        } 
        else 
        {
          return ((currentPosition / maxUnitIncrement) + 1)
                  * maxUnitIncrement
                  - currentPosition;
        }
      }
    
    tjc's avatar
    tjc committed
      
    
      /**
       * Artemis event notification
       */
      public void displayAdjustmentValueChanged(DisplayAdjustmentEvent event)
      {
    
    tjc's avatar
    tjc committed
        if(event.getType() == DisplayAdjustmentEvent.SCALE_ADJUST_EVENT)
        {
          this.nbasesInView = event.getWidthInBases();
          setDisplay(event.getStart(), event.getEnd(), event);
    
    tjc's avatar
    tjc committed
          revalidate();
    
    tjc's avatar
    tjc committed
        }
        else
        {
          setDisplay(event.getStart(), event.getEnd(), event);
        }
    
    tjc's avatar
    tjc committed
      public static void main(String[] args)
      {
        String bam = args[0];
    
    tjc's avatar
    tjc committed
        int nbasesInView = 1000;
    
    tjc's avatar
    tjc committed
        String reference = null;
        
    
    tjc's avatar
    tjc committed
        for(int i=0;i<args.length; i++)
        {
          if(args[i].equals("-a"))
            bam = args[++i];
          else if(args[i].equals("-r"))
            reference = args[++i];
          else if(args[i].equals("-v"))
            nbasesInView = Integer.parseInt(args[++i]);
          else if(args[i].equals("-s"))
            System.setProperty("samtoolDir", args[++i]);
          else if(args[i].startsWith("-h"))
          { 
            System.out.println("-h\t show help");
            
            System.out.println("-a\t BAM/SAM file to display");
            System.out.println("-r\t reference file (optional)");
            System.out.println("-v\t number of bases to display in the view (optional)");
            System.out.println("-s\t samtool directory");
    
            System.exit(0);
          }
        }
    
    
    tjc's avatar
    tjc committed
        final JamView view = new JamView(bam, reference, nbasesInView);
    
    tjc's avatar
    tjc committed
        JFrame frame = new JFrame("JAM");
    
    tjc's avatar
    tjc committed
        
        frame.addWindowFocusListener(new WindowFocusListener()
        {
          public void windowGainedFocus(WindowEvent e)
          {
            view.requestFocus();
          }
          public void windowLostFocus(WindowEvent e){}
        });
        
    
        view.addJamToPanel((JPanel)frame.getContentPane(), false, null);
    
    tjc's avatar
    tjc committed
        frame.pack();
    
    tjc's avatar
    tjc committed
        view.jspView.getVerticalScrollBar().setValue(
            view.jspView.getVerticalScrollBar().getMaximum());
    
        frame.setVisible(true);
    
    tjc's avatar
    tjc committed
      }
    
    
      public void selectionChanged(SelectionChangeEvent event)
      {
        repaint();
      }
    
    tjc's avatar
    tjc committed
    }