Desactive el dibujo de fondo en JFrame para mostrar correctamente los efectos Aero (DWM)

Tengo problemas para usar la funcionalidad DWM de Windows Vista / 7 en Windows Java. Quiero hacer que el fondo de mi cuadro use el estilo Aero. La API de Windows para hacerlo es proporcionada por la funciónDwmExtendFrameIntoClientArea en eldwmapi biblioteca. Me las arreglé para llamar al procedimiento correctamente a través de JNA, y hace lo que se supone que debe hacer (puede ver eso, por ejemplo, al cambiar el tamaño del marco, antes de la próxima pintura ve los efectos aerodinámicos adecuados en el área que aún no está pintada, ver la imagen adjunta).

Pero en algún lugar (no puedo entender dónde) se pinta un fondo sobre el efecto Aero y el efecto se pierde.

Lo que ya he probado:

Usando una costumbreContentPane con opacidad establecida enfalseEstablecer la opacidad de laLayeredPane y elRootPane a falsoUsando unFrame en vez de unaJFrameEstablecer el color de fondo de laJFrame/ContentPane a negro / totalmente transparenteUtilizarsetLayersOpaque y una variante personalizada del mismo, ver primera respuesta para más detalles

Hasta ahora no he podido eliminar ese fondo. ¿Es una limitación de AWT / Swing? ¿Cómo puedo eliminar ese fondo o usar el efecto Aero correctamente?

Tu ayuda es muy apreciada.

Captura de pantalla

Aquí una captura de pantalla de un marco sin contenido, que establece la opacidad de RootPane, LayeredPane y ContentPane en false. Lo hice rápidamente mientras cambiaba el tamaño. Verá que el efecto se aplica correctamente al área en la que Java aún no pintaba.

http://i55.tinypic.com/v614qo.png (Como nuevo usuario no puedo publicar la imagen directamente ...)

Comportamiento raro

Tras una investigación más profunda me encontré con el siguiente comportamiento extraño. Si el tamaño de la ventana es 150x150 o inferior, el contenido se muestra de forma transparente. Esto es muy problemático para los componentes normales de la ventana. Si pinta directamente en el marco anulando elpaint() método todo se dibuja semitransparente. Además, el sistema de coordenadas parece estar un poco apagado, aparece como el punto cero delJFrame se establece en el punto cero real de la ventana. Por lo tanto, Swing intenta pintar en áreas donde realmente se encuentra el borde de la ventana, que por supuesto no es visible.

Ver esta captura de pantalla:http://d-gfx.kognetwork.ch/java_aero_bug.png

Exa, código mple

Este es el código que uso.

Requierejna.jar yplatform.jar. Disponible en la página de inicio de JNA.

import com.sun.jna.Function;
import com.sun.jna.Native;
import com.sun.jna.NativeLibrary;
import com.sun.jna.Structure;
import com.sun.jna.platform.win32.WinDef.HWND;
import com.sun.jna.platform.win32.WinNT.HRESULT;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.UIManager;

public class AeroFrame extends JFrame {

    public AeroFrame() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        JLabel label = new JLabel("Testlabel");
        label.setOpaque(false);

        add(label);

        pack();

        enableAeroEffect();
    }

    private void enableAeroEffect() {
        NativeLibrary dwmapi = NativeLibrary.getInstance("dwmapi");
        HWND aeroFrameHWND = new HWND(Native.getWindowPointer(this));
        MARGINS margins = new MARGINS();
        margins.cxLeftWidth = -1;
        margins.cxRightWidth = -1;
        margins.cyBottomHeight = -1;
        margins.cyTopHeight = -1;
        //DwmExtendFrameIntoClientArea(HWND hWnd, MARGINS *pMarInset)
        //http://msdn.microsoft.com/en-us/library/aa969512%28v=VS.85%29.aspx
        Function extendFrameIntoClientArea = dwmapi.getFunction("DwmExtendFrameIntoClientArea");
        HRESULT result = (HRESULT) extendFrameIntoClientArea.invoke(HRESULT.class,
                new Object[] { aeroFrameHWND, margins});
        if(result.intValue()!=0)
            System.err.println("Call to DwmExtendFrameIntoClientArea failed.");
    }

    /**
     * http://msdn.microsoft.com/en-us/library/bb773244%28v=VS.85%29.aspx
     */
    public class MARGINS extends Structure implements Structure.ByReference {
            public int cxLeftWidth;
            public int cxRightWidth;
            public int cyTopHeight;
            public int cyBottomHeight;
    }

    public static void main(String[] args) {
        try {
            UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
            JFrame.setDefaultLookAndFeelDecorated(true);

        } catch (Exception e) {
            e.printStackTrace();
        }
        new AeroFrame().setVisible(true);
    }

}

Respuestas a la pregunta(1)

Su respuesta a la pregunta