X-Git-Url: http://source.jalview.org/gitweb/?a=blobdiff_plain;f=src%2Fjalview%2Fgui%2FSeqCanvas.java;h=7d182b2d5344ecb1ef0803f46ed67b8ab2d9c155;hb=33f8761fdb05b594fd8a3341180256003d3a91df;hp=a4ddbac157bbd053f1e2004bbac7acf87c30c5a2;hpb=e0e94503e960ce917c5d35ce8b7c065a696d0117;p=jalview.git diff --git a/src/jalview/gui/SeqCanvas.java b/src/jalview/gui/SeqCanvas.java index a4ddbac..7d182b2 100755 --- a/src/jalview/gui/SeqCanvas.java +++ b/src/jalview/gui/SeqCanvas.java @@ -295,7 +295,7 @@ public class SeqCanvas extends JComponent implements ViewportListenerI int endSeq = ranges.getEndSeq(); int transX = 0; int transY = 0; - + gg.copyArea(horizontal * charWidth, vertical * charHeight, img.getWidth(), img.getHeight(), -horizontal * charWidth, -vertical * charHeight); @@ -337,7 +337,10 @@ public class SeqCanvas extends JComponent implements ViewportListenerI drawPanel(gg, startRes, endRes, startSeq, endSeq, 0); gg.translate(-transX, -transY); - repaint(); + // Call repaint on alignment panel so that repaints from other alignment + // panel components can be aggregated. Otherwise performance of the + // overview window and others may be adversely affected. + av.getAlignPanel().repaint(); } finally { fastpainting = false; @@ -351,20 +354,20 @@ public class SeqCanvas extends JComponent implements ViewportListenerI int charHeight = av.getCharHeight(); int charWidth = av.getCharWidth(); - + ViewportRanges ranges = av.getRanges(); - + int width = getWidth(); int height = getHeight(); - + width -= (width % charWidth); height -= (height % charHeight); - + // selectImage is the selection group outline image BufferedImage selectImage = drawSelectionGroup( ranges.getStartRes(), ranges.getEndRes(), ranges.getStartSeq(), ranges.getEndSeq()); - + if ((img != null) && (fastPaint || (getVisibleRect().width != g.getClipBounds().width) || (getVisibleRect().height != g.getClipBounds().height))) @@ -388,16 +391,16 @@ public class SeqCanvas extends JComponent implements ViewportListenerI gg = (Graphics2D) img.getGraphics(); gg.setFont(av.getFont()); } - + if (av.antiAlias) { gg.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); } - + gg.setColor(Color.white); gg.fillRect(0, 0, img.getWidth(), img.getHeight()); - + if (av.getWrapAlignment()) { drawWrappedPanel(gg, getWidth(), getHeight(), ranges.getStartRes()); @@ -407,7 +410,7 @@ public class SeqCanvas extends JComponent implements ViewportListenerI drawPanel(gg, ranges.getStartRes(), ranges.getEndRes(), ranges.getStartSeq(), ranges.getEndSeq(), 0); } - + // lcimg is a local *copy* of img which we'll draw selectImage on top of BufferedImage lcimg = buildLocalImage(selectImage); g.drawImage(lcimg, 0, 0, this); @@ -504,8 +507,11 @@ public class SeqCanvas extends JComponent implements ViewportListenerI private BufferedImage buildLocalImage(BufferedImage selectImage) { // clone the cached image - BufferedImage lcimg = new BufferedImage(img.getWidth(), img.getHeight(), - img.getType()); + BufferedImage lcimg = new BufferedImage(img.getWidth(), img.getHeight(), + img.getType()); + + // BufferedImage lcimg = new BufferedImage(img.getWidth(), img.getHeight(), + // img.getType()); Graphics2D g2d = lcimg.createGraphics(); g2d.drawImage(img, 0, 0, null); @@ -545,8 +551,8 @@ public class SeqCanvas extends JComponent implements ViewportListenerI try { - lcimg = new BufferedImage(width, height, - BufferedImage.TYPE_INT_ARGB); // ARGB so alpha compositing works + lcimg = new BufferedImage(width, height, + BufferedImage.TYPE_INT_ARGB); // ARGB so alpha compositing works } catch (OutOfMemoryError er) { System.gc(); @@ -780,8 +786,8 @@ public class SeqCanvas extends JComponent implements ViewportListenerI * white fill the region to be drawn (so incremental fast paint doesn't * scribble over an existing image) */ - gg.setColor(Color.white); - gg.fillRect(0, ypos, (endx - startColumn + 1) * charWidth, + g.setColor(Color.white); + g.fillRect(0, ypos, (endx - startColumn + 1) * charWidth, wrappedRepeatHeightPx); drawPanel(g, startColumn, endx, 0, av.getAlignment().getHeight() - 1, @@ -1137,16 +1143,16 @@ public class SeqCanvas extends JComponent implements ViewportListenerI if (av.hasSearchResults()) { SearchResultsI searchResults = av.getSearchResults(); - int[] visibleResults = searchResults.getResults(nextSeq, - startRes, endRes); + int[] visibleResults = searchResults.getResults(nextSeq, startRes, + endRes); if (visibleResults != null) { for (int r = 0; r < visibleResults.length; r += 2) { seqRdr.drawHighlightedText(nextSeq, visibleResults[r], - visibleResults[r + 1], (visibleResults[r] - startRes) - * charWidth, offset - + ((i - startSeq) * charHeight)); + visibleResults[r + 1], + (visibleResults[r] - startRes) * charWidth, + offset + ((i - startSeq) * charHeight)); } } } @@ -1429,9 +1435,8 @@ public class SeqCanvas extends JComponent implements ViewportListenerI int startRes, int endRes, int startSeq, int endSeq, int verticalOffset) { - int charHeight = av.getCharHeight(); - int charWidth = av.getCharWidth(); - + int charHeight = av.getCharHeight(); + int charWidth = av.getCharWidth(); int visWidth = (endRes - startRes + 1) * charWidth; int oldY = -1; @@ -1439,140 +1444,141 @@ public class SeqCanvas extends JComponent implements ViewportListenerI boolean inGroup = false; int top = -1; int bottom = -1; - - int sx = -1; int sy = -1; - int xwidth = -1; - - for (i = startSeq; i <= endSeq; i++) - { - // position of start residue of group relative to startRes, in pixels - sx = (group.getStartRes() - startRes) * charWidth; - // width of group in pixels - xwidth = (((group.getEndRes() + 1) - group.getStartRes()) * charWidth) - - 1; + List seqs = group.getSequences(null); - sy = verticalOffset + (i - startSeq) * charHeight; + // position of start residue of group relative to startRes, in pixels + int sx = (group.getStartRes() - startRes) * charWidth; - if (sx + xwidth < 0 || sx > visWidth) - { - continue; - } + // width of group in pixels + int xwidth = (((group.getEndRes() + 1) - group.getStartRes()) + * charWidth) - 1; - if ((sx <= (endRes - startRes) * charWidth) - && group.getSequences(null) - .contains(av.getAlignment().getSequenceAt(i))) + if (!(sx + xwidth < 0 || sx > visWidth)) + { + for (i = startSeq; i <= endSeq; i++) { - if ((bottom == -1) && !group.getSequences(null) - .contains(av.getAlignment().getSequenceAt(i + 1))) - { - bottom = sy + charHeight; - } - - if (!inGroup) - { - if (((top == -1) && (i == 0)) || !group.getSequences(null) - .contains(av.getAlignment().getSequenceAt(i - 1))) - { - top = sy; - } + sy = verticalOffset + (i - startSeq) * charHeight; - oldY = sy; - inGroup = true; - } - } - else - { - if (inGroup) + if ((sx <= (endRes - startRes) * charWidth) + && seqs.contains(av.getAlignment().getSequenceAt(i))) { - // if start position is visible, draw vertical line to left of - // group - if (sx >= 0 && sx < visWidth) + if ((bottom == -1) + && !seqs.contains(av.getAlignment().getSequenceAt(i + 1))) { - g.drawLine(sx, oldY, sx, sy); + bottom = sy + charHeight; } - // if end position is visible, draw vertical line to right of - // group - if (sx + xwidth < visWidth) + if (!inGroup) { - g.drawLine(sx + xwidth, oldY, sx + xwidth, sy); - } - - if (sx < 0) - { - xwidth += sx; - sx = 0; - } - - // don't let width extend beyond current block, or group extent - // fixes JAL-2672 - if (sx + xwidth >= (endRes - startRes + 1) * charWidth) - { - xwidth = (endRes - startRes + 1) * charWidth - sx; - } - - // draw horizontal line at top of group - if (top != -1) - { - g.drawLine(sx, top, sx + xwidth, top); - top = -1; - } + if (((top == -1) && (i == 0)) || !seqs + .contains(av.getAlignment().getSequenceAt(i - 1))) + { + top = sy; + } - // draw horizontal line at bottom of group - if (bottom != -1) - { - g.drawLine(sx, bottom, sx + xwidth, bottom); - bottom = -1; + oldY = sy; + inGroup = true; } + } + else if (inGroup) + { + drawVerticals(g, sx, xwidth, visWidth, oldY, sy); + drawHorizontals(g, sx, xwidth, visWidth, top, bottom); + // reset top and bottom + top = -1; + bottom = -1; inGroup = false; } } - } - - if (inGroup) - { - sy = verticalOffset + ((i - startSeq) * charHeight); - if (sx >= 0 && sx < visWidth) + if (inGroup) { - g.drawLine(sx, oldY, sx, sy); + sy = verticalOffset + ((i - startSeq) * charHeight); + drawVerticals(g, sx, xwidth, visWidth, oldY, sy); + drawHorizontals(g, sx, xwidth, visWidth, top, bottom); } + } + } - if (sx + xwidth < visWidth) - { - g.drawLine(sx + xwidth, oldY, sx + xwidth, sy); - } + /** + * Draw horizontal selection group boundaries at top and bottom positions + * + * @param g + * graphics object to draw on + * @param sx + * start x position + * @param xwidth + * width of gap + * @param visWidth + * visWidth maximum available width + * @param top + * position to draw top of group at + * @param bottom + * position to draw bottom of group at + */ + private void drawHorizontals(Graphics2D g, int sx, int xwidth, + int visWidth, int top, int bottom) + { + int width = xwidth; + int startx = sx; + if (startx < 0) + { + width += startx; + startx = 0; + } - if (sx < 0) - { - xwidth += sx; - sx = 0; - } + // don't let width extend beyond current block, or group extent + // fixes JAL-2672 + if (startx + width >= visWidth) + { + width = visWidth - startx; + } - if (sx + xwidth > visWidth) - { - xwidth = visWidth; - } - else if (sx + xwidth >= (endRes - startRes + 1) * charWidth) - { - xwidth = (endRes - startRes + 1) * charWidth; - } + if (top != -1) + { + g.drawLine(startx, top, startx + width, top); + } - if (top != -1) - { - g.drawLine(sx, top, sx + xwidth, top); - top = -1; - } + if (bottom != -1) + { + g.drawLine(startx, bottom - 1, startx + width, bottom - 1); + } + } - if (bottom != -1) - { - g.drawLine(sx, bottom - 1, sx + xwidth, bottom - 1); - bottom = -1; - } + /** + * Draw vertical lines at sx and sx+xwidth providing they lie within + * [0,visWidth) + * + * @param g + * graphics object to draw on + * @param sx + * start x position + * @param xwidth + * width of gap + * @param visWidth + * visWidth maximum available width + * @param oldY + * top y value + * @param sy + * bottom y value + */ + private void drawVerticals(Graphics2D g, int sx, int xwidth, int visWidth, + int oldY, int sy) + { + // if start position is visible, draw vertical line to left of + // group + if (sx >= 0 && sx < visWidth) + { + g.drawLine(sx, oldY, sx, sy); + } - inGroup = false; + // if end position is visible, draw vertical line to right of + // group + if (sx + xwidth < visWidth) + { + g.drawLine(sx + xwidth, oldY, sx + xwidth, sy); } } @@ -1659,7 +1665,7 @@ public class SeqCanvas extends JComponent implements ViewportListenerI */ protected boolean drawMappedPositions(SearchResultsI results) { - if (results == null) + if ((results == null) || (gg == null)) // JAL-2784 check gg is not null { return false; } @@ -1783,31 +1789,15 @@ public class SeqCanvas extends JComponent implements ViewportListenerI { scrollX = -range; } - - // Both scrolling and resizing change viewport ranges: scrolling changes - // both start and end points, but resize only changes end values. - // Here we only want to fastpaint on a scroll, with resize using a normal - // paint, so scroll events are identified as changes to the horizontal or - // vertical start value. - if (eventName.equals(ViewportRanges.STARTRES)) - { - if (av.getWrapAlignment()) - { - fastPaintWrapped(scrollX); - } - else - { - fastPaint(scrollX, 0); - } - } - else if (eventName.equals(ViewportRanges.STARTSEQ)) - { - // scroll - fastPaint(0, (int) evt.getNewValue() - (int) evt.getOldValue()); - } - else if (eventName.equals(ViewportRanges.STARTRESANDSEQ)) - { - if (av.getWrapAlignment()) + } + // Both scrolling and resizing change viewport ranges: scrolling changes + // both start and end points, but resize only changes end values. + // Here we only want to fastpaint on a scroll, with resize using a normal + // paint, so scroll events are identified as changes to the horizontal or + // vertical start value. + if (eventName.equals(ViewportRanges.STARTRES)) + { + if (av.getWrapAlignment()) { fastPaintWrapped(scrollX); } @@ -1815,11 +1805,26 @@ public class SeqCanvas extends JComponent implements ViewportListenerI { fastPaint(scrollX, 0); } - // bizarrely, we only need to scroll on the x value here as fastpaint - // copies the full height of the image anyway. Passing in the y value - // causes nasty repaint artefacts, which only disappear on a full - // repaint. + } + else if (eventName.equals(ViewportRanges.STARTSEQ)) + { + // scroll + fastPaint(0, (int) evt.getNewValue() - (int) evt.getOldValue()); + } + else if (eventName.equals(ViewportRanges.STARTRESANDSEQ)) + { + if (av.getWrapAlignment()) + { + fastPaintWrapped(scrollX); + } + else + { + fastPaint(scrollX, 0); } + // bizarrely, we only need to scroll on the x value here as fastpaint + // copies the full height of the image anyway. Passing in the y value + // causes nasty repaint artefacts, which only disappear on a full + // repaint. } } @@ -1836,9 +1841,7 @@ public class SeqCanvas extends JComponent implements ViewportListenerI { ViewportRanges ranges = av.getRanges(); - // if (Math.abs(scrollX) > ranges.getViewportWidth()) - // JAL-2836, 2836 temporarily removed wrapped fastpaint for release 2.10.3 - if (true) + if (Math.abs(scrollX) > ranges.getViewportWidth()) { /* * shift of more than one view width is @@ -2088,7 +2091,7 @@ public class SeqCanvas extends JComponent implements ViewportListenerI */ protected boolean drawMappedPositionsWrapped(SearchResultsI results) { - if (results == null) + if ((results == null) || (gg == null)) // JAL-2784 check gg is not null { return false; }