2 * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$)
3 * Copyright (C) $$Year-Rel$$ The Jalview Authors
5 * This file is part of Jalview.
7 * Jalview is free software: you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation, either version 3
10 * of the License, or (at your option) any later version.
12 * Jalview is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty
14 * of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with Jalview. If not, see <http://www.gnu.org/licenses/>.
19 * The Jalview Authors are detailed in the 'AUTHORS' file.
21 package jalview.appletgui;
23 import jalview.analysis.AnnotationSorter;
24 import jalview.api.AlignViewportI;
25 import jalview.api.AlignmentViewPanel;
26 import jalview.bin.JalviewLite;
27 import jalview.datamodel.AlignmentI;
28 import jalview.datamodel.SearchResultsI;
29 import jalview.datamodel.SequenceI;
30 import jalview.structure.StructureSelectionManager;
31 import jalview.viewmodel.ViewportListenerI;
32 import jalview.viewmodel.ViewportRanges;
34 import java.awt.BorderLayout;
35 import java.awt.Color;
36 import java.awt.Dimension;
37 import java.awt.FontMetrics;
38 import java.awt.Frame;
39 import java.awt.Graphics;
40 import java.awt.Panel;
41 import java.awt.Scrollbar;
42 import java.awt.event.AdjustmentEvent;
43 import java.awt.event.AdjustmentListener;
44 import java.awt.event.ComponentAdapter;
45 import java.awt.event.ComponentEvent;
46 import java.awt.image.BufferedImage;
47 import java.beans.PropertyChangeEvent;
48 import java.util.List;
50 @SuppressWarnings("serial")
51 public class AlignmentPanel extends Panel
52 implements AdjustmentListener, AlignmentViewPanel, ViewportListenerI
55 public AlignViewport av;
57 OverviewPanel overviewPanel;
63 IdwidthAdjuster idwidthAdjuster;
65 public AlignFrame alignFrame;
67 ScalePanel scalePanel;
69 AnnotationPanel annotationPanel;
71 AnnotationLabels alabels;
73 ViewportRanges vpRanges;
75 // this value is set false when selection area being dragged
76 boolean fastPaint = true;
78 public AlignmentPanel(AlignFrame af, final AlignViewport av)
90 vpRanges = av.getRanges();
91 seqPanel = new SeqPanel(av, this);
92 idPanel = new IdPanel(av, this);
93 scalePanel = new ScalePanel(av, this);
94 idwidthAdjuster = new IdwidthAdjuster(this);
95 annotationPanel = new AnnotationPanel(this);
96 annotationPanelHolder.add(annotationPanel, BorderLayout.CENTER);
98 sequenceHolderPanel.add(annotationPanelHolder, BorderLayout.SOUTH);
99 alabels = new AnnotationLabels(this);
101 setAnnotationVisible(av.isShowAnnotation());
103 idPanelHolder.add(idPanel, BorderLayout.CENTER);
104 idSpaceFillerPanel1.add(idwidthAdjuster, BorderLayout.CENTER);
105 annotationSpaceFillerHolder.add(alabels, BorderLayout.CENTER);
106 scalePanelHolder.add(scalePanel, BorderLayout.CENTER);
107 seqPanelHolder.add(seqPanel, BorderLayout.CENTER);
110 setScrollValues(0, 0);
112 apvscroll.addAdjustmentListener(this);
113 hscroll.addAdjustmentListener(this);
114 vscroll.addAdjustmentListener(this);
116 addComponentListener(new ComponentAdapter()
119 public void componentResized(ComponentEvent evt)
121 // reset the viewport ranges when the alignment panel is resized
122 // in particular, this initialises the end residue value when Jalview
124 if (av.getWrapAlignment())
126 int widthInRes = seqPanel.seqCanvas
127 .getWrappedCanvasWidth(seqPanel.seqCanvas.getWidth());
128 vpRanges.setViewportWidth(widthInRes);
132 int widthInRes = seqPanel.seqCanvas.getWidth()
134 int heightInSeq = seqPanel.seqCanvas.getHeight()
135 / av.getCharHeight();
137 vpRanges.setViewportWidth(widthInRes);
138 vpRanges.setViewportHeight(heightInSeq);
140 // setScrollValues(vpRanges.getStartRes(), vpRanges.getStartSeq());
141 if (getSize().height > 0
142 && annotationPanelHolder.getSize().height > 0)
144 validateAnnotationDimensions(false);
151 Dimension d = calculateIdWidth();
152 idPanel.idCanvas.setSize(d);
154 hscrollFillerPanel.setSize(d.width, annotationPanel.getSize().height);
156 idPanel.idCanvas.setSize(d.width, seqPanel.seqCanvas.getSize().height);
157 annotationSpaceFillerHolder.setSize(d.width,
158 annotationPanel.getSize().height);
159 alabels.setSize(d.width, annotationPanel.getSize().height);
160 final AlignmentPanel ap = this;
161 av.addPropertyChangeListener(new java.beans.PropertyChangeListener()
164 public void propertyChange(java.beans.PropertyChangeEvent evt)
166 if (evt.getPropertyName().equals("alignment"))
168 PaintRefresher.Refresh(ap, av.getSequenceSetId(), true, true);
173 av.getRanges().addPropertyChangeListener(this);
177 public AlignViewportI getAlignViewport()
183 public SequenceRenderer getSequenceRenderer()
185 return seqPanel.seqCanvas.sr;
189 public jalview.api.FeatureRenderer getFeatureRenderer()
191 return seqPanel.seqCanvas.fr;
195 public jalview.api.FeatureRenderer cloneFeatureRenderer()
197 FeatureRenderer nfr = new FeatureRenderer(av);
198 nfr.transferSettings(seqPanel.seqCanvas.fr);
202 public void alignmentChanged()
204 av.alignmentChanged(this);
206 if (overviewPanel != null)
208 overviewPanel.updateOverviewImage();
211 alignFrame.updateEditMenuBar();
216 public void fontChanged()
218 // set idCanvas bufferedImage to null
219 // to prevent drawing old image
220 idPanel.idCanvas.image = null;
221 FontMetrics fm = getFontMetrics(av.getFont());
224 new Dimension(10, av.getCharHeight() + fm.getDescent()));
225 idwidthAdjuster.setSize(
226 new Dimension(10, av.getCharHeight() + fm.getDescent()));
227 av.updateSequenceIdColours();
228 annotationPanel.image = null;
229 int ap = annotationPanel.adjustPanelHeight(false);
230 Dimension d = calculateIdWidth();
231 d.setSize(d.width + 4, seqPanel.seqCanvas.getSize().height);
232 alabels.setSize(d.width + 4, ap);
234 idPanel.idCanvas.setSize(d);
235 hscrollFillerPanel.setSize(d);
237 validateAnnotationDimensions(false);
238 annotationPanel.repaint();
243 public void setIdWidth(int w, int h)
245 idPanel.idCanvas.setSize(w, h);
246 idPanelHolder.setSize(w, idPanelHolder.getSize().height);
247 annotationSpaceFillerHolder.setSize(w,
248 annotationSpaceFillerHolder.getSize().height);
249 alabels.setSize(w, alabels.getSize().height);
253 Dimension calculateIdWidth()
255 if (av.nullFrame == null)
257 av.nullFrame = new Frame();
258 av.nullFrame.addNotify();
261 Graphics g = av.nullFrame.getGraphics();
263 FontMetrics fm = g.getFontMetrics(av.font);
264 AlignmentI al = av.getAlignment();
269 while (i < al.getHeight() && al.getSequenceAt(i) != null)
271 SequenceI s = al.getSequenceAt(i);
272 id = s.getDisplayId(av.getShowJVSuffix());
274 if (fm.stringWidth(id) > idWidth)
276 idWidth = fm.stringWidth(id);
281 // Also check annotation label widths
283 if (al.getAlignmentAnnotation() != null)
285 fm = g.getFontMetrics(av.nullFrame.getFont());
286 while (i < al.getAlignmentAnnotation().length)
288 String label = al.getAlignmentAnnotation()[i].label;
289 if (fm.stringWidth(label) > idWidth)
291 idWidth = fm.stringWidth(label);
297 return new Dimension(idWidth, idPanel.idCanvas.getSize().height);
301 * Highlight the given results on the alignment.
304 public void highlightSearchResults(SearchResultsI results)
306 scrollToPosition(results);
307 seqPanel.seqCanvas.highlightSearchResults(results);
311 * scroll the view to show the position of the highlighted region in results
312 * (if any) and redraw the overview
315 * @return false if results were not found
317 public boolean scrollToPosition(SearchResultsI results)
319 return scrollToPosition(results, true);
323 * scroll the view to show the position of the highlighted region in results
327 * @param redrawOverview
328 * - when set, the overview will be recalculated (takes longer)
329 * @return false if results were not found
331 public boolean scrollToPosition(SearchResultsI results,
332 boolean redrawOverview)
334 return scrollToPosition(results, 0, redrawOverview, false);
338 * scroll the view to show the position of the highlighted region in results
342 * @param redrawOverview
343 * - when set, the overview will be recalculated (takes longer)
344 * @return false if results were not found
346 public boolean scrollToPosition(SearchResultsI results,
347 int verticalOffset, boolean redrawOverview, boolean centre)
349 // do we need to scroll the panel?
350 if (results != null && results.getSize() > 0)
352 AlignmentI alignment = av.getAlignment();
353 int seqIndex = alignment.findIndex(results);
359 * allow for offset of target sequence (actually scroll to one above it)
362 SequenceI seq = alignment.getSequenceAt(seqIndex);
363 int[] r = results.getResults(seq, 0, alignment.getWidth());
366 if (JalviewLite.debug)
369 "DEBUG: scroll didn't happen - results not within alignment : "
370 + seq.getStart() + "," + seq.getEnd());
374 if (JalviewLite.debug)
378 * System.out.println("DEBUG: scroll: start=" + r[0] +
379 * " av.getStartRes()=" + av.getStartRes() + " end=" + r[1] +
380 * " seq.end=" + seq.getEnd() + " av.getEndRes()=" + av.getEndRes() +
381 * " hextent=" + hextent);
388 * To centre results, scroll to positions half the visible width
389 * left/right of the start/end positions
393 int offset = (vpRanges.getEndRes() - vpRanges.getStartRes() + 1) / 2
395 start = Math.max(start - offset, 0);
396 end = end + offset - 1;
397 // end = Math.min(end + offset, seq.getEnd() - 1);
404 if (end == seq.getEnd())
410 * allow for offset of target sequence (actually scroll to one above it)
412 seqIndex = Math.max(0, seqIndex - verticalOffset);
413 return scrollTo(start, end, seqIndex, false, redrawOverview);
418 public boolean scrollTo(int ostart, int end, int seqIndex,
419 boolean scrollToNearest, boolean redrawOverview)
421 int startv, endv, starts, ends;//, width;
424 if (av.hasHiddenColumns())
426 AlignmentI al = av.getAlignment();
427 start = al.getHiddenColumns().absoluteToVisibleColumn(ostart);
428 end = al.getHiddenColumns().absoluteToVisibleColumn(end);
431 if (!scrollToNearest && !al.getHiddenColumns().isVisible(ostart))
433 // don't scroll - position isn't visible
443 if (!av.getWrapAlignment())
446 * int spos=av.getStartRes(),sqpos=av.getStartSeq(); if ((startv =
447 * av.getStartRes()) >= start) { spos=start-1; // seqIn //
448 * setScrollValues(start - 1, seqIndex); } else if ((endv =
449 * av.getEndRes()) <= end) { // setScrollValues(spos=startv + 1 + end -
450 * endv, seqIndex); spos=startv + 1 + end - endv; } else if ((starts =
451 * av.getStartSeq()) > seqIndex) { setScrollValues(av.getStartRes(),
452 * seqIndex); } else if ((ends = av.getEndSeq()) <= seqIndex) {
453 * setScrollValues(av.getStartRes(), starts + seqIndex - ends + 1); }
456 // below is scrolling logic up to Jalview 2.8.2
457 // if ((av.getStartRes() > end)
458 // || (av.getEndRes() < start)
459 // || ((av.getStartSeq() > seqIndex) || (av.getEndSeq() < seqIndex)))
461 // if (start > av.getAlignment().getWidth() - hextent)
463 // start = av.getAlignment().getWidth() - hextent;
470 // if (seqIndex > av.getAlignment().getHeight() - vextent)
472 // seqIndex = av.getAlignment().getHeight() - vextent;
478 // setScrollValues(start, seqIndex);
480 // logic copied from jalview.gui.AlignmentPanel:
481 if ((startv = vpRanges.getStartRes()) >= start)
484 * Scroll left to make start of search results visible
486 setScrollValues(start - 1, seqIndex);
488 else if ((endv = vpRanges.getEndRes()) <= end)
491 * Scroll right to make end of search results visible
493 setScrollValues(startv + 1 + end - endv, seqIndex);
495 else if ((starts = vpRanges.getStartSeq()) > seqIndex)
498 * Scroll up to make start of search results visible
500 setScrollValues(vpRanges.getStartRes(), seqIndex);
502 else if ((ends = vpRanges.getEndSeq()) <= seqIndex)
505 * Scroll down to make end of search results visible
507 setScrollValues(vpRanges.getStartRes(),
508 starts + seqIndex - ends + 1);
511 * Else results are already visible - no need to scroll
516 vpRanges.scrollToWrappedVisible(start);
519 paintAlignment(redrawOverview, false);
523 public OverviewPanel getOverviewPanel()
525 return overviewPanel;
528 public void setOverviewPanel(OverviewPanel op)
533 public void setAnnotationVisible(boolean b)
535 if (!av.getWrapAlignment())
537 annotationSpaceFillerHolder.setVisible(b);
538 annotationPanelHolder.setVisible(b);
542 annotationSpaceFillerHolder.setVisible(false);
543 annotationPanelHolder.setVisible(false);
550 * automatically adjust annotation panel height for new annotation whilst
551 * ensuring the alignment is still visible.
554 public void adjustAnnotationHeight()
556 // TODO: display vertical annotation scrollbar if necessary
557 // this is called after loading new annotation onto alignment
558 if (alignFrame.getSize().height == 0)
561 "adjustAnnotationHeight frame size zero NEEDS FIXING");
564 validateAnnotationDimensions(true);
565 apvscroll.addNotify();
568 paintAlignment(true, false);
572 * Calculate the annotation dimensions and refresh slider values accordingly.
573 * Need to do repaints/notifys afterwards.
575 protected void validateAnnotationDimensions(boolean adjustPanelHeight)
577 int rowHeight = av.getCharHeight();
578 int alignmentHeight = rowHeight * av.getAlignment().getHeight();
579 int annotationHeight = av.calcPanelHeight();
581 int mheight = annotationHeight;
582 Dimension d = sequenceHolderPanel.getSize();
584 int availableHeight = d.height - scalePanelHolder.getHeight();
586 if (adjustPanelHeight)
589 * If not enough vertical space, maximize annotation height while keeping
590 * at least two rows of alignment visible
592 if (annotationHeight + alignmentHeight > availableHeight)
594 annotationHeight = Math.min(annotationHeight,
595 availableHeight - 2 * rowHeight);
600 // maintain same window layout whilst updating sliders
601 annotationHeight = annotationPanelHolder.getSize().height;
604 if (availableHeight - annotationHeight < 5)
606 annotationHeight = availableHeight;
609 annotationPanel.setSize(new Dimension(d.width, annotationHeight));
610 annotationPanelHolder.setSize(new Dimension(d.width, annotationHeight));
611 // seqPanelHolder.setSize(d.width, seqandannot - height);
612 seqPanel.seqCanvas.setSize(d.width,
613 seqPanel.seqCanvas.getSize().height);
615 Dimension e = idPanel.getSize();
616 alabels.setSize(new Dimension(e.width, annotationHeight));
617 annotationSpaceFillerHolder
618 .setSize(new Dimension(e.width, annotationHeight));
620 int s = apvscroll.getValue();
621 if (s > mheight - annotationHeight)
625 apvscroll.setValues(s, annotationHeight, 0, mheight);
626 annotationPanel.setScrollOffset(apvscroll.getValue(), false);
627 alabels.setScrollOffset(apvscroll.getValue(), false);
630 public void setWrapAlignment(boolean wrap)
632 vpRanges.setStartEndSeq(0, vpRanges.getVisibleAlignmentHeight());
633 vpRanges.setStartRes(0);
634 scalePanelHolder.setVisible(!wrap);
636 hscroll.setVisible(!wrap);
637 idwidthAdjuster.setVisible(!wrap);
641 annotationPanelHolder.setVisible(false);
642 annotationSpaceFillerHolder.setVisible(false);
644 else if (av.isShowAnnotation())
646 annotationPanelHolder.setVisible(true);
647 annotationSpaceFillerHolder.setVisible(true);
650 idSpaceFillerPanel1.setVisible(!wrap);
652 fontChanged(); // This is so that the scalePanel is resized correctly
655 sequenceHolderPanel.validate();
664 public void setScrollValues(int xpos, int ypos)
669 if (av.getWrapAlignment())
671 setScrollingForWrappedPanel(x);
675 int width = av.getAlignment().getVisibleWidth();
676 int height = av.getAlignment().getHeight();
683 hextent = seqPanel.seqCanvas.getSize().width / av.getCharWidth();
684 vextent = seqPanel.seqCanvas.getSize().height / av.getCharHeight();
691 if (vextent > height)
696 if ((hextent + x) > width)
698 System.err.println("hextent was " + hextent + " and x was " + x);
703 if ((vextent + y) > height)
705 y = height - vextent;
715 System.err.println("x was " + x);
719 hscroll.setValues(x, hextent, 0, width);
720 vscroll.setValues(y, vextent, 0, height);
722 // AWT scrollbar does not fire adjustmentValueChanged for setValues
723 // so also call adjustment code!
732 * Respond to adjustment event when horizontal or vertical scrollbar is
736 * adjustment event encoding whether apvscroll, hscroll or vscroll
740 public void adjustmentValueChanged(AdjustmentEvent evt)
742 // Note that this event is NOT fired by the AWT scrollbar when setValues is
743 // called. Instead manually call adjustHorizontal and adjustVertical
745 if (evt == null || evt.getSource() == apvscroll)
747 annotationPanel.setScrollOffset(apvscroll.getValue(), false);
748 alabels.setScrollOffset(apvscroll.getValue(), false);
750 if (evt == null || evt.getSource() == hscroll)
752 int x = hscroll.getValue();
756 if (evt == null || evt.getSource() == vscroll)
758 int offy = vscroll.getValue();
759 adjustVertical(offy);
764 private void adjustHorizontal(int x)
766 int oldX = vpRanges.getStartRes();
767 int oldwidth = vpRanges.getViewportWidth();
768 int width = seqPanel.seqCanvas.getWidth() / av.getCharWidth();
770 // if we're scrolling to the position we're already at, stop
771 // this prevents infinite recursion of events when the scroll/viewport
772 // ranges values are the same
773 if ((x == oldX) && (width == oldwidth))
777 vpRanges.setViewportStartAndWidth(x, width);
779 if (av.getWrapAlignment() || !fastPaint)
786 private void adjustVertical(int newY)
788 if (av.getWrapAlignment())
791 * if we're scrolling to the position we're already at, stop
792 * this prevents infinite recursion of events when the scroll/viewport
793 * ranges values are the same
795 int oldX = vpRanges.getStartRes();
796 int oldY = vpRanges.getWrappedScrollPosition(oldX);
804 * limit page up/down to one width's worth of positions
806 int rowSize = vpRanges.getViewportWidth();
807 int newX = newY > oldY ? oldX + rowSize : oldX - rowSize;
808 vpRanges.setViewportStartAndWidth(Math.max(0, newX), rowSize);
813 int height = seqPanel.seqCanvas.getHeight() / av.getCharHeight();
814 int oldY = vpRanges.getStartSeq();
815 int oldheight = vpRanges.getViewportHeight();
817 // if we're scrolling to the position we're already at, stop
818 // this prevents infinite recursion of events when the scroll/viewport
819 // ranges values are the same
820 if ((newY == oldY) && (height == oldheight))
824 vpRanges.setViewportStartAndHeight(newY, height);
826 if (av.getWrapAlignment() || !fastPaint)
834 * A helper method to return the AlignmentPanel in the other (complementary)
835 * half of a SplitFrame view. Returns null if not in a SplitFrame.
839 private AlignmentPanel getComplementPanel()
841 AlignmentPanel ap = null;
842 if (alignFrame != null)
844 SplitFrame sf = alignFrame.getSplitFrame();
847 AlignFrame other = sf.getComplement(alignFrame);
850 ap = other.alignPanel;
858 * Follow a scrolling change in the (cDNA/Protein) complementary alignment.
859 * The aim is to keep the two alignments 'lined up' on their centre columns.
862 * holds mapped region(s) of this alignment that we are scrolling
863 * 'to'; may be modified for sequence offset by this method
865 * the number of visible sequences to show above the mapped region
867 protected void scrollToCentre(SearchResultsI sr, int seqOffset)
870 * To avoid jumpy vertical scrolling (if some sequences are gapped or not
871 * mapped), we can make the scroll-to location a sequence above the one
874 SequenceI mappedTo = sr.getResults().get(0).getSequence();
875 List<SequenceI> seqs = av.getAlignment().getSequences();
878 * This is like AlignmentI.findIndex(seq) but here we are matching the
879 * dataset sequence not the aligned sequence
881 boolean matched = false;
882 for (SequenceI seq : seqs)
884 if (mappedTo == seq.getDatasetSequence())
892 return; // failsafe, shouldn't happen
896 * Scroll to position but centring the target residue. Also set a state flag
897 * to prevent adjustmentValueChanged performing this recursively.
899 scrollToPosition(sr, seqOffset, true, true);
902 private void sendViewPosition()
904 StructureSelectionManager.getStructureSelectionManager(av.applet)
905 .sendViewPosition(this, vpRanges.getStartRes(),
906 vpRanges.getEndRes(), vpRanges.getStartSeq(),
907 vpRanges.getEndSeq());
911 * Repaint the alignment and annotations, and, optionally, any overview window
914 public void paintAlignment(boolean updateOverview,
915 boolean updateStructures)
917 final AnnotationSorter sorter = new AnnotationSorter(getAlignment(),
918 av.isShowAutocalculatedAbove());
919 sorter.sort(getAlignment().getAlignmentAnnotation(),
920 av.getSortAnnotationsBy());
923 if (updateStructures)
925 jalview.structure.StructureSelectionManager
926 .getStructureSelectionManager(av.applet)
927 .sequenceColoursChanged(this);
931 if (overviewPanel != null)
933 overviewPanel.updateOverviewImage();
939 public void update(Graphics g)
945 public void paint(Graphics g)
948 Dimension d = idPanel.idCanvas.getSize();
949 final int canvasHeight = seqPanel.seqCanvas.getSize().height;
950 if (canvasHeight != d.height)
952 idPanel.idCanvas.setSize(d.width, canvasHeight);
955 setScrollValues(vpRanges.getStartRes(), vpRanges.getStartSeq());
957 seqPanel.seqCanvas.repaint();
958 idPanel.idCanvas.repaint();
959 if (!av.getWrapAlignment())
961 if (av.isShowAnnotation())
964 annotationPanel.repaint();
966 scalePanel.repaint();
972 * Set vertical scroll bar parameters for wrapped panel
974 * @param topLeftColumn
975 * the column position at top left (0..)
977 private void setScrollingForWrappedPanel(int topLeftColumn)
979 int scrollPosition = vpRanges.getWrappedScrollPosition(topLeftColumn);
980 int maxScroll = vpRanges.getWrappedMaxScroll(topLeftColumn);
983 * a scrollbar's value can be set to at most (maximum-extent)
984 * so we add extent (1) to the maxScroll value
986 vscroll.setUnitIncrement(1);
987 vscroll.setValues(scrollPosition, 1, 0, maxScroll + 1);
990 protected Panel sequenceHolderPanel = new Panel();
992 protected Scrollbar vscroll = new Scrollbar();
994 protected Scrollbar hscroll = new Scrollbar();
996 protected Panel seqPanelHolder = new Panel();
998 protected Panel scalePanelHolder = new Panel();
1000 protected Panel idPanelHolder = new Panel();
1002 protected Panel idSpaceFillerPanel1 = new Panel();
1004 public Panel annotationSpaceFillerHolder = new Panel();
1006 protected Panel hscrollFillerPanel = new Panel();
1008 Panel annotationPanelHolder = new Panel();
1010 protected Scrollbar apvscroll = new Scrollbar();
1013 * Flag set while scrolling to follow complementary cDNA/protein scroll. When
1014 * false, suppresses invoking the same method recursively.
1016 private boolean scrollComplementaryPanel = true;
1018 private void jbInit() throws Exception
1020 // idPanelHolder.setPreferredSize(new Dimension(70, 10));
1021 this.setLayout(new BorderLayout());
1023 // sequenceHolderPanel.setPreferredSize(new Dimension(150, 150));
1024 sequenceHolderPanel.setLayout(new BorderLayout());
1025 seqPanelHolder.setLayout(new BorderLayout());
1026 scalePanelHolder.setBackground(Color.white);
1028 // scalePanelHolder.setPreferredSize(new Dimension(10, 30));
1029 scalePanelHolder.setLayout(new BorderLayout());
1030 idPanelHolder.setLayout(new BorderLayout());
1031 idSpaceFillerPanel1.setBackground(Color.white);
1033 // idSpaceFillerPanel1.setPreferredSize(new Dimension(10, 30));
1034 idSpaceFillerPanel1.setLayout(new BorderLayout());
1035 annotationSpaceFillerHolder.setBackground(Color.white);
1037 // annotationSpaceFillerHolder.setPreferredSize(new Dimension(10, 80));
1038 annotationSpaceFillerHolder.setLayout(new BorderLayout());
1039 hscroll.setOrientation(Scrollbar.HORIZONTAL);
1041 Panel hscrollHolder = new Panel();
1042 hscrollHolder.setLayout(new BorderLayout());
1043 hscrollFillerPanel.setBackground(Color.white);
1044 apvscroll.setOrientation(Scrollbar.VERTICAL);
1045 apvscroll.setVisible(true);
1046 apvscroll.addAdjustmentListener(this);
1048 annotationPanelHolder.setBackground(Color.white);
1049 annotationPanelHolder.setLayout(new BorderLayout());
1050 annotationPanelHolder.add(apvscroll, BorderLayout.EAST);
1051 // hscrollFillerPanel.setPreferredSize(new Dimension(70, 10));
1052 hscrollHolder.setBackground(Color.white);
1054 // annotationScroller.setPreferredSize(new Dimension(10, 80));
1055 // this.setPreferredSize(new Dimension(220, 166));
1056 seqPanelHolder.setBackground(Color.white);
1057 idPanelHolder.setBackground(Color.white);
1058 sequenceHolderPanel.add(scalePanelHolder, BorderLayout.NORTH);
1059 sequenceHolderPanel.add(seqPanelHolder, BorderLayout.CENTER);
1060 seqPanelHolder.add(vscroll, BorderLayout.EAST);
1062 // Panel3.add(secondaryPanelHolder, BorderLayout.SOUTH);
1063 this.add(idPanelHolder, BorderLayout.WEST);
1064 idPanelHolder.add(idSpaceFillerPanel1, BorderLayout.NORTH);
1065 idPanelHolder.add(annotationSpaceFillerHolder, BorderLayout.SOUTH);
1066 this.add(hscrollHolder, BorderLayout.SOUTH);
1067 hscrollHolder.add(hscroll, BorderLayout.CENTER);
1068 hscrollHolder.add(hscrollFillerPanel, BorderLayout.WEST);
1069 this.add(sequenceHolderPanel, BorderLayout.CENTER);
1073 * hides or shows dynamic annotation rows based on groups and av state flags
1075 public void updateAnnotation()
1077 updateAnnotation(false);
1080 public void updateAnnotation(boolean applyGlobalSettings)
1082 updateAnnotation(applyGlobalSettings, false);
1085 public void updateAnnotation(boolean applyGlobalSettings,
1086 boolean preserveNewGroupSettings)
1088 av.updateGroupAnnotationSettings(applyGlobalSettings,
1089 preserveNewGroupSettings);
1090 adjustAnnotationHeight();
1094 public AlignmentI getAlignment()
1096 return av.getAlignment();
1100 public String getViewName()
1106 public StructureSelectionManager getStructureSelectionManager()
1108 return StructureSelectionManager
1109 .getStructureSelectionManager(av.applet);
1113 public void raiseOOMWarning(String string, OutOfMemoryError error)
1116 System.err.println("Out of memory whilst '" + string + "'");
1117 error.printStackTrace();
1121 * Set a flag to say we are scrolling to follow a (cDNA/protein) complement.
1125 protected void setToScrollComplementPanel(boolean b)
1127 this.scrollComplementaryPanel = b;
1131 * Get whether to scroll complement panel
1133 * @return true if cDNA/protein complement panels should be scrolled
1135 protected boolean isSetToScrollComplementPanel()
1137 return this.scrollComplementaryPanel;
1142 * Property change event fired when a change is made to the viewport ranges
1143 * object associated with this alignment panel's viewport
1145 public void propertyChange(PropertyChangeEvent evt)
1147 // update this panel's scroll values based on the new viewport ranges values
1148 int x = vpRanges.getStartRes();
1149 int y = vpRanges.getStartSeq();
1150 setScrollValues(x, y);
1152 // now update any complementary alignment (its viewport ranges object
1153 // is different so does not get automatically updated)
1154 if (isSetToScrollComplementPanel())
1156 setToScrollComplementPanel(false);
1157 av.scrollComplementaryAlignment(getComplementPanel());
1158 setToScrollComplementPanel(true);
1164 public void overviewDone(BufferedImage miniMe)
1166 overviewPanel.canvas.finalizeDraw(miniMe);