< prev index next >
src/windows/classes/sun/awt/windows/TranslucentWindowPainter.java
Print this page
rev 1556 : 6794764: Translucent windows are completely repainted on every paint event, on Windows
6719382: Printing of AWT components on windows is not working
6726866: Repainting artifacts when resizing or dragging JInternalFrames in non-opaque toplevel
6683775: Painting artifacts is seen when panel is made setOpaque(false) for a translucent window
Reviewed-by: anthony, tdv, alexp
*** 103,115 ****
this.peer = peer;
this.window = (Window)peer.getTarget();
}
/**
! * Creates (if needed), clears and returns the buffer for this painter.
*/
! protected abstract Image getBackBuffer();
/**
* Updates the the window associated with this painter with the contents
* of the passed image.
* The image can not be null, and NPE will be thrown if it is.
--- 103,116 ----
this.peer = peer;
this.window = (Window)peer.getTarget();
}
/**
! * Creates (if needed), clears (if requested) and returns the buffer
! * for this painter.
*/
! protected abstract Image getBackBuffer(boolean clear);
/**
* Updates the the window associated with this painter with the contents
* of the passed image.
* The image can not be null, and NPE will be thrown if it is.
*** 121,174 ****
* recreated as needed.
*/
public abstract void flush();
/**
! * Updates the window associated with the painter given the passed image.
! * If the passed image is null the painter will use its own buffer for
! * rendering the contents of the window into it and updating the window.
*
! * If the passed buffer has dimensions different from the window, it is
! * copied into the internal buffer first and the latter is used to update
! * the window.
! *
! * @param bb the image to update the non opaque window with, or null.
! * If not null, the image must be of ARGB_PRE type.
*/
! public void updateWindow(Image bb) {
boolean done = false;
! if (bb != null && (window.getWidth() != bb.getWidth(null) ||
! window.getHeight() != bb.getHeight(null)))
! {
! Image ourBB = getBackBuffer();
! Graphics2D g = (Graphics2D)ourBB.getGraphics();
! g.drawImage(bb, 0, 0, null);
! g.dispose();
! bb = ourBB;
! }
! do {
! if (bb == null) {
! bb = getBackBuffer();
Graphics2D g = (Graphics2D)bb.getGraphics();
try {
window.paintAll(g);
} finally {
g.dispose();
}
}
- peer.paintAppletWarning((Graphics2D)bb.getGraphics(),
- bb.getWidth(null), bb.getHeight(null));
-
done = update(bb);
- // in case they passed us a lost VI, next time around we'll use our
- // own bb because we can not validate and restore the contents of
- // their VI
if (!done) {
! bb = null;
}
- } while (!done);
}
private static final Image clearImage(Image bb) {
Graphics2D g = (Graphics2D)bb.getGraphics();
int w = bb.getWidth(null);
--- 122,155 ----
* recreated as needed.
*/
public abstract void flush();
/**
! * Updates the window associated with the painter.
*
! * @param repaint indicates if the window should be completely repainted
! * to the back buffer using {@link java.awt.Window#paintAll} before update.
*/
! public void updateWindow(boolean repaint) {
boolean done = false;
! Image bb = getBackBuffer(repaint);
! while (!done) {
! if (repaint) {
Graphics2D g = (Graphics2D)bb.getGraphics();
try {
window.paintAll(g);
} finally {
g.dispose();
}
}
done = update(bb);
if (!done) {
! repaint = true;
! bb = getBackBuffer(true);
! }
}
}
private static final Image clearImage(Image bb) {
Graphics2D g = (Graphics2D)bb.getGraphics();
int w = bb.getWidth(null);
*** 188,221 ****
*
* This painter handles all types of images passed to its paint(Image)
* method (VI, BI, regular Images).
*/
private static class BIWindowPainter extends TranslucentWindowPainter {
! private WeakReference<BufferedImage> biRef;
protected BIWindowPainter(WWindowPeer peer) {
super(peer);
}
! private BufferedImage getBIBackBuffer() {
int w = window.getWidth();
int h = window.getHeight();
! BufferedImage bb = biRef == null ? null : biRef.get();
! if (bb == null || bb.getWidth() != w || bb.getHeight() != h) {
! if (bb != null) {
! bb.flush();
! bb = null;
! }
! bb = new BufferedImage(w, h, BufferedImage.TYPE_INT_ARGB_PRE);
! biRef = new WeakReference<BufferedImage>(bb);
}
! return (BufferedImage)clearImage(bb);
! }
!
! @Override
! protected Image getBackBuffer() {
! return getBIBackBuffer();
}
@Override
protected boolean update(Image bb) {
VolatileImage viBB = null;
--- 169,196 ----
*
* This painter handles all types of images passed to its paint(Image)
* method (VI, BI, regular Images).
*/
private static class BIWindowPainter extends TranslucentWindowPainter {
! private BufferedImage backBuffer;
protected BIWindowPainter(WWindowPeer peer) {
super(peer);
}
! @Override
! protected Image getBackBuffer(boolean clear) {
int w = window.getWidth();
int h = window.getHeight();
! if (backBuffer == null ||
! backBuffer.getWidth() != w ||
! backBuffer.getHeight() != h)
! {
! flush();
! backBuffer = new BufferedImage(w, h, BufferedImage.TYPE_INT_ARGB_PRE);
}
! return clear ? (BufferedImage)clearImage(backBuffer) : backBuffer;
}
@Override
protected boolean update(Image bb) {
VolatileImage viBB = null;
*** 244,299 ****
}
}
}
// copy the passed image into our own buffer, then upload
! BufferedImage bi = getBIBackBuffer();
! Graphics2D g = (Graphics2D)bi.getGraphics();
! g.setComposite(AlphaComposite.Src);
! g.drawImage(bb, 0, 0, null);
int data[] =
((DataBufferInt)bi.getRaster().getDataBuffer()).getData();
peer.updateWindowImpl(data, bi.getWidth(), bi.getHeight());
return (viBB != null ? !viBB.contentsLost() : true);
}
public void flush() {
! if (biRef != null) {
! biRef.clear();
}
}
}
/**
* A version of the painter which uses VolatileImage as the internal buffer.
* The window is painted into this VI and then copied into the parent's
* Java heap-based buffer (which is then uploaded to the layered window)
*/
private static class VIWindowPainter extends BIWindowPainter {
! private WeakReference<VolatileImage> viRef;
protected VIWindowPainter(WWindowPeer peer) {
super(peer);
}
@Override
! protected Image getBackBuffer() {
int w = window.getWidth();
int h = window.getHeight();
GraphicsConfiguration gc = peer.getGraphicsConfiguration();
- VolatileImage viBB = viRef == null ? null : viRef.get();
-
if (viBB == null || viBB.getWidth() != w || viBB.getHeight() != h ||
viBB.validate(gc) == IMAGE_INCOMPATIBLE)
{
! if (viBB != null) {
! viBB.flush();
! viBB = null;
! }
if (gc instanceof AccelGraphicsConfig) {
AccelGraphicsConfig agc = ((AccelGraphicsConfig)gc);
viBB = agc.createCompatibleVolatileImage(w, h,
TRANSLUCENT,
--- 219,267 ----
}
}
}
// copy the passed image into our own buffer, then upload
! BufferedImage bi = (BufferedImage)clearImage(backBuffer);
int data[] =
((DataBufferInt)bi.getRaster().getDataBuffer()).getData();
peer.updateWindowImpl(data, bi.getWidth(), bi.getHeight());
return (viBB != null ? !viBB.contentsLost() : true);
}
public void flush() {
! if (backBuffer != null) {
! backBuffer.flush();
! backBuffer = null;
}
}
}
/**
* A version of the painter which uses VolatileImage as the internal buffer.
* The window is painted into this VI and then copied into the parent's
* Java heap-based buffer (which is then uploaded to the layered window)
*/
private static class VIWindowPainter extends BIWindowPainter {
! private VolatileImage viBB;
protected VIWindowPainter(WWindowPeer peer) {
super(peer);
}
@Override
! protected Image getBackBuffer(boolean clear) {
int w = window.getWidth();
int h = window.getHeight();
GraphicsConfiguration gc = peer.getGraphicsConfiguration();
if (viBB == null || viBB.getWidth() != w || viBB.getHeight() != h ||
viBB.validate(gc) == IMAGE_INCOMPATIBLE)
{
! flush();
if (gc instanceof AccelGraphicsConfig) {
AccelGraphicsConfig agc = ((AccelGraphicsConfig)gc);
viBB = agc.createCompatibleVolatileImage(w, h,
TRANSLUCENT,
*** 301,326 ****
}
if (viBB == null) {
viBB = gc.createCompatibleVolatileImage(w, h, TRANSLUCENT);
}
viBB.validate(gc);
- viRef = new WeakReference<VolatileImage>(viBB);
}
! return clearImage(viBB);
}
@Override
public void flush() {
- if (viRef != null) {
- VolatileImage viBB = viRef.get();
if (viBB != null) {
viBB.flush();
viBB = null;
}
- viRef.clear();
- }
}
}
/**
* Optimized version of hw painter. Uses VolatileImages for the
--- 269,289 ----
}
if (viBB == null) {
viBB = gc.createCompatibleVolatileImage(w, h, TRANSLUCENT);
}
viBB.validate(gc);
}
! return clear ? clearImage(viBB) : viBB;
}
@Override
public void flush() {
if (viBB != null) {
viBB.flush();
viBB = null;
}
}
}
/**
* Optimized version of hw painter. Uses VolatileImages for the
< prev index next >