diff --git a/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/AnnotationRulerColumn.java b/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/AnnotationRulerColumn.java index a768997e447..c52f8267083 100644 --- a/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/AnnotationRulerColumn.java +++ b/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/AnnotationRulerColumn.java @@ -35,6 +35,7 @@ import org.eclipse.swt.graphics.Font; import org.eclipse.swt.graphics.GC; import org.eclipse.swt.graphics.Image; +import org.eclipse.swt.graphics.ImageGcDrawer; import org.eclipse.swt.graphics.Point; import org.eclipse.swt.graphics.Rectangle; import org.eclipse.swt.widgets.Canvas; @@ -266,6 +267,13 @@ public Control createControl(CompositeRuler parentRuler, Composite parentControl fCachedTextWidget= null; }); + fCanvas.addListener(SWT.ZoomChanged, e -> { + if (fBuffer != null) { + fBuffer.dispose(); + fBuffer= null; + } + }); + fMouseListener= new MouseListener() { @Override public void mouseUp(MouseEvent event) { @@ -517,10 +525,18 @@ private void doubleBufferPaint(GC dest) { fBuffer= null; } } - if (fBuffer == null) - fBuffer= new Image(fCanvas.getDisplay(), size.x, size.y); + if (fBuffer == null) { + ImageGcDrawer imageGcDrawer= (gc, imageWidth, imageHeight) -> { + doPaint(gc, new Point(imageWidth, imageHeight)); + }; + fBuffer= new Image(fCanvas.getDisplay(), imageGcDrawer, size.x, size.y); + } else { + doPaint(new GC(fBuffer), size); + } + dest.drawImage(fBuffer, 0, 0); + } - GC gc= new GC(fBuffer); + private void doPaint(GC gc, Point size) { gc.setFont(fCachedTextWidget.getFont()); try { gc.setBackground(fCanvas.getBackground()); @@ -533,8 +549,6 @@ private void doubleBufferPaint(GC dest) { } finally { gc.dispose(); } - - dest.drawImage(fBuffer, 0, 0); } /** diff --git a/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/ChangeRulerColumn.java b/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/ChangeRulerColumn.java index 99b4a093158..3c11a0d1f24 100644 --- a/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/ChangeRulerColumn.java +++ b/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/ChangeRulerColumn.java @@ -22,6 +22,7 @@ import org.eclipse.swt.graphics.Font; import org.eclipse.swt.graphics.GC; import org.eclipse.swt.graphics.Image; +import org.eclipse.swt.graphics.ImageGcDrawer; import org.eclipse.swt.graphics.Point; import org.eclipse.swt.graphics.Rectangle; import org.eclipse.swt.widgets.Canvas; @@ -199,6 +200,13 @@ public Control createControl(CompositeRuler parentRuler, Composite parentControl fCachedTextWidget= null; }); + fCanvas.addListener(SWT.ZoomChanged, e -> { + if (fBuffer != null) { + fBuffer.dispose(); + fBuffer= null; + } + }); + fCanvas.addMouseListener(fMouseHandler); fCanvas.addMouseMoveListener(fMouseHandler); @@ -249,19 +257,13 @@ private void doubleBufferPaint(GC dest) { fBuffer= null; } } - if (fBuffer == null) - fBuffer= new Image(fCanvas.getDisplay(), size.x, size.y); - - GC gc= new GC(fBuffer); - gc.setFont(fCanvas.getFont()); - - try { - gc.setBackground(getBackground()); - gc.fillRectangle(0, 0, size.x, size.y); - - doPaint(gc); - } finally { - gc.dispose(); + if (fBuffer == null) { + ImageGcDrawer imageGcDrawer= (gc, imageWidth, imageHeight) -> { + doPaint(gc, new Point(imageWidth, imageHeight)); + }; + fBuffer= new Image(fCanvas.getDisplay(), imageGcDrawer, size.x, size.y); + } else { + doPaint(new GC(fBuffer), size); } dest.drawImage(fBuffer, 0, 0); @@ -291,6 +293,19 @@ protected final boolean isViewerCompletelyShown() { return JFaceTextUtil.isShowingEntireContents(fCachedTextWidget); } + private void doPaint(GC gc, Point size) { + gc.setFont(fCanvas.getFont()); + + try { + gc.setBackground(getBackground()); + gc.fillRectangle(0, 0, size.x, size.y); + + doPaint(gc); + } finally { + gc.dispose(); + } + } + /** * Draws the ruler column. * diff --git a/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/LineNumberRulerColumn.java b/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/LineNumberRulerColumn.java index 0060369d027..46bb997df56 100644 --- a/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/LineNumberRulerColumn.java +++ b/bundles/org.eclipse.jface.text/src/org/eclipse/jface/text/source/LineNumberRulerColumn.java @@ -34,6 +34,7 @@ import org.eclipse.swt.graphics.FontMetrics; import org.eclipse.swt.graphics.GC; import org.eclipse.swt.graphics.Image; +import org.eclipse.swt.graphics.ImageGcDrawer; import org.eclipse.swt.graphics.Point; import org.eclipse.swt.graphics.Rectangle; import org.eclipse.swt.widgets.Canvas; @@ -616,7 +617,13 @@ public void addMouseListener(MouseListener listener) { fCachedTextWidget= null; }); - fCanvas.addListener(SWT.ZoomChanged, e -> computeIndentations()); + fCanvas.addListener(SWT.ZoomChanged, e -> { + computeIndentations(); + if (fBuffer != null) { + fBuffer.dispose(); + fBuffer= null; + } + }); fMouseHandler= new MouseHandler(); fCanvas.addMouseListener(fMouseHandler); @@ -681,8 +688,17 @@ private void doubleBufferPaint(GC dest) { boolean bufferStillValid = fBuffer != null; if (fBuffer == null) { - fBuffer= new Image(fCanvas.getDisplay(), size.x, size.y); - } + ImageGcDrawer imageGcDrawer= (gc, imageWidth, imageHeight) -> { + ILineRange lines= JFaceTextUtil.getVisibleModelLines(fCachedTextViewer); + if (lines == null) { + return; + } + // We redraw everything; paint directly into the buffer + initializeGC(gc, 0, 0, imageWidth, imageHeight); + doPaint(gc, lines); + }; + fBuffer= new Image(fCanvas.getDisplay(), imageGcDrawer, size.x, size.y); + } else { GC bufferGC= new GC(fBuffer); Image newBuffer= null; try { @@ -745,16 +761,7 @@ private void doubleBufferPaint(GC dest) { fLastBottomModelLine= bottomModelLine; fLastHeight= height; if (dy != 0) { - // Some rulers may paint outside the line region. Let them paint in a new image, - // the copy the wanted bits. - newBuffer= new Image(fCanvas.getDisplay(), size.x, size.y); - GC localGC= new GC(newBuffer); - try { - initializeGC(localGC, 0, bufferY, size.x, bufferH); - doPaint(localGC, visibleLines); - } finally { - localGC.dispose(); - } + newBuffer= newBufferImage(size, bufferY, bufferH, visibleLines); bufferGC.drawImage(newBuffer, 0, bufferY, size.x, bufferH, 0, bufferY, size.x, bufferH); if (dy > 0 && bufferY + bufferH < size.y) { // Scrolled down in the text, but didn't use the full height of the Canvas: clear @@ -774,9 +781,24 @@ private void doubleBufferPaint(GC dest) { newBuffer.dispose(); } } + } dest.drawImage(fBuffer, 0, 0); } + private Image newBufferImage(Point size, int bufferY, int bufferH, final ILineRange visibleLines) { + ImageGcDrawer imageGcDrawer= (localGC, imageWidth, imageHeight) -> { + // Some rulers may paint outside the line region. Let them paint in a new image, + // the copy the wanted bits. + try { + initializeGC(localGC, 0, bufferY, imageWidth, bufferH); + doPaint(localGC, visibleLines); + } finally { + localGC.dispose(); + } + }; + return new Image(fCanvas.getDisplay(), imageGcDrawer, size.x, size.y); + } + private void initializeGC(GC gc, int x, int y, int width, int height) { gc.setFont(fCanvas.getFont()); if (fForeground != null) {