Is The Java Tutorials Translucent Window example giving trouble to those playing with jdk7?

只愿长相守 提交于 2019-11-26 17:13:10

问题


Here's the example.

If you build and run TranslucentWindow in let's say, NetBeans IDE 7.0, which supports jdk7, you'll get the following exception:

Exception in thread "AWT-EventQueue-0" java.awt.IllegalComponentStateException: The frame is decorated
    at java.awt.Frame.setOpacity(Frame.java:960)
    at main.TranslucentWindow.<init>(TranslucentWindow.java:23)
    at main.TranslucentWindow$1.run(TranslucentWindow.java:47)
    at java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:251)
    at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:705)
    at java.awt.EventQueue.access$000(EventQueue.java:101)
    at java.awt.EventQueue$3.run(EventQueue.java:666)
    at java.awt.EventQueue$3.run(EventQueue.java:664)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76)
    at java.awt.EventQueue.dispatchEvent(EventQueue.java:675)
    at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:211)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:128)
    at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:117)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:113)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:105)
    at java.awt.EventDispatchThread.run(EventDispatchThread.java:90)
BUILD SUCCESSFUL (total time: 1 second)

According to this stack trace, the offending line is tw.setOpacity(0.55f). But, as the error indicates, if you invoke setUndecorated(true) on the frame, then it won't throw the exception and will create a translucent window, albeit without any decoration (which is a pain). Is this normal? Shouldn't this code run right "out-of-the-box"? Am I overlooking something?

EDIT

Why does their translucent window appear decorated, or is this custom rendering?

What it is...

What it should be...


回答1:


Right from the JavaDocs for java.awt.frame.setOpacity() in JDK7:

The following conditions must be met in order to set the opacity value less than 1.0f:

  • The TRANSLUCENT translucency must be supported by the underlying system
  • The window must be undecorated (see setUndecorated(boolean) and Dialog.setUndecorated(boolean))
  • The window must not be in full-screen mode (see GraphicsDevice.setFullScreenWindow(Window))

If the requested opacity value is less than 1.0f, and any of the above conditions are not met, the window opacity will not change, and the IllegalComponentStateException will be thrown.

The behavior that you are seeing is documented and is expected behavior.




回答2:


This is a verified bug. I have sent Oracle information on their sample code failing using the default install of JDK 1.7.0 or JRE7. Using the source code below compiled into TranslucentWindow.java, it fails and produces the exception initially indicated above.

From web page Oracle's Translucency / Shaped Windows Page

// Taken from http://download.oracle.com/javase/tutorial/uiswing/misc/trans_shaped_windows.html#uniform 
import java.awt.*;
import javax.swing.*;
import static java.awt.GraphicsDevice.WindowTranslucency.*;

public class TranslucentWindow extends JFrame {
public TranslucentWindow() {
    super("TranslucentWindow");
    setLayout(new GridBagLayout());

    setSize(300,200);
    setLocationRelativeTo(null);
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

    //Add a sample button.
    add(new JButton("I am a Button"));
}

public static void main(String[] args)  {
        // Determine if the GraphicsDevice supports translucency.
        GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
        GraphicsDevice gd = ge.getDefaultScreenDevice();

        //If translucent windows aren't supported, exit.
        if (!gd.isWindowTranslucencySupported(TRANSLUCENT))
    {
        System.err.println("Translucency is not supported");
        System.exit(0);
    }

    // Create the GUI on the event-dispatching thread
    SwingUtilities.invokeLater(new Runnable()
    {
        @Override
        public void run()
        {
            TranslucentWindow tw = new TranslucentWindow();
            // Set the window to 55% opaque (45% translucent).
            tw.setOpacity(0.55f);
            // Display the window.
            tw.setVisible(true);
        }
    });
}

}

Exception in thread "AWT-EventQueue-0" java.awt.IllegalComponentStateException: The frame is decorated
    at java.awt.Frame.setOpacity(Frame.java:960)
    at TranslucentWindow$1.run(TranslucentWindow.java:38)
    at java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:251)
    at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:705)
    at java.awt.EventQueue.access$000(EventQueue.java:101)
    at java.awt.EventQueue$3.run(EventQueue.java:666)
    at java.awt.EventQueue$3.run(EventQueue.java:664)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76)
    at java.awt.EventQueue.dispatchEvent(EventQueue.java:675)
    at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:211)
    at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:128)
    at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:117)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:113)
    at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:105)
    at java.awt.EventDispatchThread.run(EventDispatchThread.java:90)



回答3:


Use com.sun.awt.AWTUtilities.setWindowOpacity(w, 0.5f) in JDK 7.

See here.




回答4:


Hi the problem with this code is that it is missing the following line of code in the main() method:

JFrame.setDefaultLookAndFeelDecorated(true);

It should go right after the code that checks if translucent windows aren't supported and exits:

    //If translucent windows aren't supported, exit.
    if (!gd.isWindowTranslucencySupported(TRANSLUCENT)) {
        System.err.println(
            "Translucency is not supported");
            System.exit(0);
    }

    JFrame.setDefaultLookAndFeelDecorated(true);

    // Create the GUI on the event-dispatching thread
    SwingUtilities.invokeLater(new Runnable() {
        @Override
        public void run() {
            TranslucentWindow tw = new TranslucentWindow();

            // Set the window to 55% opaque (45% translucent).
            tw.setOpacity(0.55f);

            // Display the window.
            tw.setVisible(true);
        }
    });

Also, the image of the uniform translucent image is misleading because it uses the java look and feel. Instead the image should use the Windows system look and feel (assuming you're on Windows). If you try to use the Java look and feel (i.e., JFrame.setDefaultLookAndFeelDecorated(false);), then it will throw the same error as before. I was hoping that the translucent window would work with the Java look and feel, but I don't think this is possible.




回答5:


I think you need to setUndecorated before setBackground this will fix the problem



来源:https://stackoverflow.com/questions/6259269/is-the-java-tutorials-translucent-window-example-giving-trouble-to-those-playing

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!