提交 b4bb9818 编写于 作者: L lana

Merge

......@@ -32,10 +32,20 @@ import javax.swing.plaf.basic.BasicPanelUI;
import com.apple.laf.AquaUtils.RecyclableSingleton;
import com.apple.laf.AquaUtils.RecyclableSingletonFromDefaultConstructor;
import java.awt.Graphics;
public class AquaPanelUI extends BasicPanelUI {
static RecyclableSingleton<AquaPanelUI> instance = new RecyclableSingletonFromDefaultConstructor<AquaPanelUI>(AquaPanelUI.class);
public static ComponentUI createUI(final JComponent c) {
return instance.get();
}
@Override
public final void update(final Graphics g, final JComponent c) {
if (c.isOpaque()) {
AquaUtils.fillRect(g, c);
}
paint(g, c);
}
}
......@@ -319,4 +319,12 @@ public class AquaRootPaneUI extends BasicRootPaneUI implements AncestorListener,
updateComponentTreeUIActivation(element, active);
}
}
@Override
public final void update(final Graphics g, final JComponent c) {
if (c.isOpaque()) {
AquaUtils.fillRect(g, c);
}
paint(g, c);
}
}
......@@ -73,9 +73,7 @@ public class AquaToolBarUI extends BasicToolBarUI implements SwingConstants {
g.translate(x, y);
if (c.isOpaque()) {
final Color background = c.getBackground();
g.setColor(background);
g.fillRect(0, 0, w - 1, h - 1);
AquaUtils.fillRect(g, c, c.getBackground(), 0, 0, w - 1, h - 1);
}
final Color oldColor = g.getColor();
......@@ -137,4 +135,12 @@ public class AquaToolBarUI extends BasicToolBarUI implements SwingConstants {
return true;
}
}
@Override
public final void update(final Graphics g, final JComponent c) {
if (c.isOpaque()) {
AquaUtils.fillRect(g, c);
}
paint(g, c);
}
}
......@@ -28,18 +28,19 @@ package com.apple.laf;
import java.awt.*;
import java.awt.image.*;
import java.lang.ref.SoftReference;
import java.lang.ref.WeakReference;
import java.lang.reflect.Method;
import java.security.PrivilegedAction;
import java.util.*;
import javax.swing.*;
import javax.swing.border.Border;
import javax.swing.plaf.UIResource;
import sun.awt.AppContext;
import sun.lwawt.macosx.CImage;
import sun.lwawt.macosx.CImage.Creator;
import sun.lwawt.macosx.CPlatformWindow;
import sun.swing.SwingUtilities2;
import com.apple.laf.AquaImageFactory.SlicedImageControl;
......@@ -389,4 +390,51 @@ public class AquaUtils {
return false;
}
}
protected static boolean isWindowTextured(final Component c) {
if (!(c instanceof JComponent)) {
return false;
}
final JRootPane pane = ((JComponent) c).getRootPane();
if (pane == null) {
return false;
}
Object prop = pane.getClientProperty(
CPlatformWindow.WINDOW_BRUSH_METAL_LOOK);
if (prop != null) {
return Boolean.parseBoolean(prop.toString());
}
prop = pane.getClientProperty(CPlatformWindow.WINDOW_STYLE);
return prop != null && "textured".equals(prop);
}
private static Color resetAlpha(final Color color) {
return new Color(color.getRed(), color.getGreen(), color.getBlue(), 0);
}
protected static void fillRect(final Graphics g, final Component c) {
fillRect(g, c, c.getBackground(), 0, 0, c.getWidth(), c.getHeight());
}
protected static void fillRect(final Graphics g, final Component c,
final Color color, final int x, final int y,
final int w, final int h) {
if (!(g instanceof Graphics2D)) {
return;
}
final Graphics2D cg = (Graphics2D) g.create();
try {
if (color instanceof UIResource && isWindowTextured(c)
&& color.equals(SystemColor.window)) {
cg.setComposite(AlphaComposite.Src);
cg.setColor(resetAlpha(color));
} else {
cg.setColor(color);
}
cg.fillRect(x, y, w, h);
} finally {
cg.dispose();
}
}
}
......@@ -48,6 +48,9 @@ public class CGraphicsDevice extends GraphicsDevice {
private static AWTPermission fullScreenExclusivePermission;
// Save/restore DisplayMode for the Full Screen mode
private DisplayMode originalMode;
public CGraphicsDevice(int displayID) {
this.displayID = displayID;
configs = new GraphicsConfiguration[] {
......@@ -124,18 +127,22 @@ public class CGraphicsDevice extends GraphicsDevice {
}
boolean fsSupported = isFullScreenSupported();
if (fsSupported && old != null) {
// enter windowed mode (and restore original display mode)
exitFullScreenExclusive(old);
// TODO: restore display mode
if (originalMode != null) {
setDisplayMode(originalMode);
originalMode = null;
}
}
super.setFullScreenWindow(w);
if (fsSupported && w != null) {
// TODO: save current display mode
if (isDisplayChangeSupported()) {
originalMode = getDisplayMode();
}
// enter fullscreen mode
enterFullScreenExclusive(w);
}
......
......@@ -68,11 +68,12 @@ public class CGLLayer extends CFRetainedResource {
}
public boolean isOpaque() {
return peer.isOpaque();
return !peer.isTranslucent();
}
public int getTransparency() {
return (peer.isOpaque() ? Transparency.OPAQUE : Transparency.TRANSLUCENT);
return peer.isTranslucent() ? Transparency.TRANSLUCENT :
Transparency.OPAQUE;
}
public Object getDestination() {
......
......@@ -424,8 +424,7 @@ public abstract class LWComponentPeer<T extends Component, D extends JComponent>
@Override
public final Graphics getGraphics() {
Graphics g = getWindowPeerOrSelf().isOpaque() ? getOnscreenGraphics()
: getOffscreenGraphics();
final Graphics g = getOnscreenGraphics();
if (g != null) {
synchronized (getPeerTreeLock()){
applyConstrain(g);
......@@ -443,13 +442,7 @@ public abstract class LWComponentPeer<T extends Component, D extends JComponent>
final LWWindowPeer wp = getWindowPeerOrSelf();
return wp.getOnscreenGraphics(getForeground(), getBackground(),
getFont());
}
public final Graphics getOffscreenGraphics() {
final LWWindowPeer wp = getWindowPeerOrSelf();
return wp.getOffscreenGraphics(getForeground(), getBackground(),
getFont());
}
private void applyConstrain(final Graphics g) {
......@@ -463,7 +456,7 @@ public abstract class LWComponentPeer<T extends Component, D extends JComponent>
}
//TODO Move this method to SG2D?
private void SG2DConstraint(final SunGraphics2D sg2d, Region r) {
void SG2DConstraint(final SunGraphics2D sg2d, Region r) {
sg2d.constrainX = sg2d.transX;
sg2d.constrainY = sg2d.transY;
......@@ -710,7 +703,7 @@ public abstract class LWComponentPeer<T extends Component, D extends JComponent>
// Obtain the metrics from the offscreen window where this peer is
// mostly drawn to.
// TODO: check for "use platform metrics" settings
Graphics g = getWindowPeer().getOffscreenGraphics();
Graphics g = getWindowPeer().getGraphics();
try {
if (g != null) {
return g.getFontMetrics(f);
......@@ -1011,14 +1004,33 @@ public abstract class LWComponentPeer<T extends Component, D extends JComponent>
@Override
public final void applyShape(final Region shape) {
synchronized (getStateLock()) {
region = shape;
if (region == shape || (region != null && region.equals(shape))) {
return;
}
}
applyShapeImpl(shape);
}
void applyShapeImpl(final Region shape) {
synchronized (getStateLock()) {
if (shape != null) {
region = Region.WHOLE_REGION.getIntersection(shape);
} else {
region = null;
}
}
repaintParent(getBounds());
}
protected final Region getRegion() {
synchronized (getStateLock()) {
return region == null ? Region.getInstance(getSize()) : region;
return isShaped() ? region : Region.getInstance(getSize());
}
}
public boolean isShaped() {
synchronized (getStateLock()) {
return region != null;
}
}
......@@ -1386,11 +1398,6 @@ public abstract class LWComponentPeer<T extends Component, D extends JComponent>
}
}
// Just a helper method, thus final
protected final void flushOffscreenGraphics() {
flushOffscreenGraphics(getSize());
}
protected static final void flushOnscreenGraphics(){
final OGLRenderQueue rq = OGLRenderQueue.getInstance();
rq.lock();
......@@ -1401,36 +1408,6 @@ public abstract class LWComponentPeer<T extends Component, D extends JComponent>
}
}
/*
* Flushes the given rectangle from the back buffer to the screen.
*/
protected void flushOffscreenGraphics(Rectangle r) {
flushOffscreenGraphics(r.x, r.y, r.width, r.height);
}
private void flushOffscreenGraphics(int x, int y, int width, int height) {
Image bb = getWindowPeerOrSelf().getBackBuffer();
if (bb != null) {
// g is a screen Graphics from the delegate
final Graphics g = getOnscreenGraphics();
if (g != null && g instanceof Graphics2D) {
try {
Graphics2D g2d = (Graphics2D)g;
Point p = localToWindow(new Point(0, 0));
Composite composite = g2d.getComposite();
g2d.setComposite(AlphaComposite.Src);
g.drawImage(bb, x, y, x + width, y + height, p.x + x,
p.y + y, p.x + x + width, p.y + y + height,
null);
g2d.setComposite(composite);
} finally {
g.dispose();
}
}
}
}
/**
* Used by ContainerPeer to skip all the paint events during layout.
*
......
......@@ -58,9 +58,6 @@ final class LWRepaintArea extends RepaintArea {
private static void flushBuffers(final LWComponentPeer peer) {
if (peer != null) {
if (!peer.getWindowPeerOrSelf().isOpaque()) {
peer.flushOffscreenGraphics();
}
peer.flushOnscreenGraphics();
}
}
......
......@@ -522,12 +522,6 @@ public abstract class LWToolkit extends SunToolkit implements Runnable {
postEvent(targetToAppContext(event.getSource()), event);
}
// use peer's back buffer to implement non-opaque windows.
@Override
public boolean needUpdateWindow() {
return true;
}
@Override
public void grab(Window w) {
if (w.getPeer() != null) {
......
......@@ -37,6 +37,7 @@ import sun.awt.*;
import sun.java2d.*;
import sun.java2d.loops.Blit;
import sun.java2d.loops.CompositeType;
import sun.java2d.pipe.Region;
import sun.util.logging.PlatformLogger;
public class LWWindowPeer
......@@ -109,6 +110,10 @@ public class LWWindowPeer
private volatile boolean skipNextFocusChange;
private static final Color nonOpaqueBackground = new Color(0, 0, 0, 0);
private volatile boolean textured;
/**
* Current modal blocker or null.
*
......@@ -169,6 +174,11 @@ public class LWWindowPeer
setAlwaysOnTop(getTarget().isAlwaysOnTop());
updateMinimumSize();
final Shape shape = getTarget().getShape();
if (shape != null) {
applyShape(Region.getInstance(shape, null));
}
final float opacity = getTarget().getOpacity();
if (opacity < 1.0f) {
setOpacity(opacity);
......@@ -178,7 +188,7 @@ public class LWWindowPeer
updateInsets(platformWindow.getInsets());
if (getSurfaceData() == null) {
replaceSurfaceData();
replaceSurfaceData(false);
}
}
......@@ -280,7 +290,7 @@ public class LWWindowPeer
// "buffer", that's why numBuffers - 1
assert numBuffers > 1;
replaceSurfaceData(numBuffers - 1, caps);
replaceSurfaceData(numBuffers - 1, caps, false);
} catch (InvalidPipeException z) {
throw new AWTException(z.toString());
}
......@@ -420,19 +430,44 @@ public class LWWindowPeer
public final void setOpaque(final boolean isOpaque) {
if (this.isOpaque != isOpaque) {
this.isOpaque = isOpaque;
getPlatformWindow().setOpaque(isOpaque);
replaceSurfaceData();
repaintPeer();
updateOpaque();
}
}
public final boolean isOpaque() {
return isOpaque;
private void updateOpaque() {
getPlatformWindow().setOpaque(!isTranslucent());
replaceSurfaceData(false);
repaintPeer();
}
@Override
public void updateWindow() {
flushOffscreenGraphics();
}
public final boolean isTextured() {
return textured;
}
public final void setTextured(final boolean isTextured) {
textured = isTextured;
}
public final boolean isTranslucent() {
synchronized (getStateLock()) {
/*
* Textured window is a special case of translucent window.
* The difference is only in nswindow background. So when we set
* texture property our peer became fully translucent. It doesn't
* fill background, create non opaque backbuffers and layer etc.
*/
return !isOpaque || isShaped() || isTextured();
}
}
@Override
final void applyShapeImpl(final Region shape) {
super.applyShapeImpl(shape);
updateOpaque();
}
@Override
......@@ -587,7 +622,20 @@ public class LWWindowPeer
getFont());
if (g != null) {
try {
g.clearRect(0, 0, w, h);
if (g instanceof Graphics2D) {
((Graphics2D) g).setComposite(AlphaComposite.Src);
}
if (isTranslucent()) {
g.setColor(nonOpaqueBackground);
g.fillRect(0, 0, w, h);
}
if (!isTextured()) {
if (g instanceof SunGraphics2D) {
SG2DConstraint((SunGraphics2D) g, getRegion());
}
g.setColor(getBackground());
g.fillRect(0, 0, w, h);
}
} finally {
g.dispose();
}
......@@ -894,35 +942,6 @@ public class LWWindowPeer
});
}
/**
* This method returns a back buffer Graphics to render all the
* peers to. After the peer is painted, the back buffer contents
* should be flushed to the screen. All the target painting
* (Component.paint() method) should be done directly to the screen.
*/
protected final Graphics getOffscreenGraphics(Color fg, Color bg, Font f) {
final Image bb = getBackBuffer();
if (bb == null) {
return null;
}
if (fg == null) {
fg = SystemColor.windowText;
}
if (bg == null) {
bg = SystemColor.window;
}
if (f == null) {
f = DEFAULT_FONT;
}
final Graphics2D g = (Graphics2D) bb.getGraphics();
if (g != null) {
g.setColor(fg);
g.setBackground(bg);
g.setFont(f);
}
return g;
}
/*
* May be called by delegate to provide SD to Java2D code.
*/
......@@ -933,11 +952,16 @@ public class LWWindowPeer
}
private void replaceSurfaceData() {
replaceSurfaceData(backBufferCount, backBufferCaps);
replaceSurfaceData(true);
}
private void replaceSurfaceData(boolean blit) {
replaceSurfaceData(backBufferCount, backBufferCaps, blit);
}
private void replaceSurfaceData(int newBackBufferCount,
BufferCapabilities newBackBufferCaps) {
BufferCapabilities newBackBufferCaps,
boolean blit) {
synchronized (surfaceDataLock) {
final SurfaceData oldData = getSurfaceData();
surfaceData = platformWindow.replaceSurfaceData();
......@@ -950,7 +974,10 @@ public class LWWindowPeer
if (getSurfaceData() != null && oldData != getSurfaceData()) {
clearBackground(size.width, size.height);
}
blitSurfaceData(oldData, getSurfaceData());
if (blit) {
blitSurfaceData(oldData, getSurfaceData());
}
if (oldData != null && oldData != getSurfaceData()) {
// TODO: drop oldData for D3D/WGL pipelines
......@@ -965,11 +992,18 @@ public class LWWindowPeer
Graphics g = backBuffer.getGraphics();
try {
Rectangle r = getBounds();
g.setColor(getBackground());
if (g instanceof Graphics2D) {
((Graphics2D) g).setComposite(AlphaComposite.Src);
}
g.setColor(nonOpaqueBackground);
g.fillRect(0, 0, r.width, r.height);
if (g instanceof SunGraphics2D) {
SG2DConstraint((SunGraphics2D) g, getRegion());
}
if (!isTextured()) {
g.setColor(getBackground());
g.fillRect(0, 0, r.width, r.height);
}
if (oldBB != null) {
// Draw the old back buffer to the new one
g.drawImage(oldBB, 0, 0, null);
......@@ -993,7 +1027,7 @@ public class LWWindowPeer
CompositeType.Src,
dst.getSurfaceType());
if (blit != null) {
blit.Blit(src, dst, ((Graphics2D) getGraphics()).getComposite(),
blit.Blit(src, dst, AlphaComposite.Src,
getRegion(), 0, 0, 0, 0, size.width, size.height);
}
}
......
......@@ -117,7 +117,7 @@ public class CPlatformEmbeddedFrame implements PlatformWindow {
Rectangle r = peer.getBounds();
Image im = null;
if (!r.isEmpty()) {
int transparency = (peer.isOpaque() ? Transparency.OPAQUE : Transparency.TRANSLUCENT);
int transparency = peer.isTranslucent() ? Transparency.TRANSLUCENT : Transparency.OPAQUE;
im = peer.getGraphicsConfiguration().createCompatibleImage(r.width, r.height, transparency);
}
return im;
......
......@@ -64,7 +64,7 @@ public class CPlatformView extends CFRetainedResource {
}
public boolean isOpaque() {
return peer.isOpaque();
return !peer.isTranslucent();
}
/*
......
......@@ -209,6 +209,7 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
private boolean undecorated; // initialized in getInitialStyleBits()
private Rectangle normalBounds = null; // not-null only for undecorated maximized windows
private CPlatformResponder responder;
private volatile boolean zoomed = false; // from native perspective
public CPlatformWindow(final PeerType peerType) {
super(0, true);
......@@ -298,7 +299,7 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
// If the target is a dialog, popup or tooltip we want it to ignore the brushed metal look.
if (isPopup) {
styleBits = SET(styleBits, TEXTURED, true);
styleBits = SET(styleBits, TEXTURED, false);
// Popups in applets don't activate applet's process
styleBits = SET(styleBits, NONACTIVATING, true);
}
......@@ -372,6 +373,8 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
}
}
peer.setTextured(IS(TEXTURED, styleBits));
return styleBits;
}
......@@ -467,26 +470,42 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
nativeSetNSWindowBounds(getNSWindowPtr(), x, y, w, h);
}
private void zoom() {
private boolean isMaximized() {
return undecorated ? this.normalBounds != null : zoomed;
}
private void maximize() {
if (isMaximized()) {
return;
}
if (!undecorated) {
zoomed = true;
CWrapper.NSWindow.zoom(getNSWindowPtr());
} else {
// OS X handles -zoom incorrectly for undecorated windows
final boolean isZoomed = this.normalBounds == null;
deliverZoom(isZoomed);
Rectangle toBounds;
if (isZoomed) {
this.normalBounds = peer.getBounds();
long screen = CWrapper.NSWindow.screen(getNSWindowPtr());
toBounds = CWrapper.NSScreen.visibleFrame(screen).getBounds();
// Flip the y coordinate
Rectangle frame = CWrapper.NSScreen.frame(screen).getBounds();
toBounds.y = frame.height - toBounds.y - toBounds.height;
} else {
toBounds = normalBounds;
this.normalBounds = null;
}
deliverZoom(true);
this.normalBounds = peer.getBounds();
long screen = CWrapper.NSWindow.screen(getNSWindowPtr());
Rectangle toBounds = CWrapper.NSScreen.visibleFrame(screen).getBounds();
// Flip the y coordinate
Rectangle frame = CWrapper.NSScreen.frame(screen).getBounds();
toBounds.y = frame.height - toBounds.y - toBounds.height;
setBounds(toBounds.x, toBounds.y, toBounds.width, toBounds.height);
}
}
private void unmaximize() {
if (!isMaximized()) {
return;
}
if (!undecorated) {
zoomed = false;
CWrapper.NSWindow.zoom(getNSWindowPtr());
} else {
deliverZoom(false);
Rectangle toBounds = this.normalBounds;
this.normalBounds = null;
setBounds(toBounds.x, toBounds.y, toBounds.width, toBounds.height);
}
}
......@@ -499,9 +518,9 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
public void setVisible(boolean visible) {
final long nsWindowPtr = getNSWindowPtr();
// 1. Process parent-child relationship when hiding
// Process parent-child relationship when hiding
if (!visible) {
// 1a. Unparent my children
// Unparent my children
for (Window w : target.getOwnedWindows()) {
WindowPeer p = (WindowPeer)w.getPeer();
if (p instanceof LWWindowPeer) {
......@@ -512,30 +531,17 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
}
}
// 1b. Unparent myself
// Unparent myself
if (owner != null && owner.isVisible()) {
CWrapper.NSWindow.removeChildWindow(owner.getNSWindowPtr(), nsWindowPtr);
}
}
// 2. Configure stuff
// Configure stuff
updateIconImages();
updateFocusabilityForAutoRequestFocus(false);
// 3. Manage the extended state when hiding
if (!visible) {
// Cancel out the current native state of the window
switch (peer.getState()) {
case Frame.ICONIFIED:
CWrapper.NSWindow.deminiaturize(nsWindowPtr);
break;
case Frame.MAXIMIZED_BOTH:
zoom();
break;
}
}
// 4. Actually show or hide the window
// Actually show or hide the window
LWWindowPeer blocker = peer.getBlocker();
if (blocker == null || !visible) {
// If it ain't blocked, or is being hidden, go regular way
......@@ -564,16 +570,19 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
}
this.visible = visible;
// 5. Manage the extended state when showing
// Manage the extended state when showing
if (visible) {
// Re-apply the extended state as expected in shared code
// Apply the extended state as expected in shared code
if (target instanceof Frame) {
switch (((Frame)target).getExtendedState()) {
case Frame.ICONIFIED:
CWrapper.NSWindow.miniaturize(nsWindowPtr);
break;
case Frame.MAXIMIZED_BOTH:
zoom();
maximize();
break;
default: // NORMAL
unmaximize(); // in case it was maximized, otherwise this is a no-op
break;
}
}
......@@ -581,12 +590,12 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
nativeSynthesizeMouseEnteredExitedEvents(nsWindowPtr);
// 6. Configure stuff #2
// Configure stuff #2
updateFocusabilityForAutoRequestFocus(true);
// 7. Manage parent-child relationship when showing
// Manage parent-child relationship when showing
if (visible) {
// 7a. Add myself as a child
// Add myself as a child
if (owner != null && owner.isVisible()) {
CWrapper.NSWindow.addChildWindow(owner.getNSWindowPtr(), nsWindowPtr, CWrapper.NSWindow.NSWindowAbove);
if (target.isAlwaysOnTop()) {
......@@ -594,7 +603,7 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
}
}
// 7b. Add my own children to myself
// Add my own children to myself
for (Window w : target.getOwnedWindows()) {
WindowPeer p = (WindowPeer)w.getPeer();
if (p instanceof LWWindowPeer) {
......@@ -609,7 +618,7 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
}
}
// 8. Deal with the blocker of the window being shown
// Deal with the blocker of the window being shown
if (blocker != null && visible) {
// Make sure the blocker is above its siblings
((CPlatformWindow)blocker.getPlatformWindow()).orderAboveSiblings();
......@@ -733,10 +742,19 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
@Override
public void setOpaque(boolean isOpaque) {
CWrapper.NSWindow.setOpaque(getNSWindowPtr(), isOpaque);
if (!isOpaque) {
if (!isOpaque && !peer.isTextured()) {
long clearColor = CWrapper.NSColor.clearColor();
CWrapper.NSWindow.setBackgroundColor(getNSWindowPtr(), clearColor);
}
//This is a temporary workaround. Looks like after 7124236 will be fixed
//the correct place for invalidateShadow() is CGLayer.drawInCGLContext.
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
invalidateShadow();
}
});
}
@Override
......@@ -767,7 +785,7 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
if (prevWindowState == Frame.MAXIMIZED_BOTH) {
// let's return into the normal states first
// the zoom call toggles between the normal and the max states
zoom();
unmaximize();
}
CWrapper.NSWindow.miniaturize(nsWindowPtr);
break;
......@@ -776,14 +794,14 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
// let's return into the normal states first
CWrapper.NSWindow.deminiaturize(nsWindowPtr);
}
zoom();
maximize();
break;
case Frame.NORMAL:
if (prevWindowState == Frame.ICONIFIED) {
CWrapper.NSWindow.deminiaturize(nsWindowPtr);
} else if (prevWindowState == Frame.MAXIMIZED_BOTH) {
// the zoom call toggles between the normal and the max states
zoom();
unmaximize();
}
break;
default:
......@@ -805,6 +823,10 @@ public class CPlatformWindow extends CFRetainedResource implements PlatformWindo
nativeSetEnabled(getNSWindowPtr(), !blocked);
}
public final void invalidateShadow(){
nativeRevalidateNSWindowShadow(getNSWindowPtr());
}
// ----------------------------------------------------------------------
// UTILITY METHODS
// ----------------------------------------------------------------------
......
......@@ -749,6 +749,11 @@ public class LWCToolkit extends LWToolkit {
(modalityType == Dialog.ModalityType.TOOLKIT_MODAL);
}
@Override
public boolean isWindowShapingSupported() {
return true;
}
@Override
public boolean isWindowTranslucencySupported() {
return true;
......@@ -759,6 +764,10 @@ public class LWCToolkit extends LWToolkit {
return true;
}
public boolean isSwingBackbufferTranslucencySupported() {
return true;
}
@Override
public boolean enableInputMethodsForTextComponent() {
return true;
......
......@@ -941,14 +941,17 @@ JNIEXPORT void JNICALL Java_sun_lwawt_macosx_CPlatformWindow_nativeRevalidateNSW
(JNIEnv *env, jclass clazz, jlong windowPtr)
{
JNF_COCOA_ENTER(env);
AWT_ASSERT_NOT_APPKIT_THREAD;
NSWindow *nsWindow = OBJC(windowPtr);
[JNFRunLoop performOnMainThreadWaiting:NO withBlock:^(){
AWT_ASSERT_APPKIT_THREAD;
if ([NSThread isMainThread]) {
[nsWindow invalidateShadow];
}];
} else {
[JNFRunLoop performOnMainThreadWaiting:NO withBlock:^(){
AWT_ASSERT_APPKIT_THREAD;
[nsWindow invalidateShadow];
}];
}
JNF_COCOA_EXIT(env);
}
......
......@@ -28,7 +28,7 @@
/*
* Convert the mode string to the more convinient bits per pixel value
*/
static int getBPPFromModeString(CFStringRef mode)
static int getBPPFromModeString(CFStringRef mode)
{
if ((CFStringCompare(mode, CFSTR(kIO30BitDirectPixels), kCFCompareCaseInsensitive) == kCFCompareEqualTo)) {
// This is a strange mode, where we using 10 bits per RGB component and pack it into 32 bits
......@@ -44,7 +44,7 @@ static int getBPPFromModeString(CFStringRef mode)
else if (CFStringCompare(mode, CFSTR(IO8BitIndexedPixels), kCFCompareCaseInsensitive) == kCFCompareEqualTo) {
return 8;
}
return 0;
}
......@@ -68,6 +68,11 @@ static CGDisplayModeRef getBestModeForParameters(CFArrayRef allModes, int w, int
// One of the key parameters does not match
continue;
}
if (refrate == 0) { // REFRESH_RATE_UNKNOWN
return cRef;
}
// Refresh rate might be 0 in display mode and we ask for specific display rate
// but if we do not find exact match then 0 refresh rate might be just Ok
if (CGDisplayModeGetRefreshRate(cRef) == refrate) {
......@@ -165,7 +170,10 @@ Java_sun_awt_CGraphicsDevice_nativeSetDisplayMode
}
}
}];
} else {
[JNFException raise:env as:kIllegalArgumentException reason:"Invalid display mode"];
}
CFRelease(allModes);
JNF_COCOA_EXIT(env);
}
......
......@@ -1586,10 +1586,18 @@ public class JViewport extends JComponent implements Accessible
int bdx = blitToX - blitFromX;
int bdy = blitToY - blitFromY;
Composite oldComposite = null;
// Shift the scrolled region
if (g instanceof Graphics2D) {
Graphics2D g2d = (Graphics2D) g;
oldComposite = g2d.getComposite();
g2d.setComposite(AlphaComposite.Src);
}
rm.copyArea(this, g, blitFromX, blitFromY, blitW, blitH, bdx, bdy,
false);
if (oldComposite != null) {
((Graphics2D) g).setComposite(oldComposite);
}
// Paint the newly exposed region.
int x = view.getX();
int y = view.getY();
......
......@@ -118,6 +118,11 @@ public class RepaintManager
// Whether or not a VolatileImage should be used for double-buffered painting
static boolean volatileImageBufferEnabled = true;
/**
* Type of VolatileImage which should be used for double-buffered
* painting.
*/
private static final int volatileBufferType;
/**
* Value of the system property awt.nativeDoubleBuffering.
*/
......@@ -204,6 +209,13 @@ public class RepaintManager
((SunGraphicsEnvironment)ge).addDisplayChangedListener(
new DisplayChangedHandler());
}
Toolkit tk = Toolkit.getDefaultToolkit();
if ((tk instanceof SunToolkit)
&& ((SunToolkit) tk).isSwingBackbufferTranslucencySupported()) {
volatileBufferType = Transparency.TRANSLUCENT;
} else {
volatileBufferType = Transparency.OPAQUE;
}
}
/**
......@@ -989,7 +1001,8 @@ public class RepaintManager
if (image != null) {
image.flush();
}
image = config.createCompatibleVolatileImage(width, height);
image = config.createCompatibleVolatileImage(width, height,
volatileBufferType);
volatileMap.put(config, image);
}
return image;
......@@ -1483,9 +1496,26 @@ public class RepaintManager
for(y=clipY, maxy = clipY + clipH; y < maxy ; y += bh) {
osg.translate(-x, -y);
osg.setClip(x,y,bw,bh);
if (volatileBufferType != Transparency.OPAQUE
&& osg instanceof Graphics2D) {
final Graphics2D g2d = (Graphics2D) osg;
final Color oldBg = g2d.getBackground();
g2d.setBackground(c.getBackground());
g2d.clearRect(x, y, bw, bh);
g2d.setBackground(oldBg);
}
c.paintToOffscreen(osg, x, y, bw, bh, maxx, maxy);
g.setClip(x, y, bw, bh);
g.drawImage(image, x, y, c);
if (volatileBufferType != Transparency.OPAQUE
&& g instanceof Graphics2D) {
final Graphics2D g2d = (Graphics2D) g;
final Composite oldComposite = g2d.getComposite();
g2d.setComposite(AlphaComposite.Src);
g2d.drawImage(image, x, y, c);
g2d.setComposite(oldComposite);
} else {
g.drawImage(image, x, y, c);
}
osg.translate(x, y);
}
}
......
......@@ -319,7 +319,8 @@ public class SwingUtilities implements SwingConstants
newEvent = new MouseWheelEvent(newSource,
sourceWheelEvent.getID(),
sourceWheelEvent.getWhen(),
sourceWheelEvent.getModifiers(),
sourceWheelEvent.getModifiers()
| sourceWheelEvent.getModifiersEx(),
p.x,p.y,
sourceWheelEvent.getXOnScreen(),
sourceWheelEvent.getYOnScreen(),
......@@ -334,7 +335,8 @@ public class SwingUtilities implements SwingConstants
newEvent = new MenuDragMouseEvent(newSource,
sourceMenuDragEvent.getID(),
sourceMenuDragEvent.getWhen(),
sourceMenuDragEvent.getModifiers(),
sourceMenuDragEvent.getModifiers()
| sourceMenuDragEvent.getModifiersEx(),
p.x,p.y,
sourceMenuDragEvent.getXOnScreen(),
sourceMenuDragEvent.getYOnScreen(),
......@@ -347,7 +349,8 @@ public class SwingUtilities implements SwingConstants
newEvent = new MouseEvent(newSource,
sourceEvent.getID(),
sourceEvent.getWhen(),
sourceEvent.getModifiers(),
sourceEvent.getModifiers()
| sourceEvent.getModifiersEx(),
p.x,p.y,
sourceEvent.getXOnScreen(),
sourceEvent.getYOnScreen(),
......
......@@ -440,7 +440,7 @@ public class TitledBorder extends AbstractBorder
* @return the title-font of the titled border
*/
public Font getTitleFont() {
return titleFont;
return titleFont == null ? UIManager.getFont("TitledBorder.font") : titleFont;
}
/**
......@@ -449,7 +449,7 @@ public class TitledBorder extends AbstractBorder
* @return the title-color of the titled border
*/
public Color getTitleColor() {
return titleColor;
return titleColor == null ? UIManager.getColor("TitledBorder.titleColor") : titleColor;
}
......@@ -681,10 +681,6 @@ public class TitledBorder extends AbstractBorder
if (font != null) {
return font;
}
font = UIManager.getFont("TitledBorder.font");
if (font != null) {
return font;
}
if (c != null) {
font = c.getFont();
if (font != null) {
......@@ -699,10 +695,6 @@ public class TitledBorder extends AbstractBorder
if (color != null) {
return color;
}
color = UIManager.getColor("TitledBorder.titleColor");
if (color != null) {
return color;
}
return (c != null)
? c.getForeground()
: null;
......
......@@ -1984,6 +1984,13 @@ public abstract class SunToolkit extends Toolkit
return false;
}
/**
* Returns true if swing backbuffer should be translucent.
*/
public boolean isSwingBackbufferTranslucencySupported() {
return false;
}
/**
* Returns whether or not a containing top level window for the passed
* component is
......@@ -2105,25 +2112,41 @@ class PostEventQueue {
private EventQueueItem queueTail = null;
private final EventQueue eventQueue;
// For the case when queue is cleared but events are not posted
private volatile boolean isFlushing = false;
PostEventQueue(EventQueue eq) {
eventQueue = eq;
}
public synchronized boolean noEvents() {
return queueHead == null;
return queueHead == null && !isFlushing;
}
/*
* Continually post pending AWTEvents to the Java EventQueue. The method
* is synchronized to ensure the flush is completed before a new event
* can be posted to this queue.
*
* 7177040: The method couldn't be wholly synchronized because of calls
* of EventQueue.postEvent() that uses pushPopLock, otherwise it could
* potentially lead to deadlock
*/
public synchronized void flush() {
EventQueueItem tempQueue = queueHead;
queueHead = queueTail = null;
while (tempQueue != null) {
eventQueue.postEvent(tempQueue.event);
tempQueue = tempQueue.next;
public void flush() {
EventQueueItem tempQueue;
synchronized (this) {
tempQueue = queueHead;
queueHead = queueTail = null;
isFlushing = true;
}
try {
while (tempQueue != null) {
eventQueue.postEvent(tempQueue.event);
tempQueue = tempQueue.next;
}
}
finally {
isFlushing = false;
}
}
......
......@@ -393,7 +393,16 @@ OGLBlitSwToTexture(SurfaceDataRasInfo *srcInfo, OGLPixelFormat *pf,
OGLSDOps *dstOps,
jint dx1, jint dy1, jint dx2, jint dy2)
{
jboolean adjustAlpha = (pf != NULL && !pf->hasAlpha);
j2d_glBindTexture(dstOps->textureTarget, dstOps->textureID);
if (adjustAlpha) {
// if the source surface does not have an alpha channel,
// we need to ensure that the alpha values are forced to 1.0f
j2d_glPixelTransferf(GL_ALPHA_SCALE, 0.0f);
j2d_glPixelTransferf(GL_ALPHA_BIAS, 1.0f);
}
// in case pixel stride is not a multiple of scanline stride the copy
// has to be done line by line (see 6207877)
if (srcInfo->scanStride % srcInfo->pixelStride != 0) {
......@@ -413,6 +422,11 @@ OGLBlitSwToTexture(SurfaceDataRasInfo *srcInfo, OGLPixelFormat *pf,
dx1, dy1, dx2-dx1, dy2-dy1,
pf->format, pf->type, srcInfo->rasBase);
}
if (adjustAlpha) {
// restore scale/bias to their original values
j2d_glPixelTransferf(GL_ALPHA_SCALE, 1.0f);
j2d_glPixelTransferf(GL_ALPHA_BIAS, 0.0f);
}
}
/**
......
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
/*
@test
@bug 7177173
@summary The maximized state shouldn't be reset upon hiding a frame
@author anthony.petrov@oracle.com: area=awt.toplevel
@run main HideMaximized
*/
import java.awt.*;
public class HideMaximized {
public static void main(String[] args) {
if (!Toolkit.getDefaultToolkit().isFrameStateSupported(Frame.MAXIMIZED_BOTH)) {
// Nothing to test
return;
}
// First test a decorated frame
Frame frame = new Frame("test");
test(frame);
// Now test an undecorated frames
frame = new Frame("undecorated test");
frame.setUndecorated(true);
test(frame);
}
private static void test(Frame frame) {
frame.setExtendedState(Frame.MAXIMIZED_BOTH);
frame.setVisible(true);
try { Thread.sleep(1000); } catch (Exception ex) {}
if (frame.getExtendedState() != Frame.MAXIMIZED_BOTH) {
throw new RuntimeException("The maximized state has not been applied");
}
// This will hide the frame, and also clean things up for safe exiting
frame.dispose();
try { Thread.sleep(1000); } catch (Exception ex) {}
if (frame.getExtendedState() != Frame.MAXIMIZED_BOTH) {
throw new RuntimeException("The maximized state has been reset");
}
}
}
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
import java.awt.Frame;
import java.awt.event.InputEvent;
import java.awt.event.MouseEvent;
import java.awt.event.MouseWheelEvent;
import javax.swing.SwingUtilities;
import javax.swing.event.MenuDragMouseEvent;
/**
* @test
* @bug 7170657
* @author Sergey Bylokhov
*/
public final class bug7170657 {
private static boolean FAILED;
public static void main(final String[] args) {
final int mask = InputEvent.META_DOWN_MASK | InputEvent.CTRL_MASK;
Frame f = new Frame();
MouseEvent mwe = new MouseWheelEvent(f, 1, 1, mask, 1, 1, 1, 1, 1, true,
1, 1, 1);
MouseEvent mdme = new MenuDragMouseEvent(f, 1, 1, mask, 1, 1, 1, 1, 1,
true, null, null);
MouseEvent me = new MouseEvent(f, 1, 1, mask, 1, 1, 1, 1, 1, true,
MouseEvent.NOBUTTON);
test(f, mwe);
test(f, mdme);
test(f, me);
if (FAILED) {
throw new RuntimeException("Wrong mouse event");
}
}
private static void test(final Frame frame, final MouseEvent me) {
MouseEvent newme = SwingUtilities.convertMouseEvent(frame, me, frame);
if (me.getModifiersEx() != newme.getModifiersEx()
|| me.getModifiers() != newme.getModifiers()) {
fail(me, newme);
}
}
private static void fail(final MouseEvent exp, final MouseEvent act) {
System.err.println("Expected: " + exp);
System.err.println("Actual: " + act);
FAILED = true;
}
}
/*
* Copyright 2012 Red Hat, Inc. All Rights Reserved.
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*/
import java.awt.Color;
import java.awt.Font;
import javax.swing.border.EmptyBorder;
import javax.swing.border.TitledBorder;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
/* @test
* @bug 7022041
* @summary This test check the behaviour of getTitleFont() and getTitleColor()
* methods of the TitledBorder class.
* @author Pavel Tisnovsky
*/
public class Test7022041 {
public static void main(String[] args) throws Exception {
UIManager.LookAndFeelInfo[] installedLookAndFeels = UIManager.getInstalledLookAndFeels();
// try to test all installed Look and Feels
for (UIManager.LookAndFeelInfo lookAndFeel : installedLookAndFeels) {
String name = lookAndFeel.getName();
System.out.println("Testing " + name);
// Some Look and Feels work only when test is run in a GUI environment
// (GTK+ LAF is an example)
try {
UIManager.setLookAndFeel(lookAndFeel.getClassName());
checkTitleColor();
System.out.println(" titleColor test ok");
checkTitleFont();
System.out.println(" titleFont test ok");
}
catch (UnsupportedLookAndFeelException e) {
System.out.println(" Note: LookAndFeel " + name
+ " is not supported on this configuration");
}
}
}
/**
* Check behaviour of method TitledBorder.getTitleColor()
*/
private static void checkTitleColor() {
TitledBorder titledBorder = new TitledBorder(new EmptyBorder(1, 1, 1, 1));
Color defaultColor = UIManager.getLookAndFeelDefaults().getColor("TitledBorder.titleColor");
Color titledBorderColor = titledBorder.getTitleColor();
// check default configuration
if (defaultColor == null) {
if (titledBorderColor == null) {
return;
}
else {
throw new RuntimeException("TitledBorder default color should be null");
}
}
if (!defaultColor.equals(titledBorderColor)) {
throw new RuntimeException("L&F default color " + defaultColor.toString()
+ " differs from TitledBorder color " + titledBorderColor.toString());
}
// title color is explicitly specified
Color color = Color.green;
titledBorder.setTitleColor(color);
if (!color.equals(titledBorder.getTitleColor())) {
throw new RuntimeException("TitledBorder color should be " + color.toString());
}
// title color is unspecified
titledBorder.setTitleColor(null);
if (!defaultColor.equals(titledBorder.getTitleColor())) {
throw new RuntimeException("L&F default color " + defaultColor.toString()
+ " differs from TitledBorder color " + titledBorderColor.toString());
}
}
/**
* Check behaviour of method TitledBorder.getTitleFont()
*/
private static void checkTitleFont() {
TitledBorder titledBorder = new TitledBorder(new EmptyBorder(1, 1, 1, 1));
Font defaultFont = UIManager.getLookAndFeelDefaults().getFont("TitledBorder.font");
Font titledBorderFont = titledBorder.getTitleFont();
// check default configuration
if (defaultFont == null) {
if (titledBorderFont == null) {
return;
}
else {
throw new RuntimeException("TitledBorder default font should be null");
}
}
if (!defaultFont.equals(titledBorderFont)) {
throw new RuntimeException("L&F default font " + defaultFont.toString()
+ " differs from TitledBorder font " + titledBorderFont.toString());
}
// title font is explicitly specified
Font font = new Font("Dialog", Font.PLAIN, 10);
titledBorder.setTitleFont(font);
if (!font.equals(titledBorder.getTitleFont())) {
throw new RuntimeException("TitledBorder font should be " + font.toString());
}
// title Font is unspecified
titledBorder.setTitleFont(null);
if (!defaultFont.equals(titledBorder.getTitleFont())) {
throw new RuntimeException("L&F default font " + defaultFont.toString()
+ " differs from TitledBorder font " + titledBorderFont.toString());
}
}
}
/*
* Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
import java.awt.Color;
import java.awt.Graphics;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsEnvironment;
import java.awt.Transparency;
import java.awt.image.BufferedImage;
import java.awt.image.VolatileImage;
/**
* @test
* @bug 7181438
* @summary Verifies that we get correct alpha, when we draw opaque
* BufferedImage to non opaque VolatileImage via intermediate opaque texture.
* @author Sergey Bylokhov
* @run main/othervm -Dsun.java2d.accthreshold=0 bug7181438
*/
public final class bug7181438 {
private static final int SIZE = 500;
public static void main(final String[] args) {
final BufferedImage bi = createBufferedImage();
final VolatileImage vi = createVolatileImage();
final Graphics s2dVi = vi.getGraphics();
//sw->texture->surface blit
s2dVi.drawImage(bi, 0, 0, null);
final BufferedImage results = vi.getSnapshot();
for (int i = 0; i < SIZE; ++i) {
for (int j = 0; j < SIZE; ++j) {
//Image should be opaque: (black color and alpha = 255)
if (results.getRGB(i, j) != 0xFF000000) {
throw new RuntimeException("Failed: Wrong alpha");
}
}
}
System.out.println("Passed");
}
private static VolatileImage createVolatileImage() {
final GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
final GraphicsConfiguration gc = ge.getDefaultScreenDevice().getDefaultConfiguration();
return gc.createCompatibleVolatileImage(SIZE, SIZE,
Transparency.TRANSLUCENT);
}
private static BufferedImage createBufferedImage() {
final BufferedImage bi = new BufferedImage(SIZE, SIZE,
BufferedImage.TYPE_INT_RGB);
final Graphics bg = bi.getGraphics();
//Black color and alpha = 0
bg.setColor(new Color(0, 0, 0, 0));
bg.fillRect(0, 0, SIZE, SIZE);
bg.dispose();
return bi;
}
}
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册