+ /*
+ * relocate the regions of the alignment that are still visible
+ */
+ shiftWrappedAlignment(-scrollX);
+
+ /*
+ * add new columns (sequence, annotation)
+ * - at top left if scrollX < 0
+ * - at right of last two widths if scrollX > 0
+ */
+ if (scrollX < 0)
+ {
+ int startRes = ranges.getStartRes();
+ drawWrappedWidth(gg, wrappedSpaceAboveAlignment, startRes, startRes
+ - scrollX - 1, getHeight());
+ }
+ else
+ {
+ fastPaintWrappedAddRight(scrollX);
+ }
+
+ /*
+ * draw all scales (if shown) and hidden column markers
+ */
+ drawWrappedDecorators(gg, ranges.getStartRes());
+
+ repaint();
+ } finally
+ {
+ fastpainting = false;
+ }
+ }
+
+ /**
+ * Draws the specified number of columns at the 'end' (bottom right) of a
+ * wrapped alignment view, including sequences and annotations if shown, but
+ * not scales. Also draws the same number of columns at the right hand end of
+ * the second last width shown, if the last width is not full height (so
+ * cannot simply be copied from the graphics image).
+ *
+ * @param columns
+ */
+ protected void fastPaintWrappedAddRight(int columns)
+ {
+ if (columns == 0)
+ {
+ return;
+ }
+
+ ViewportRanges ranges = av.getRanges();
+ int viewportWidth = ranges.getViewportWidth();
+ int charWidth = av.getCharWidth();
+
+ /**
+ * draw full height alignment in the second last row, last columns, if the
+ * last row was not full height
+ */
+ int visibleWidths = wrappedVisibleWidths;
+ int canvasHeight = getHeight();
+ boolean lastWidthPartHeight = (wrappedVisibleWidths * wrappedRepeatHeightPx) > canvasHeight;
+
+ if (lastWidthPartHeight)
+ {
+ int widthsAbove = Math.max(0, visibleWidths - 2);
+ int ypos = wrappedRepeatHeightPx * widthsAbove
+ + wrappedSpaceAboveAlignment;
+ int endRes = ranges.getEndRes();
+ endRes += widthsAbove * viewportWidth;
+ int startRes = endRes - columns;
+ int xOffset = ((startRes - ranges.getStartRes()) % viewportWidth)
+ * charWidth;
+
+ /*
+ * white fill first to erase annotations
+ */
+ gg.translate(xOffset, 0);
+ gg.setColor(Color.white);
+ gg.fillRect(labelWidthWest, ypos,
+ (endRes - startRes + 1) * charWidth, wrappedRepeatHeightPx);
+ gg.translate(-xOffset, 0);
+
+ drawWrappedWidth(gg, ypos, startRes, endRes, canvasHeight);
+ }
+
+ /*
+ * draw newly visible columns in last wrapped width (none if we
+ * have reached the end of the alignment)
+ * y-offset for drawing last width is height of widths above,
+ * plus one gap row
+ */
+ int widthsAbove = visibleWidths - 1;
+ int ypos = wrappedRepeatHeightPx * widthsAbove
+ + wrappedSpaceAboveAlignment;
+ int endRes = ranges.getEndRes();
+ endRes += widthsAbove * viewportWidth;
+ int startRes = endRes - columns + 1;
+
+ /*
+ * white fill first to erase annotations
+ */
+ int xOffset = ((startRes - ranges.getStartRes()) % viewportWidth)
+ * charWidth;
+ gg.translate(xOffset, 0);
+ gg.setColor(Color.white);
+ int width = viewportWidth * charWidth - xOffset;
+ gg.fillRect(labelWidthWest, ypos, width, wrappedRepeatHeightPx);
+ gg.translate(-xOffset, 0);
+
+ gg.setFont(av.getFont());
+ gg.setColor(Color.black);
+
+ if (startRes < ranges.getVisibleAlignmentWidth())
+ {
+ drawWrappedWidth(gg, ypos, startRes, endRes, canvasHeight);
+ }
+
+ /*
+ * and finally, white fill any space below the visible alignment
+ */
+ int heightBelow = canvasHeight - visibleWidths * wrappedRepeatHeightPx;
+ if (heightBelow > 0)
+ {
+ gg.setColor(Color.white);
+ gg.fillRect(0, canvasHeight - heightBelow, getWidth(), heightBelow);
+ }